coolify/tests/Feature/ApplicationRollbackTest.php
Andras Bacsai a565fc3b36 fix(rollback): escape commit SHA to prevent shell injection
Properly escape commit SHA using escapeshellarg() before passing it
to shell commands. Add comprehensive tests for git commit rollback
scenarios including shallow clone, fallback behavior, and HEAD handling.
2026-02-27 23:26:31 +01:00

104 lines
3.3 KiB
PHP

<?php
use App\Models\Application;
use App\Models\ApplicationSetting;
use App\Models\Environment;
use App\Models\Project;
use App\Models\Server;
use App\Models\Team;
use Illuminate\Foundation\Testing\RefreshDatabase;
uses(RefreshDatabase::class);
describe('Application Rollback', function () {
beforeEach(function () {
$team = Team::factory()->create();
$project = Project::create([
'team_id' => $team->id,
'name' => 'Test Project',
'uuid' => (string) str()->uuid(),
]);
$environment = Environment::create([
'project_id' => $project->id,
'name' => 'rollback-test-env',
'uuid' => (string) str()->uuid(),
]);
$server = Server::factory()->create(['team_id' => $team->id]);
$this->application = Application::factory()->create([
'environment_id' => $environment->id,
'destination_id' => $server->id,
'git_commit_sha' => 'HEAD',
]);
});
test('setGitImportSettings uses passed commit instead of application git_commit_sha', function () {
ApplicationSetting::create([
'application_id' => $this->application->id,
'is_git_shallow_clone_enabled' => false,
]);
$rollbackCommit = 'abc123def456';
$result = $this->application->setGitImportSettings(
deployment_uuid: 'test-uuid',
git_clone_command: 'git clone',
public: true,
commit: $rollbackCommit
);
expect($result)->toContain($rollbackCommit);
});
test('setGitImportSettings with shallow clone fetches specific commit', function () {
ApplicationSetting::create([
'application_id' => $this->application->id,
'is_git_shallow_clone_enabled' => true,
]);
$rollbackCommit = 'abc123def456';
$result = $this->application->setGitImportSettings(
deployment_uuid: 'test-uuid',
git_clone_command: 'git clone',
public: true,
commit: $rollbackCommit
);
expect($result)
->toContain('git fetch --depth=1 origin')
->toContain($rollbackCommit);
});
test('setGitImportSettings falls back to git_commit_sha when no commit passed', function () {
$this->application->update(['git_commit_sha' => 'def789abc012']);
ApplicationSetting::create([
'application_id' => $this->application->id,
'is_git_shallow_clone_enabled' => false,
]);
$result = $this->application->setGitImportSettings(
deployment_uuid: 'test-uuid',
git_clone_command: 'git clone',
public: true,
);
expect($result)->toContain('def789abc012');
});
test('setGitImportSettings does not append checkout when commit is HEAD', function () {
ApplicationSetting::create([
'application_id' => $this->application->id,
'is_git_shallow_clone_enabled' => false,
]);
$result = $this->application->setGitImportSettings(
deployment_uuid: 'test-uuid',
git_clone_command: 'git clone',
public: true,
);
expect($result)->not->toContain('advice.detachedHead=false checkout');
});
});