// The three helpers the town-crier leg needs from core's announce pipeline. // // Core owns `announce_jobs`, the worker that drains it and the retry policy; // this module owns one leg of it (MODULE_API.md §2.4). These three lived in // core's `announceJobs.logic` and are reproduced here rather than added to // `ctx`, because each is a few lines of pure string handling with no state and // no policy — the kind of thing a contract member would only make harder to // change on both sides. // // The one that could NOT be vendored is `baseUrl`. Core's version reads // `process.env.APP_BASE_URL`, and §2.7 forbids a module reading core's // environment — it is core's deployment fact, not the module's. So it comes off // `ctx.site.baseUrl` (API 1.1.0), read per call rather than captured, which also // means a module built before an env change keeps agreeing with core after it. // NOT destructured. `core.baseUrl` is a getter that resolves `ctx`, so pulling // it out here would run at require time — before `register()` — and throw. Read // it inside the function, where `ctx` exists. const core = require('../core') /** Where this deployment is reachable, without a trailing slash. */ function baseUrl() { return core.baseUrl } /** * The public link that goes in an announcement. * * News has no per-post route — core's SPA has only the list — so this links the * list, matching what the pre-pipeline Discord announce did. It names a CORE * route on purpose: the news list is core's page and stays core's through the * whole extraction, so this is a module linking to its host, not a leftover. */ function articleUrl(base) { return `${String(base || '').replace(/\/+$/, '')}/site/news` } /** * Squeeze a leg client's `{ ok, status, data, error }` into the one line stored * in `announce_job_legs.last_error` and shown in the admin panel. */ function legError(result) { if (!result) return 'no response' if (result.status) { return result.data && result.data.message ? `${result.status}: ${result.data.message}` : result.error || `status ${result.status}` } return result.error || 'request failed' } module.exports = { baseUrl, articleUrl, legError }