corpus

Log | Files | Refs | README | LICENSE

commit 95053ec72011d16c922192e687ae5445e80260a1
parent c004ec32133da069ac9da7ab78da7bf88ea2b2e7
Author: mtmn <miro@haravara.org>
Date:   Sat, 18 Apr 2026 03:46:50 +0200

chore: add access logs

Diffstat:
Msrc/Main.purs | 3+--
Msrc/Metrics.js | 22+++++++++++++---------
Msrc/Metrics.purs | 5+++--
3 files changed, 17 insertions(+), 13 deletions(-)

diff --git a/src/Main.purs b/src/Main.purs @@ -803,8 +803,7 @@ handleRequest contexts req res = do Nothing -> serveNotFound res Just url -> do let path = URL.pathname url - Log.info $ method <> " " <> rawUrl - Metrics.observeHttpRequest method (normalizePath path) res + Metrics.observeHttpRequest method (normalizePath path) Log.info res case path of "/client.js" -> serveClientJs res "/favicon.png" -> serveAsset "image/png" "assets/favicon.png" res diff --git a/src/Metrics.js b/src/Metrics.js @@ -92,15 +92,19 @@ export const getContentType = () => registry.contentType; // Attaches a 'finish' listener to the response to record latency and status // after the response is fully written. Safe to call before routing. -export const observeHttpRequest = (method) => (path) => (res) => () => { - const startMs = Date.now(); - res.once("finish", () => { - const durationSecs = (Date.now() - startMs) / 1000; - const status = String(res.statusCode || 0); - httpRequestsTotal.inc({ method, path, status }); - httpRequestDurationSeconds.observe({ method, path }, durationSecs); - }); -}; +// logFn: (String -> Effect Unit) — the structured logger to call on completion. +export const observeHttpRequest = + (method) => (path) => (logFn) => (res) => () => { + const startMs = Date.now(); + res.once("finish", () => { + const durationMs = Date.now() - startMs; + const durationSecs = durationMs / 1000; + const status = String(res.statusCode || 0); + httpRequestsTotal.inc({ method, path, status }); + httpRequestDurationSeconds.observe({ method, path }, durationSecs); + logFn(`${method} ${path} ${status} ${durationMs}ms`)(); + }); + }; export const incSyncRuns = (user) => (source) => (result) => () => syncRunsTotal.inc({ user, source, result }); diff --git a/src/Metrics.purs b/src/Metrics.purs @@ -15,9 +15,10 @@ foreign import getMetricsImpl :: (String -> Effect Unit) -> (String -> Effect Un foreign import getContentType :: Effect String -- | Attaches a 'finish' listener to `res` so that, once the response is --- | fully written, the request count and latency histogram are updated. +-- | fully written, the request count and latency histogram are updated, +-- | and the provided log function is called with "METHOD path status Nms". -- | Call once at the top of the request handler before routing. -foreign import observeHttpRequest :: String -> String -> ServerResponse -> Effect Unit +foreign import observeHttpRequest :: String -> String -> (String -> Effect Unit) -> ServerResponse -> Effect Unit -- Sync foreign import incSyncRuns :: String -> String -> String -> Effect Unit