> ## Documentation Index
> Fetch the complete documentation index at: https://help.propops.app/llms.txt
> Use this file to discover all available pages before exploring further.

# Management

> Manage, upgrade, back up, and troubleshoot your PropOps Docker deployment.

## Managing containers

| Task                          | Command                                           |
| ----------------------------- | ------------------------------------------------- |
| Start all services            | `docker compose up -d`                            |
| Stop all services             | `docker compose down`                             |
| View logs (all)               | `docker compose logs -f`                          |
| View web logs only            | `docker compose logs -f web`                      |
| Restart web container         | `docker compose restart web`                      |
| Open a shell in the container | `docker compose exec web bash`                    |
| Apply database migrations     | `docker compose exec web php scripts/migrate.php` |

<Warning>
  Always use `docker compose down` (without `-v`) to stop containers. Adding `-v` deletes all data volumes including your database.
</Warning>

***

## Backups

### Database backup

```bash theme={null}
docker compose exec -T db mariadb-dump \
  -u propops_user -p"your_db_password" propops \
  > backup-$(date +%Y%m%d).sql
```

### Full data backup

Back up the entire `docker-data/` directory to capture uploads, configuration, and database files:

```bash theme={null}
tar -czf propops-backup-$(date +%Y%m%d).tar.gz docker-data/
```

### Scheduled backups

Add to your crontab for nightly automatic backups:

```bash theme={null}
crontab -e
```

```bash theme={null}
# Database backup at 2am
0 2 * * * cd /path/to/PropOps-Web && docker compose exec -T db mariadb-dump -u propops_user -p"your_db_password" propops > /backups/db-$(date +\%Y\%m\%d).sql

# Full data backup at 3am
0 3 * * * tar -czf /backups/propops-$(date +\%Y\%m\%d).tar.gz /path/to/PropOps-Web/docker-data/
```

***

## Troubleshooting

<AccordionGroup>
  <Accordion title="Containers won't start">
    Check for port conflicts — another process may already be using port 8080 or 3306:

    ```bash theme={null}
    sudo lsof -i :8080
    sudo lsof -i :3306
    ```

    Review container logs for the specific error:

    ```bash theme={null}
    docker compose logs web
    docker compose logs db
    ```
  </Accordion>

  <Accordion title="Database connection refused">
    The `db` container may still be initialising. Check its status:

    ```bash theme={null}
    docker compose ps
    ```

    If the database shows `starting`, wait 30–60 seconds and try again. On the very first boot, MariaDB needs time to apply the schema and migrations.

    Also verify that the `DB_HOST`, `DB_NAME`, `DB_USER`, and `DB_PASS` values in your `.env` match the `environment` section in `docker-compose.yml`.
  </Accordion>

  <Accordion title="File uploads failing">
    Check that the uploads directory is owned by `www-data`:

    ```bash theme={null}
    docker compose exec web ls -la /var/www/html/uploads
    ```

    The entrypoint script sets ownership automatically, but if you manually created directories on the host they may have incorrect permissions. Fix with:

    ```bash theme={null}
    docker compose exec web chown -R www-data:www-data /var/www/html/uploads
    ```

    If using a reverse proxy, also check that `client_max_body_size` is set to at least `50M` in your Nginx configuration.
  </Accordion>

  <Accordion title="Push notifications not working">
    Ensure the following variables are set in your `.env`:

    * `WEB_PUSH_ENABLED=true`
    * `VAPID_PUBLIC_KEY`
    * `VAPID_PRIVATE_KEY`
    * `VAPID_SUBJECT`

    HTTPS is required for push notifications — they will not work over plain HTTP.
  </Accordion>

  <Accordion title="Emails not sending">
    Test your SMTP configuration from inside the container:

    ```bash theme={null}
    docker compose exec web php scripts/test-email.php you@yourcompany.com
    ```

    Verify that `APP_URL` is set to your public HTTPS URL. Email links are built from this value.
  </Accordion>

  <Accordion title="Lost PII encryption keys">
    If you have lost your `docker-data/config/.env` file and the `PII_ENCRYPTION_KEY` or `PII_HMAC_KEY` values, encrypted data in the database (names, emails, phone numbers) and encrypted job files (documents, photos, videos, GDPR reports) cannot be decrypted. There is no recovery method.

    Always back up `docker-data/config/.env` to a secure location.
  </Accordion>
</AccordionGroup>
