[{"data":1,"prerenderedAt":3083},["ShallowReactive",2],{"navigation_docs":3,"-extend-custom-framework":534,"-extend-custom-framework-surround":3078},[4,30,80,128,308,440,499],{"title":5,"path":6,"stem":7,"children":8,"page":29},"Start","\u002Fstart","1.start",[9,14,19,24],{"title":10,"path":11,"stem":12,"icon":13},"Introduction","\u002Fstart\u002Fintroduction","1.start\u002F1.introduction","i-lucide-info",{"title":15,"path":16,"stem":17,"icon":18},"Why start with evlog","\u002Fstart\u002Fwhy-evlog","1.start\u002F2.why-evlog","i-lucide-rocket",{"title":20,"path":21,"stem":22,"icon":23},"Installation","\u002Fstart\u002Finstallation","1.start\u002F3.installation","i-lucide-download",{"title":25,"path":26,"stem":27,"icon":28},"Quick Start","\u002Fstart\u002Fquick-start","1.start\u002F4.quick-start","i-lucide-zap",false,{"title":31,"path":32,"stem":33,"children":34,"page":29},"Learn","\u002Flearn","2.learn",[35,40,45,50,55,60,65,70,75],{"title":36,"path":37,"stem":38,"icon":39},"Overview","\u002Flearn\u002Foverview","2.learn\u002F0.overview","i-lucide-list",{"title":41,"path":42,"stem":43,"icon":44},"Simple Logging","\u002Flearn\u002Fsimple-logging","2.learn\u002F1.simple-logging","i-lucide-terminal",{"title":46,"path":47,"stem":48,"icon":49},"Wide Events","\u002Flearn\u002Fwide-events","2.learn\u002F2.wide-events","i-lucide-layers",{"title":51,"path":52,"stem":53,"icon":54},"Structured Errors","\u002Flearn\u002Fstructured-errors","2.learn\u002F3.structured-errors","i-lucide-shield-alert",{"title":56,"path":57,"stem":58,"icon":59},"Lifecycle","\u002Flearn\u002Flifecycle","2.learn\u002F4.lifecycle","i-lucide-arrow-right-left",{"title":61,"path":62,"stem":63,"icon":64},"Sampling","\u002Flearn\u002Fsampling","2.learn\u002F5.sampling","i-lucide-filter",{"title":66,"path":67,"stem":68,"icon":69},"Auto-Redaction","\u002Flearn\u002Fredaction","2.learn\u002F6.redaction","i-lucide-eye-off",{"title":71,"path":72,"stem":73,"icon":74},"Typed Fields","\u002Flearn\u002Ftyped-fields","2.learn\u002F7.typed-fields","i-simple-icons-typescript",{"title":76,"path":77,"stem":78,"icon":79},"Catalogs","\u002Flearn\u002Fcatalogs","2.learn\u002F8.catalogs","i-lucide-book-open",{"title":81,"path":82,"stem":83,"children":84,"page":29},"CLI","\u002Fcli","3.cli",[85,88,93,98,103,108,113,118,123],{"title":36,"path":86,"stem":87,"icon":44},"\u002Fcli\u002Foverview","3.cli\u002F0.overview",{"title":89,"path":90,"stem":91,"icon":92},"init","\u002Fcli\u002Finit","3.cli\u002F1.init","i-lucide-wand-sparkles",{"title":94,"path":95,"stem":96,"icon":97},"map","\u002Fcli\u002Fmap","3.cli\u002F2.map","i-lucide-radar",{"title":99,"path":100,"stem":101,"icon":102},"Rules","\u002Fcli\u002Frules","3.cli\u002F3.rules","i-lucide-list-checks",{"title":104,"path":105,"stem":106,"icon":107},"Scoring","\u002Fcli\u002Fscoring","3.cli\u002F4.scoring","i-lucide-gauge",{"title":109,"path":110,"stem":111,"icon":112},"CI","\u002Fcli\u002Fci","3.cli\u002F5.ci","i-lucide-git-pull-request",{"title":114,"path":115,"stem":116,"icon":117},"doctor","\u002Fcli\u002Fdoctor","3.cli\u002F6.doctor","i-lucide-stethoscope",{"title":119,"path":120,"stem":121,"icon":122},"telemetry","\u002Fcli\u002Ftelemetry","3.cli\u002F7.telemetry","i-lucide-bar-chart-3",{"title":124,"path":125,"stem":126,"icon":127},"agents","\u002Fcli\u002Fagents","3.cli\u002F8.agents","i-lucide-bot",{"title":129,"path":130,"stem":131,"children":132,"page":29},"Integrate","\u002Fintegrate","4.integrate",[133,137,220],{"title":36,"path":134,"stem":135,"icon":136},"\u002Fintegrate\u002Foverview","4.integrate\u002F0.overview","i-lucide-plug",{"title":138,"path":139,"stem":140,"children":141,"page":29},"Adapters","\u002Fintegrate\u002Fadapters","4.integrate\u002Fadapters",[142,145,175,200],{"title":36,"path":143,"stem":144,"icon":39},"\u002Fintegrate\u002Fadapters\u002Foverview","4.integrate\u002Fadapters\u002F01.overview",{"title":146,"path":147,"stem":148,"children":149,"page":29},"Cloud","\u002Fintegrate\u002Fadapters\u002Fcloud","4.integrate\u002Fadapters\u002Fcloud",[150,155,160,165,170],{"title":151,"path":152,"stem":153,"icon":154},"Axiom","\u002Fintegrate\u002Fadapters\u002Fcloud\u002Faxiom","4.integrate\u002Fadapters\u002Fcloud\u002F01.axiom","i-custom-axiom",{"title":156,"path":157,"stem":158,"icon":159},"PostHog","\u002Fintegrate\u002Fadapters\u002Fcloud\u002Fposthog","4.integrate\u002Fadapters\u002Fcloud\u002F02.posthog","i-simple-icons-posthog",{"title":161,"path":162,"stem":163,"icon":164},"Sentry","\u002Fintegrate\u002Fadapters\u002Fcloud\u002Fsentry","4.integrate\u002Fadapters\u002Fcloud\u002F03.sentry","i-simple-icons-sentry",{"title":166,"path":167,"stem":168,"icon":169},"Better Stack","\u002Fintegrate\u002Fadapters\u002Fcloud\u002Fbetter-stack","4.integrate\u002Fadapters\u002Fcloud\u002F04.better-stack","i-simple-icons-betterstack",{"title":171,"path":172,"stem":173,"icon":174},"Datadog","\u002Fintegrate\u002Fadapters\u002Fcloud\u002Fdatadog","4.integrate\u002Fadapters\u002Fcloud\u002F05.datadog","i-simple-icons-datadog",{"title":176,"path":177,"stem":178,"children":179,"page":29},"Cloud or Self-Hosted","\u002Fintegrate\u002Fadapters\u002Fhybrid","4.integrate\u002Fadapters\u002Fhybrid",[180,185,190,195],{"title":181,"path":182,"stem":183,"icon":184},"Grafana Loki","\u002Fintegrate\u002Fadapters\u002Fhybrid\u002Floki","4.integrate\u002Fadapters\u002Fhybrid\u002F01.loki","i-simple-icons-grafana",{"title":186,"path":187,"stem":188,"icon":189},"ClickHouse","\u002Fintegrate\u002Fadapters\u002Fhybrid\u002Fclickhouse","4.integrate\u002Fadapters\u002Fhybrid\u002F02.clickhouse","i-simple-icons-clickhouse",{"title":191,"path":192,"stem":193,"icon":194},"OTLP","\u002Fintegrate\u002Fadapters\u002Fhybrid\u002Fotlp","4.integrate\u002Fadapters\u002Fhybrid\u002F03.otlp","i-simple-icons-opentelemetry",{"title":196,"path":197,"stem":198,"icon":199},"HyperDX","\u002Fintegrate\u002Fadapters\u002Fhybrid\u002Fhyperdx","4.integrate\u002Fadapters\u002Fhybrid\u002F04.hyperdx","i-custom-hyperdx",{"title":201,"path":202,"stem":203,"children":204,"page":29},"Self-Hosted","\u002Fintegrate\u002Fadapters\u002Fself-hosted","4.integrate\u002Fadapters\u002Fself-hosted",[205,210,215],{"title":206,"path":207,"stem":208,"icon":209},"File System","\u002Fintegrate\u002Fadapters\u002Fself-hosted\u002Ffs","4.integrate\u002Fadapters\u002Fself-hosted\u002F01.fs","i-lucide-hard-drive",{"title":211,"path":212,"stem":213,"icon":214},"NuxtHub","\u002Fintegrate\u002Fadapters\u002Fself-hosted\u002Fnuxthub","4.integrate\u002Fadapters\u002Fself-hosted\u002F02.nuxthub","i-simple-icons-nuxt",{"title":216,"path":217,"stem":218,"icon":219},"Memory","\u002Fintegrate\u002Fadapters\u002Fself-hosted\u002Fmemory","4.integrate\u002Fadapters\u002Fself-hosted\u002F03.memory","i-lucide-cpu",{"title":221,"path":222,"stem":223,"children":224,"page":29},"Frameworks","\u002Fintegrate\u002Fframeworks","4.integrate\u002Fframeworks",[225,229,234,239,244,249,254,259,264,269,274,279,284,289,293,298,303],{"title":36,"path":226,"stem":227,"icon":228},"\u002Fintegrate\u002Fframeworks\u002Foverview","4.integrate\u002Fframeworks\u002F00.overview","i-lucide-layout-grid",{"title":230,"path":231,"stem":232,"icon":233},"Nuxt","\u002Fintegrate\u002Fframeworks\u002Fnuxt","4.integrate\u002Fframeworks\u002F01.nuxt","i-simple-icons-nuxtdotjs",{"title":235,"path":236,"stem":237,"icon":238},"Next.js","\u002Fintegrate\u002Fframeworks\u002Fnextjs","4.integrate\u002Fframeworks\u002F02.nextjs","i-simple-icons-nextdotjs",{"title":240,"path":241,"stem":242,"icon":243},"SvelteKit","\u002Fintegrate\u002Fframeworks\u002Fsveltekit","4.integrate\u002Fframeworks\u002F03.sveltekit","i-simple-icons-svelte",{"title":245,"path":246,"stem":247,"icon":248},"Nitro","\u002Fintegrate\u002Fframeworks\u002Fnitro","4.integrate\u002Fframeworks\u002F04.nitro","i-custom-nitro",{"title":250,"path":251,"stem":252,"icon":253},"TanStack Start","\u002Fintegrate\u002Fframeworks\u002Ftanstack-start","4.integrate\u002Fframeworks\u002F05.tanstack-start","i-custom-tanstack",{"title":255,"path":256,"stem":257,"icon":258},"NestJS","\u002Fintegrate\u002Fframeworks\u002Fnestjs","4.integrate\u002Fframeworks\u002F06.nestjs","i-simple-icons-nestjs",{"title":260,"path":261,"stem":262,"icon":263},"Express","\u002Fintegrate\u002Fframeworks\u002Fexpress","4.integrate\u002Fframeworks\u002F07.express","i-simple-icons-express",{"title":265,"path":266,"stem":267,"icon":268},"Hono","\u002Fintegrate\u002Fframeworks\u002Fhono","4.integrate\u002Fframeworks\u002F08.hono","i-simple-icons-hono",{"title":270,"path":271,"stem":272,"icon":273},"Fastify","\u002Fintegrate\u002Fframeworks\u002Ffastify","4.integrate\u002Fframeworks\u002F09.fastify","i-simple-icons-fastify",{"title":275,"path":276,"stem":277,"icon":278},"Elysia","\u002Fintegrate\u002Fframeworks\u002Felysia","4.integrate\u002Fframeworks\u002F10.elysia","i-custom-elysia",{"title":280,"path":281,"stem":282,"icon":283},"React Router","\u002Fintegrate\u002Fframeworks\u002Freact-router","4.integrate\u002Fframeworks\u002F11.react-router","i-custom-reactrouter",{"title":285,"path":286,"stem":287,"icon":288},"Cloudflare Workers","\u002Fintegrate\u002Fframeworks\u002Fcloudflare-workers","4.integrate\u002Fframeworks\u002F12.cloudflare-workers","i-simple-icons-cloudflare",{"title":290,"path":291,"stem":292,"icon":74},"Standalone","\u002Fintegrate\u002Fframeworks\u002Fstandalone","4.integrate\u002Fframeworks\u002F13.standalone",{"title":294,"path":295,"stem":296,"icon":297},"Astro","\u002Fintegrate\u002Fframeworks\u002Fastro","4.integrate\u002Fframeworks\u002F14.astro","i-simple-icons-astro",{"title":299,"path":300,"stem":301,"icon":302},"oRPC","\u002Fintegrate\u002Fframeworks\u002Forpc","4.integrate\u002Fframeworks\u002F15.orpc","i-lucide-network",{"title":304,"path":305,"stem":306,"icon":307},"AWS Lambda","\u002Fintegrate\u002Fframeworks\u002Faws-lambda","4.integrate\u002Fframeworks\u002F16.aws-lambda","i-custom-lambda",{"title":309,"path":310,"stem":311,"children":312,"page":29},"Use Cases","\u002Fuse-cases","5.use-cases",[313,316,321,350,377,409,430,435],{"title":36,"path":314,"stem":315,"icon":102},"\u002Fuse-cases\u002Foverview","5.use-cases\u002F0.overview",{"title":317,"path":318,"stem":319,"icon":320},"Client Logging","\u002Fuse-cases\u002Fclient-logging","5.use-cases\u002F1.client-logging","i-lucide-monitor",{"title":322,"icon":323,"path":324,"stem":325,"children":326,"page":29},"AI SDK","i-simple-icons-vercel","\u002Fuse-cases\u002Fai-sdk","5.use-cases\u002F2.ai-sdk",[327,330,335,340,345],{"title":36,"path":328,"stem":329,"icon":39},"\u002Fuse-cases\u002Fai-sdk\u002Foverview","5.use-cases\u002F2.ai-sdk\u002F01.overview",{"title":331,"path":332,"stem":333,"icon":334},"Usage","\u002Fuse-cases\u002Fai-sdk\u002Fusage","5.use-cases\u002F2.ai-sdk\u002F02.usage","i-lucide-code",{"title":336,"path":337,"stem":338,"icon":339},"Options","\u002Fuse-cases\u002Fai-sdk\u002Foptions","5.use-cases\u002F2.ai-sdk\u002F03.options","i-lucide-sliders",{"title":341,"path":342,"stem":343,"icon":344},"Metadata","\u002Fuse-cases\u002Fai-sdk\u002Fmetadata","5.use-cases\u002F2.ai-sdk\u002F04.metadata","i-lucide-database",{"title":346,"path":347,"stem":348,"icon":349},"Telemetry","\u002Fuse-cases\u002Fai-sdk\u002Ftelemetry","5.use-cases\u002F2.ai-sdk\u002F05.telemetry","i-lucide-activity",{"title":351,"icon":352,"path":353,"stem":354,"children":355,"page":29},"Better Auth","i-simple-icons-betterauth","\u002Fuse-cases\u002Fbetter-auth","5.use-cases\u002F3.better-auth",[356,359,364,369,373],{"title":36,"path":357,"stem":358,"icon":39},"\u002Fuse-cases\u002Fbetter-auth\u002Foverview","5.use-cases\u002F3.better-auth\u002F01.overview",{"title":360,"path":361,"stem":362,"icon":363},"Identify User","\u002Fuse-cases\u002Fbetter-auth\u002Fidentify-user","5.use-cases\u002F3.better-auth\u002F02.identify-user","i-lucide-user-check",{"title":365,"path":366,"stem":367,"icon":368},"Middleware","\u002Fuse-cases\u002Fbetter-auth\u002Fmiddleware","5.use-cases\u002F3.better-auth\u002F03.middleware","i-lucide-shield",{"title":370,"path":371,"stem":372,"icon":320},"Client Sync","\u002Fuse-cases\u002Fbetter-auth\u002Fclient-sync","5.use-cases\u002F3.better-auth\u002F04.client-sync",{"title":374,"path":375,"stem":376,"icon":107},"Performance","\u002Fuse-cases\u002Fbetter-auth\u002Fperformance","5.use-cases\u002F3.better-auth\u002F05.performance",{"title":378,"icon":379,"path":380,"stem":381,"children":382,"page":29},"Audit Logs","i-lucide-shield-check","\u002Fuse-cases\u002Faudit","5.use-cases\u002F4.audit",[383,386,391,396,401,405],{"title":36,"path":384,"stem":385,"icon":39},"\u002Fuse-cases\u002Faudit\u002Foverview","5.use-cases\u002F4.audit\u002F01.overview",{"title":387,"path":388,"stem":389,"icon":390},"Schema","\u002Fuse-cases\u002Faudit\u002Fschema","5.use-cases\u002F4.audit\u002F02.schema","i-lucide-file-text",{"title":392,"path":393,"stem":394,"icon":395},"Recording","\u002Fuse-cases\u002Faudit\u002Frecording","5.use-cases\u002F4.audit\u002F03.recording","i-lucide-pen-line",{"title":397,"path":398,"stem":399,"icon":400},"Drains","\u002Fuse-cases\u002Faudit\u002Fpipeline","5.use-cases\u002F4.audit\u002F04.pipeline","i-lucide-link",{"title":402,"path":403,"stem":404,"icon":379},"Compliance","\u002Fuse-cases\u002Faudit\u002Fcompliance","5.use-cases\u002F4.audit\u002F05.compliance",{"title":406,"path":407,"stem":408,"icon":79},"Recipes","\u002Fuse-cases\u002Faudit\u002Frecipes","5.use-cases\u002F4.audit\u002F06.recipes",{"title":346,"icon":107,"path":410,"stem":411,"children":412,"page":29},"\u002Fuse-cases\u002Ftelemetry","5.use-cases\u002F4.telemetry",[413,416,421,426],{"title":36,"path":414,"stem":415,"icon":39},"\u002Fuse-cases\u002Ftelemetry\u002Foverview","5.use-cases\u002F4.telemetry\u002F01.overview",{"title":417,"path":418,"stem":419,"icon":420},"Setup","\u002Fuse-cases\u002Ftelemetry\u002Fsetup","5.use-cases\u002F4.telemetry\u002F02.setup","i-lucide-wrench",{"title":422,"path":423,"stem":424,"icon":425},"Ingest","\u002Fuse-cases\u002Ftelemetry\u002Fingest","5.use-cases\u002F4.telemetry\u002F03.ingest","i-lucide-server",{"title":427,"path":428,"stem":429,"icon":79},"Reference","\u002Fuse-cases\u002Ftelemetry\u002Freference","5.use-cases\u002F4.telemetry\u002F04.reference",{"title":431,"path":432,"stem":433,"icon":434},"Enrichers","\u002Fuse-cases\u002Fenrichers","5.use-cases\u002F5.enrichers","i-lucide-sparkles",{"title":436,"path":437,"stem":438,"icon":439},"eve","\u002Fuse-cases\u002Feve","5.use-cases\u002F5.eve","i-custom-eve",{"title":441,"path":442,"stem":443,"children":444,"page":29},"Extend","\u002Fextend","6.extend",[445,449,454,459,463,468,472,476,480,484,489,494],{"title":36,"path":446,"stem":447,"icon":448},"\u002Fextend\u002Foverview","6.extend\u002F0.overview","i-lucide-blocks",{"title":450,"path":451,"stem":452,"icon":453},"Stream","\u002Fextend\u002Fstream","6.extend\u002F1.stream","i-lucide-radio-tower",{"title":455,"path":456,"stem":457,"icon":458},"Custom framework","\u002Fextend\u002Fcustom-framework","6.extend\u002F10.custom-framework","i-lucide-puzzle",{"title":460,"path":461,"stem":462,"icon":453},"Diagnostics channel","\u002Fextend\u002Fdiagnostics-channel","6.extend\u002F11.diagnostics-channel",{"title":464,"path":465,"stem":466,"icon":467},"FS reader","\u002Fextend\u002Ffs-reader","6.extend\u002F2.fs-reader","i-lucide-folder-search",{"title":406,"path":469,"stem":470,"icon":471},"\u002Fextend\u002Fconsumer-recipes","6.extend\u002F3.consumer-recipes","i-lucide-chef-hat",{"title":473,"path":474,"stem":475,"icon":448},"Plugins","\u002Fextend\u002Fplugins","6.extend\u002F4.plugins",{"title":477,"path":478,"stem":479,"icon":434},"Custom enrichers","\u002Fextend\u002Fcustom-enrichers","6.extend\u002F5.custom-enrichers",{"title":481,"path":482,"stem":483,"icon":64},"Tail sampling","\u002Fextend\u002Ftail-sampling","6.extend\u002F6.tail-sampling",{"title":485,"path":486,"stem":487,"icon":488},"Identity headers","\u002Fextend\u002Fidentity-headers","6.extend\u002F7.identity-headers","i-lucide-fingerprint",{"title":490,"path":491,"stem":492,"icon":493},"Custom drains","\u002Fextend\u002Fcustom-drains","6.extend\u002F8.custom-drains","i-lucide-share-2",{"title":495,"path":496,"stem":497,"icon":498},"Drain pipeline","\u002Fextend\u002Fdrain-pipeline","6.extend\u002F9.drain-pipeline","i-lucide-workflow",{"title":427,"path":500,"stem":501,"children":502,"page":29},"\u002Freference","7.reference",[503,508,511,516,520,525,529],{"title":504,"path":505,"stem":506,"icon":507},"Configuration","\u002Freference\u002Fconfiguration","7.reference\u002F1.configuration","i-lucide-settings",{"title":374,"path":509,"stem":510,"icon":107},"\u002Freference\u002Fperformance","7.reference\u002F2.performance",{"title":512,"path":513,"stem":514,"icon":515},"Vite Plugin","\u002Freference\u002Fvite-plugin","7.reference\u002F3.vite-plugin","i-custom-vite",{"title":517,"path":518,"stem":519,"icon":379},"Best Practices","\u002Freference\u002Fbest-practices","7.reference\u002F4.best-practices",{"title":521,"path":522,"stem":523,"icon":524},"vs Other Loggers","\u002Freference\u002Fvs-other-loggers","7.reference\u002F5.vs-other-loggers","i-lucide-scale",{"title":526,"path":527,"stem":528,"icon":434},"Agent Skills","\u002Freference\u002Fagent-skills","7.reference\u002F6.agent-skills",{"title":530,"path":531,"stem":532,"icon":533},"Cost","\u002Freference\u002Fcost","7.reference\u002F7.cost","i-lucide-receipt",{"id":535,"title":536,"body":537,"description":3068,"extension":3069,"links":3070,"meta":3074,"navigation":3075,"path":456,"seo":3076,"stem":457,"__hash__":3077},"docs\u002F6.extend\u002F10.custom-framework.md","Custom Framework Integration",{"type":538,"value":539,"toc":3055},"minimark",[540,553,561,571,654,817,822,893,897,1113,1136,1140,1149,1974,1980,1988,1991,2051,2054,2058,2070,2180,2194,2198,2210,2219,2336,2351,2593,2603,2607,2614,2864,2871,2875,2878,3002,3013,3017,3051],[541,542,543,544,548,549,552],"p",{},"When the framework you use doesn't have an ",[545,546,547],"code",{},"evlog\u002F\u003Cframework>"," package yet, you build the integration yourself. ",[545,550,551],{},"evlog\u002Ftoolkit"," ships the same building blocks that power every built-in integration (Hono, Express, Fastify, Elysia, NestJS, SvelteKit), so you only write the framework-specific glue.",[541,554,555,556,560],{},"The mental model is always the same: ",[557,558,559],"strong",{},"request lifecycle → logger creation → enrich → drain",". The toolkit handles the request-context plumbing.",[562,563,566,567,570],"callout",{"color":564,"icon":565},"warning","i-lucide-flask-conical","The toolkit API is marked as ",[557,568,569],{},"beta",". The surface is stable (used by all built-in integrations) but may evolve based on community feedback.",[572,573,574,590],"table",{},[575,576,577],"thead",{},[578,579,580,584,587],"tr",{},[581,582,583],"th",{},"Surface",[581,585,586],{},"What it does",[581,588,589],{},"When to use",[591,592,593,615,638],"tbody",{},[578,594,595,605,608],{},[596,597,598],"td",{},[599,600,602],"a",{"href":601},"#manifest-mode-recommended",[545,603,604],{},"defineFrameworkIntegration()",[596,606,607],{},"Declaratively wire request extraction + logger attachment",[596,609,610,611,614],{},"HTTP frameworks with a ",[545,612,613],{},"(ctx, next)"," middleware shape (Hono, Express, Fastify, Elysia, NestJS-shaped)",[578,616,617,625,628],{},[596,618,619],{},[599,620,622],{"href":621},"#custom-mode",[545,623,624],{},"createMiddlewareLogger()",[596,626,627],{},"Imperative path: create the logger at request start, emit on response end",[596,629,630,631,633,634,637],{},"Frameworks whose lifecycle doesn't fit ",[545,632,613],{}," (NestJS interceptors, Next.js App Router, SvelteKit ",[545,635,636],{},"handle",")",[578,639,640,648,651],{},[596,641,642],{},[599,643,645],{"href":644},"#non-http-runtimes",[545,646,647],{},"createRequestLogger()",[596,649,650],{},"Wrap any unit of work in a logger lifecycle",[596,652,653],{},"Non-HTTP runtimes (queue workers, CLI, cron, durable workflows)",[655,656,659,662,809],"prompt",{":actions":657,"description":658,"icon":458},"[\"copy\",\"cursor\",\"claude\"]","Build an evlog integration for a custom framework",[541,660,661],{},"Wire evlog into an HTTP framework (or non-HTTP runtime) that doesn't have a built-in integration.",[663,664,665,699,713,723,737,752,763,789,800],"ul",{},[666,667,668,669,671,672,675,676,678,679,682,683,686,687,690,691,694,695,698],"li",{},"For HTTP frameworks with ",[545,670,613],{},", use ",[545,673,674],{},"defineFrameworkIntegration"," from ",[545,677,551],{}," — declare ",[545,680,681],{},"extractRequest(ctx)"," returning ",[545,684,685],{},"{ method, path, headers, requestId? }",", ",[545,688,689],{},"attachLogger(ctx, logger)",", and an optional storage from ",[545,692,693],{},"createLoggerStorage()"," (prefer ",[545,696,697],{},"evlog\u002Ftoolkit\u002Fstorage"," on Workers \u002F edge)",[666,700,701,702,705,706,709,710,712],{},"Headers may be either Web ",[545,703,704],{},"Headers"," or Node ",[545,707,708],{},"IncomingHttpHeaders"," — ",[545,711,674],{}," normalizes both",[666,714,715,716,719,720],{},"In your middleware, call ",[545,717,718],{},"integration.start(ctx, options)"," which returns ",[545,721,722],{},"{ skipped, finish, runWith, logger, middlewareOptions }",[666,724,725,726,729,730,733,734],{},"If ",[545,727,728],{},"skipped"," is ",[545,731,732],{},"true",", skip directly to ",[545,735,736],{},"next",[666,738,739,740,743,744,747,748,751],{},"Run downstream handlers inside ",[545,741,742],{},"runWith(() => next())"," so ",[545,745,746],{},"AsyncLocalStorage"," and ",[545,749,750],{},"log.fork()"," work",[666,753,754,755,758,759,762],{},"On success: ",[545,756,757],{},"await finish({ status })","; on error: ",[545,760,761],{},"await finish({ error })"," then re-throw",[666,764,765,766,686,769,686,772,686,775,686,778,686,781,784,785,788],{},"Expose ",[545,767,768],{},"drain",[545,770,771],{},"enrich",[545,773,774],{},"keep",[545,776,777],{},"include",[545,779,780],{},"exclude",[545,782,783],{},"routes",", and ",[545,786,787],{},"plugins"," options",[666,790,791,792,795,796,799],{},"On Cloudflare Workers \u002F Vercel Edge, pass ",[545,793,794],{},"waitUntil"," (or ",[545,797,798],{},"extractWaitUntil"," on the manifest) so async drains complete after the response",[666,801,802,803,675,806,808],{},"For non-HTTP runtimes (queue workers, CLI, cron), use ",[545,804,805],{},"createRequestLogger",[545,807,551],{}," directly — wrap each unit of work in a logger lifecycle",[541,810,811,812],{},"Docs: ",[599,813,814],{"href":814,"rel":815},"https:\u002F\u002Fwww.evlog.dev\u002Fextend\u002Fcustom-framework",[816],"nofollow",[818,819,821],"h2",{"id":820},"install","Install",[823,824,825,850,864,878],"code-group",{},[826,827,833],"pre",{"className":828,"code":829,"filename":830,"language":831,"meta":832,"style":832},"language-bash shiki shiki-themes material-theme-lighter material-theme material-theme-palenight","pnpm add evlog\n","pnpm","bash","",[545,834,835],{"__ignoreMap":832},[836,837,840,843,847],"span",{"class":838,"line":839},"line",1,[836,841,830],{"class":842},"sBMFI",[836,844,846],{"class":845},"sfazB"," add",[836,848,849],{"class":845}," evlog\n",[826,851,854],{"className":828,"code":852,"filename":853,"language":831,"meta":832,"style":832},"bun add evlog\n","bun",[545,855,856],{"__ignoreMap":832},[836,857,858,860,862],{"class":838,"line":839},[836,859,853],{"class":842},[836,861,846],{"class":845},[836,863,849],{"class":845},[826,865,868],{"className":828,"code":866,"filename":867,"language":831,"meta":832,"style":832},"yarn add evlog\n","yarn",[545,869,870],{"__ignoreMap":832},[836,871,872,874,876],{"class":838,"line":839},[836,873,867],{"class":842},[836,875,846],{"class":845},[836,877,849],{"class":845},[826,879,882],{"className":828,"code":880,"filename":881,"language":831,"meta":832,"style":832},"npm install evlog\n","npm",[545,883,884],{"__ignoreMap":832},[836,885,886,888,891],{"class":838,"line":839},[836,887,881],{"class":842},[836,889,890],{"class":845}," install",[836,892,849],{"class":845},[818,894,896],{"id":895},"whats-in-the-toolkit","What's in the toolkit",[572,898,899,909],{},[575,900,901],{},[578,902,903,906],{},[581,904,905],{},"Export",[581,907,908],{},"Purpose",[591,910,911,921,931,945,955,979,992,1005,1017,1040,1058,1072,1103],{},[578,912,913,918],{},[596,914,915],{},[545,916,917],{},"defineFrameworkIntegration(spec)",[596,919,920],{},"Manifest factory — extract request, create logger, attach, run with ALS",[578,922,923,928],{},[596,924,925],{},[545,926,927],{},"createMiddlewareLogger(opts)",[596,929,930],{},"Lower-level lifecycle (custom mode)",[578,932,933,938],{},[596,934,935,937],{},[545,936,794],{}," on middleware options",[596,939,940,941,637],{},"Defer drain on Cloudflare Workers \u002F Vercel Edge (see ",[599,942,944],{"href":943},"#serverless-workers-edge","Serverless",[578,946,947,952],{},[596,948,949],{},[545,950,951],{},"createRequestLogger(opts)",[596,953,954],{},"Wrap a non-HTTP unit of work in a logger lifecycle",[578,956,957,962],{},[596,958,959],{},[545,960,961],{},"BaseEvlogOptions",[596,963,964,965,686,967,686,969,686,971,686,973,686,975,686,977],{},"Base user-facing options — ",[545,966,768],{},[545,968,771],{},[545,970,774],{},[545,972,777],{},[545,974,780],{},[545,976,783],{},[545,978,787],{},[578,980,981,986],{},[596,982,983],{},[545,984,985],{},"MiddlewareLoggerResult",[596,987,988,989],{},"Return type: ",[545,990,991],{},"{ logger, finish, skipped }",[578,993,994,999],{},[596,995,996],{},[545,997,998],{},"extractSafeHeaders(headers)",[596,1000,1001,1002,1004],{},"Filter sensitive headers from a Web API ",[545,1003,704],{}," object",[578,1006,1007,1012],{},[596,1008,1009],{},[545,1010,1011],{},"extractSafeNodeHeaders(headers)",[596,1013,1014,1015],{},"Filter sensitive headers from Node.js ",[545,1016,708],{},[578,1018,1019,1024],{},[596,1020,1021],{},[545,1022,1023],{},"createLoggerStorage(hint)",[596,1025,1026,1027,1030,1031,1033,1034,1036,1037,637],{},"Factory returning ",[545,1028,1029],{},"{ storage, useLogger }"," backed by ",[545,1032,746],{}," — also on ",[545,1035,697],{}," (prefer that entry on Workers \u002F edge to isolate ",[545,1038,1039],{},"node:async_hooks",[578,1041,1042,1047],{},[596,1043,1044],{},[545,1045,1046],{},"attachForkToLogger(storage, parent, opts)",[596,1048,1049,1050,1053,1054,1057],{},"Wires ",[545,1051,1052],{},"log.fork(label, fn)"," onto the request logger so consumers can spawn correlated background work — used by manifest mode automatically; call manually in custom mode after ",[545,1055,1056],{},"createMiddlewareLogger"," returns the logger and before the lifecycle finishes",[578,1059,1060,1065],{},[596,1061,1062],{},[545,1063,1064],{},"defineEvlog(config)",[596,1066,1067,1068,1071],{},"Canonical config object — works for ",[545,1069,1070],{},"initLogger"," and middleware options",[578,1073,1074,1079],{},[596,1075,1076],{},[545,1077,1078],{},"definePlugin(plugin)",[596,1080,1081,1082,686,1085,686,1087,686,1089,686,1091,686,1094,686,1097,686,1100],{},"Plugin contract — opt into any subset of ",[545,1083,1084],{},"setup",[545,1086,771],{},[545,1088,768],{},[545,1090,774],{},[545,1092,1093],{},"onRequestStart",[545,1095,1096],{},"onRequestFinish",[545,1098,1099],{},"onClientLog",[545,1101,1102],{},"extendLogger",[578,1104,1105,1110],{},[596,1106,1107],{},[545,1108,1109],{},"composeEnrichers \u002F composeDrains \u002F composeKeep \u002F composePlugins",[596,1111,1112],{},"Combine multiple extensions into one",[541,1114,1115,1116,686,1119,686,1122,686,1125,784,1128,1131,1132,1135],{},"Types like ",[545,1117,1118],{},"RequestLogger",[545,1120,1121],{},"DrainContext",[545,1123,1124],{},"EnrichContext",[545,1126,1127],{},"WideEvent",[545,1129,1130],{},"TailSamplingContext"," are exported from the main ",[545,1133,1134],{},"evlog"," package.",[818,1137,1139],{"id":1138},"manifest-mode-recommended","Manifest mode (recommended)",[541,1141,1142,1143,1145,1146,1148],{},"Most frameworks fit a ",[545,1144,613],{}," middleware shape. For those, write a manifest describing how to extract the request and attach the logger. ",[545,1147,674],{}," does the rest.",[1150,1151,1152],"code-collapse",{},[826,1153,1158],{"className":1154,"code":1155,"filename":1156,"language":1157,"meta":832,"style":832},"language-typescript shiki shiki-themes material-theme-lighter material-theme material-theme-palenight","import type { IncomingMessage, ServerResponse } from 'node:http'\nimport {\n  createLoggerStorage,\n  defineFrameworkIntegration,\n  type BaseEvlogOptions,\n} from 'evlog\u002Ftoolkit'\n\u002F\u002F On Workers \u002F edge, prefer: import { createLoggerStorage } from 'evlog\u002Ftoolkit\u002Fstorage'\nimport type { RequestLogger } from 'evlog'\n\nexport type MyFrameworkEvlogOptions = BaseEvlogOptions\n\nconst { storage, useLogger } = createLoggerStorage(\n  'Cannot access logger outside of middleware context. Make sure evlog middleware is registered before your routes.',\n)\n\nexport { useLogger }\n\nconst integration = defineFrameworkIntegration\u003CIncomingMessage>({\n  name: 'my-framework',\n  extractRequest: (req) => ({\n    method: req.method || 'GET',\n    path: req.url || '\u002F',\n    headers: req.headers,\n    requestId: typeof req.headers['x-request-id'] === 'string'\n      ? req.headers['x-request-id']\n      : undefined,\n  }),\n  attachLogger: (req, logger) => {\n    (req as IncomingMessage & { log: RequestLogger }).log = logger\n  },\n  storage,\n})\n\nexport function evlog(options: MyFrameworkEvlogOptions = {}) {\n  return async (req: IncomingMessage, res: ServerResponse, next: () => Promise\u003Cvoid>) => {\n    const { skipped, finish, runWith } = integration.start(req, options)\n    if (skipped) {\n      await next()\n      return\n    }\n    try {\n      await runWith(() => next())\n      await finish({ status: res.statusCode })\n    } catch (error) {\n      await finish({ error: error as Error })\n      throw error\n    }\n  }\n}\n","my-framework-evlog.ts","typescript",[545,1159,1160,1198,1206,1215,1223,1234,1248,1255,1277,1284,1302,1307,1334,1348,1354,1359,1372,1377,1406,1425,1449,1478,1504,1521,1559,1580,1589,1599,1622,1661,1667,1675,1682,1687,1714,1767,1810,1825,1836,1842,1848,1856,1875,1903,1921,1948,1957,1962,1968],{"__ignoreMap":832},[836,1161,1162,1166,1169,1173,1177,1180,1183,1186,1189,1192,1195],{"class":838,"line":839},[836,1163,1165],{"class":1164},"s7zQu","import",[836,1167,1168],{"class":1164}," type",[836,1170,1172],{"class":1171},"sMK4o"," {",[836,1174,1176],{"class":1175},"sTEyZ"," IncomingMessage",[836,1178,1179],{"class":1171},",",[836,1181,1182],{"class":1175}," ServerResponse",[836,1184,1185],{"class":1171}," }",[836,1187,1188],{"class":1164}," from",[836,1190,1191],{"class":1171}," '",[836,1193,1194],{"class":845},"node:http",[836,1196,1197],{"class":1171},"'\n",[836,1199,1201,1203],{"class":838,"line":1200},2,[836,1202,1165],{"class":1164},[836,1204,1205],{"class":1171}," {\n",[836,1207,1209,1212],{"class":838,"line":1208},3,[836,1210,1211],{"class":1175},"  createLoggerStorage",[836,1213,1214],{"class":1171},",\n",[836,1216,1218,1221],{"class":838,"line":1217},4,[836,1219,1220],{"class":1175},"  defineFrameworkIntegration",[836,1222,1214],{"class":1171},[836,1224,1226,1229,1232],{"class":838,"line":1225},5,[836,1227,1228],{"class":1164},"  type",[836,1230,1231],{"class":1175}," BaseEvlogOptions",[836,1233,1214],{"class":1171},[836,1235,1237,1240,1242,1244,1246],{"class":838,"line":1236},6,[836,1238,1239],{"class":1171},"}",[836,1241,1188],{"class":1164},[836,1243,1191],{"class":1171},[836,1245,551],{"class":845},[836,1247,1197],{"class":1171},[836,1249,1251],{"class":838,"line":1250},7,[836,1252,1254],{"class":1253},"sHwdD","\u002F\u002F On Workers \u002F edge, prefer: import { createLoggerStorage } from 'evlog\u002Ftoolkit\u002Fstorage'\n",[836,1256,1258,1260,1262,1264,1267,1269,1271,1273,1275],{"class":838,"line":1257},8,[836,1259,1165],{"class":1164},[836,1261,1168],{"class":1164},[836,1263,1172],{"class":1171},[836,1265,1266],{"class":1175}," RequestLogger",[836,1268,1185],{"class":1171},[836,1270,1188],{"class":1164},[836,1272,1191],{"class":1171},[836,1274,1134],{"class":845},[836,1276,1197],{"class":1171},[836,1278,1280],{"class":838,"line":1279},9,[836,1281,1283],{"emptyLinePlaceholder":1282},true,"\n",[836,1285,1287,1290,1293,1296,1299],{"class":838,"line":1286},10,[836,1288,1289],{"class":1164},"export",[836,1291,1168],{"class":1292},"spNyl",[836,1294,1295],{"class":842}," MyFrameworkEvlogOptions",[836,1297,1298],{"class":1171}," =",[836,1300,1301],{"class":842}," BaseEvlogOptions\n",[836,1303,1305],{"class":838,"line":1304},11,[836,1306,1283],{"emptyLinePlaceholder":1282},[836,1308,1310,1313,1315,1318,1320,1323,1325,1327,1331],{"class":838,"line":1309},12,[836,1311,1312],{"class":1292},"const",[836,1314,1172],{"class":1171},[836,1316,1317],{"class":1175}," storage",[836,1319,1179],{"class":1171},[836,1321,1322],{"class":1175}," useLogger ",[836,1324,1239],{"class":1171},[836,1326,1298],{"class":1171},[836,1328,1330],{"class":1329},"s2Zo4"," createLoggerStorage",[836,1332,1333],{"class":1175},"(\n",[836,1335,1337,1340,1343,1346],{"class":838,"line":1336},13,[836,1338,1339],{"class":1171},"  '",[836,1341,1342],{"class":845},"Cannot access logger outside of middleware context. Make sure evlog middleware is registered before your routes.",[836,1344,1345],{"class":1171},"'",[836,1347,1214],{"class":1171},[836,1349,1351],{"class":838,"line":1350},14,[836,1352,1353],{"class":1175},")\n",[836,1355,1357],{"class":838,"line":1356},15,[836,1358,1283],{"emptyLinePlaceholder":1282},[836,1360,1362,1364,1366,1369],{"class":838,"line":1361},16,[836,1363,1289],{"class":1164},[836,1365,1172],{"class":1171},[836,1367,1368],{"class":1175}," useLogger",[836,1370,1371],{"class":1171}," }\n",[836,1373,1375],{"class":838,"line":1374},17,[836,1376,1283],{"emptyLinePlaceholder":1282},[836,1378,1380,1382,1385,1388,1391,1394,1397,1400,1403],{"class":838,"line":1379},18,[836,1381,1312],{"class":1292},[836,1383,1384],{"class":1175}," integration ",[836,1386,1387],{"class":1171},"=",[836,1389,1390],{"class":1329}," defineFrameworkIntegration",[836,1392,1393],{"class":1171},"\u003C",[836,1395,1396],{"class":842},"IncomingMessage",[836,1398,1399],{"class":1171},">",[836,1401,1402],{"class":1175},"(",[836,1404,1405],{"class":1171},"{\n",[836,1407,1409,1413,1416,1418,1421,1423],{"class":838,"line":1408},19,[836,1410,1412],{"class":1411},"swJcz","  name",[836,1414,1415],{"class":1171},":",[836,1417,1191],{"class":1171},[836,1419,1420],{"class":845},"my-framework",[836,1422,1345],{"class":1171},[836,1424,1214],{"class":1171},[836,1426,1428,1431,1433,1436,1440,1442,1445,1447],{"class":838,"line":1427},20,[836,1429,1430],{"class":1329},"  extractRequest",[836,1432,1415],{"class":1171},[836,1434,1435],{"class":1171}," (",[836,1437,1439],{"class":1438},"sHdIc","req",[836,1441,637],{"class":1171},[836,1443,1444],{"class":1292}," =>",[836,1446,1435],{"class":1175},[836,1448,1405],{"class":1171},[836,1450,1452,1455,1457,1460,1463,1466,1469,1471,1474,1476],{"class":838,"line":1451},21,[836,1453,1454],{"class":1411},"    method",[836,1456,1415],{"class":1171},[836,1458,1459],{"class":1175}," req",[836,1461,1462],{"class":1171},".",[836,1464,1465],{"class":1175},"method ",[836,1467,1468],{"class":1171},"||",[836,1470,1191],{"class":1171},[836,1472,1473],{"class":845},"GET",[836,1475,1345],{"class":1171},[836,1477,1214],{"class":1171},[836,1479,1481,1484,1486,1488,1490,1493,1495,1497,1500,1502],{"class":838,"line":1480},22,[836,1482,1483],{"class":1411},"    path",[836,1485,1415],{"class":1171},[836,1487,1459],{"class":1175},[836,1489,1462],{"class":1171},[836,1491,1492],{"class":1175},"url ",[836,1494,1468],{"class":1171},[836,1496,1191],{"class":1171},[836,1498,1499],{"class":845},"\u002F",[836,1501,1345],{"class":1171},[836,1503,1214],{"class":1171},[836,1505,1507,1510,1512,1514,1516,1519],{"class":838,"line":1506},23,[836,1508,1509],{"class":1411},"    headers",[836,1511,1415],{"class":1171},[836,1513,1459],{"class":1175},[836,1515,1462],{"class":1171},[836,1517,1518],{"class":1175},"headers",[836,1520,1214],{"class":1171},[836,1522,1524,1527,1529,1532,1534,1536,1539,1541,1544,1546,1549,1552,1554,1557],{"class":838,"line":1523},24,[836,1525,1526],{"class":1411},"    requestId",[836,1528,1415],{"class":1171},[836,1530,1531],{"class":1171}," typeof",[836,1533,1459],{"class":1175},[836,1535,1462],{"class":1171},[836,1537,1538],{"class":1175},"headers[",[836,1540,1345],{"class":1171},[836,1542,1543],{"class":845},"x-request-id",[836,1545,1345],{"class":1171},[836,1547,1548],{"class":1175},"] ",[836,1550,1551],{"class":1171},"===",[836,1553,1191],{"class":1171},[836,1555,1556],{"class":845},"string",[836,1558,1197],{"class":1171},[836,1560,1562,1565,1567,1569,1571,1573,1575,1577],{"class":838,"line":1561},25,[836,1563,1564],{"class":1171},"      ?",[836,1566,1459],{"class":1175},[836,1568,1462],{"class":1171},[836,1570,1538],{"class":1175},[836,1572,1345],{"class":1171},[836,1574,1543],{"class":845},[836,1576,1345],{"class":1171},[836,1578,1579],{"class":1175},"]\n",[836,1581,1583,1586],{"class":838,"line":1582},26,[836,1584,1585],{"class":1171},"      :",[836,1587,1588],{"class":1171}," undefined,\n",[836,1590,1592,1595,1597],{"class":838,"line":1591},27,[836,1593,1594],{"class":1171},"  }",[836,1596,637],{"class":1175},[836,1598,1214],{"class":1171},[836,1600,1602,1605,1607,1609,1611,1613,1616,1618,1620],{"class":838,"line":1601},28,[836,1603,1604],{"class":1329},"  attachLogger",[836,1606,1415],{"class":1171},[836,1608,1435],{"class":1171},[836,1610,1439],{"class":1438},[836,1612,1179],{"class":1171},[836,1614,1615],{"class":1438}," logger",[836,1617,637],{"class":1171},[836,1619,1444],{"class":1292},[836,1621,1205],{"class":1171},[836,1623,1625,1628,1630,1633,1635,1638,1640,1643,1645,1647,1649,1651,1653,1656,1658],{"class":838,"line":1624},29,[836,1626,1627],{"class":1411},"    (",[836,1629,1439],{"class":1175},[836,1631,1632],{"class":1164}," as",[836,1634,1176],{"class":842},[836,1636,1637],{"class":1171}," &",[836,1639,1172],{"class":1171},[836,1641,1642],{"class":1411}," log",[836,1644,1415],{"class":1171},[836,1646,1266],{"class":842},[836,1648,1185],{"class":1171},[836,1650,637],{"class":1411},[836,1652,1462],{"class":1171},[836,1654,1655],{"class":1175},"log",[836,1657,1298],{"class":1171},[836,1659,1660],{"class":1175}," logger\n",[836,1662,1664],{"class":838,"line":1663},30,[836,1665,1666],{"class":1171},"  },\n",[836,1668,1670,1673],{"class":838,"line":1669},31,[836,1671,1672],{"class":1175},"  storage",[836,1674,1214],{"class":1171},[836,1676,1678,1680],{"class":838,"line":1677},32,[836,1679,1239],{"class":1171},[836,1681,1353],{"class":1175},[836,1683,1685],{"class":838,"line":1684},33,[836,1686,1283],{"emptyLinePlaceholder":1282},[836,1688,1690,1692,1695,1698,1700,1703,1705,1707,1709,1712],{"class":838,"line":1689},34,[836,1691,1289],{"class":1164},[836,1693,1694],{"class":1292}," function",[836,1696,1697],{"class":1329}," evlog",[836,1699,1402],{"class":1171},[836,1701,1702],{"class":1438},"options",[836,1704,1415],{"class":1171},[836,1706,1295],{"class":842},[836,1708,1298],{"class":1171},[836,1710,1711],{"class":1171}," {})",[836,1713,1205],{"class":1171},[836,1715,1717,1720,1723,1725,1727,1729,1731,1733,1736,1738,1740,1742,1745,1747,1750,1752,1755,1757,1760,1763,1765],{"class":838,"line":1716},35,[836,1718,1719],{"class":1164},"  return",[836,1721,1722],{"class":1292}," async",[836,1724,1435],{"class":1171},[836,1726,1439],{"class":1438},[836,1728,1415],{"class":1171},[836,1730,1176],{"class":842},[836,1732,1179],{"class":1171},[836,1734,1735],{"class":1438}," res",[836,1737,1415],{"class":1171},[836,1739,1182],{"class":842},[836,1741,1179],{"class":1171},[836,1743,1744],{"class":1329}," next",[836,1746,1415],{"class":1171},[836,1748,1749],{"class":1171}," ()",[836,1751,1444],{"class":1292},[836,1753,1754],{"class":842}," Promise",[836,1756,1393],{"class":1171},[836,1758,1759],{"class":842},"void",[836,1761,1762],{"class":1171},">)",[836,1764,1444],{"class":1292},[836,1766,1205],{"class":1171},[836,1768,1770,1773,1775,1778,1780,1783,1785,1788,1790,1792,1795,1797,1800,1802,1804,1806,1808],{"class":838,"line":1769},36,[836,1771,1772],{"class":1292},"    const",[836,1774,1172],{"class":1171},[836,1776,1777],{"class":1175}," skipped",[836,1779,1179],{"class":1171},[836,1781,1782],{"class":1175}," finish",[836,1784,1179],{"class":1171},[836,1786,1787],{"class":1175}," runWith",[836,1789,1185],{"class":1171},[836,1791,1298],{"class":1171},[836,1793,1794],{"class":1175}," integration",[836,1796,1462],{"class":1171},[836,1798,1799],{"class":1329},"start",[836,1801,1402],{"class":1411},[836,1803,1439],{"class":1175},[836,1805,1179],{"class":1171},[836,1807,788],{"class":1175},[836,1809,1353],{"class":1411},[836,1811,1813,1816,1818,1820,1823],{"class":838,"line":1812},37,[836,1814,1815],{"class":1164},"    if",[836,1817,1435],{"class":1411},[836,1819,728],{"class":1175},[836,1821,1822],{"class":1411},") ",[836,1824,1405],{"class":1171},[836,1826,1828,1831,1833],{"class":838,"line":1827},38,[836,1829,1830],{"class":1164},"      await",[836,1832,1744],{"class":1329},[836,1834,1835],{"class":1411},"()\n",[836,1837,1839],{"class":838,"line":1838},39,[836,1840,1841],{"class":1164},"      return\n",[836,1843,1845],{"class":838,"line":1844},40,[836,1846,1847],{"class":1171},"    }\n",[836,1849,1851,1854],{"class":838,"line":1850},41,[836,1852,1853],{"class":1164},"    try",[836,1855,1205],{"class":1171},[836,1857,1859,1861,1863,1865,1868,1870,1872],{"class":838,"line":1858},42,[836,1860,1830],{"class":1164},[836,1862,1787],{"class":1329},[836,1864,1402],{"class":1411},[836,1866,1867],{"class":1171},"()",[836,1869,1444],{"class":1292},[836,1871,1744],{"class":1329},[836,1873,1874],{"class":1411},"())\n",[836,1876,1878,1880,1882,1884,1887,1890,1892,1894,1896,1899,1901],{"class":838,"line":1877},43,[836,1879,1830],{"class":1164},[836,1881,1782],{"class":1329},[836,1883,1402],{"class":1411},[836,1885,1886],{"class":1171},"{",[836,1888,1889],{"class":1411}," status",[836,1891,1415],{"class":1171},[836,1893,1735],{"class":1175},[836,1895,1462],{"class":1171},[836,1897,1898],{"class":1175},"statusCode",[836,1900,1185],{"class":1171},[836,1902,1353],{"class":1411},[836,1904,1906,1909,1912,1914,1917,1919],{"class":838,"line":1905},44,[836,1907,1908],{"class":1171},"    }",[836,1910,1911],{"class":1164}," catch",[836,1913,1435],{"class":1411},[836,1915,1916],{"class":1175},"error",[836,1918,1822],{"class":1411},[836,1920,1405],{"class":1171},[836,1922,1924,1926,1928,1930,1932,1935,1937,1939,1941,1944,1946],{"class":838,"line":1923},45,[836,1925,1830],{"class":1164},[836,1927,1782],{"class":1329},[836,1929,1402],{"class":1411},[836,1931,1886],{"class":1171},[836,1933,1934],{"class":1411}," error",[836,1936,1415],{"class":1171},[836,1938,1934],{"class":1175},[836,1940,1632],{"class":1164},[836,1942,1943],{"class":842}," Error",[836,1945,1185],{"class":1171},[836,1947,1353],{"class":1411},[836,1949,1951,1954],{"class":838,"line":1950},46,[836,1952,1953],{"class":1164},"      throw",[836,1955,1956],{"class":1175}," error\n",[836,1958,1960],{"class":838,"line":1959},47,[836,1961,1847],{"class":1171},[836,1963,1965],{"class":838,"line":1964},48,[836,1966,1967],{"class":1171},"  }\n",[836,1969,1971],{"class":838,"line":1970},49,[836,1972,1973],{"class":1171},"}\n",[541,1975,1976,1977,1979],{},"That's it. This middleware gets every feature for free: route filtering, drain adapters, enrichers, tail sampling, error capture, plugin lifecycle hooks, ",[545,1978,750],{},", and duration tracking.",[1981,1982,1984,1985,1987],"h3",{"id":1983},"what-defineframeworkintegration-does","What ",[545,1986,674],{}," does",[541,1989,1990],{},"Given the manifest above, the helper:",[1992,1993,1994,2003,2014,2020,2024,2034],"ol",{},[666,1995,1996,1997,1999,2000,2002],{},"Normalizes headers (auto-detects ",[545,1998,704],{}," vs ",[545,2001,708],{},").",[666,2004,2005,2006,2009,2010,2013],{},"Generates a ",[545,2007,2008],{},"requestId"," if ",[545,2011,2012],{},"extractRequest"," doesn't return one.",[666,2015,2016,2017,2019],{},"Calls ",[545,2018,1056],{}," with the merged options.",[666,2021,2016,2022,1462],{},[545,2023,689],{},[666,2025,2026,2027,2029,2030,2033],{},"Attaches ",[545,2028,750],{}," to the logger when ",[545,2031,2032],{},"storage"," is provided (so users can spawn correlated background work).",[666,2035,2036,2037,2040,2041,2044,2045,2048,2049,1462],{},"Exposes ",[545,2038,2039],{},"runWith(fn)"," — runs ",[545,2042,2043],{},"fn()"," inside ",[545,2046,2047],{},"storage.run(logger, …)"," if storage is configured, otherwise just calls ",[545,2050,2043],{},[541,2052,2053],{},"You're left with only the framework-specific glue: where to read the request from, where to attach the logger, and how to compute the response status.",[818,2055,2057],{"id":2056},"custom-mode","Custom mode",[541,2059,2060,2061,2063,2064,2066,2067,2069],{},"If your framework's lifecycle doesn't fit a clean ",[545,2062,613],{}," shape (NestJS interceptors, Next.js App Router, SvelteKit ",[545,2065,636],{},"), drop one level lower and call ",[545,2068,1056],{}," directly:",[826,2071,2073],{"className":1154,"code":2072,"language":1157,"meta":832,"style":832},"import { createMiddlewareLogger, extractSafeNodeHeaders } from 'evlog\u002Ftoolkit'\n\nconst { logger, finish, skipped } = createMiddlewareLogger({\n  method,\n  path,\n  requestId,\n  headers: extractSafeNodeHeaders(rawHeaders),\n  ...options,\n})\n",[545,2074,2075,2099,2103,2130,2137,2144,2151,2165,2174],{"__ignoreMap":832},[836,2076,2077,2079,2081,2084,2086,2089,2091,2093,2095,2097],{"class":838,"line":839},[836,2078,1165],{"class":1164},[836,2080,1172],{"class":1171},[836,2082,2083],{"class":1175}," createMiddlewareLogger",[836,2085,1179],{"class":1171},[836,2087,2088],{"class":1175}," extractSafeNodeHeaders",[836,2090,1185],{"class":1171},[836,2092,1188],{"class":1164},[836,2094,1191],{"class":1171},[836,2096,551],{"class":845},[836,2098,1197],{"class":1171},[836,2100,2101],{"class":838,"line":1200},[836,2102,1283],{"emptyLinePlaceholder":1282},[836,2104,2105,2107,2109,2111,2113,2115,2117,2120,2122,2124,2126,2128],{"class":838,"line":1208},[836,2106,1312],{"class":1292},[836,2108,1172],{"class":1171},[836,2110,1615],{"class":1175},[836,2112,1179],{"class":1171},[836,2114,1782],{"class":1175},[836,2116,1179],{"class":1171},[836,2118,2119],{"class":1175}," skipped ",[836,2121,1239],{"class":1171},[836,2123,1298],{"class":1171},[836,2125,2083],{"class":1329},[836,2127,1402],{"class":1175},[836,2129,1405],{"class":1171},[836,2131,2132,2135],{"class":838,"line":1217},[836,2133,2134],{"class":1175},"  method",[836,2136,1214],{"class":1171},[836,2138,2139,2142],{"class":838,"line":1225},[836,2140,2141],{"class":1175},"  path",[836,2143,1214],{"class":1171},[836,2145,2146,2149],{"class":838,"line":1236},[836,2147,2148],{"class":1175},"  requestId",[836,2150,1214],{"class":1171},[836,2152,2153,2156,2158,2160,2163],{"class":838,"line":1250},[836,2154,2155],{"class":1411},"  headers",[836,2157,1415],{"class":1171},[836,2159,2088],{"class":1329},[836,2161,2162],{"class":1175},"(rawHeaders)",[836,2164,1214],{"class":1171},[836,2166,2167,2170,2172],{"class":838,"line":1257},[836,2168,2169],{"class":1171},"  ...",[836,2171,1702],{"class":1175},[836,2173,1214],{"class":1171},[836,2175,2176,2178],{"class":838,"line":1279},[836,2177,1239],{"class":1171},[836,2179,1353],{"class":1175},[541,2181,2182,2183,2186,2187,2189,2190,2193],{},"You'll be responsible for ALS wrapping (",[545,2184,2185],{},"storage.run","), ",[545,2188,750],{}," attachment (via ",[545,2191,2192],{},"attachForkToLogger","), and finishing the lifecycle, but you keep the full pipeline (route filtering, sampling, emit, enrich, drain, plugins) for free.",[818,2195,2197],{"id":2196},"serverless-workers-edge","Serverless (Workers \u002F Edge)",[541,2199,2200,2201,2203,2204,2209],{},"On Cloudflare Workers and Vercel Edge, the runtime can terminate as soon as the response is returned. If your drain sends HTTP to an observability backend, pass ",[545,2202,794],{}," so enrich still runs inline but drain work survives after the response, the same behavior as ",[599,2205,2206],{"href":286},[545,2207,2208],{},"evlog\u002Fworkers"," and the Nitro plugin.",[541,2211,2212,2215,2216,2218],{},[557,2213,2214],{},"Custom mode."," Pass ",[545,2217,794],{}," per request:",[826,2220,2222],{"className":1154,"code":2221,"language":1157,"meta":832,"style":832},"import { waitUntil } from '@vercel\u002Ffunctions'\n\u002F\u002F import { waitUntil } from 'cloudflare:workers' \u002F\u002F Vercel-style global on some runtimes\n\nconst { logger, finish, skipped } = createMiddlewareLogger({\n  method,\n  path,\n  requestId,\n  headers: extractSafeNodeHeaders(rawHeaders),\n  waitUntil, \u002F\u002F or ctx.waitUntil.bind(ctx) on Cloudflare\n  ...options,\n})\n",[545,2223,2224,2244,2252,2256,2282,2288,2294,2300,2312,2322,2330],{"__ignoreMap":832},[836,2225,2226,2228,2230,2233,2235,2237,2239,2242],{"class":838,"line":839},[836,2227,1165],{"class":1164},[836,2229,1172],{"class":1171},[836,2231,2232],{"class":1175}," waitUntil",[836,2234,1185],{"class":1171},[836,2236,1188],{"class":1164},[836,2238,1191],{"class":1171},[836,2240,2241],{"class":845},"@vercel\u002Ffunctions",[836,2243,1197],{"class":1171},[836,2245,2246,2249],{"class":838,"line":1200},[836,2247,2248],{"class":1253},"\u002F\u002F import { waitUntil } from 'cloudflare:workers'",[836,2250,2251],{"class":1253}," \u002F\u002F Vercel-style global on some runtimes\n",[836,2253,2254],{"class":838,"line":1208},[836,2255,1283],{"emptyLinePlaceholder":1282},[836,2257,2258,2260,2262,2264,2266,2268,2270,2272,2274,2276,2278,2280],{"class":838,"line":1217},[836,2259,1312],{"class":1292},[836,2261,1172],{"class":1171},[836,2263,1615],{"class":1175},[836,2265,1179],{"class":1171},[836,2267,1782],{"class":1175},[836,2269,1179],{"class":1171},[836,2271,2119],{"class":1175},[836,2273,1239],{"class":1171},[836,2275,1298],{"class":1171},[836,2277,2083],{"class":1329},[836,2279,1402],{"class":1175},[836,2281,1405],{"class":1171},[836,2283,2284,2286],{"class":838,"line":1225},[836,2285,2134],{"class":1175},[836,2287,1214],{"class":1171},[836,2289,2290,2292],{"class":838,"line":1236},[836,2291,2141],{"class":1175},[836,2293,1214],{"class":1171},[836,2295,2296,2298],{"class":838,"line":1250},[836,2297,2148],{"class":1175},[836,2299,1214],{"class":1171},[836,2301,2302,2304,2306,2308,2310],{"class":838,"line":1257},[836,2303,2155],{"class":1411},[836,2305,1415],{"class":1171},[836,2307,2088],{"class":1329},[836,2309,2162],{"class":1175},[836,2311,1214],{"class":1171},[836,2313,2314,2317,2319],{"class":838,"line":1279},[836,2315,2316],{"class":1175},"  waitUntil",[836,2318,1179],{"class":1171},[836,2320,2321],{"class":1253}," \u002F\u002F or ctx.waitUntil.bind(ctx) on Cloudflare\n",[836,2323,2324,2326,2328],{"class":838,"line":1286},[836,2325,2169],{"class":1171},[836,2327,1702],{"class":1175},[836,2329,1214],{"class":1171},[836,2331,2332,2334],{"class":838,"line":1304},[836,2333,1239],{"class":1171},[836,2335,1353],{"class":1175},[541,2337,2338,2341,2342,2344,2345,2347,2348,2350],{},[557,2339,2340],{},"Manifest mode."," Either pass ",[545,2343,794],{}," in ",[545,2346,718],{}," or declare ",[545,2349,798],{}," on the manifest when the hook lives on the framework context:",[826,2352,2354],{"className":1154,"code":2353,"language":1157,"meta":832,"style":832},"const integration = defineFrameworkIntegration\u003CWorkerContext>({\n  name: 'my-framework',\n  extractRequest: (ctx) => ({ \u002F* … *\u002F }),\n  attachLogger: (ctx, logger) => { \u002F* … *\u002F },\n  extractWaitUntil: ctx => ctx.executionCtx.waitUntil.bind(ctx.executionCtx),\n})\n\nexport function evlog(options: BaseEvlogOptions = {}) {\n  return async (ctx, next) => {\n    const { skipped, finish, runWith } = integration.start(ctx, options)\n    \u002F\u002F Per-request override still works:\n    \u002F\u002F integration.start(ctx, { ...options, waitUntil: ctx.executionCtx.waitUntil.bind(ctx.executionCtx) })\n    \u002F\u002F …\n  }\n}\n",[545,2355,2356,2377,2391,2419,2444,2482,2488,2492,2514,2534,2570,2575,2580,2585,2589],{"__ignoreMap":832},[836,2357,2358,2360,2362,2364,2366,2368,2371,2373,2375],{"class":838,"line":839},[836,2359,1312],{"class":1292},[836,2361,1384],{"class":1175},[836,2363,1387],{"class":1171},[836,2365,1390],{"class":1329},[836,2367,1393],{"class":1171},[836,2369,2370],{"class":842},"WorkerContext",[836,2372,1399],{"class":1171},[836,2374,1402],{"class":1175},[836,2376,1405],{"class":1171},[836,2378,2379,2381,2383,2385,2387,2389],{"class":838,"line":1200},[836,2380,1412],{"class":1411},[836,2382,1415],{"class":1171},[836,2384,1191],{"class":1171},[836,2386,1420],{"class":845},[836,2388,1345],{"class":1171},[836,2390,1214],{"class":1171},[836,2392,2393,2395,2397,2399,2402,2404,2406,2408,2410,2413,2415,2417],{"class":838,"line":1208},[836,2394,1430],{"class":1329},[836,2396,1415],{"class":1171},[836,2398,1435],{"class":1171},[836,2400,2401],{"class":1438},"ctx",[836,2403,637],{"class":1171},[836,2405,1444],{"class":1292},[836,2407,1435],{"class":1175},[836,2409,1886],{"class":1171},[836,2411,2412],{"class":1253}," \u002F* … *\u002F",[836,2414,1185],{"class":1171},[836,2416,637],{"class":1175},[836,2418,1214],{"class":1171},[836,2420,2421,2423,2425,2427,2429,2431,2433,2435,2437,2439,2441],{"class":838,"line":1217},[836,2422,1604],{"class":1329},[836,2424,1415],{"class":1171},[836,2426,1435],{"class":1171},[836,2428,2401],{"class":1438},[836,2430,1179],{"class":1171},[836,2432,1615],{"class":1438},[836,2434,637],{"class":1171},[836,2436,1444],{"class":1292},[836,2438,1172],{"class":1171},[836,2440,2412],{"class":1253},[836,2442,2443],{"class":1171}," },\n",[836,2445,2446,2449,2451,2454,2456,2458,2460,2463,2465,2467,2469,2472,2475,2477,2480],{"class":838,"line":1225},[836,2447,2448],{"class":1329},"  extractWaitUntil",[836,2450,1415],{"class":1171},[836,2452,2453],{"class":1438}," ctx",[836,2455,1444],{"class":1292},[836,2457,2453],{"class":1175},[836,2459,1462],{"class":1171},[836,2461,2462],{"class":1175},"executionCtx",[836,2464,1462],{"class":1171},[836,2466,794],{"class":1175},[836,2468,1462],{"class":1171},[836,2470,2471],{"class":1329},"bind",[836,2473,2474],{"class":1175},"(ctx",[836,2476,1462],{"class":1171},[836,2478,2479],{"class":1175},"executionCtx)",[836,2481,1214],{"class":1171},[836,2483,2484,2486],{"class":838,"line":1236},[836,2485,1239],{"class":1171},[836,2487,1353],{"class":1175},[836,2489,2490],{"class":838,"line":1250},[836,2491,1283],{"emptyLinePlaceholder":1282},[836,2493,2494,2496,2498,2500,2502,2504,2506,2508,2510,2512],{"class":838,"line":1257},[836,2495,1289],{"class":1164},[836,2497,1694],{"class":1292},[836,2499,1697],{"class":1329},[836,2501,1402],{"class":1171},[836,2503,1702],{"class":1438},[836,2505,1415],{"class":1171},[836,2507,1231],{"class":842},[836,2509,1298],{"class":1171},[836,2511,1711],{"class":1171},[836,2513,1205],{"class":1171},[836,2515,2516,2518,2520,2522,2524,2526,2528,2530,2532],{"class":838,"line":1279},[836,2517,1719],{"class":1164},[836,2519,1722],{"class":1292},[836,2521,1435],{"class":1171},[836,2523,2401],{"class":1438},[836,2525,1179],{"class":1171},[836,2527,1744],{"class":1438},[836,2529,637],{"class":1171},[836,2531,1444],{"class":1292},[836,2533,1205],{"class":1171},[836,2535,2536,2538,2540,2542,2544,2546,2548,2550,2552,2554,2556,2558,2560,2562,2564,2566,2568],{"class":838,"line":1286},[836,2537,1772],{"class":1292},[836,2539,1172],{"class":1171},[836,2541,1777],{"class":1175},[836,2543,1179],{"class":1171},[836,2545,1782],{"class":1175},[836,2547,1179],{"class":1171},[836,2549,1787],{"class":1175},[836,2551,1185],{"class":1171},[836,2553,1298],{"class":1171},[836,2555,1794],{"class":1175},[836,2557,1462],{"class":1171},[836,2559,1799],{"class":1329},[836,2561,1402],{"class":1411},[836,2563,2401],{"class":1175},[836,2565,1179],{"class":1171},[836,2567,788],{"class":1175},[836,2569,1353],{"class":1411},[836,2571,2572],{"class":838,"line":1304},[836,2573,2574],{"class":1253},"    \u002F\u002F Per-request override still works:\n",[836,2576,2577],{"class":838,"line":1309},[836,2578,2579],{"class":1253},"    \u002F\u002F integration.start(ctx, { ...options, waitUntil: ctx.executionCtx.waitUntil.bind(ctx.executionCtx) })\n",[836,2581,2582],{"class":838,"line":1336},[836,2583,2584],{"class":1253},"    \u002F\u002F …\n",[836,2586,2587],{"class":838,"line":1350},[836,2588,1967],{"class":1171},[836,2590,2591],{"class":838,"line":1356},[836,2592,1973],{"class":1171},[541,2594,2595,2596,2599,2600,2602],{},"Per-request ",[545,2597,2598],{},"options.waitUntil"," takes precedence over ",[545,2601,798],{},". Without either, drains are awaited (correct for traditional Node.js servers).",[818,2604,2606],{"id":2605},"non-http-runtimes","Non-HTTP runtimes",[541,2608,2609,2610,675,2612,2069],{},"For queue workers, CLI drivers, cron jobs, or durable execution engines, skip the HTTP-shaped helpers and use ",[545,2611,805],{},[545,2613,551],{},[826,2615,2619],{"className":2616,"code":2617,"language":2618,"meta":832,"style":832},"language-ts shiki shiki-themes material-theme-lighter material-theme material-theme-palenight","import { createRequestLogger } from 'evlog\u002Ftoolkit'\n\nasync function processJob(job: Job) {\n  const logger = createRequestLogger({\n    service: 'jobs',\n    context: { jobId: job.id, queue: job.queue },\n  })\n\n  try {\n    await runJob(job)\n    logger.set({ status: 'success' })\n  } catch (err) {\n    logger.error(err)\n    throw err\n  } finally {\n    await logger.emit()\n  }\n}\n","ts",[545,2620,2621,2640,2644,2668,2683,2699,2737,2743,2747,2754,2768,2797,2812,2826,2834,2843,2856,2860],{"__ignoreMap":832},[836,2622,2623,2625,2627,2630,2632,2634,2636,2638],{"class":838,"line":839},[836,2624,1165],{"class":1164},[836,2626,1172],{"class":1171},[836,2628,2629],{"class":1175}," createRequestLogger",[836,2631,1185],{"class":1171},[836,2633,1188],{"class":1164},[836,2635,1191],{"class":1171},[836,2637,551],{"class":845},[836,2639,1197],{"class":1171},[836,2641,2642],{"class":838,"line":1200},[836,2643,1283],{"emptyLinePlaceholder":1282},[836,2645,2646,2649,2651,2654,2656,2659,2661,2664,2666],{"class":838,"line":1208},[836,2647,2648],{"class":1292},"async",[836,2650,1694],{"class":1292},[836,2652,2653],{"class":1329}," processJob",[836,2655,1402],{"class":1171},[836,2657,2658],{"class":1438},"job",[836,2660,1415],{"class":1171},[836,2662,2663],{"class":842}," Job",[836,2665,637],{"class":1171},[836,2667,1205],{"class":1171},[836,2669,2670,2673,2675,2677,2679,2681],{"class":838,"line":1217},[836,2671,2672],{"class":1292},"  const",[836,2674,1615],{"class":1175},[836,2676,1298],{"class":1171},[836,2678,2629],{"class":1329},[836,2680,1402],{"class":1411},[836,2682,1405],{"class":1171},[836,2684,2685,2688,2690,2692,2695,2697],{"class":838,"line":1225},[836,2686,2687],{"class":1411},"    service",[836,2689,1415],{"class":1171},[836,2691,1191],{"class":1171},[836,2693,2694],{"class":845},"jobs",[836,2696,1345],{"class":1171},[836,2698,1214],{"class":1171},[836,2700,2701,2704,2706,2708,2711,2713,2716,2718,2721,2723,2726,2728,2730,2732,2735],{"class":838,"line":1236},[836,2702,2703],{"class":1411},"    context",[836,2705,1415],{"class":1171},[836,2707,1172],{"class":1171},[836,2709,2710],{"class":1411}," jobId",[836,2712,1415],{"class":1171},[836,2714,2715],{"class":1175}," job",[836,2717,1462],{"class":1171},[836,2719,2720],{"class":1175},"id",[836,2722,1179],{"class":1171},[836,2724,2725],{"class":1411}," queue",[836,2727,1415],{"class":1171},[836,2729,2715],{"class":1175},[836,2731,1462],{"class":1171},[836,2733,2734],{"class":1175},"queue",[836,2736,2443],{"class":1171},[836,2738,2739,2741],{"class":838,"line":1250},[836,2740,1594],{"class":1171},[836,2742,1353],{"class":1411},[836,2744,2745],{"class":838,"line":1257},[836,2746,1283],{"emptyLinePlaceholder":1282},[836,2748,2749,2752],{"class":838,"line":1279},[836,2750,2751],{"class":1164},"  try",[836,2753,1205],{"class":1171},[836,2755,2756,2759,2762,2764,2766],{"class":838,"line":1286},[836,2757,2758],{"class":1164},"    await",[836,2760,2761],{"class":1329}," runJob",[836,2763,1402],{"class":1411},[836,2765,2658],{"class":1175},[836,2767,1353],{"class":1411},[836,2769,2770,2773,2775,2778,2780,2782,2784,2786,2788,2791,2793,2795],{"class":838,"line":1304},[836,2771,2772],{"class":1175},"    logger",[836,2774,1462],{"class":1171},[836,2776,2777],{"class":1329},"set",[836,2779,1402],{"class":1411},[836,2781,1886],{"class":1171},[836,2783,1889],{"class":1411},[836,2785,1415],{"class":1171},[836,2787,1191],{"class":1171},[836,2789,2790],{"class":845},"success",[836,2792,1345],{"class":1171},[836,2794,1185],{"class":1171},[836,2796,1353],{"class":1411},[836,2798,2799,2801,2803,2805,2808,2810],{"class":838,"line":1309},[836,2800,1594],{"class":1171},[836,2802,1911],{"class":1164},[836,2804,1435],{"class":1411},[836,2806,2807],{"class":1175},"err",[836,2809,1822],{"class":1411},[836,2811,1405],{"class":1171},[836,2813,2814,2816,2818,2820,2822,2824],{"class":838,"line":1336},[836,2815,2772],{"class":1175},[836,2817,1462],{"class":1171},[836,2819,1916],{"class":1329},[836,2821,1402],{"class":1411},[836,2823,2807],{"class":1175},[836,2825,1353],{"class":1411},[836,2827,2828,2831],{"class":838,"line":1350},[836,2829,2830],{"class":1164},"    throw",[836,2832,2833],{"class":1175}," err\n",[836,2835,2836,2838,2841],{"class":838,"line":1356},[836,2837,1594],{"class":1171},[836,2839,2840],{"class":1164}," finally",[836,2842,1205],{"class":1171},[836,2844,2845,2847,2849,2851,2854],{"class":838,"line":1361},[836,2846,2758],{"class":1164},[836,2848,1615],{"class":1175},[836,2850,1462],{"class":1171},[836,2852,2853],{"class":1329},"emit",[836,2855,1835],{"class":1411},[836,2857,2858],{"class":838,"line":1374},[836,2859,1967],{"class":1171},[836,2861,2862],{"class":838,"line":1379},[836,2863,1973],{"class":1171},[541,2865,2866,2867,2870],{},"Same enrichers, same drain hook, same ",[599,2868,2869],{"href":486},"identity headers"," on outbound HTTP drain requests. Only the entry point shape changes.",[818,2872,2874],{"id":2873},"reference-implementations","Reference implementations",[541,2876,2877],{},"Study these built-in integrations for framework-specific patterns:",[572,2879,2880,2896],{},[575,2881,2882],{},[578,2883,2884,2887,2890,2893],{},[581,2885,2886],{},"Framework",[581,2888,2889],{},"Lines",[581,2891,2892],{},"Mode",[581,2894,2895],{},"Source",[591,2897,2898,2915,2931,2948,2965,2982],{},[578,2899,2900,2902,2905,2908],{},[596,2901,265],{},[596,2903,2904],{},"~50",[596,2906,2907],{},"manifest",[596,2909,2910],{},[599,2911,2914],{"href":2912,"rel":2913},"https:\u002F\u002Fgithub.com\u002Fhugorcd\u002Fevlog\u002Fblob\u002Fmain\u002Fpackages\u002Fevlog\u002Fsrc\u002Fhono\u002Findex.ts",[816],"hono\u002Findex.ts",[578,2916,2917,2919,2921,2924],{},[596,2918,260],{},[596,2920,2904],{},[596,2922,2923],{},"manifest + ALS",[596,2925,2926],{},[599,2927,2930],{"href":2928,"rel":2929},"https:\u002F\u002Fgithub.com\u002Fhugorcd\u002Fevlog\u002Fblob\u002Fmain\u002Fpackages\u002Fevlog\u002Fsrc\u002Fexpress\u002Findex.ts",[816],"express\u002Findex.ts",[578,2932,2933,2935,2938,2941],{},[596,2934,270],{},[596,2936,2937],{},"~70",[596,2939,2940],{},"manifest + Fastify hooks",[596,2942,2943],{},[599,2944,2947],{"href":2945,"rel":2946},"https:\u002F\u002Fgithub.com\u002Fhugorcd\u002Fevlog\u002Fblob\u002Fmain\u002Fpackages\u002Fevlog\u002Fsrc\u002Ffastify\u002Findex.ts",[816],"fastify\u002Findex.ts",[578,2949,2950,2952,2955,2958],{},[596,2951,275],{},[596,2953,2954],{},"~80",[596,2956,2957],{},"manifest + custom ALS scoping",[596,2959,2960],{},[599,2961,2964],{"href":2962,"rel":2963},"https:\u002F\u002Fgithub.com\u002Fhugorcd\u002Fevlog\u002Fblob\u002Fmain\u002Fpackages\u002Fevlog\u002Fsrc\u002Felysia\u002Findex.ts",[816],"elysia\u002Findex.ts",[578,2966,2967,2969,2972,2975],{},[596,2968,255],{},[596,2970,2971],{},"~120",[596,2973,2974],{},"custom (interceptor)",[596,2976,2977],{},[599,2978,2981],{"href":2979,"rel":2980},"https:\u002F\u002Fgithub.com\u002Fhugorcd\u002Fevlog\u002Fblob\u002Fmain\u002Fpackages\u002Fevlog\u002Fsrc\u002Fnestjs\u002F",[816],"nestjs\u002F",[578,2983,2984,2986,2989,2995],{},[596,2985,240],{},[596,2987,2988],{},"~90",[596,2990,2991,2992,2994],{},"custom (",[545,2993,636],{}," hook)",[596,2996,2997],{},[599,2998,3001],{"href":2999,"rel":3000},"https:\u002F\u002Fgithub.com\u002Fhugorcd\u002Fevlog\u002Fblob\u002Fmain\u002Fpackages\u002Fevlog\u002Fsrc\u002Fsveltekit\u002F",[816],"sveltekit\u002F",[562,3003,3006,3007,3012],{"color":3004,"icon":3005},"neutral","i-lucide-heart","Built an integration for a framework we don't support? ",[599,3008,3011],{"href":3009,"rel":3010},"https:\u002F\u002Fgithub.com\u002Fhugorcd\u002Fevlog\u002Fpulls",[816],"Open a PR",". The community will thank you.",[818,3014,3016],{"id":3015},"next-steps","Next steps",[663,3018,3019,3025,3031,3036,3041,3046],{},[666,3020,3021,3024],{},[599,3022,3023],{"href":491},"Custom Drains"," — same toolkit shape for drain destinations",[666,3026,3027,3030],{},[599,3028,3029],{"href":478},"Custom Enrichers"," — same toolkit shape for derived event fields",[666,3032,3033,3035],{},[599,3034,473],{"href":474}," — multi-hook extensions (drain + enrich + keep in one object)",[666,3037,3038,3040],{},[599,3039,46],{"href":47}," — design comprehensive events with context layering",[666,3042,3043,3045],{},[599,3044,61],{"href":62}," — control log volume with head and tail sampling",[666,3047,3048,3050],{},[599,3049,138],{"href":143}," — send logs to Axiom, Sentry, PostHog, and more",[3052,3053,3054],"style",{},"html pre.shiki code .sBMFI, html code.shiki .sBMFI{--shiki-light:#E2931D;--shiki-default:#FFCB6B;--shiki-dark:#FFCB6B}html pre.shiki code .sfazB, html code.shiki .sfazB{--shiki-light:#91B859;--shiki-default:#C3E88D;--shiki-dark:#C3E88D}html .light .shiki span {color: var(--shiki-light);background: var(--shiki-light-bg);font-style: var(--shiki-light-font-style);font-weight: var(--shiki-light-font-weight);text-decoration: var(--shiki-light-text-decoration);}html.light .shiki span {color: var(--shiki-light);background: var(--shiki-light-bg);font-style: var(--shiki-light-font-style);font-weight: var(--shiki-light-font-weight);text-decoration: var(--shiki-light-text-decoration);}html .default .shiki span {color: var(--shiki-default);background: var(--shiki-default-bg);font-style: var(--shiki-default-font-style);font-weight: var(--shiki-default-font-weight);text-decoration: var(--shiki-default-text-decoration);}html .shiki span {color: var(--shiki-default);background: var(--shiki-default-bg);font-style: var(--shiki-default-font-style);font-weight: var(--shiki-default-font-weight);text-decoration: var(--shiki-default-text-decoration);}html .dark .shiki span {color: var(--shiki-dark);background: var(--shiki-dark-bg);font-style: var(--shiki-dark-font-style);font-weight: var(--shiki-dark-font-weight);text-decoration: var(--shiki-dark-text-decoration);}html.dark .shiki span {color: var(--shiki-dark);background: var(--shiki-dark-bg);font-style: var(--shiki-dark-font-style);font-weight: var(--shiki-dark-font-weight);text-decoration: var(--shiki-dark-text-decoration);}html pre.shiki code .s7zQu, html code.shiki .s7zQu{--shiki-light:#39ADB5;--shiki-light-font-style:italic;--shiki-default:#89DDFF;--shiki-default-font-style:italic;--shiki-dark:#89DDFF;--shiki-dark-font-style:italic}html pre.shiki code .sMK4o, html code.shiki .sMK4o{--shiki-light:#39ADB5;--shiki-default:#89DDFF;--shiki-dark:#89DDFF}html pre.shiki code .sTEyZ, html code.shiki .sTEyZ{--shiki-light:#90A4AE;--shiki-default:#EEFFFF;--shiki-dark:#BABED8}html pre.shiki code .sHwdD, html code.shiki .sHwdD{--shiki-light:#90A4AE;--shiki-light-font-style:italic;--shiki-default:#546E7A;--shiki-default-font-style:italic;--shiki-dark:#676E95;--shiki-dark-font-style:italic}html pre.shiki code .spNyl, html code.shiki .spNyl{--shiki-light:#9C3EDA;--shiki-default:#C792EA;--shiki-dark:#C792EA}html pre.shiki code .s2Zo4, html code.shiki .s2Zo4{--shiki-light:#6182B8;--shiki-default:#82AAFF;--shiki-dark:#82AAFF}html pre.shiki code .swJcz, html code.shiki .swJcz{--shiki-light:#E53935;--shiki-default:#F07178;--shiki-dark:#F07178}html pre.shiki code .sHdIc, html code.shiki .sHdIc{--shiki-light:#90A4AE;--shiki-light-font-style:italic;--shiki-default:#EEFFFF;--shiki-default-font-style:italic;--shiki-dark:#BABED8;--shiki-dark-font-style:italic}",{"title":832,"searchDepth":1200,"depth":1200,"links":3056},[3057,3058,3059,3063,3064,3065,3066,3067],{"id":820,"depth":1200,"text":821},{"id":895,"depth":1200,"text":896},{"id":1138,"depth":1200,"text":1139,"children":3060},[3061],{"id":1983,"depth":1208,"text":3062},"What defineFrameworkIntegration does",{"id":2056,"depth":1200,"text":2057},{"id":2196,"depth":1200,"text":2197},{"id":2605,"depth":1200,"text":2606},{"id":2873,"depth":1200,"text":2874},{"id":3015,"depth":1200,"text":3016},"Build evlog support for an HTTP framework (or non-HTTP runtime) without a built-in integration. Use defineFrameworkIntegration for the (ctx, next) middleware shape, or createMiddlewareLogger \u002F createRequestLogger for everything else.","md",[3071,3073],{"label":3023,"icon":493,"to":491,"color":3004,"variant":3072},"subtle",{"label":3029,"icon":434,"to":478,"color":3004,"variant":3072},{},{"title":455,"icon":458},{"title":536,"description":3068},"Y_7My-WvB0CIHtS81EDliLWaa2AByhGJ5I32u3NrSl8",[3079,3081],{"title":450,"path":451,"stem":452,"description":3080,"icon":453,"children":-1},"Subscribe to wide events flowing through evlog — in-process with createStreamDrain, or over the network with the local SSE stream server.",{"title":460,"path":461,"stem":462,"description":3082,"icon":453,"children":-1},"Publish every wide event on a node:diagnostics_channel so any consumer can subscribe without importing evlog — and so Cloudflare forwards them to a Tail Worker with no drain.",1786792897836]