722 lines
25 KiB
Bash
Executable File
722 lines
25 KiB
Bash
Executable File
#!/bin/bash
|
|
|
|
# C-Relay-PG Build and Restart Script
|
|
# Builds the project first, then stops any running relay and starts a new one in the background
|
|
|
|
echo "=== C Nostr Relay Build and Restart Script ==="
|
|
|
|
# Parse command line arguments
|
|
PRESERVE_DATABASE=false
|
|
HELP=false
|
|
USE_TEST_KEYS=false
|
|
ADMIN_KEY=""
|
|
RELAY_KEY=""
|
|
PORT_OVERRIDE=""
|
|
DEBUG_LEVEL="5"
|
|
START_CACHING=false
|
|
RESET_BACKFILL=false
|
|
DB_BACKEND="postgres"
|
|
DB_CONNSTRING=""
|
|
DB_HOST=""
|
|
DB_PORT=""
|
|
DB_NAME=""
|
|
DB_USER=""
|
|
DB_PASSWORD=""
|
|
|
|
# Key validation function
|
|
validate_hex_key() {
|
|
local key="$1"
|
|
local key_type="$2"
|
|
|
|
if [ ${#key} -ne 64 ]; then
|
|
echo "ERROR: $key_type key must be exactly 64 characters"
|
|
return 1
|
|
fi
|
|
|
|
if ! [[ "$key" =~ ^[0-9a-fA-F]{64}$ ]]; then
|
|
echo "ERROR: $key_type key must contain only hex characters (0-9, a-f, A-F)"
|
|
return 1
|
|
fi
|
|
|
|
return 0
|
|
}
|
|
|
|
while [[ $# -gt 0 ]]; do
|
|
case $1 in
|
|
-a|--admin-key)
|
|
if [ -z "$2" ]; then
|
|
echo "ERROR: Admin key option requires a value"
|
|
HELP=true
|
|
shift
|
|
else
|
|
ADMIN_KEY="$2"
|
|
shift 2
|
|
fi
|
|
;;
|
|
-r|--relay-key)
|
|
if [ -z "$2" ]; then
|
|
echo "ERROR: Relay key option requires a value"
|
|
HELP=true
|
|
shift
|
|
else
|
|
RELAY_KEY="$2"
|
|
shift 2
|
|
fi
|
|
;;
|
|
-p|--port)
|
|
if [ -z "$2" ]; then
|
|
echo "ERROR: Port option requires a value"
|
|
HELP=true
|
|
shift
|
|
else
|
|
PORT_OVERRIDE="$2"
|
|
shift 2
|
|
fi
|
|
;;
|
|
-d|--preserve-database)
|
|
PRESERVE_DATABASE=true
|
|
shift
|
|
;;
|
|
--start-caching)
|
|
START_CACHING=true
|
|
shift
|
|
;;
|
|
--reset-backfill)
|
|
RESET_BACKFILL=true
|
|
shift
|
|
;;
|
|
--test-keys|-t)
|
|
USE_TEST_KEYS=true
|
|
# Read keys from .test_keys file
|
|
if [ -f ".test_keys" ]; then
|
|
echo "Reading test keys from .test_keys file..."
|
|
# Source the file to get the variables
|
|
source .test_keys
|
|
# Remove any single quotes from the values
|
|
# Note: -a flag expects ADMIN_PUBKEY (public key), not ADMIN_PRIVKEY
|
|
ADMIN_KEY=$(echo "$ADMIN_PUBKEY" | tr -d "'")
|
|
RELAY_KEY=$(echo "$SERVER_PRIVKEY" | tr -d "'")
|
|
echo "Using admin pubkey from .test_keys: ${ADMIN_KEY:0:16}..."
|
|
echo "Using relay privkey from .test_keys: ${RELAY_KEY:0:16}..."
|
|
else
|
|
echo "ERROR: .test_keys file not found"
|
|
echo "Please create a .test_keys file with the following format:"
|
|
echo " ADMIN_PUBKEY='your_admin_public_key_hex'"
|
|
echo " SERVER_PRIVKEY='your_relay_private_key_hex'"
|
|
exit 1
|
|
fi
|
|
shift
|
|
;;
|
|
--debug-level=*)
|
|
DEBUG_LEVEL="${1#*=}"
|
|
shift
|
|
;;
|
|
-d=*)
|
|
DEBUG_LEVEL="${1#*=}"
|
|
shift
|
|
;;
|
|
--debug-level)
|
|
if [ -z "$2" ]; then
|
|
echo "ERROR: Debug level option requires a value"
|
|
HELP=true
|
|
shift
|
|
else
|
|
DEBUG_LEVEL="$2"
|
|
shift 2
|
|
fi
|
|
;;
|
|
-d)
|
|
if [ -z "$2" ]; then
|
|
echo "ERROR: Debug level option requires a value"
|
|
HELP=true
|
|
shift
|
|
else
|
|
DEBUG_LEVEL="$2"
|
|
shift 2
|
|
fi
|
|
;;
|
|
--db-backend)
|
|
if [ -z "$2" ]; then
|
|
echo "ERROR: --db-backend requires a value (sqlite|postgres)"
|
|
HELP=true
|
|
shift
|
|
else
|
|
DB_BACKEND="$2"
|
|
shift 2
|
|
fi
|
|
;;
|
|
--db-backend=*)
|
|
DB_BACKEND="${1#*=}"
|
|
shift
|
|
;;
|
|
--db-connstring)
|
|
if [ -z "$2" ]; then
|
|
echo "ERROR: --db-connstring requires a value"
|
|
HELP=true
|
|
shift
|
|
else
|
|
DB_CONNSTRING="$2"
|
|
shift 2
|
|
fi
|
|
;;
|
|
--db-connstring=*)
|
|
DB_CONNSTRING="${1#*=}"
|
|
shift
|
|
;;
|
|
--db-host)
|
|
if [ -z "$2" ]; then
|
|
echo "ERROR: --db-host requires a value"
|
|
HELP=true
|
|
shift
|
|
else
|
|
DB_HOST="$2"
|
|
shift 2
|
|
fi
|
|
;;
|
|
--db-port)
|
|
if [ -z "$2" ]; then
|
|
echo "ERROR: --db-port requires a value"
|
|
HELP=true
|
|
shift
|
|
else
|
|
DB_PORT="$2"
|
|
shift 2
|
|
fi
|
|
;;
|
|
--db-name)
|
|
if [ -z "$2" ]; then
|
|
echo "ERROR: --db-name requires a value"
|
|
HELP=true
|
|
shift
|
|
else
|
|
DB_NAME="$2"
|
|
shift 2
|
|
fi
|
|
;;
|
|
--db-user)
|
|
if [ -z "$2" ]; then
|
|
echo "ERROR: --db-user requires a value"
|
|
HELP=true
|
|
shift
|
|
else
|
|
DB_USER="$2"
|
|
shift 2
|
|
fi
|
|
;;
|
|
--db-password)
|
|
if [ -z "$2" ]; then
|
|
echo "ERROR: --db-password requires a value"
|
|
HELP=true
|
|
shift
|
|
else
|
|
DB_PASSWORD="$2"
|
|
shift 2
|
|
fi
|
|
;;
|
|
--help|-h)
|
|
HELP=true
|
|
shift
|
|
;;
|
|
*)
|
|
echo "Unknown option: $1"
|
|
HELP=true
|
|
shift
|
|
;;
|
|
esac
|
|
done
|
|
|
|
# Validate custom keys if provided
|
|
if [ -n "$ADMIN_KEY" ]; then
|
|
if ! validate_hex_key "$ADMIN_KEY" "Admin"; then
|
|
exit 1
|
|
fi
|
|
fi
|
|
|
|
if [ -n "$RELAY_KEY" ]; then
|
|
if ! validate_hex_key "$RELAY_KEY" "Relay"; then
|
|
exit 1
|
|
fi
|
|
fi
|
|
|
|
# Validate port if provided
|
|
if [ -n "$PORT_OVERRIDE" ]; then
|
|
if ! [[ "$PORT_OVERRIDE" =~ ^[0-9]+$ ]] || [ "$PORT_OVERRIDE" -lt 1 ] || [ "$PORT_OVERRIDE" -gt 65535 ]; then
|
|
echo "ERROR: Port must be a number between 1 and 65535"
|
|
exit 1
|
|
fi
|
|
fi
|
|
|
|
# Validate strict port flag (only makes sense with port override)
|
|
if [ "$USE_TEST_KEYS" = true ] && [ -z "$PORT_OVERRIDE" ]; then
|
|
echo "WARNING: --strict-port is always used with test keys. Consider specifying a custom port with -p."
|
|
fi
|
|
|
|
# Validate debug level if provided
|
|
if [ -n "$DEBUG_LEVEL" ]; then
|
|
if ! [[ "$DEBUG_LEVEL" =~ ^[0-5]$ ]]; then
|
|
echo "ERROR: Debug level must be 0-5, got: $DEBUG_LEVEL"
|
|
exit 1
|
|
fi
|
|
fi
|
|
|
|
# Validate DB backend
|
|
if [ "$DB_BACKEND" != "sqlite" ] && [ "$DB_BACKEND" != "postgres" ]; then
|
|
echo "ERROR: Invalid --db-backend value '$DB_BACKEND'. Use sqlite or postgres."
|
|
exit 1
|
|
fi
|
|
|
|
# Validate DB port if provided
|
|
if [ -n "$DB_PORT" ]; then
|
|
if ! [[ "$DB_PORT" =~ ^[0-9]+$ ]] || [ "$DB_PORT" -lt 1 ] || [ "$DB_PORT" -gt 65535 ]; then
|
|
echo "ERROR: --db-port must be a number between 1 and 65535"
|
|
exit 1
|
|
fi
|
|
fi
|
|
|
|
if [ "$DB_BACKEND" = "postgres" ] && [ -z "$DB_CONNSTRING" ]; then
|
|
[ -z "$DB_HOST" ] && DB_HOST="localhost"
|
|
[ -z "$DB_PORT" ] && DB_PORT="5432"
|
|
[ -z "$DB_NAME" ] && DB_NAME="crelay"
|
|
[ -z "$DB_USER" ] && DB_USER="crelay"
|
|
[ -z "$DB_PASSWORD" ] && DB_PASSWORD="crelay"
|
|
fi
|
|
|
|
ensure_postgres_database() {
|
|
if ! command -v psql >/dev/null 2>&1; then
|
|
echo "ERROR: psql not found. Install PostgreSQL client tools to continue."
|
|
return 1
|
|
fi
|
|
|
|
echo "Ensuring PostgreSQL database exists: host=$DB_HOST port=$DB_PORT dbname=$DB_NAME user=$DB_USER"
|
|
|
|
if [ -n "$DB_PASSWORD" ]; then
|
|
export PGPASSWORD="$DB_PASSWORD"
|
|
fi
|
|
|
|
# Prefer local postgres superuser for provisioning when available.
|
|
if sudo -n -u postgres psql -d postgres -tAc "SELECT 1" >/dev/null 2>&1; then
|
|
sudo -u postgres psql -d postgres -tAc "SELECT 1 FROM pg_roles WHERE rolname = '$DB_USER'" | grep -q 1 || \
|
|
sudo -u postgres psql -d postgres -v ON_ERROR_STOP=1 -c "CREATE ROLE \"$DB_USER\" LOGIN PASSWORD '$DB_PASSWORD';" || return 1
|
|
|
|
sudo -u postgres psql -d postgres -v ON_ERROR_STOP=1 -c "ALTER ROLE \"$DB_USER\" WITH LOGIN PASSWORD '$DB_PASSWORD';" >/dev/null || return 1
|
|
|
|
if [ "$PRESERVE_DATABASE" = false ]; then
|
|
echo "Resetting PostgreSQL database '$DB_NAME' for fresh start..."
|
|
|
|
# Ensure no active sessions block DROP DATABASE (common when relay is still running).
|
|
sudo -u postgres psql -d postgres -v ON_ERROR_STOP=1 -c \
|
|
"SELECT pg_terminate_backend(pid) FROM pg_stat_activity WHERE datname = '$DB_NAME' AND pid <> pg_backend_pid();" >/dev/null || return 1
|
|
|
|
# Prefer force drop when supported; fallback to regular dropdb.
|
|
if ! sudo -u postgres dropdb --if-exists --force "$DB_NAME" >/dev/null 2>&1; then
|
|
sudo -u postgres dropdb --if-exists "$DB_NAME" >/dev/null 2>&1 || return 1
|
|
fi
|
|
|
|
sudo -u postgres createdb -O "$DB_USER" "$DB_NAME" >/dev/null 2>&1 || return 1
|
|
echo "✓ Recreated PostgreSQL database '$DB_NAME' owned by '$DB_USER'"
|
|
else
|
|
DB_EXISTS=$(sudo -u postgres psql -d postgres -tAc "SELECT 1 FROM pg_database WHERE datname = '$DB_NAME'" 2>/dev/null | tr -d '[:space:]')
|
|
if [ "$DB_EXISTS" != "1" ]; then
|
|
sudo -u postgres createdb -O "$DB_USER" "$DB_NAME" >/dev/null 2>&1 || return 1
|
|
echo "✓ Created PostgreSQL database '$DB_NAME'"
|
|
else
|
|
echo "✓ PostgreSQL database '$DB_NAME' already exists"
|
|
fi
|
|
fi
|
|
|
|
sudo -u postgres psql -d postgres -v ON_ERROR_STOP=1 -c "GRANT ALL PRIVILEGES ON DATABASE \"$DB_NAME\" TO \"$DB_USER\";" >/dev/null || return 1
|
|
sudo -u postgres psql -d "$DB_NAME" -v ON_ERROR_STOP=1 -c "ALTER SCHEMA public OWNER TO \"$DB_USER\"; GRANT ALL ON SCHEMA public TO \"$DB_USER\";" >/dev/null || return 1
|
|
return 0
|
|
fi
|
|
|
|
# Fallback: use configured DB user directly.
|
|
if ! psql -h "$DB_HOST" -p "$DB_PORT" -U "$DB_USER" -d postgres -v ON_ERROR_STOP=1 -tAc "SELECT 1" >/dev/null 2>&1; then
|
|
echo "ERROR: Cannot connect to PostgreSQL server/database 'postgres' with current settings"
|
|
echo " host=$DB_HOST port=$DB_PORT user=$DB_USER"
|
|
return 1
|
|
fi
|
|
|
|
DB_EXISTS=$(psql -h "$DB_HOST" -p "$DB_PORT" -U "$DB_USER" -d postgres -tAc "SELECT 1 FROM pg_database WHERE datname = '$DB_NAME'" 2>/dev/null | tr -d '[:space:]')
|
|
if [ "$DB_EXISTS" != "1" ]; then
|
|
echo "Database '$DB_NAME' not found. Creating..."
|
|
if ! createdb -h "$DB_HOST" -p "$DB_PORT" -U "$DB_USER" "$DB_NAME" >/dev/null 2>&1; then
|
|
echo "ERROR: Failed to create PostgreSQL database '$DB_NAME'"
|
|
return 1
|
|
fi
|
|
echo "✓ Created PostgreSQL database '$DB_NAME'"
|
|
else
|
|
echo "✓ PostgreSQL database '$DB_NAME' already exists"
|
|
fi
|
|
|
|
return 0
|
|
}
|
|
|
|
# Show help
|
|
if [ "$HELP" = true ]; then
|
|
echo "Usage: $0 [OPTIONS]"
|
|
echo ""
|
|
echo "Options:"
|
|
echo " -a, --admin-key <hex> 64-character hex admin private key"
|
|
echo " -r, --relay-key <hex> 64-character hex relay private key"
|
|
echo " -p, --port <port> Custom port override (default: 8888)"
|
|
echo " -d, --debug-level <0-5> Set debug level: 0=none, 1=errors, 2=warnings, 3=info, 4=debug, 5=trace"
|
|
echo " --preserve-database Keep existing database files (don't delete for fresh start)"
|
|
echo " --test-keys, -t Use deterministic test keys for development (admin: all 'a's, relay: all '1's)"
|
|
echo " --db-backend <name> Database backend: postgres (default) or sqlite"
|
|
echo " --db-connstring <str> PostgreSQL libpq connection string"
|
|
echo " --db-host <host> PostgreSQL host"
|
|
echo " --db-port <port> PostgreSQL port"
|
|
echo " --db-name <name> PostgreSQL database name"
|
|
echo " --db-user <user> PostgreSQL database user"
|
|
echo " --db-password <pass> PostgreSQL database password"
|
|
echo " --start-caching Auto-start the caching service on startup"
|
|
echo " --reset-backfill Clear caching backfill progress (use with --start-caching)"
|
|
echo " --help, -h Show this help message"
|
|
echo ""
|
|
echo "Event-Based Configuration:"
|
|
echo " This relay now uses event-based configuration stored directly in the database."
|
|
echo " On first startup, keys are automatically generated and printed once."
|
|
echo " Database file: <relay_pubkey>.db (created automatically)"
|
|
echo ""
|
|
echo "Examples:"
|
|
echo " $0 # Fresh start with random keys"
|
|
echo " $0 -a <admin-hex> -r <relay-hex> # Use custom keys"
|
|
echo " $0 -a <admin-hex> -p 9000 # Custom admin key on port 9000"
|
|
echo " $0 -p 7777 --strict-port # Fail if port 7777 unavailable (no fallback)"
|
|
echo " $0 -p 8080 --strict-port -d=3 # Custom port with strict binding and debug"
|
|
echo " $0 --debug-level=3 # Start with debug level 3 (info)"
|
|
echo " $0 -d=5 # Start with debug level 5 (trace)"
|
|
echo " $0 --preserve-database # Preserve existing database and keys"
|
|
echo " $0 --test-keys # Use test keys for consistent development"
|
|
echo " $0 -t --preserve-database # Use test keys and preserve database"
|
|
echo ""
|
|
echo "Default PostgreSQL connection (when no DB flags provided):"
|
|
echo " host=localhost port=5432 dbname=crelay user=crelay password=crelay"
|
|
echo ""
|
|
echo "Key Format: Keys must be exactly 64 hexadecimal characters (0-9, a-f, A-F)"
|
|
echo "Default behavior: Deletes existing database files to start fresh with new keys"
|
|
echo " for development purposes"
|
|
exit 0
|
|
fi
|
|
|
|
# Handle database file cleanup for fresh start
|
|
if [ "$PRESERVE_DATABASE" = false ]; then
|
|
if ls *.db* >/dev/null 2>&1 || ls build/*.db* >/dev/null 2>&1; then
|
|
echo "Removing existing database files (including WAL/SHM) to trigger fresh key generation..."
|
|
rm -f *.db* build/*.db*
|
|
echo "✓ Database files removed - will generate new keys and database"
|
|
else
|
|
echo "No existing database found - will generate fresh setup"
|
|
fi
|
|
else
|
|
echo "Preserving existing database files (build process does not touch database files)"
|
|
fi
|
|
|
|
# Clean up legacy files that are no longer used
|
|
rm -rf dev-config/ 2>/dev/null
|
|
rm -f db/c_nostr_relay.db* 2>/dev/null
|
|
|
|
if [ "$DB_BACKEND" = "postgres" ] && [ -z "$DB_CONNSTRING" ]; then
|
|
ensure_postgres_database || exit 1
|
|
fi
|
|
|
|
# Embed web files into C headers before building
|
|
echo "Embedding web files..."
|
|
./embed_web_files.sh
|
|
|
|
# Build the project - ONLY static build
|
|
echo "Building project (static binary, backend: $DB_BACKEND)..."
|
|
./build_static.sh --db-backend "$DB_BACKEND"
|
|
|
|
# Exit if static build fails - no fallback
|
|
if [ $? -ne 0 ]; then
|
|
echo "ERROR: Static build failed. Cannot proceed without static binary."
|
|
echo "Please fix the build errors and try again."
|
|
exit 1
|
|
fi
|
|
|
|
# Check if build was successful
|
|
if [ $? -ne 0 ]; then
|
|
echo "ERROR: Build failed. Cannot restart relay."
|
|
exit 1
|
|
fi
|
|
|
|
# Check if static relay binary exists after build - ONLY use static binary
|
|
ARCH=$(uname -m)
|
|
case "$ARCH" in
|
|
x86_64)
|
|
BINARY_PATH="./build/c_relay_pg_static_x86_64"
|
|
;;
|
|
aarch64|arm64)
|
|
BINARY_PATH="./build/c_relay_pg_static_arm64"
|
|
;;
|
|
*)
|
|
BINARY_PATH="./build/c_relay_pg_static_$ARCH"
|
|
;;
|
|
esac
|
|
|
|
# Verify static binary exists - no fallbacks
|
|
if [ ! -f "$BINARY_PATH" ]; then
|
|
echo "ERROR: Static relay binary not found: $BINARY_PATH"
|
|
echo ""
|
|
echo "The relay requires the static binary with JSON1 support."
|
|
echo "Please run: ./build_static.sh"
|
|
echo ""
|
|
exit 1
|
|
fi
|
|
|
|
echo "Using static binary: $BINARY_PATH"
|
|
|
|
# Build the caching_relay binary (from caching/ directory)
|
|
# This is needed because the caching service launcher forks this binary.
|
|
if [ -d "caching" ] && [ -f "caching/Makefile" ]; then
|
|
echo "Building caching_relay binary..."
|
|
(cd caching && make) > /dev/null 2>&1
|
|
if [ $? -ne 0 ]; then
|
|
echo "WARNING: caching_relay build failed. The caching service will not be available."
|
|
echo "You can build it manually with: cd caching && make"
|
|
else
|
|
echo "✓ caching_relay binary built successfully"
|
|
fi
|
|
fi
|
|
|
|
echo "Build successful. Proceeding with relay restart..."
|
|
|
|
# Kill existing relay if running - start aggressive immediately
|
|
echo "Stopping any existing relay servers..."
|
|
|
|
# Get all relay processes and kill them immediately with -9
|
|
RELAY_PIDS=$(pgrep -f "c_relay_pg_" || echo "")
|
|
if [ -n "$RELAY_PIDS" ]; then
|
|
echo "Force killing relay processes immediately: $RELAY_PIDS"
|
|
kill -9 $RELAY_PIDS 2>/dev/null
|
|
else
|
|
echo "No existing relay processes found"
|
|
fi
|
|
|
|
# Kill any stale caching_relay processes from previous runs.
|
|
# The caching service is forked by the relay with setsid(), so it detaches
|
|
# from the relay's process group and survives when the relay is killed -9.
|
|
# Without this, every restart orphans the previous caching_relay child and
|
|
# a new relay forks another, leading to many stale processes with dead PG
|
|
# connections spamming errors. Kill them here so the new relay starts fresh.
|
|
CACHING_PIDS=$(pgrep -f "caching_relay" || echo "")
|
|
if [ -n "$CACHING_PIDS" ]; then
|
|
echo "Killing stale caching_relay processes: $CACHING_PIDS"
|
|
kill -9 $CACHING_PIDS 2>/dev/null || true
|
|
sleep 1
|
|
else
|
|
echo "No existing caching_relay processes found"
|
|
fi
|
|
|
|
# Ensure port 8888 is completely free with retry loop
|
|
echo "Ensuring port 8888 is available..."
|
|
for attempt in {1..15}; do
|
|
if ! lsof -i :8888 >/dev/null 2>&1; then
|
|
echo "Port 8888 is now free"
|
|
break
|
|
fi
|
|
|
|
echo "Attempt $attempt: Port 8888 still in use, force killing..."
|
|
# Kill anything using port 8888
|
|
fuser -k 8888/tcp 2>/dev/null || true
|
|
|
|
# Double-check for any remaining relay processes
|
|
REMAINING_PIDS=$(pgrep -f "c_relay_pg_" || echo "")
|
|
if [ -n "$REMAINING_PIDS" ]; then
|
|
echo "Killing remaining relay processes: $REMAINING_PIDS"
|
|
kill -9 $REMAINING_PIDS 2>/dev/null || true
|
|
fi
|
|
|
|
sleep 2
|
|
|
|
if [ $attempt -eq 15 ]; then
|
|
echo "ERROR: Could not free port 8888 after 15 attempts"
|
|
echo "Current processes using port:"
|
|
lsof -i :8888 2>/dev/null || echo "No process details available"
|
|
echo "You may need to manually kill processes or reboot"
|
|
exit 1
|
|
fi
|
|
done
|
|
|
|
# Final safety check - ensure no relay or caching processes remain
|
|
FINAL_PIDS=$(pgrep -f "c_relay_pg_" || echo "")
|
|
if [ -n "$FINAL_PIDS" ]; then
|
|
echo "Final cleanup: killing relay processes $FINAL_PIDS"
|
|
kill -9 $FINAL_PIDS 2>/dev/null || true
|
|
sleep 1
|
|
fi
|
|
|
|
FINAL_CACHING_PIDS=$(pgrep -f "caching_relay" || echo "")
|
|
if [ -n "$FINAL_CACHING_PIDS" ]; then
|
|
echo "Final cleanup: killing stale caching_relay processes $FINAL_CACHING_PIDS"
|
|
kill -9 $FINAL_CACHING_PIDS 2>/dev/null || true
|
|
sleep 1
|
|
fi
|
|
|
|
# Clean up PID file
|
|
rm -f relay.pid
|
|
|
|
# Database initialization is now handled automatically by the relay
|
|
# with event-based configuration system
|
|
echo "Database will be initialized automatically on startup if needed"
|
|
|
|
# Start relay in background with output redirection
|
|
echo "Starting relay server..."
|
|
echo "Debug: Current processes: $(ps aux | grep 'c_relay_pg_' | grep -v grep || echo 'None')"
|
|
|
|
# Build command line arguments for relay binary
|
|
RELAY_ARGS=""
|
|
|
|
if [ -n "$ADMIN_KEY" ]; then
|
|
RELAY_ARGS="$RELAY_ARGS -a $ADMIN_KEY"
|
|
echo "Using custom admin key: ${ADMIN_KEY:0:16}..."
|
|
fi
|
|
|
|
if [ -n "$RELAY_KEY" ]; then
|
|
RELAY_ARGS="$RELAY_ARGS -r $RELAY_KEY"
|
|
echo "Using custom relay key: ${RELAY_KEY:0:16}..."
|
|
fi
|
|
|
|
if [ -n "$PORT_OVERRIDE" ]; then
|
|
RELAY_ARGS="$RELAY_ARGS -p $PORT_OVERRIDE"
|
|
echo "Using custom port: $PORT_OVERRIDE"
|
|
fi
|
|
|
|
if [ -n "$DEBUG_LEVEL" ]; then
|
|
RELAY_ARGS="$RELAY_ARGS --debug-level=$DEBUG_LEVEL"
|
|
echo "Using debug level: $DEBUG_LEVEL"
|
|
fi
|
|
|
|
if [ -n "$DB_CONNSTRING" ]; then
|
|
RELAY_ARGS="$RELAY_ARGS --db-connstring '$DB_CONNSTRING'"
|
|
echo "Using PostgreSQL connection string override"
|
|
fi
|
|
|
|
if [ -n "$DB_HOST" ]; then
|
|
RELAY_ARGS="$RELAY_ARGS --db-host '$DB_HOST'"
|
|
fi
|
|
|
|
if [ -n "$DB_PORT" ]; then
|
|
RELAY_ARGS="$RELAY_ARGS --db-port '$DB_PORT'"
|
|
fi
|
|
|
|
if [ -n "$DB_NAME" ]; then
|
|
RELAY_ARGS="$RELAY_ARGS --db-name '$DB_NAME'"
|
|
fi
|
|
|
|
if [ -n "$DB_USER" ]; then
|
|
RELAY_ARGS="$RELAY_ARGS --db-user '$DB_USER'"
|
|
fi
|
|
|
|
if [ -n "$DB_PASSWORD" ]; then
|
|
RELAY_ARGS="$RELAY_ARGS --db-password '$DB_PASSWORD'"
|
|
fi
|
|
|
|
if [ "$START_CACHING" = true ]; then
|
|
RELAY_ARGS="$RELAY_ARGS --start-caching"
|
|
echo "Auto-starting caching service on startup"
|
|
fi
|
|
|
|
if [ "$RESET_BACKFILL" = true ]; then
|
|
RELAY_ARGS="$RELAY_ARGS --reset-backfill"
|
|
echo "Resetting caching backfill progress before start"
|
|
fi
|
|
|
|
# Change to build directory before starting relay so database files are created there
|
|
cd build
|
|
# Start relay in background and capture its PID
|
|
if [ "$USE_TEST_KEYS" = true ]; then
|
|
echo "Using test keys from .test_keys file..."
|
|
# shellcheck disable=SC2086
|
|
eval ./$(basename $BINARY_PATH) -a "$ADMIN_KEY" -r "$RELAY_KEY" $RELAY_ARGS --strict-port > ../relay.log 2>&1 &
|
|
elif [ -n "$RELAY_ARGS" ]; then
|
|
echo "Starting relay with custom configuration..."
|
|
# shellcheck disable=SC2086
|
|
eval ./$(basename $BINARY_PATH) $RELAY_ARGS --strict-port > ../relay.log 2>&1 &
|
|
else
|
|
# No command line arguments needed for random key generation
|
|
echo "Starting relay with random key generation..."
|
|
./$(basename $BINARY_PATH) --debug-level=$DEBUG_LEVEL --strict-port > ../relay.log 2>&1 &
|
|
fi
|
|
RELAY_PID=$!
|
|
# Change back to original directory
|
|
cd ..
|
|
|
|
echo "Started with PID: $RELAY_PID"
|
|
|
|
# Check if server is still running after short delay
|
|
sleep 3
|
|
|
|
# Check if process is still alive
|
|
if ps -p "$RELAY_PID" >/dev/null 2>&1; then
|
|
echo "Relay started successfully!"
|
|
echo "PID: $RELAY_PID"
|
|
|
|
# Wait for relay to fully initialize and detect the actual port it's using
|
|
sleep 2
|
|
|
|
# Extract actual port from relay logs
|
|
ACTUAL_PORT=""
|
|
if [ -f relay.log ]; then
|
|
# Look for the success message with actual port
|
|
ACTUAL_PORT=$(grep "WebSocket relay started on ws://127.0.0.1:" relay.log 2>/dev/null | tail -1 | sed -n 's/.*ws:\/\/127\.0\.0\.1:\([0-9]*\).*/\1/p')
|
|
|
|
# If we couldn't find the port in logs, try to detect from netstat
|
|
if [ -z "$ACTUAL_PORT" ]; then
|
|
ACTUAL_PORT=$(netstat -tln 2>/dev/null | grep -E ":888[0-9]" | head -1 | sed -n 's/.*:\([0-9]*\).*/\1/p')
|
|
fi
|
|
fi
|
|
|
|
# Display the actual endpoint
|
|
if [ -n "$ACTUAL_PORT" ]; then
|
|
if [ "$ACTUAL_PORT" = "8888" ]; then
|
|
echo "WebSocket endpoint: ws://127.0.0.1:$ACTUAL_PORT"
|
|
else
|
|
echo "WebSocket endpoint: ws://127.0.0.1:$ACTUAL_PORT (fell back from port 8888)"
|
|
fi
|
|
else
|
|
echo "WebSocket endpoint: ws://127.0.0.1:8888 (port detection failed - check logs)"
|
|
fi
|
|
|
|
echo "HTTP endpoint: http://127.0.0.1:${ACTUAL_PORT:-8888}"
|
|
echo "Log file: relay.log"
|
|
echo ""
|
|
|
|
# Save PID for debugging
|
|
echo $RELAY_PID > relay.pid
|
|
|
|
# Check if new keys were generated and display them
|
|
sleep 1 # Give relay time to write initial logs
|
|
if grep -q "IMPORTANT: SAVE THIS ADMIN PRIVATE KEY SECURELY!" relay.log 2>/dev/null; then
|
|
echo "=== IMPORTANT: NEW ADMIN PRIVATE KEY GENERATED ==="
|
|
echo ""
|
|
# Extract and display the admin private key section from the log
|
|
grep -A 15 -B 2 "IMPORTANT: SAVE THIS ADMIN PRIVATE KEY SECURELY!" relay.log | head -n 20
|
|
echo ""
|
|
echo "⚠️ SAVE THIS ADMIN PRIVATE KEY SECURELY - IT CONTROLS YOUR RELAY CONFIGURATION!"
|
|
echo "⚠️ This key is needed to update configuration and is only displayed once"
|
|
echo "⚠️ The relay and database information is also logged in relay.log for reference"
|
|
echo ""
|
|
fi
|
|
|
|
echo "=== Event-Based Relay Server Running ==="
|
|
echo "Configuration: Event-based (kind 33334 Nostr events)"
|
|
echo "Database: Automatically created with relay pubkey naming"
|
|
echo "To kill relay: pkill -f 'c_relay_pg_'"
|
|
echo "To kill caching service: pkill -f 'caching_relay'"
|
|
echo "To check status: ps aux | grep c_relay_pg_"
|
|
echo "To view logs: tail -f relay.log"
|
|
echo "To view caching logs: tail -f build/caching_relay.log"
|
|
echo "Binary: $BINARY_PATH (zero configuration needed)"
|
|
echo "Ready for Nostr client connections!"
|
|
else
|
|
echo "ERROR: Relay failed to start"
|
|
echo "Debug: Check relay.log for error details:"
|
|
echo "--- Last 10 lines of relay.log ---"
|
|
tail -n 10 relay.log 2>/dev/null || echo "No log file found"
|
|
echo "--- End log ---"
|
|
exit 1
|
|
fi
|
|
|
|
echo "" |