What does this PR do?

Fixes #7528 — database services in Docker Compose files deployed via GitHub App (dockercompose buildpack) are now detected, registered as ServiceDatabase records, and fully available for backup scheduling — including the UI, deployment conflict protection, and automatic cleanup on compose changes.

/claim #7528


Problem

When deploying via GitHub App (dockercompose buildpack), database services in the compose file were not being detected and ServiceDatabase records were not being created. This meant automated backups were impossible for databases defined in GitHub App Docker Compose deployments.

The Empty Docker Compose / one-click Services path already worked correctly.

Root Cause

parseDockerComposeFile() has two separate code paths:

Path Calls isDatabaseImage()? Creates ServiceDatabase?
Service model path (lines ~1400) ✅ Yes ✅ Yes
Application model path (lines ~2416) ✅ Yes No — only set a flag

The service_databases table had a non-nullable service_id FK, making it structurally impossible to associate a ServiceDatabase with an Application resource.


Solution

This PR addresses all three requirements raised in the pinned comment:

1. Database schema + backend (ServiceDatabase creation)

  • Migration: Makes service_id nullable; adds nullable application_id FK → applications
  • parseDockerComposeFile() Application path: After isDatabaseImage() detection, creates/updates ServiceDatabase records linked via application_id (PR deployments excluded, mirrors Service path logic exactly)
  • ServiceDatabase model: Added application() relationship (belongsTo Application); helper methods getParentResource(), getServer(), getContainerName(), getDestinationNetwork(), getParentUuid(); updated ownedByCurrentTeam() to include application-owned databases

2. Scheduled Backup config & UI

  • New route: GET /compose-databases/{service_name}/backupsproject.application.compose.database.backups
  • New Livewire component: App\Livewire\Project\Application\ComposeServiceBackups
  • New Blade view: livewire/project/application/compose-service-backups.blade.php — reuses existing livewire:project.database.scheduled-backups and livewire:project.database.create-scheduled-backup components, no duplication
  • Application config sidebar: Shows a Database Backups section with a link per backup-capable database service when build_pack === 'dockercompose'

3. Overlapping Re-deployments protection

  • ApplicationDeploymentJob: Before starting a deployment, checks for any running ScheduledDatabaseBackupExecution linked to this application’s compose databases. If found, cancels the deployment with a clear log message — user retries after backup completes.
  • DatabaseBackupJob: Before running a backup, checks if a deployment is queued or in_progress for the parent application. If so, skips the backup run (logged). Both guards are symmetric.

4. Compose Changes cleanup

After parseDockerComposeFile() finishes processing the Application path, any ServiceDatabase records whose name is no longer present in the current compose services list are deleted along with their associated ScheduledDatabaseBackup records. This prevents orphaned backup jobs running against containers that no longer exist.

5. Downstream fixes

All code that previously assumed serviceDatabase->service-> now uses the new helper methods, so both Service-owned and Application-owned databases work transparently:

  • DatabaseBackupJob — server, container name, network resolution
  • BackupExecutions — server resolution
  • BackupEdit — server resolution + post-delete redirect
  • ScheduledDatabaseBackup.server()
  • StartDatabaseProxy
  • routes/web.php download.backup handler

Files Changed

File Change
database/migrations/2026_02_25_100000_add_application_id_to_service_databases.php New migration
app/Models/ServiceDatabase.php Application relationship + helper methods
bootstrap/helpers/shared.php DB creation + stale cleanup in Application path
app/Jobs/ApplicationDeploymentJob.php Backup conflict guard
app/Jobs/DatabaseBackupJob.php Deployment conflict guard + helper usage
app/Livewire/Project/Application/ComposeServiceBackups.php New Livewire component
resources/views/livewire/project/application/compose-service-backups.blade.php New Blade view
resources/views/livewire/project/application/configuration.blade.php DB Backups sidebar section
routes/web.php New route + server helper fix
app/Livewire/Project/Database/BackupEdit.php Helper usage + redirect fix
app/Livewire/Project/Database/BackupExecutions.php Helper usage
app/Models/ScheduledDatabaseBackup.php Helper usage in server()
app/Actions/Database/StartDatabaseProxy.php Helper usage

Type of change

  • Bug fix (non-breaking change which fixes an issue)
  • New feature (non-breaking change which adds functionality)

Before / After

Deployment Method Creates ServiceDatabase Backup UI Re-deploy lock Compose cleanup
Empty Docker Compose (Service) ✅ unchanged ✅ unchanged n/a ✅ unchanged
GitHub App dockercompose (Application) ❌ → ❌ → ❌ → ❌ →
One-click Services ✅ unchanged ✅ unchanged n/a ✅ unchanged

Claim

Total prize pool $100
Total paid $0
Status Pending
Submitted February 25, 2026
Last updated February 25, 2026

Contributors

GO

GoThundercats

@GoThundercats

100%

Sponsors

IL

Ilias Ism

@me

$100