mcp / start.sh
arcticaurora's picture
Update start.sh
94b10f1 verified
#!/bin/bash
set -e
# ======================= Supabase Config =======================
# Strip any whitespace/newlines from environment variables
export SUPABASE_URL="${SUPABASE_URL//[$'\t\r\n ']}"
export SUPABASE_ANON_KEY="${SUPABASE_ANON_KEY//[$'\t\r\n ']}"
export CONFIG_ID="mcp_settings"
# ================================================================
# --- Define paths ---
APP_SRC_DIR="/app"
RUN_DIR="/tmp/mcphub"
CONFIG_FILE_NAME="mcp_settings.json"
CONFIG_FILE_PATH="${RUN_DIR}/${CONFIG_FILE_NAME}"
echo "--- MCPHub with Supabase Storage ---"
# 1. Create runtime directory and copy files
echo "Setting up runtime environment..."
mkdir -p "$RUN_DIR"
cp -a "${APP_SRC_DIR}/." "$RUN_DIR/"
# 2. Download config from Supabase
echo "Loading configuration..."
RESPONSE=$(curl --http1.1 -s -S -X GET \
"${SUPABASE_URL}/rest/v1/configs?id=eq.${CONFIG_ID}&select=content" \
-H "apikey: ${SUPABASE_ANON_KEY}" \
-H "Authorization: Bearer ${SUPABASE_ANON_KEY}" \
-H "Accept: application/json" 2>&1)
if [ -n "$RESPONSE" ] && [ "$RESPONSE" != "[]" ] && [[ ! "$RESPONSE" =~ "ERROR" ]]; then
echo "$RESPONSE" | python3 -c "
import sys, json
try:
data = json.load(sys.stdin)
if data and len(data) > 0:
print(json.dumps(data[0]['content']))
else:
print('{}')
except:
print('{}')
" > "$CONFIG_FILE_PATH"
echo "✅ Configuration loaded"
else
echo "{}" > "$CONFIG_FILE_PATH"
echo "⚠️ Using default configuration"
fi
# 3. Function to sync file to Supabase
sync_to_supabase() {
if [ ! -f "$CONFIG_FILE_PATH" ]; then
return 1
fi
# Create JSON payload using Python (just for JSON formatting)
PAYLOAD=$(python3 -c "
import json
from datetime import datetime
with open('$CONFIG_FILE_PATH', 'r') as f:
config = json.load(f)
payload = {
'content': config,
'updated_at': datetime.utcnow().strftime('%Y-%m-%dT%H:%M:%S')
}
print(json.dumps(payload))
" 2>/dev/null)
if [ -n "$PAYLOAD" ]; then
# Upload using curl
curl --http1.1 -s -X PATCH \
"${SUPABASE_URL}/rest/v1/configs?id=eq.${CONFIG_ID}" \
-H "apikey: ${SUPABASE_ANON_KEY}" \
-H "Authorization: Bearer ${SUPABASE_ANON_KEY}" \
-H "Content-Type: application/json" \
-H "Prefer: return=minimal" \
-d "$PAYLOAD" > /dev/null 2>&1
if [ $? -eq 0 ]; then
echo "✅ Config synced to Supabase at $(date)"
fi
fi
}
# 4. Heartbeat function to keep Supabase active
send_heartbeat() {
curl --http1.1 -s -X POST \
"${SUPABASE_URL}/rest/v1/heartbeat" \
-H "apikey: ${SUPABASE_ANON_KEY}" \
-H "Authorization: Bearer ${SUPABASE_ANON_KEY}" \
-H "Content-Type: application/json" \
-H "Prefer: return=minimal" \
-d "{\"source\": \"mcphub-$(hostname 2>/dev/null || echo 'docker')\"}" > /dev/null 2>&1
if [ $? -eq 0 ]; then
echo "♥️ Heartbeat sent at $(date)"
fi
}
# 5. Start background sync process
echo "Starting background sync..."
(
LAST_HASH=""
if [ -f "$CONFIG_FILE_PATH" ]; then
LAST_HASH=$(md5sum "$CONFIG_FILE_PATH" | awk '{ print $1 }')
fi
while true; do
sleep 30
if [ -f "$CONFIG_FILE_PATH" ]; then
CURRENT_HASH=$(md5sum "$CONFIG_FILE_PATH" | awk '{ print $1 }')
if [ "$CURRENT_HASH" != "$LAST_HASH" ]; then
sync_to_supabase
LAST_HASH=$CURRENT_HASH
fi
fi
done
) &
# 6. Start heartbeat process to keep Supabase active
echo "Starting heartbeat process..."
(
# Send initial heartbeat
send_heartbeat
# Send heartbeat every 6 hours
while true; do
sleep 21600 # 6 hours
send_heartbeat
done
) &
# 7. Start application
echo "🚀 Starting MCPHub server..."
cd "$RUN_DIR"
npm start
echo "MCPHub server stopped."