#!/usr/bin/env node
// Wirecore Bridge CLI
import { WirecoreBridge } from './wirecore-bridge.js'
import process from 'bare-process'
import os from 'bare-os'
import path from 'bare-path'
import goodbye from 'graceful-goodbye'
function getStorageDir () {
const p = os.platform()
const name = 'wirecore'
if (p === 'darwin') return path.join(os.homedir(), 'Library', 'Application Support', name)
if (p === 'win32') return path.join(os.homedir(), 'AppData', 'Roaming', name)
return path.join(os.homedir(), '.config', name)
}
const storagePath = process.env.PEAR_STORAGE || getStorageDir()
const relayUrl = process.env.RELAY_URL || 'https://7rnx.net/relay'
// Parse command line args
const args = process.argv.slice(2)
const command = args[0] || 'help'
// Show usage
function showUsage() {
console.log('🌉 Wirecore Bridge - Relay Integration\n')
console.log('Usage:')
console.log(' pear run . bridge start Start daemon (watch + periodic pull)')
console.log(' pear run . bridge push Push all local posts to relay')
console.log(' pear run . bridge pull Pull posts from relay')
console.log(' pear run . bridge watch Watch for new posts and auto-push')
console.log(' pear run . bridge sync One-time sync (push + pull)')
console.log(' pear run . bridge status Show bridge status\n')
console.log('Environment Variables:')
console.log(' RELAY_URL Relay server URL (default: https://7rnx.net/relay)')
console.log(' PEAR_STORAGE Storage path (default: auto-detect from Pear)\n')
console.log('Examples:')
console.log(' # Start bridge daemon')
console.log(' pear run . bridge start')
console.log('')
console.log(' # One-time push of all posts')
console.log(' pear run . bridge push')
console.log('')
console.log(' # Check status')
console.log(' pear run . bridge status')
console.log('')
console.log(' # Use different relay')
console.log(' RELAY_URL=https://pub.wiredove.net pear run . bridge start')
}
async function main() {
// Show help
if (command === 'help' || command === '--help' || command === '-h') {
showUsage()
process.exit(0)
}
console.log('[bridge] Storage:', storagePath)
console.log('[bridge] Relay:', relayUrl)
// Initialize bridge (CLI runs standalone, so no existing store)
const bridge = new WirecoreBridge(relayUrl, null, storagePath)
try {
await bridge.init()
} catch (err) {
console.error('❌ Failed to initialize bridge:', err.message)
console.error('\nMake sure you have initialized wirecore first:')
console.error(' pear run . cli init')
process.exit(1)
}
// Set up cleanup on exit
goodbye(async () => {
console.log('\n👋 Shutting down bridge...')
await bridge.close()
})
// Execute command
try {
switch (command) {
case 'start':
// Parse pull interval from args (--interval 300)
let pullInterval = 5 * 60 * 1000 // 5 minutes default
const intervalIndex = args.indexOf('--interval')
if (intervalIndex !== -1 && args[intervalIndex + 1]) {
pullInterval = parseInt(args[intervalIndex + 1]) * 1000
}
await bridge.start(pullInterval)
break
case 'push':
await bridge.push()
process.exit(0)
break
case 'pull':
await bridge.pull()
process.exit(0)
break
case 'watch':
await bridge.watch()
break
case 'sync':
await bridge.sync()
process.exit(0)
break
case 'status':
await bridge.status()
process.exit(0)
break
default:
console.error(`❌ Unknown command: ${command}\n`)
showUsage()
process.exit(1)
}
} catch (err) {
console.error('❌ Error:', err.message)
if (process.env.DEBUG) {
console.error(err.stack)
}
process.exit(1)
}
}
main().catch(err => {
console.error('Fatal error:', err.message)
if (process.env.DEBUG) {
console.error(err.stack)
}
process.exit(1)
})