/** * ───────────────────────────────────────────── * SPB Git — Personal Git Platform * ───────────────────────────────────────────── * Author : Simon-Pierre Boucher * Contact : contact@spboucher.ai * File : deploy/ecosystem.config.cjs * Purpose : pm2 process definitions — server + ngrok tunnel * License : MIT © Simon-Pierre Boucher * ───────────────────────────────────────────── * * Usage on m3u96a: * pm2 start deploy/ecosystem.config.cjs * pm2 save && pm2 startup # survive reboots */ const path = require('node:path'); const APP_DIR = path.resolve(__dirname, '..'); const LOG_DIR = process.env.SPBGIT_LOG_DIR || path.join(process.env.HOME || '/tmp', 'srv/spbgit/logs'); module.exports = { apps: [ { name: 'spbgit-server', cwd: APP_DIR, script: 'src/server.mjs', interpreter: 'node', autorestart: true, max_restarts: 25, restart_delay: 2000, max_memory_restart: '750M', out_file: path.join(LOG_DIR, 'server-out.log'), error_file: path.join(LOG_DIR, 'server-err.log'), merge_logs: true, time: true, env: { NODE_ENV: 'production', }, }, { name: 'spbgit-tunnel', cwd: APP_DIR, script: 'ngrok', // SPBGIT_NGROK_CONFIG lets the host point at a resolved config that // carries the real authtoken (deploy/ngrok.yml is the tracked template). args: `start --config ${process.env.SPBGIT_NGROK_CONFIG || 'deploy/ngrok.yml'} spbgit`, interpreter: 'none', autorestart: true, // Exponential backoff (caps at 15 min) so the tunnel self-heals once // the domain reservation / network issue is fixed — without log spam. max_restarts: 1000, exp_backoff_restart_delay: 10000, out_file: path.join(LOG_DIR, 'tunnel-out.log'), error_file: path.join(LOG_DIR, 'tunnel-err.log'), merge_logs: true, time: true, }, ], };