import { describe, expect, test } from "bun:test"; import { MetricsRegistry } from "../src/metrics.ts"; import { createOperationTracer, createOtlpLogExporter, createPerformanceProfiler, createPrometheusPushExporter, createSentryCompatibleReporter, createZipkinExporter, renderPrometheus, } from "../src/integrations.ts"; describe("observability integrations", () => { test("records every framework operation kind and failures", async () => { const spans: any[] = []; const tracer = createOperationTracer({ exporter: { export: (records) => { spans.push(...records); }, }, now: (() => { let time = 0; return () => (time += 5); })(), }); for (const kind of [ "database", "cache", "queue", "realtime", "server-action", "application", ] as const) expect(await tracer.span(kind, `${kind}.work`, async () => kind)).toBe(kind); await expect( tracer.span("application", "failure", async () => { throw new Error("boom"); }), ).rejects.toThrow("boom"); expect(spans.map((span) => span.attributes["wrnexus.span.kind"])).toContain("database"); expect(spans.at(-1).status).toBe("error"); }); test("exports Prometheus, Zipkin/Jaeger, OTLP logs and Sentry-compatible errors", async () => { const requests: Array<{ url: string; init?: RequestInit }> = []; const send = (async (url: URL | RequestInfo, init?: RequestInit) => { requests.push({ url: String(url), init }); return new Response(null, { status: 200 }); }) as typeof fetch; const registry = new MetricsRegistry(() => 10); registry.increment("http.requests", 1, { route: "/" }); expect(renderPrometheus(registry.snapshot())).toContain('http_requests{route="/"} 1'); await createPrometheusPushExporter("https://prom.test", { fetch: send }).export( registry.snapshot(), ); const span = { name: "db", traceId: "1".repeat(32), spanId: "2".repeat(16), sampled: true, startTime: 1, endTime: 2, durationMs: 1, status: "ok" as const, attributes: {}, }; await createZipkinExporter("https://zipkin.test", { fetch: send }).export([span]); await createOtlpLogExporter("https://otlp.test", { fetch: send }).export([ { timestamp: new Date(0).toISOString(), level: "info", message: "ready", service: "app", attributes: {}, }, ]); expect( await createSentryCompatibleReporter("https://sentry.test", { fetch: send }).capture( new Error("bad"), ), ).toHaveLength(32); expect(requests).toHaveLength(4); }); test("profiles application operations", async () => { const profiles: any[] = []; let time = 0; const profile = createPerformanceProfiler({ now: () => (time += 4), onProfile: (value) => profiles.push(value), }); expect(await profile("render", () => "ok")).toBe("ok"); expect(profiles[0]).toMatchObject({ name: "render", durationMs: 4 }); }); test("operation exporter failures reach diagnostics without recursive telemetry", async () => { const diagnostics: string[] = []; const tracer = createOperationTracer({ exporter: { export: () => Promise.reject(new Error("offline")) }, diagnostic: (message) => diagnostics.push(message), }); await expect(tracer.span("database", "query", async () => 1)).resolves.toBe(1); expect(diagnostics).toEqual(["operation span export failed"]); }); });