refactor(dev): replace v5:sync-dev-lima-servers with V5DevLimaSeeder

Switch Lima VM dev-environment sync from a custom Artisan command to a
database seeder. The seeder creates/updates the Development-Lima cluster
and its two servers idempotently, reading ssh_user from the
COOLIFY_CLI_SSH_USER env var (exposed via config('coold.dev_ssh_user')).

dev.sh now passes COOLIFY_CLI_SSH_USER and runs db:seed instead of
building per-server --server flag arrays.
This commit is contained in:
Andras Bacsai
2026-06-16 17:10:40 +02:00
parent 9566b259b2
commit 295addb6b0
7 changed files with 129 additions and 22 deletions
@@ -29,3 +29,11 @@ it('defaults coold dev VM settings in Laravel config', function () {
->and(config('coold.dev_builder_capacity'))->toBe(2)
->and(config('coold.dev_builder_enabled'))->toBeTrue();
});
it('runs the v5 dev Lima seeder with the normal development database seeder', function () {
$databaseSeeder = file_get_contents(database_path('seeders/DatabaseSeeder.php'));
$developmentSeederBlock = str($databaseSeeder)->after("if (in_array(config('app.env'), ['local', 'development', 'dev'], true)) {")->before(' }')->toString();
expect($developmentSeederBlock)->toContain('DevelopmentRailpackExamplesSeeder::class')
->and($developmentSeederBlock)->toContain('V5DevLimaSeeder::class');
});
@@ -59,13 +59,14 @@ it('retries dev coolify bootstrap because fresh Lima setup can complete across p
->and($script)->toContain('fresh Lima hosts can finish setup after partial bootstrap phases');
});
it('syncs bootstrapped Lima VMs into v5 development server state', function () {
it('seeds bootstrapped Lima VMs into v5 development server state', function () {
$script = file_get_contents(base_path('scripts/dev.sh'));
expect($script)->toContain('sync_v5_dev_lima_servers()')
->and($script)->toContain('v5:sync-dev-lima-servers')
->and($script)->toContain('--cluster="Development-Lima"')
->and($script)->toContain('--server "${instance}|${node}|$(coolify_ssh_user)|22"');
->and($script)->toContain('COOLIFY_CLI_SSH_USER="$ssh_user"')
->and($script)->toContain('db:seed --class=V5DevLimaSeeder --force')
->and($script)->not->toContain('v5:sync-dev-lima-servers')
->and($script)->not->toContain('--server "${instance}|${node}|$(coolify_ssh_user)|22"');
});
it('supports down cleanup as the preferred VM cleanup command', function () {
+23
View File
@@ -11,6 +11,7 @@ use App\Models\User;
use App\Models\V5\Cluster;
use App\Models\V5\Server as V5Server;
use App\Services\Flux\FluxHealth;
use Database\Seeders\V5DevLimaSeeder;
use Illuminate\Support\Facades\Artisan;
use Illuminate\Support\Facades\Config;
use Illuminate\Support\Facades\Process;
@@ -465,6 +466,28 @@ it('syncs dev Lima VMs into v5 clusters and servers', function () {
->and(V5Server::query()->where('name', 'coold-dev-2')->where('host', 'lima-coold-dev-2')->exists())->toBeTrue();
});
it('seeds dev Lima VMs into v5 clusters and servers idempotently', function () {
createSharedUserAndTeamTables();
[$user, $team] = createV5UserWithTeam();
createV5PrivateKey($team, 'Dev Lima Key');
config()->set('coold.dev_builder_capacity', 2);
(new V5DevLimaSeeder)->run();
(new V5DevLimaSeeder)->run();
$cluster = Cluster::query()->where('name', 'Development-Lima')->sole();
expect($cluster->team_id)->toBe($team->id)
->and($cluster->created_by_user_id)->toBe($user->id)
->and($cluster->description)->toBe('Local Lima development cluster managed by scripts/dev.sh.')
->and(V5Server::query()->count())->toBe(2)
->and(V5Server::query()->where('name', 'coold-dev')->where('host', 'lima-coold-dev')->where('ssh_user', get_current_user())->where('ssh_port', 22)->exists())->toBeTrue()
->and(V5Server::query()->where('name', 'coold-dev-2')->where('host', 'lima-coold-dev-2')->where('ssh_user', get_current_user())->where('ssh_port', 22)->exists())->toBeTrue()
->and(V5Server::query()->where('status', 'installed')->count())->toBe(2)
->and(V5Server::query()->where('builder_enabled', true)->where('builder_capacity', 2)->count())->toBe(2)
->and(V5Server::query()->where('cluster_id', $cluster->id)->count())->toBe(2);
});
function fakeFluxHealth(bool $available = true, string $message = 'Flux is running.'): void
{
app()->instance(FluxHealth::class, Mockery::mock(FluxHealth::class, function (MockInterface $mock) use ($available, $message) {