mirror of
https://github.com/coollabsio/coolify.git
synced 2026-11-04 10:42:23 +00:00
fix(mcp): save MCP deployments as MCP, not as API deployments
This commit is contained in:
1 parent
c3a21eceeb
commit
b063a41624
13 files changed
+70
-9
No files matched your search
@@ -9,6 +9,7 @@ The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.1.0/),
|
||||
### Fixed
|
||||
|
||||
- Handle an existing Cloudflare DNS record with a different IP when Coolify adds the DNS record of a new domain automatically. Coolify now replaces the record when it created the record and no other resource uses it. Otherwise it opens the **Configure DNS** dialog, where you can replace the record, and the domain shows the conflict instead of "Not checked"
|
||||
- Save deployments started through the MCP server as MCP deployments, not as API deployments. The deployment list shows them with the **MCP** source and filter, and the API and MCP deployment data have a new `is_mcp` field
|
||||
|
||||
## [v4.6.0] - 2026-11-02
|
||||
|
||||
|
||||
@@ -26,6 +26,7 @@ class Index extends Component
|
||||
'commit_message',
|
||||
'is_webhook',
|
||||
'is_api',
|
||||
'is_mcp',
|
||||
'rollback',
|
||||
'server_id',
|
||||
'server_name',
|
||||
@@ -297,6 +298,7 @@ class Index extends Component
|
||||
WHEN pull_request_id > 0 THEN 'pull-request'
|
||||
WHEN is_webhook THEN 'webhook'
|
||||
WHEN rollback THEN 'rollback'
|
||||
WHEN is_mcp THEN 'mcp'
|
||||
WHEN is_api THEN 'api'
|
||||
ELSE 'manual'
|
||||
END AS source_key
|
||||
@@ -309,6 +311,7 @@ class Index extends Component
|
||||
'pull-request' => 'Pull requests',
|
||||
'webhook' => 'Webhooks',
|
||||
'api' => 'API',
|
||||
'mcp' => 'MCP',
|
||||
'rollback' => 'Rollbacks',
|
||||
];
|
||||
|
||||
|
||||
@@ -125,7 +125,7 @@ class Control extends Tool
|
||||
deployment_uuid: $deploymentUuid,
|
||||
force_rebuild: false,
|
||||
restart_only: $action === 'restart',
|
||||
is_api: true,
|
||||
is_mcp: true,
|
||||
no_questions_asked: $action === 'start',
|
||||
);
|
||||
|
||||
|
||||
@@ -74,7 +74,7 @@ class Deploy extends Tool
|
||||
deployment_uuid: $deploymentUuid,
|
||||
pull_request_id: $pullRequestId,
|
||||
force_rebuild: $force,
|
||||
is_api: true,
|
||||
is_mcp: true,
|
||||
no_questions_asked: true,
|
||||
);
|
||||
|
||||
|
||||
@@ -72,6 +72,7 @@ class GetDeployment extends Tool
|
||||
'force_rebuild' => $deployment->force_rebuild,
|
||||
'is_webhook' => $deployment->is_webhook,
|
||||
'is_api' => $deployment->is_api,
|
||||
'is_mcp' => $deployment->is_mcp,
|
||||
'restart_only' => $deployment->restart_only,
|
||||
'rollback' => $deployment->rollback,
|
||||
'git_type' => $deployment->git_type,
|
||||
|
||||
@@ -120,6 +120,7 @@ class ListDeployments extends Tool
|
||||
'force_rebuild' => $deployment->force_rebuild,
|
||||
'is_webhook' => $deployment->is_webhook,
|
||||
'is_api' => $deployment->is_api,
|
||||
'is_mcp' => $deployment->is_mcp,
|
||||
'deployment_url' => $deployment->deployment_url,
|
||||
'created_at' => $deployment->created_at,
|
||||
'updated_at' => $deployment->updated_at,
|
||||
|
||||
@@ -1378,12 +1378,14 @@ class Application extends BaseModel
|
||||
'webhook', 'webhooks' => $query->orWhere('is_webhook', true),
|
||||
'rollback', 'rollbacks' => $query->orWhere('rollback', true),
|
||||
'api' => $query->orWhere('is_api', true),
|
||||
'mcp' => $query->orWhere('is_mcp', true),
|
||||
'manual' => $query->orWhere(function ($sourceQuery) {
|
||||
$sourceQuery
|
||||
->where('pull_request_id', '<=', 0)
|
||||
->where('is_webhook', false)
|
||||
->where('rollback', false)
|
||||
->where('is_api', false);
|
||||
->where('is_api', false)
|
||||
->where('is_mcp', false);
|
||||
}),
|
||||
default => null,
|
||||
};
|
||||
@@ -1409,7 +1411,8 @@ class Application extends BaseModel
|
||||
'webhook' => $sourceQuery->where('pull_request_id', '<=', 0)->where('is_webhook', true),
|
||||
'rollback' => $sourceQuery->where('pull_request_id', '<=', 0)->where('is_webhook', false)->where('rollback', true),
|
||||
'api' => $sourceQuery->where('pull_request_id', '<=', 0)->where('is_webhook', false)->where('rollback', false)->where('is_api', true),
|
||||
'manual' => $sourceQuery->where('pull_request_id', '<=', 0)->where('is_webhook', false)->where('rollback', false)->where('is_api', false),
|
||||
'mcp' => $sourceQuery->where('pull_request_id', '<=', 0)->where('is_webhook', false)->where('rollback', false)->where('is_mcp', true),
|
||||
'manual' => $sourceQuery->where('pull_request_id', '<=', 0)->where('is_webhook', false)->where('rollback', false)->where('is_api', false)->where('is_mcp', false),
|
||||
default => $sourceQuery->where('id', -1),
|
||||
};
|
||||
});
|
||||
|
||||
@@ -32,6 +32,7 @@ use OpenApi\Attributes as OA;
|
||||
'status' => ['type' => 'string'],
|
||||
'is_webhook' => ['type' => 'boolean'],
|
||||
'is_api' => ['type' => 'boolean'],
|
||||
'is_mcp' => ['type' => 'boolean'],
|
||||
'created_at' => ['type' => 'string'],
|
||||
'updated_at' => ['type' => 'string'],
|
||||
'logs' => ['type' => 'string'],
|
||||
@@ -89,7 +90,11 @@ class ApplicationDeploymentQueue extends Model
|
||||
}
|
||||
|
||||
$application = $deployment->application;
|
||||
$source = $deployment->is_api ? 'api' : 'ui';
|
||||
$source = match (true) {
|
||||
(bool) $deployment->is_mcp => 'mcp',
|
||||
(bool) $deployment->is_api => 'api',
|
||||
default => 'ui',
|
||||
};
|
||||
|
||||
auditLog("{$source}.application.rollback", [
|
||||
'team_id' => $application?->team()?->id,
|
||||
@@ -108,7 +113,11 @@ class ApplicationDeploymentQueue extends Model
|
||||
}
|
||||
|
||||
$application = $deployment->application;
|
||||
$source = $deployment->is_api ? 'api' : 'ui';
|
||||
$source = match (true) {
|
||||
(bool) $deployment->is_mcp => 'mcp',
|
||||
(bool) $deployment->is_api => 'api',
|
||||
default => 'ui',
|
||||
};
|
||||
|
||||
auditLog("{$source}.deployment.cancelled", [
|
||||
'team_id' => $application?->team()?->id,
|
||||
@@ -145,6 +154,7 @@ class ApplicationDeploymentQueue extends Model
|
||||
'rollback',
|
||||
'commit_message',
|
||||
'is_api',
|
||||
'is_mcp',
|
||||
'build_server_id',
|
||||
'horizon_job_id',
|
||||
'horizon_job_worker',
|
||||
|
||||
@@ -16,7 +16,7 @@ use Illuminate\Support\Facades\DB;
|
||||
use Illuminate\Support\Facades\Log;
|
||||
use Spatie\Url\Url;
|
||||
|
||||
function queue_application_deployment(Application $application, string $deployment_uuid, ?int $pull_request_id = 0, ?string $commit = null, bool $force_rebuild = false, bool $is_webhook = false, bool $is_api = false, bool $restart_only = false, ?string $git_type = null, bool $no_questions_asked = false, ?Server $server = null, ?StandaloneDocker $destination = null, bool $only_this_server = false, bool $rollback = false, ?string $docker_registry_image_tag = null, ?string $parent_deployment_uuid = null)
|
||||
function queue_application_deployment(Application $application, string $deployment_uuid, ?int $pull_request_id = 0, ?string $commit = null, bool $force_rebuild = false, bool $is_webhook = false, bool $is_api = false, bool $restart_only = false, ?string $git_type = null, bool $no_questions_asked = false, ?Server $server = null, ?StandaloneDocker $destination = null, bool $only_this_server = false, bool $rollback = false, ?string $docker_registry_image_tag = null, ?string $parent_deployment_uuid = null, bool $is_mcp = false)
|
||||
{
|
||||
$commit = $commit ?: ($application->git_commit_sha ?: 'HEAD');
|
||||
$commit = validateGitRef($commit, 'deployment commit');
|
||||
@@ -35,7 +35,11 @@ function queue_application_deployment(Application $application, string $deployme
|
||||
$destination_id = $destination->id;
|
||||
}
|
||||
|
||||
$admission = DB::transaction(function () use ($application, $application_id, $commit, $deployment_uuid, $deployment_url, $destination_id, $docker_registry_image_tag, $force_rebuild, $git_type, $is_api, $is_webhook, $no_questions_asked, $only_this_server, $parent_deployment_uuid, $pull_request_id, $restart_only, $rollback, $server_id, $server_name) {
|
||||
// MCP tools also call the REST API controllers through an internal request.
|
||||
$is_mcp = $is_mcp || request()->attributes->get('mcp_rest_bridge') === true;
|
||||
$is_api = $is_api && ! $is_mcp;
|
||||
|
||||
$admission = DB::transaction(function () use ($application, $application_id, $commit, $deployment_uuid, $deployment_url, $destination_id, $docker_registry_image_tag, $force_rebuild, $git_type, $is_api, $is_mcp, $is_webhook, $no_questions_asked, $only_this_server, $parent_deployment_uuid, $pull_request_id, $restart_only, $rollback, $server_id, $server_name) {
|
||||
// Lock stable rows because an empty deployment queue has no row to lock.
|
||||
Application::query()->whereKey($application_id)->lockForUpdate()->firstOrFail();
|
||||
$serverForQueueCheck = Server::query()->whereKey($server_id)->lockForUpdate()->firstOrFail();
|
||||
@@ -80,6 +84,7 @@ function queue_application_deployment(Application $application, string $deployme
|
||||
'force_rebuild' => $force_rebuild,
|
||||
'is_webhook' => $is_webhook,
|
||||
'is_api' => $is_api,
|
||||
'is_mcp' => $is_mcp,
|
||||
'restart_only' => $restart_only,
|
||||
'commit' => $commit,
|
||||
'rollback' => $rollback,
|
||||
@@ -106,7 +111,7 @@ function queue_application_deployment(Application $application, string $deployme
|
||||
|
||||
$deployment = $admission['deployment'];
|
||||
|
||||
if (auth()->check() && ! $is_webhook && ! $is_api && ! $rollback) {
|
||||
if (auth()->check() && ! $is_webhook && ! $is_api && ! $is_mcp && ! $rollback) {
|
||||
auditLog($restart_only ? 'ui.application.restarted' : 'ui.application.deployed', [
|
||||
'application_uuid' => $application->uuid,
|
||||
'application_name' => $application->name,
|
||||
|
||||
+30
@@ -0,0 +1,30 @@
|
||||
<?php
|
||||
|
||||
use Illuminate\Database\Migrations\Migration;
|
||||
use Illuminate\Database\Schema\Blueprint;
|
||||
use Illuminate\Support\Facades\Schema;
|
||||
|
||||
return new class extends Migration
|
||||
{
|
||||
public function up(): void
|
||||
{
|
||||
if (Schema::hasColumn('application_deployment_queues', 'is_mcp')) {
|
||||
return;
|
||||
}
|
||||
|
||||
Schema::table('application_deployment_queues', function (Blueprint $table) {
|
||||
$table->boolean('is_mcp')->default(false);
|
||||
});
|
||||
}
|
||||
|
||||
public function down(): void
|
||||
{
|
||||
if (! Schema::hasColumn('application_deployment_queues', 'is_mcp')) {
|
||||
return;
|
||||
}
|
||||
|
||||
Schema::table('application_deployment_queues', function (Blueprint $table) {
|
||||
$table->dropColumn('is_mcp');
|
||||
});
|
||||
}
|
||||
};
|
||||
@@ -27187,6 +27187,9 @@
|
||||
"is_api": {
|
||||
"type": "boolean"
|
||||
},
|
||||
"is_mcp": {
|
||||
"type": "boolean"
|
||||
},
|
||||
"created_at": {
|
||||
"type": "string"
|
||||
},
|
||||
|
||||
@@ -17360,6 +17360,8 @@ components:
|
||||
type: boolean
|
||||
is_api:
|
||||
type: boolean
|
||||
is_mcp:
|
||||
type: boolean
|
||||
created_at:
|
||||
type: string
|
||||
updated_at:
|
||||
|
||||
@@ -237,6 +237,7 @@
|
||||
(bool) data_get($deployment, 'is_webhook') => 'Webhook',
|
||||
$pullRequestId > 0 => 'Pull request #' . $pullRequestId,
|
||||
(bool) data_get($deployment, 'rollback') => 'Rollback',
|
||||
(bool) data_get($deployment, 'is_mcp') => 'MCP',
|
||||
(bool) data_get($deployment, 'is_api') => 'API',
|
||||
default => 'Manual',
|
||||
};
|
||||
@@ -244,6 +245,7 @@
|
||||
$pullRequestId > 0 => 'pull-request',
|
||||
(bool) data_get($deployment, 'is_webhook') => 'webhook',
|
||||
(bool) data_get($deployment, 'rollback') => 'rollback',
|
||||
(bool) data_get($deployment, 'is_mcp') => 'mcp',
|
||||
(bool) data_get($deployment, 'is_api') => 'api',
|
||||
default => 'manual',
|
||||
};
|
||||
|
||||
Reference in new issue
Block a user