Skip to content

Commit

Permalink
Merge branch 'next' into fix-dev-error
Browse files Browse the repository at this point in the history
  • Loading branch information
peaklabs-dev authored Sep 23, 2024
2 parents b7139f8 + 6f8c4a4 commit 92772f9
Show file tree
Hide file tree
Showing 124 changed files with 2,488 additions and 1,128 deletions.
2 changes: 1 addition & 1 deletion .env.development.example
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@ APP_KEY=
APP_URL=http://localhost
APP_PORT=8000
APP_DEBUG=true
SSH_MUX_ENABLED=false
SSH_MUX_ENABLED=true

# PostgreSQL Database Configuration
DB_DATABASE=coolify
Expand Down
17 changes: 10 additions & 7 deletions .github/workflows/remove-labels-and-assignees-on-close.yml
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,7 @@ jobs:
github-token: ${{ secrets.GITHUB_TOKEN }}
script: |
const { owner, repo } = context.repo;
async function processIssue(issueNumber) {
try {
const { data: currentLabels } = await github.rest.issues.listLabelsOnIssue({
Expand Down Expand Up @@ -65,11 +65,14 @@ jobs:
}
if (context.eventName === 'pull_request' || context.eventName === 'pull_request_target') {
const { data: closedIssues } = await github.rest.search.issuesAndPullRequests({
q: `repo:${owner}/${repo} is:issue is:closed linked:${context.payload.pull_request.number}`,
per_page: 100
});
for (const issue of closedIssues.items) {
await processIssue(issue.number);
const pr = context.payload.pull_request;
if (pr.body) {
const issueReferences = pr.body.match(/#(\d+)/g);
if (issueReferences) {
for (const reference of issueReferences) {
const issueNumber = parseInt(reference.substring(1));
await processIssue(issueNumber);
}
}
}
}
54 changes: 22 additions & 32 deletions app/Actions/Application/StopApplication.php
Original file line number Diff line number Diff line change
Expand Up @@ -3,50 +3,40 @@
namespace App\Actions\Application;

use App\Models\Application;
use App\Actions\Server\CleanupDocker;
use Lorisleiva\Actions\Concerns\AsAction;

class StopApplication
{
use AsAction;

public function handle(Application $application, bool $previewDeployments = false)
public function handle(Application $application, bool $previewDeployments = false, bool $dockerCleanup = true)
{
if ($application->destination->server->isSwarm()) {
instant_remote_process(["docker stack rm {$application->uuid}"], $application->destination->server);

return;
}

$servers = collect([]);
$servers->push($application->destination->server);
$application->additional_servers->map(function ($server) use ($servers) {
$servers->push($server);
});
foreach ($servers as $server) {
if (! $server->isFunctional()) {
try {
$server = $application->destination->server;
if (!$server->isFunctional()) {
return 'Server is not functional';
}
if ($previewDeployments) {
$containers = getCurrentApplicationContainerStatus($server, $application->id, includePullrequests: true);
} else {
$containers = getCurrentApplicationContainerStatus($server, $application->id, 0);
}
if ($containers->count() > 0) {
foreach ($containers as $container) {
$containerName = data_get($container, 'Names');
if ($containerName) {
instant_remote_process(command: ["docker stop --time=30 $containerName"], server: $server, throwError: false);
instant_remote_process(command: ["docker rm $containerName"], server: $server, throwError: false);
instant_remote_process(command: ["docker rm -f {$containerName}"], server: $server, throwError: false);
}
}
ray('Stopping application: ' . $application->name);

if ($server->isSwarm()) {
instant_remote_process(["docker stack rm {$application->uuid}"], $server);
return;
}

$containersToStop = $application->getContainersToStop($previewDeployments);
$application->stopContainers($containersToStop, $server);

if ($application->build_pack === 'dockercompose') {
// remove network
$uuid = $application->uuid;
instant_remote_process(["docker network disconnect {$uuid} coolify-proxy"], $server, false);
instant_remote_process(["docker network rm {$uuid}"], $server, false);
$application->delete_connected_networks($application->uuid);
}

if ($dockerCleanup) {
CleanupDocker::run($server, true);
}
} catch (\Exception $e) {
ray($e->getMessage());
return $e->getMessage();
}
}
}
3 changes: 2 additions & 1 deletion app/Actions/CoolifyTask/RunRemoteProcess.php
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@
use Illuminate\Support\Facades\DB;
use Illuminate\Support\Facades\Process;
use Spatie\Activitylog\Models\Activity;
use App\Helpers\SshMultiplexingHelper;

class RunRemoteProcess
{
Expand Down Expand Up @@ -137,7 +138,7 @@ protected function getCommand(): string
$command = $this->activity->getExtraProperty('command');
$server = Server::whereUuid($server_uuid)->firstOrFail();

return generateSshCommand($server, $command);
return SshMultiplexingHelper::generateSshCommand($server, $command);
}

protected function handleOutput(string $type, string $output)
Expand Down
49 changes: 45 additions & 4 deletions app/Actions/Database/StopDatabase.php
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@

namespace App\Actions\Database;

use App\Actions\Server\CleanupDocker;
use App\Models\StandaloneClickhouse;
use App\Models\StandaloneDragonfly;
use App\Models\StandaloneKeydb;
Expand All @@ -10,25 +11,65 @@
use App\Models\StandaloneMysql;
use App\Models\StandalonePostgresql;
use App\Models\StandaloneRedis;
use Illuminate\Support\Facades\Process;
use Lorisleiva\Actions\Concerns\AsAction;

class StopDatabase
{
use AsAction;

public function handle(StandaloneRedis|StandalonePostgresql|StandaloneMongodb|StandaloneMysql|StandaloneMariadb|StandaloneKeydb|StandaloneDragonfly|StandaloneClickhouse $database)
public function handle(StandaloneRedis|StandalonePostgresql|StandaloneMongodb|StandaloneMysql|StandaloneMariadb|StandaloneKeydb|StandaloneDragonfly|StandaloneClickhouse $database, bool $isDeleteOperation = false, bool $dockerCleanup = true)
{
$server = $database->destination->server;
if (! $server->isFunctional()) {
return 'Server is not functional';
}

instant_remote_process(command: ["docker stop --time=30 $database->uuid"], server: $server, throwError: false);
instant_remote_process(command: ["docker rm $database->uuid"], server: $server, throwError: false);
instant_remote_process(command: ["docker rm -f $database->uuid"], server: $server, throwError: false);
$this->stopContainer($database, $database->uuid, 300);
if (! $isDeleteOperation) {
if ($dockerCleanup) {
CleanupDocker::run($server, true);
}
}

if ($database->is_public) {
StopDatabaseProxy::run($database);
}

return 'Database stopped successfully';
}

private function stopContainer($database, string $containerName, int $timeout = 300): void
{
$server = $database->destination->server;

$process = Process::timeout($timeout)->start("docker stop --time=$timeout $containerName");

$startTime = time();
while ($process->running()) {
if (time() - $startTime >= $timeout) {
$this->forceStopContainer($containerName, $server);
break;
}
usleep(100000);
}

$this->removeContainer($containerName, $server);
}

private function forceStopContainer(string $containerName, $server): void
{
instant_remote_process(command: ["docker kill $containerName"], server: $server, throwError: false);
}

private function removeContainer(string $containerName, $server): void
{
instant_remote_process(command: ["docker rm -f $containerName"], server: $server, throwError: false);
}

private function deleteConnectedNetworks($uuid, $server)
{
instant_remote_process(["docker network disconnect {$uuid} coolify-proxy"], $server, false);
instant_remote_process(["docker network rm {$uuid}"], $server, false);
}
}
2 changes: 1 addition & 1 deletion app/Actions/Proxy/CheckProxy.php
Original file line number Diff line number Diff line change
Expand Up @@ -26,7 +26,7 @@ public function handle(Server $server, $fromUI = false)
if (is_null($proxyType) || $proxyType === 'NONE' || $server->proxy->force_stop) {
return false;
}
['uptime' => $uptime, 'error' => $error] = $server->validateConnection();
['uptime' => $uptime, 'error' => $error] = $server->validateConnection(false);
if (! $uptime) {
throw new \Exception($error);
}
Expand Down
30 changes: 26 additions & 4 deletions app/Actions/Service/DeleteService.php
Original file line number Diff line number Diff line change
Expand Up @@ -3,17 +3,18 @@
namespace App\Actions\Service;

use App\Models\Service;
use App\Actions\Server\CleanupDocker;
use Lorisleiva\Actions\Concerns\AsAction;

class DeleteService
{
use AsAction;

public function handle(Service $service)
public function handle(Service $service, bool $deleteConfigurations, bool $deleteVolumes, bool $dockerCleanup, bool $deleteConnectedNetworks)
{
try {
$server = data_get($service, 'server');
if ($server->isFunctional()) {
if ($deleteVolumes && $server->isFunctional()) {
$storagesToDelete = collect([]);

$service->environment_variables()->delete();
Expand All @@ -33,13 +34,29 @@ public function handle(Service $service)
foreach ($storagesToDelete as $storage) {
$commands[] = "docker volume rm -f $storage->name";
}
$commands[] = "docker rm -f $service->uuid";

instant_remote_process($commands, $server, false);
// Execute volume deletion first, this must be done first otherwise volumes will not be deleted.
if (!empty($commands)) {
foreach ($commands as $command) {
$result = instant_remote_process([$command], $server, false);
if ($result !== 0) {
ray("Failed to execute: $command");
}
}
}
}

if ($deleteConnectedNetworks) {
$service->delete_connected_networks($service->uuid);
}

instant_remote_process(["docker rm -f $service->uuid"], $server, throwError: false);
} catch (\Exception $e) {
throw new \Exception($e->getMessage());
} finally {
if ($deleteConfigurations) {
$service->delete_configurations();
}
foreach ($service->applications()->get() as $application) {
$application->forceDelete();
}
Expand All @@ -50,6 +67,11 @@ public function handle(Service $service)
$task->delete();
}
$service->tags()->detach();
$service->forceDelete();

if ($dockerCleanup) {
CleanupDocker::run($server, true);
}
}
}
}
33 changes: 10 additions & 23 deletions app/Actions/Service/StopService.php
Original file line number Diff line number Diff line change
Expand Up @@ -3,46 +3,33 @@
namespace App\Actions\Service;

use App\Models\Service;
use App\Actions\Server\CleanupDocker;
use Lorisleiva\Actions\Concerns\AsAction;

class StopService
{
use AsAction;

public function handle(Service $service)
public function handle(Service $service, bool $isDeleteOperation = false, bool $dockerCleanup = true)
{
try {
$server = $service->destination->server;
if (! $server->isFunctional()) {
if (!$server->isFunctional()) {
return 'Server is not functional';
}
ray('Stopping service: '.$service->name);
$applications = $service->applications()->get();
foreach ($applications as $application) {
if ($applications->count() < 6) {
instant_remote_process(command: ["docker stop --time=10 {$application->name}-{$service->uuid}"], server: $server, throwError: false);
}
instant_remote_process(command: ["docker rm {$application->name}-{$service->uuid}"], server: $server, throwError: false);
instant_remote_process(command: ["docker rm -f {$application->name}-{$service->uuid}"], server: $server, throwError: false);
$application->update(['status' => 'exited']);
}
$dbs = $service->databases()->get();
foreach ($dbs as $db) {
if ($dbs->count() < 6) {

instant_remote_process(command: ["docker stop --time=10 {$db->name}-{$service->uuid}"], server: $server, throwError: false);
$containersToStop = $service->getContainersToStop();
$service->stopContainers($containersToStop, $server);

if (!$isDeleteOperation) {
$service->delete_connected_networks($service->uuid);
if ($dockerCleanup) {
CleanupDocker::run($server, true);
}
instant_remote_process(command: ["docker rm {$db->name}-{$service->uuid}"], server: $server, throwError: false);
instant_remote_process(command: ["docker rm -f {$db->name}-{$service->uuid}"], server: $server, throwError: false);
$db->update(['status' => 'exited']);
}
instant_remote_process(["docker network disconnect {$service->uuid} coolify-proxy"], $service->server);
instant_remote_process(["docker network rm {$service->uuid}"], $service->server);
} catch (\Exception $e) {
ray($e->getMessage());

return $e->getMessage();
}

}
}
10 changes: 6 additions & 4 deletions app/Console/Kernel.php
Original file line number Diff line number Diff line change
Expand Up @@ -43,6 +43,8 @@ protected function schedule(Schedule $schedule): void
$schedule->command('uploads:clear')->everyTwoMinutes();

$schedule->command('telescope:prune')->daily();

$schedule->job(new PullHelperImageJob)->everyFiveMinutes()->onOneServer();
} else {
// Instance Jobs
$schedule->command('horizon:snapshot')->everyFiveMinutes();
Expand Down Expand Up @@ -77,11 +79,11 @@ private function pull_images($schedule)
}
})->cron($settings->update_check_frequency)->timezone($settings->instance_timezone)->onOneServer();
}
$schedule->job(new PullHelperImageJob($server))
->cron($settings->update_check_frequency)
->timezone($settings->instance_timezone)
->onOneServer();
}
$schedule->job(new PullHelperImageJob)
->cron($settings->update_check_frequency)
->timezone($settings->instance_timezone)
->onOneServer();
}

private function schedule_updates($schedule)
Expand Down
Loading

0 comments on commit 92772f9

Please sign in to comment.