diff options
| author | Elizabeth Hunt <me@liz.coffee> | 2025-12-14 20:36:24 -0800 |
|---|---|---|
| committer | Elizabeth Hunt <me@liz.coffee> | 2025-12-14 20:36:24 -0800 |
| commit | 6bf57766feb8321f860baf300140563cd9539053 (patch) | |
| tree | d80ff78c2a7f4dbea79f9ee850542aee1b735ef4 /src/index.ts | |
| download | posthook-6bf57766feb8321f860baf300140563cd9539053.tar.gz posthook-6bf57766feb8321f860baf300140563cd9539053.zip | |
Init
Diffstat (limited to 'src/index.ts')
| -rw-r--r-- | src/index.ts | 64 |
1 files changed, 64 insertions, 0 deletions
diff --git a/src/index.ts b/src/index.ts new file mode 100644 index 0000000..cbc946a --- /dev/null +++ b/src/index.ts @@ -0,0 +1,64 @@ +#!/usr/bin/env node + +import { argv, Either, getEnv, type IEither, HonoProxy } from '@emprespresso/pengueno'; +import { PosthookServer } from './server/index.js'; +import { Storage } from './storage/index.js'; +import { TokenSigner } from './token/index.js'; + +const main = async (_argv = process.argv.slice(2)): Promise<IEither<Error, void>> => { + const argsResult = argv( + ['--port', '--host', '--data-dir', '--token-secret'], + { + '--port': { absent: 9000, present: (port) => parseInt(port) }, + '--host': { absent: '0.0.0.0', present: (host) => host }, + '--data-dir': { absent: './data', present: (dir) => dir }, + '--token-secret': { absent: undefined, present: (secret) => secret }, + }, + _argv, + ); + + return argsResult + .mapRight((args) => ({ + port: args['--port'], + host: args['--host'], + dataDir: args['--data-dir'], + tokenSecret: args['--token-secret'], + })) + .flatMapAsync(async (config) => { + // Initialize storage + const storage = new Storage(config.dataDir); + const initResult = await storage.init(); + + if (initResult.left().present()) { + return Either.left(initResult.left().get()); + } + + // Initialize token signer (use env var or command line arg or generate random) + const envSecret = getEnv('POSTHOOK_TOKEN_SECRET'); + const secret = config.tokenSecret ?? (envSecret.present() ? envSecret.get() : undefined); + const signer = new TokenSigner(secret); + + if (config.tokenSecret === undefined && !envSecret.present()) { + console.log('No token secret provided; generated a random one (will not persist across restarts).'); + console.log('Set POSTHOOK_TOKEN_SECRET or pass --token-secret to use a persistent secret.'); + } + + console.log(`Storage initialized at: ${config.dataDir}`); + console.log(`Starting server on ${config.host}:${config.port}`); + + // Create and start server + const server = new PosthookServer(storage, signer); + const hono = new HonoProxy(server); + + return hono.serve(config.port, config.host); + }); +}; + +if (process.argv[1] === import.meta.filename) { + await main().then((eitherDone) => + eitherDone.mapLeft((err) => { + console.error('error:', err); + process.exit(1); + }), + ); +} |
