feat(god-mode): add self-redeploy endpoint via Coolify webhook
This commit is contained in:
111
src/pages/api/god/redeploy.ts
Normal file
111
src/pages/api/god/redeploy.ts
Normal file
@@ -0,0 +1,111 @@
|
|||||||
|
import type { APIRoute } from 'astro';
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 🔱 GOD MODE - Self-Redeploy Endpoint
|
||||||
|
*
|
||||||
|
* Triggers a Coolify redeploy via webhook
|
||||||
|
* Allows God Mode to update itself with latest code from GitHub
|
||||||
|
*/
|
||||||
|
|
||||||
|
// God Mode Token validation
|
||||||
|
function validateGodToken(request: Request): boolean {
|
||||||
|
const token = request.headers.get('X-God-Token') ||
|
||||||
|
request.headers.get('Authorization')?.replace('Bearer ', '') ||
|
||||||
|
new URL(request.url).searchParams.get('token');
|
||||||
|
|
||||||
|
const godToken = process.env.GOD_MODE_TOKEN || import.meta.env.GOD_MODE_TOKEN;
|
||||||
|
|
||||||
|
if (!godToken) {
|
||||||
|
console.warn('⚠️ GOD_MODE_TOKEN not set - backdoor is open!');
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
return token === godToken;
|
||||||
|
}
|
||||||
|
|
||||||
|
export const POST: APIRoute = async ({ request }) => {
|
||||||
|
if (!validateGodToken(request)) {
|
||||||
|
return new Response(JSON.stringify({ error: 'Unauthorized - Invalid God Mode Token' }), {
|
||||||
|
status: 401,
|
||||||
|
headers: { 'Content-Type': 'application/json' }
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
try {
|
||||||
|
const webhookUrl = process.env.COOLIFY_WEBHOOK_URL;
|
||||||
|
|
||||||
|
if (!webhookUrl) {
|
||||||
|
return new Response(JSON.stringify({
|
||||||
|
error: 'COOLIFY_WEBHOOK_URL not configured',
|
||||||
|
help: 'Add COOLIFY_WEBHOOK_URL to environment variables in Coolify settings'
|
||||||
|
}), {
|
||||||
|
status: 400,
|
||||||
|
headers: { 'Content-Type': 'application/json' }
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
// Trigger Coolify webhook
|
||||||
|
const response = await fetch(webhookUrl, {
|
||||||
|
method: 'GET', // Coolify webhooks use GET
|
||||||
|
headers: {
|
||||||
|
'User-Agent': 'God-Mode-Self-Deploy'
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
if (response.ok) {
|
||||||
|
return new Response(JSON.stringify({
|
||||||
|
success: true,
|
||||||
|
message: 'Redeploy triggered successfully',
|
||||||
|
status: response.status,
|
||||||
|
timestamp: new Date().toISOString(),
|
||||||
|
note: 'God Mode will restart in ~3-5 minutes with latest code from GitHub'
|
||||||
|
}), {
|
||||||
|
status: 200,
|
||||||
|
headers: { 'Content-Type': 'application/json' }
|
||||||
|
});
|
||||||
|
} else {
|
||||||
|
const errorText = await response.text();
|
||||||
|
return new Response(JSON.stringify({
|
||||||
|
success: false,
|
||||||
|
error: 'Webhook request failed',
|
||||||
|
status: response.status,
|
||||||
|
details: errorText
|
||||||
|
}), {
|
||||||
|
status: 500,
|
||||||
|
headers: { 'Content-Type': 'application/json' }
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
} catch (error: any) {
|
||||||
|
return new Response(JSON.stringify({
|
||||||
|
error: error.message,
|
||||||
|
stack: error.stack
|
||||||
|
}), {
|
||||||
|
status: 500,
|
||||||
|
headers: { 'Content-Type': 'application/json' }
|
||||||
|
});
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
export const GET: APIRoute = async ({ request }) => {
|
||||||
|
if (!validateGodToken(request)) {
|
||||||
|
return new Response(JSON.stringify({ error: 'Unauthorized' }), {
|
||||||
|
status: 401,
|
||||||
|
headers: { 'Content-Type': 'application/json' }
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
const webhookConfigured = !!process.env.COOLIFY_WEBHOOK_URL;
|
||||||
|
|
||||||
|
return new Response(JSON.stringify({
|
||||||
|
endpoint: 'POST /api/god/redeploy',
|
||||||
|
description: 'Trigger self-redeploy via Coolify webhook',
|
||||||
|
webhook_configured: webhookConfigured,
|
||||||
|
webhook_url: webhookConfigured ? 'Configured ✅' : 'Not set ❌',
|
||||||
|
usage: 'POST request with X-God-Token header',
|
||||||
|
example: 'curl -X POST -H "X-God-Token: YOUR_TOKEN" https://spark.jumpstartscaling.com/api/god/redeploy'
|
||||||
|
}), {
|
||||||
|
status: 200,
|
||||||
|
headers: { 'Content-Type': 'application/json' }
|
||||||
|
});
|
||||||
|
};
|
||||||
Reference in New Issue
Block a user