@smoothbricks/lmao 0.1.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +269 -0
- package/dist/allocator.wasm +0 -0
- package/dist/bun/preload.d.ts +11 -0
- package/dist/bun/preload.d.ts.map +1 -0
- package/dist/bun/preload.js +10 -0
- package/dist/bun/trace-preload.d.ts +8 -0
- package/dist/bun/trace-preload.d.ts.map +1 -0
- package/dist/bun/trace-preload.js +12 -0
- package/dist/es.d.ts +8 -0
- package/dist/es.d.ts.map +1 -0
- package/dist/es.js +9 -0
- package/dist/index.d.ts +41 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +84 -0
- package/dist/lib/JsBufferStrategy.d.ts +49 -0
- package/dist/lib/JsBufferStrategy.d.ts.map +1 -0
- package/dist/lib/JsBufferStrategy.js +60 -0
- package/dist/lib/archive/chunkCompaction.d.ts +15 -0
- package/dist/lib/archive/chunkCompaction.d.ts.map +1 -0
- package/dist/lib/archive/chunkCompaction.js +24 -0
- package/dist/lib/archive/chunkEnvelope.d.ts +21 -0
- package/dist/lib/archive/chunkEnvelope.d.ts.map +1 -0
- package/dist/lib/archive/chunkEnvelope.js +55 -0
- package/dist/lib/archive/chunkRouting.d.ts +10 -0
- package/dist/lib/archive/chunkRouting.d.ts.map +1 -0
- package/dist/lib/archive/chunkRouting.js +47 -0
- package/dist/lib/archive/chunkStats.d.ts +12 -0
- package/dist/lib/archive/chunkStats.d.ts.map +1 -0
- package/dist/lib/archive/chunkStats.js +10 -0
- package/dist/lib/archive/index.d.ts +5 -0
- package/dist/lib/archive/index.d.ts.map +1 -0
- package/dist/lib/archive/index.js +4 -0
- package/dist/lib/arrow/capacityStats.d.ts +9 -0
- package/dist/lib/arrow/capacityStats.d.ts.map +1 -0
- package/dist/lib/arrow/capacityStats.js +231 -0
- package/dist/lib/arrow/dictionaries.d.ts +27 -0
- package/dist/lib/arrow/dictionaries.d.ts.map +1 -0
- package/dist/lib/arrow/dictionaries.js +135 -0
- package/dist/lib/arrow/flechette.d.ts +40 -0
- package/dist/lib/arrow/flechette.d.ts.map +1 -0
- package/dist/lib/arrow/flechette.js +67 -0
- package/dist/lib/arrow/utils.d.ts +38 -0
- package/dist/lib/arrow/utils.d.ts.map +1 -0
- package/dist/lib/arrow/utils.js +112 -0
- package/dist/lib/buffer/Nanoseconds.d.ts +109 -0
- package/dist/lib/buffer/Nanoseconds.d.ts.map +1 -0
- package/dist/lib/buffer/Nanoseconds.js +86 -0
- package/dist/lib/bufferStrategy.d.ts +95 -0
- package/dist/lib/bufferStrategy.d.ts.map +1 -0
- package/dist/lib/bufferStrategy.js +1 -0
- package/dist/lib/capacityTuning.d.ts +50 -0
- package/dist/lib/capacityTuning.d.ts.map +1 -0
- package/dist/lib/capacityTuning.js +65 -0
- package/dist/lib/codegen/evaluatorGenerator.d.ts +35 -0
- package/dist/lib/codegen/evaluatorGenerator.d.ts.map +1 -0
- package/dist/lib/codegen/evaluatorGenerator.js +199 -0
- package/dist/lib/codegen/fixedPositionWriterGenerator.d.ts +139 -0
- package/dist/lib/codegen/fixedPositionWriterGenerator.d.ts.map +1 -0
- package/dist/lib/codegen/fixedPositionWriterGenerator.js +289 -0
- package/dist/lib/codegen/spanLoggerGenerator.d.ts +115 -0
- package/dist/lib/codegen/spanLoggerGenerator.d.ts.map +1 -0
- package/dist/lib/codegen/spanLoggerGenerator.js +575 -0
- package/dist/lib/convertToArrow.d.ts +40 -0
- package/dist/lib/convertToArrow.d.ts.map +1 -0
- package/dist/lib/convertToArrow.js +1467 -0
- package/dist/lib/defineOpContext.d.ts +96 -0
- package/dist/lib/defineOpContext.d.ts.map +1 -0
- package/dist/lib/defineOpContext.js +227 -0
- package/dist/lib/errors/Blocked.d.ts +113 -0
- package/dist/lib/errors/Blocked.d.ts.map +1 -0
- package/dist/lib/errors/Blocked.js +68 -0
- package/dist/lib/errors/CodeError.d.ts +101 -0
- package/dist/lib/errors/CodeError.d.ts.map +1 -0
- package/dist/lib/errors/CodeError.js +42 -0
- package/dist/lib/errors/RetriesExhausted.d.ts +67 -0
- package/dist/lib/errors/RetriesExhausted.d.ts.map +1 -0
- package/dist/lib/errors/RetriesExhausted.js +31 -0
- package/dist/lib/errors/Transient.d.ts +115 -0
- package/dist/lib/errors/Transient.d.ts.map +1 -0
- package/dist/lib/errors/Transient.js +54 -0
- package/dist/lib/errors/index.d.ts +14 -0
- package/dist/lib/errors/index.d.ts.map +1 -0
- package/dist/lib/errors/index.js +16 -0
- package/dist/lib/errors/retry-policy.d.ts +60 -0
- package/dist/lib/errors/retry-policy.d.ts.map +1 -0
- package/dist/lib/errors/retry-policy.js +54 -0
- package/dist/lib/flushScheduler.d.ts +162 -0
- package/dist/lib/flushScheduler.d.ts.map +1 -0
- package/dist/lib/flushScheduler.js +388 -0
- package/dist/lib/library.d.ts +149 -0
- package/dist/lib/library.d.ts.map +1 -0
- package/dist/lib/library.js +588 -0
- package/dist/lib/logApi.d.ts +61 -0
- package/dist/lib/logApi.d.ts.map +1 -0
- package/dist/lib/logApi.js +12 -0
- package/dist/lib/logBinding.d.ts +63 -0
- package/dist/lib/logBinding.d.ts.map +1 -0
- package/dist/lib/logBinding.js +1 -0
- package/dist/lib/op.d.ts +105 -0
- package/dist/lib/op.d.ts.map +1 -0
- package/dist/lib/op.js +59 -0
- package/dist/lib/opContext/contextTypes.d.ts +88 -0
- package/dist/lib/opContext/contextTypes.d.ts.map +1 -0
- package/dist/lib/opContext/contextTypes.js +34 -0
- package/dist/lib/opContext/createOpGroup.d.ts +57 -0
- package/dist/lib/opContext/createOpGroup.d.ts.map +1 -0
- package/dist/lib/opContext/createOpGroup.js +341 -0
- package/dist/lib/opContext/defineOp.d.ts +83 -0
- package/dist/lib/opContext/defineOp.d.ts.map +1 -0
- package/dist/lib/opContext/defineOp.js +197 -0
- package/dist/lib/opContext/featureFlagTypes.d.ts +58 -0
- package/dist/lib/opContext/featureFlagTypes.d.ts.map +1 -0
- package/dist/lib/opContext/featureFlagTypes.js +1 -0
- package/dist/lib/opContext/index.d.ts +13 -0
- package/dist/lib/opContext/index.d.ts.map +1 -0
- package/dist/lib/opContext/index.js +15 -0
- package/dist/lib/opContext/opGroupTypes.d.ts +250 -0
- package/dist/lib/opContext/opGroupTypes.d.ts.map +1 -0
- package/dist/lib/opContext/opGroupTypes.js +31 -0
- package/dist/lib/opContext/opTypes.d.ts +48 -0
- package/dist/lib/opContext/opTypes.d.ts.map +1 -0
- package/dist/lib/opContext/opTypes.js +7 -0
- package/dist/lib/opContext/spanContextTypes.d.ts +347 -0
- package/dist/lib/opContext/spanContextTypes.d.ts.map +1 -0
- package/dist/lib/opContext/spanContextTypes.js +1 -0
- package/dist/lib/opContext/types.d.ts +297 -0
- package/dist/lib/opContext/types.d.ts.map +1 -0
- package/dist/lib/opContext/types.js +16 -0
- package/dist/lib/result.d.ts +308 -0
- package/dist/lib/result.d.ts.map +1 -0
- package/dist/lib/result.js +359 -0
- package/dist/lib/schema/LogSchema.d.ts +62 -0
- package/dist/lib/schema/LogSchema.d.ts.map +1 -0
- package/dist/lib/schema/LogSchema.js +134 -0
- package/dist/lib/schema/builder.d.ts +12 -0
- package/dist/lib/schema/builder.d.ts.map +1 -0
- package/dist/lib/schema/builder.js +169 -0
- package/dist/lib/schema/defineFeatureFlags.d.ts +60 -0
- package/dist/lib/schema/defineFeatureFlags.d.ts.map +1 -0
- package/dist/lib/schema/defineFeatureFlags.js +29 -0
- package/dist/lib/schema/defineLogSchema.d.ts +87 -0
- package/dist/lib/schema/defineLogSchema.d.ts.map +1 -0
- package/dist/lib/schema/defineLogSchema.js +171 -0
- package/dist/lib/schema/evaluator.d.ts +267 -0
- package/dist/lib/schema/evaluator.d.ts.map +1 -0
- package/dist/lib/schema/evaluator.js +169 -0
- package/dist/lib/schema/extend.d.ts +14 -0
- package/dist/lib/schema/extend.d.ts.map +1 -0
- package/dist/lib/schema/extend.js +51 -0
- package/dist/lib/schema/systemSchema.d.ts +112 -0
- package/dist/lib/schema/systemSchema.d.ts.map +1 -0
- package/dist/lib/schema/systemSchema.js +260 -0
- package/dist/lib/schema/typeGuards.d.ts +52 -0
- package/dist/lib/schema/typeGuards.d.ts.map +1 -0
- package/dist/lib/schema/typeGuards.js +127 -0
- package/dist/lib/schema/types.d.ts +156 -0
- package/dist/lib/schema/types.d.ts.map +1 -0
- package/dist/lib/schema/types.js +4 -0
- package/dist/lib/spanBuffer.d.ts +133 -0
- package/dist/lib/spanBuffer.d.ts.map +1 -0
- package/dist/lib/spanBuffer.js +442 -0
- package/dist/lib/spanBufferHelpers.d.ts +53 -0
- package/dist/lib/spanBufferHelpers.d.ts.map +1 -0
- package/dist/lib/spanBufferHelpers.js +65 -0
- package/dist/lib/spanBufferStats.d.ts +38 -0
- package/dist/lib/spanBufferStats.d.ts.map +1 -0
- package/dist/lib/spanBufferStats.js +1 -0
- package/dist/lib/spanContext.d.ts +141 -0
- package/dist/lib/spanContext.d.ts.map +1 -0
- package/dist/lib/spanContext.js +763 -0
- package/dist/lib/sqlite/index.d.ts +14 -0
- package/dist/lib/sqlite/index.d.ts.map +1 -0
- package/dist/lib/sqlite/index.js +12 -0
- package/dist/lib/sqlite/sqlite-async-writer.d.ts +24 -0
- package/dist/lib/sqlite/sqlite-async-writer.d.ts.map +1 -0
- package/dist/lib/sqlite/sqlite-async-writer.js +65 -0
- package/dist/lib/sqlite/sqlite-common.d.ts +37 -0
- package/dist/lib/sqlite/sqlite-common.d.ts.map +1 -0
- package/dist/lib/sqlite/sqlite-common.js +207 -0
- package/dist/lib/sqlite/sqlite-d1.d.ts +25 -0
- package/dist/lib/sqlite/sqlite-d1.d.ts.map +1 -0
- package/dist/lib/sqlite/sqlite-d1.js +67 -0
- package/dist/lib/sqlite/sqlite-db.d.ts +29 -0
- package/dist/lib/sqlite/sqlite-db.d.ts.map +1 -0
- package/dist/lib/sqlite/sqlite-db.js +1 -0
- package/dist/lib/sqlite/sqlite-node.d.ts +16 -0
- package/dist/lib/sqlite/sqlite-node.d.ts.map +1 -0
- package/dist/lib/sqlite/sqlite-node.js +68 -0
- package/dist/lib/sqlite/sqlite-writer.d.ts +39 -0
- package/dist/lib/sqlite/sqlite-writer.d.ts.map +1 -0
- package/dist/lib/sqlite/sqlite-writer.js +78 -0
- package/dist/lib/testing/bun-harness.d.ts +150 -0
- package/dist/lib/testing/bun-harness.d.ts.map +1 -0
- package/dist/lib/testing/bun-harness.js +729 -0
- package/dist/lib/testing/extractFacts.d.ts +73 -0
- package/dist/lib/testing/extractFacts.d.ts.map +1 -0
- package/dist/lib/testing/extractFacts.js +237 -0
- package/dist/lib/testing/facts.d.ts +235 -0
- package/dist/lib/testing/facts.d.ts.map +1 -0
- package/dist/lib/testing/facts.js +209 -0
- package/dist/lib/testing/index.d.ts +58 -0
- package/dist/lib/testing/index.d.ts.map +1 -0
- package/dist/lib/testing/index.js +74 -0
- package/dist/lib/testing/queryable-span.d.ts +39 -0
- package/dist/lib/testing/queryable-span.d.ts.map +1 -0
- package/dist/lib/testing/queryable-span.js +58 -0
- package/dist/lib/testing/span-query.d.ts +21 -0
- package/dist/lib/testing/span-query.d.ts.map +1 -0
- package/dist/lib/testing/span-query.js +47 -0
- package/dist/lib/testing/stdio-replay.d.ts +4 -0
- package/dist/lib/testing/stdio-replay.d.ts.map +1 -0
- package/dist/lib/testing/stdio-replay.js +42 -0
- package/dist/lib/testing/trace-query.d.ts +59 -0
- package/dist/lib/testing/trace-query.d.ts.map +1 -0
- package/dist/lib/testing/trace-query.js +462 -0
- package/dist/lib/testing/vitest-harness.d.ts +135 -0
- package/dist/lib/testing/vitest-harness.d.ts.map +1 -0
- package/dist/lib/testing/vitest-harness.js +486 -0
- package/dist/lib/threadId.d.ts +58 -0
- package/dist/lib/threadId.d.ts.map +1 -0
- package/dist/lib/threadId.js +123 -0
- package/dist/lib/traceContext.d.ts +116 -0
- package/dist/lib/traceContext.d.ts.map +1 -0
- package/dist/lib/traceContext.js +37 -0
- package/dist/lib/traceId.d.ts +78 -0
- package/dist/lib/traceId.d.ts.map +1 -0
- package/dist/lib/traceId.js +87 -0
- package/dist/lib/traceRoot.d.ts +133 -0
- package/dist/lib/traceRoot.d.ts.map +1 -0
- package/dist/lib/traceRoot.es.d.ts +75 -0
- package/dist/lib/traceRoot.es.d.ts.map +1 -0
- package/dist/lib/traceRoot.es.js +129 -0
- package/dist/lib/traceRoot.js +19 -0
- package/dist/lib/traceRoot.node.d.ts +77 -0
- package/dist/lib/traceRoot.node.d.ts.map +1 -0
- package/dist/lib/traceRoot.node.js +133 -0
- package/dist/lib/traceRoot.universal.d.ts +3 -0
- package/dist/lib/traceRoot.universal.d.ts.map +1 -0
- package/dist/lib/traceRoot.universal.js +17 -0
- package/dist/lib/tracer.d.ts +296 -0
- package/dist/lib/tracer.d.ts.map +1 -0
- package/dist/lib/tracer.js +346 -0
- package/dist/lib/tracers/ArrayQueueTracer.d.ts +56 -0
- package/dist/lib/tracers/ArrayQueueTracer.d.ts.map +1 -0
- package/dist/lib/tracers/ArrayQueueTracer.js +67 -0
- package/dist/lib/tracers/CompositeTracer.d.ts +24 -0
- package/dist/lib/tracers/CompositeTracer.d.ts.map +1 -0
- package/dist/lib/tracers/CompositeTracer.js +57 -0
- package/dist/lib/tracers/NoOpTracer.d.ts +58 -0
- package/dist/lib/tracers/NoOpTracer.d.ts.map +1 -0
- package/dist/lib/tracers/NoOpTracer.js +41 -0
- package/dist/lib/tracers/SQLiteTracer.d.ts +42 -0
- package/dist/lib/tracers/SQLiteTracer.d.ts.map +1 -0
- package/dist/lib/tracers/SQLiteTracer.js +84 -0
- package/dist/lib/tracers/StdioTracer.d.ts +83 -0
- package/dist/lib/tracers/StdioTracer.d.ts.map +1 -0
- package/dist/lib/tracers/StdioTracer.js +270 -0
- package/dist/lib/tracers/TestTracer.d.ts +95 -0
- package/dist/lib/tracers/TestTracer.d.ts.map +1 -0
- package/dist/lib/tracers/TestTracer.js +87 -0
- package/dist/lib/tracers/index.d.ts +12 -0
- package/dist/lib/tracers/index.d.ts.map +1 -0
- package/dist/lib/tracers/index.js +11 -0
- package/dist/lib/types.d.ts +366 -0
- package/dist/lib/types.d.ts.map +1 -0
- package/dist/lib/types.js +1 -0
- package/dist/lib/utf8Cache.d.ts +111 -0
- package/dist/lib/utf8Cache.d.ts.map +1 -0
- package/dist/lib/utf8Cache.js +177 -0
- package/dist/lib/wasm/WasmBufferStrategy.d.ts +88 -0
- package/dist/lib/wasm/WasmBufferStrategy.d.ts.map +1 -0
- package/dist/lib/wasm/WasmBufferStrategy.js +138 -0
- package/dist/lib/wasm/wasmAllocator.d.ts +109 -0
- package/dist/lib/wasm/wasmAllocator.d.ts.map +1 -0
- package/dist/lib/wasm/wasmAllocator.js +227 -0
- package/dist/lib/wasm/wasmSpanBuffer.d.ts +123 -0
- package/dist/lib/wasm/wasmSpanBuffer.d.ts.map +1 -0
- package/dist/lib/wasm/wasmSpanBuffer.js +772 -0
- package/dist/lib/wasm/wasmTraceRoot.d.ts +167 -0
- package/dist/lib/wasm/wasmTraceRoot.d.ts.map +1 -0
- package/dist/lib/wasm/wasmTraceRoot.js +264 -0
- package/dist/node.d.ts +7 -0
- package/dist/node.d.ts.map +1 -0
- package/dist/node.js +8 -0
- package/dist/testing.d.ts +18 -0
- package/dist/testing.d.ts.map +1 -0
- package/dist/testing.js +17 -0
- package/package.json +193 -0
- package/src/bun/preload.ts +11 -0
- package/src/bun/trace-preload.ts +14 -0
- package/src/es.ts +11 -0
- package/src/index.ts +194 -0
- package/src/lib/JsBufferStrategy.ts +102 -0
- package/src/lib/__tests__/arrow-builder-integration/arrow-conversion.test.ts +485 -0
- package/src/lib/__tests__/arrow-builder-integration/binary-arrow-conversion.test.ts +390 -0
- package/src/lib/__tests__/arrow-builder-integration/binary-comparison.test.ts +647 -0
- package/src/lib/__tests__/arrow-builder-integration/binary-format-compliance.test.ts +292 -0
- package/src/lib/__tests__/arrow-builder-integration/buffer-chaining.test.ts +354 -0
- package/src/lib/__tests__/arrow-builder-integration/foundation.test.ts +127 -0
- package/src/lib/__tests__/arrow-builder-integration/integration.test.ts +392 -0
- package/src/lib/__tests__/arrow-builder-integration/lazy-columns.test.ts +389 -0
- package/src/lib/__tests__/arrow-conversion-algorithms.test.ts +54 -0
- package/src/lib/__tests__/arrow-test-helpers.ts +71 -0
- package/src/lib/__tests__/binary-e2e.test.ts +203 -0
- package/src/lib/__tests__/buffer-overflow-op-api.test.ts +608 -0
- package/src/lib/__tests__/buffer-overflow.test.ts +612 -0
- package/src/lib/__tests__/capacity-tuning.test.ts +544 -0
- package/src/lib/__tests__/effective-schema.test.ts +439 -0
- package/src/lib/__tests__/flechette.test.ts +42 -0
- package/src/lib/__tests__/flushScheduler.test.ts +537 -0
- package/src/lib/__tests__/integration.test.ts +600 -0
- package/src/lib/__tests__/library.test.ts +934 -0
- package/src/lib/__tests__/nested-library-tasks.test.ts +849 -0
- package/src/lib/__tests__/op-context-binding.test.ts +135 -0
- package/src/lib/__tests__/op-metadata.test.ts +198 -0
- package/src/lib/__tests__/op-type-safety.test.ts +71 -0
- package/src/lib/__tests__/package-exports.test.ts +57 -0
- package/src/lib/__tests__/remapped-buffer-view-integration.test.ts +319 -0
- package/src/lib/__tests__/remapped-buffer-view.test.ts +635 -0
- package/src/lib/__tests__/scope-attributes.test.ts +348 -0
- package/src/lib/__tests__/span-lifecycle.test.ts +680 -0
- package/src/lib/__tests__/sync-async-trace.test.ts +435 -0
- package/src/lib/__tests__/test-helpers.ts +318 -0
- package/src/lib/__tests__/timestamp.test.ts +259 -0
- package/src/lib/__tests__/trace-archive-primitives.test.ts +98 -0
- package/src/lib/__tests__/traceContext-type-enforcement.test.ts +271 -0
- package/src/lib/__tests__/tracer.test.ts +211 -0
- package/src/lib/__tests__/type-narrowing.test.ts +137 -0
- package/src/lib/archive/chunkCompaction.ts +44 -0
- package/src/lib/archive/chunkEnvelope.ts +79 -0
- package/src/lib/archive/chunkRouting.ts +70 -0
- package/src/lib/archive/chunkStats.ts +25 -0
- package/src/lib/archive/index.ts +4 -0
- package/src/lib/arrow/capacityStats.ts +340 -0
- package/src/lib/arrow/dictionaries.ts +159 -0
- package/src/lib/arrow/flechette.ts +114 -0
- package/src/lib/arrow/utils.ts +126 -0
- package/src/lib/buffer/Nanoseconds.ts +131 -0
- package/src/lib/bufferStrategy.ts +106 -0
- package/src/lib/capacityTuning.ts +102 -0
- package/src/lib/codegen/__tests__/__snapshots__/evaluatorGenerator.test.ts.snap +160 -0
- package/src/lib/codegen/__tests__/__snapshots__/scopeGenerator.test.ts.snap +196 -0
- package/src/lib/codegen/__tests__/__snapshots__/spanLoggerGenerator.test.ts.snap +1965 -0
- package/src/lib/codegen/__tests__/evaluatorGenerator.test.ts +516 -0
- package/src/lib/codegen/__tests__/nullBitmap.test.ts +207 -0
- package/src/lib/codegen/__tests__/spanLoggerGenerator.test.ts +237 -0
- package/src/lib/codegen/evaluatorGenerator.ts +309 -0
- package/src/lib/codegen/fixedPositionWriterGenerator.ts +444 -0
- package/src/lib/codegen/spanLoggerGenerator.ts +715 -0
- package/src/lib/convertToArrow.ts +1805 -0
- package/src/lib/defineOpContext.ts +398 -0
- package/src/lib/errors/Blocked.ts +165 -0
- package/src/lib/errors/CodeError.ts +132 -0
- package/src/lib/errors/RetriesExhausted.ts +78 -0
- package/src/lib/errors/Transient.ts +168 -0
- package/src/lib/errors/__tests__/Blocked-config.test.ts +152 -0
- package/src/lib/errors/__tests__/Transient.test.ts +129 -0
- package/src/lib/errors/__tests__/retry-policy.test.ts +85 -0
- package/src/lib/errors/index.ts +24 -0
- package/src/lib/errors/retry-policy.ts +87 -0
- package/src/lib/flushScheduler.ts +509 -0
- package/src/lib/library.ts +682 -0
- package/src/lib/logApi.ts +70 -0
- package/src/lib/logBinding.ts +67 -0
- package/src/lib/op.ts +103 -0
- package/src/lib/opContext/__tests__/retry.test.ts +764 -0
- package/src/lib/opContext/contextTypes.ts +130 -0
- package/src/lib/opContext/createOpGroup.ts +456 -0
- package/src/lib/opContext/defineOp.ts +281 -0
- package/src/lib/opContext/featureFlagTypes.ts +54 -0
- package/src/lib/opContext/index.ts +16 -0
- package/src/lib/opContext/opGroupTypes.ts +342 -0
- package/src/lib/opContext/opTypes.ts +80 -0
- package/src/lib/opContext/spanContextTypes.ts +398 -0
- package/src/lib/opContext/types.ts +403 -0
- package/src/lib/result.ts +550 -0
- package/src/lib/schema/LogSchema.ts +153 -0
- package/src/lib/schema/__tests__/defineLogSchema.test.ts +342 -0
- package/src/lib/schema/__tests__/featureFlags.test.ts +443 -0
- package/src/lib/schema/builder.ts +201 -0
- package/src/lib/schema/defineFeatureFlags.ts +91 -0
- package/src/lib/schema/defineLogSchema.ts +291 -0
- package/src/lib/schema/evaluator.ts +404 -0
- package/src/lib/schema/extend.ts +69 -0
- package/src/lib/schema/systemSchema.ts +339 -0
- package/src/lib/schema/typeGuards.ts +163 -0
- package/src/lib/schema/types.ts +265 -0
- package/src/lib/spanBuffer.ts +571 -0
- package/src/lib/spanBufferHelpers.ts +73 -0
- package/src/lib/spanBufferStats.ts +40 -0
- package/src/lib/spanContext.ts +1566 -0
- package/src/lib/sqlite/__tests__/sqlite-common.test.ts +89 -0
- package/src/lib/sqlite/index.ts +26 -0
- package/src/lib/sqlite/sqlite-async-writer.ts +101 -0
- package/src/lib/sqlite/sqlite-common.ts +309 -0
- package/src/lib/sqlite/sqlite-d1.ts +104 -0
- package/src/lib/sqlite/sqlite-db.ts +32 -0
- package/src/lib/sqlite/sqlite-node.ts +83 -0
- package/src/lib/sqlite/sqlite-writer.ts +128 -0
- package/src/lib/testing/TRACE-TESTING.md +100 -0
- package/src/lib/testing/__tests__/bun-harness.test.ts +108 -0
- package/src/lib/testing/__tests__/extractFacts.test.ts +279 -0
- package/src/lib/testing/__tests__/facts.test.ts +324 -0
- package/src/lib/testing/__tests__/vitest-harness.test.ts +32 -0
- package/src/lib/testing/bun-harness.ts +990 -0
- package/src/lib/testing/extractFacts.ts +362 -0
- package/src/lib/testing/facts.ts +470 -0
- package/src/lib/testing/index.ts +141 -0
- package/src/lib/testing/queryable-span.ts +108 -0
- package/src/lib/testing/span-query.ts +65 -0
- package/src/lib/testing/stdio-replay.ts +50 -0
- package/src/lib/testing/trace-query.ts +329 -0
- package/src/lib/testing/vitest-harness.ts +691 -0
- package/src/lib/threadId.ts +135 -0
- package/src/lib/traceContext.ts +182 -0
- package/src/lib/traceId.ts +142 -0
- package/src/lib/traceRoot.es.ts +157 -0
- package/src/lib/traceRoot.node.ts +170 -0
- package/src/lib/traceRoot.ts +154 -0
- package/src/lib/traceRoot.universal.ts +22 -0
- package/src/lib/tracer.ts +896 -0
- package/src/lib/tracers/ArrayQueueTracer.ts +76 -0
- package/src/lib/tracers/CompositeTracer.ts +76 -0
- package/src/lib/tracers/NoOpTracer.ts +73 -0
- package/src/lib/tracers/SQLiteTracer.ts +115 -0
- package/src/lib/tracers/StdioTracer.ts +380 -0
- package/src/lib/tracers/TestTracer.ts +146 -0
- package/src/lib/tracers/__tests__/ArrayQueueTracer.test.ts +184 -0
- package/src/lib/tracers/__tests__/NoOpTracer.test.ts +204 -0
- package/src/lib/tracers/__tests__/StdioTracer.test.ts +313 -0
- package/src/lib/tracers/__tests__/TestTracer.test.ts +200 -0
- package/src/lib/tracers/index.ts +12 -0
- package/src/lib/types.ts +498 -0
- package/src/lib/utf8Cache.ts +201 -0
- package/src/lib/wasm/WasmBufferStrategy.ts +219 -0
- package/src/lib/wasm/__tests__/WasmBufferStrategy.test.ts +256 -0
- package/src/lib/wasm/__tests__/wasm-integration.test.ts +476 -0
- package/src/lib/wasm/__tests__/wasmAllocator.test.ts +699 -0
- package/src/lib/wasm/__tests__/wasmSpanBuffer.test.ts +449 -0
- package/src/lib/wasm/__tests__/wasmTraceRoot.test.ts +390 -0
- package/src/lib/wasm/__tests__/wasmTracer.test.ts.disabled +444 -0
- package/src/lib/wasm/allocator.zig +945 -0
- package/src/lib/wasm/wasmAllocator.ts +469 -0
- package/src/lib/wasm/wasmSpanBuffer.ts +1014 -0
- package/src/lib/wasm/wasmTraceRoot.ts +315 -0
- package/src/node.ts +10 -0
- package/src/testing.ts +18 -0
|
@@ -0,0 +1,108 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* QueryableSpan - Ergonomic wrapper around SpanBuffer for test assertions.
|
|
3
|
+
*
|
|
4
|
+
* Provides a clean API for navigating the span tree and extracting facts
|
|
5
|
+
* without needing to know SpanBuffer internals.
|
|
6
|
+
*
|
|
7
|
+
* @example
|
|
8
|
+
* ```typescript
|
|
9
|
+
* const q = querySpan(tracer.rootBuffers[0]);
|
|
10
|
+
* expect(q.name).toBe('my-op');
|
|
11
|
+
* expect(q.find('validate')?.facts().has(spanOk('validate'))).toBe(true);
|
|
12
|
+
* expect(q.names()).toContain('save');
|
|
13
|
+
* ```
|
|
14
|
+
*
|
|
15
|
+
* @module queryable-span
|
|
16
|
+
*/
|
|
17
|
+
|
|
18
|
+
import type { LogSchema } from '../schema/LogSchema.js';
|
|
19
|
+
import type { SpanBuffer } from '../types.js';
|
|
20
|
+
import { type ExtractFactsOptions, extractFacts } from './extractFacts.js';
|
|
21
|
+
import type { FactArray } from './facts.js';
|
|
22
|
+
|
|
23
|
+
export interface QueryableSpan<T extends LogSchema = LogSchema> {
|
|
24
|
+
/** Span name (from message_values[0]) */
|
|
25
|
+
readonly name: string;
|
|
26
|
+
|
|
27
|
+
/** Extract all facts from this span and its children */
|
|
28
|
+
facts(options?: ExtractFactsOptions): FactArray;
|
|
29
|
+
|
|
30
|
+
/** Find first child span by name (depth-first) */
|
|
31
|
+
find(name: string): QueryableSpan<T> | undefined;
|
|
32
|
+
|
|
33
|
+
/** Find all spans matching name (depth-first) */
|
|
34
|
+
findAll(name: string): QueryableSpan<T>[];
|
|
35
|
+
|
|
36
|
+
/** Direct child spans */
|
|
37
|
+
readonly children: QueryableSpan<T>[];
|
|
38
|
+
|
|
39
|
+
/** All descendant span names (flat list, depth-first) */
|
|
40
|
+
names(): string[];
|
|
41
|
+
|
|
42
|
+
/** Raw SpanBuffer for advanced use */
|
|
43
|
+
readonly buffer: SpanBuffer<T>;
|
|
44
|
+
}
|
|
45
|
+
|
|
46
|
+
/** Wrap a SpanBuffer as a QueryableSpan for ergonomic test assertions */
|
|
47
|
+
export function querySpan<T extends LogSchema>(buffer: SpanBuffer<T>): QueryableSpan<T> {
|
|
48
|
+
return new QueryableSpanImpl(buffer);
|
|
49
|
+
}
|
|
50
|
+
|
|
51
|
+
class QueryableSpanImpl<T extends LogSchema> implements QueryableSpan<T> {
|
|
52
|
+
constructor(readonly buffer: SpanBuffer<T>) {}
|
|
53
|
+
|
|
54
|
+
get name(): string {
|
|
55
|
+
return this.buffer.message_values[0];
|
|
56
|
+
}
|
|
57
|
+
|
|
58
|
+
facts(options?: ExtractFactsOptions): FactArray {
|
|
59
|
+
return extractFacts(this.buffer, options);
|
|
60
|
+
}
|
|
61
|
+
|
|
62
|
+
find(name: string): QueryableSpan<T> | undefined {
|
|
63
|
+
return findInChildren(this.buffer._children as SpanBuffer<T>[], name);
|
|
64
|
+
}
|
|
65
|
+
|
|
66
|
+
findAll(name: string): QueryableSpan<T>[] {
|
|
67
|
+
const results: QueryableSpan<T>[] = [];
|
|
68
|
+
collectAll(this.buffer._children as SpanBuffer<T>[], name, results);
|
|
69
|
+
return results;
|
|
70
|
+
}
|
|
71
|
+
|
|
72
|
+
get children(): QueryableSpan<T>[] {
|
|
73
|
+
return (this.buffer._children as SpanBuffer<T>[]).map((child) => new QueryableSpanImpl(child));
|
|
74
|
+
}
|
|
75
|
+
|
|
76
|
+
names(): string[] {
|
|
77
|
+
const result: string[] = [];
|
|
78
|
+
collectNames(this.buffer._children as SpanBuffer<T>[], result);
|
|
79
|
+
return result;
|
|
80
|
+
}
|
|
81
|
+
}
|
|
82
|
+
|
|
83
|
+
function findInChildren<T extends LogSchema>(children: SpanBuffer<T>[], name: string): QueryableSpan<T> | undefined {
|
|
84
|
+
for (const child of children) {
|
|
85
|
+
if (child.message_values[0] === name) {
|
|
86
|
+
return new QueryableSpanImpl(child);
|
|
87
|
+
}
|
|
88
|
+
const found = findInChildren(child._children as SpanBuffer<T>[], name);
|
|
89
|
+
if (found) return found;
|
|
90
|
+
}
|
|
91
|
+
return undefined;
|
|
92
|
+
}
|
|
93
|
+
|
|
94
|
+
function collectAll<T extends LogSchema>(children: SpanBuffer<T>[], name: string, results: QueryableSpan<T>[]): void {
|
|
95
|
+
for (const child of children) {
|
|
96
|
+
if (child.message_values[0] === name) {
|
|
97
|
+
results.push(new QueryableSpanImpl(child));
|
|
98
|
+
}
|
|
99
|
+
collectAll(child._children as SpanBuffer<T>[], name, results);
|
|
100
|
+
}
|
|
101
|
+
}
|
|
102
|
+
|
|
103
|
+
function collectNames<T extends LogSchema>(children: SpanBuffer<T>[], result: string[]): void {
|
|
104
|
+
for (const child of children) {
|
|
105
|
+
result.push(child.message_values[0]);
|
|
106
|
+
collectNames(child._children as SpanBuffer<T>[], result);
|
|
107
|
+
}
|
|
108
|
+
}
|
|
@@ -0,0 +1,65 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Standalone span query functions — tree-shakable alternative to QueryableSpan.
|
|
3
|
+
*
|
|
4
|
+
* These functions operate directly on SpanBuffer instances without wrapping.
|
|
5
|
+
* Prefer these when you only need one or two operations and want minimal overhead.
|
|
6
|
+
*
|
|
7
|
+
* @module span-query
|
|
8
|
+
*/
|
|
9
|
+
|
|
10
|
+
import type { LogSchema } from '../schema/LogSchema.js';
|
|
11
|
+
import type { SpanBuffer } from '../types.js';
|
|
12
|
+
import { type ExtractFactsOptions, extractFacts } from './extractFacts.js';
|
|
13
|
+
import type { FactArray } from './facts.js';
|
|
14
|
+
|
|
15
|
+
/** Find first descendant span by name (depth-first) */
|
|
16
|
+
export function findSpan<T extends LogSchema>(root: SpanBuffer<T>, name: string): SpanBuffer<T> | undefined {
|
|
17
|
+
for (const child of root._children) {
|
|
18
|
+
const typed = child as SpanBuffer<T>;
|
|
19
|
+
if (typed.message_values[0] === name) return typed;
|
|
20
|
+
const found = findSpan(typed, name);
|
|
21
|
+
if (found) return found;
|
|
22
|
+
}
|
|
23
|
+
return undefined;
|
|
24
|
+
}
|
|
25
|
+
|
|
26
|
+
/** Find all descendant spans matching name (depth-first) */
|
|
27
|
+
export function findAllSpans<T extends LogSchema>(root: SpanBuffer<T>, name: string): SpanBuffer<T>[] {
|
|
28
|
+
const results: SpanBuffer<T>[] = [];
|
|
29
|
+
collectSpans(root, name, results);
|
|
30
|
+
return results;
|
|
31
|
+
}
|
|
32
|
+
|
|
33
|
+
/** Extract facts for a specific named span within a root buffer tree */
|
|
34
|
+
export function extractFactsFor<T extends LogSchema>(
|
|
35
|
+
root: SpanBuffer<T>,
|
|
36
|
+
spanName: string,
|
|
37
|
+
options?: ExtractFactsOptions,
|
|
38
|
+
): FactArray | undefined {
|
|
39
|
+
const span = findSpan(root, spanName);
|
|
40
|
+
if (!span) return undefined;
|
|
41
|
+
return extractFacts(span, options);
|
|
42
|
+
}
|
|
43
|
+
|
|
44
|
+
/** Collect all descendant span names (flat list, depth-first) */
|
|
45
|
+
export function spanNames<T extends LogSchema>(root: SpanBuffer<T>): string[] {
|
|
46
|
+
const result: string[] = [];
|
|
47
|
+
collectNames(root._children as SpanBuffer<T>[], result);
|
|
48
|
+
return result;
|
|
49
|
+
}
|
|
50
|
+
|
|
51
|
+
function collectSpans<T extends LogSchema>(root: SpanBuffer<T>, name: string, results: SpanBuffer<T>[]): void {
|
|
52
|
+
for (const child of root._children) {
|
|
53
|
+
const typed = child as SpanBuffer<T>;
|
|
54
|
+
if (typed.message_values[0] === name) results.push(typed);
|
|
55
|
+
collectSpans(typed, name, results);
|
|
56
|
+
}
|
|
57
|
+
}
|
|
58
|
+
|
|
59
|
+
function collectNames<T extends LogSchema>(children: SpanBuffer<T>[], result: string[]): void {
|
|
60
|
+
for (const child of children) {
|
|
61
|
+
const typed = child as SpanBuffer<T>;
|
|
62
|
+
result.push(typed.message_values[0]);
|
|
63
|
+
collectNames(typed._children as SpanBuffer<T>[], result);
|
|
64
|
+
}
|
|
65
|
+
}
|
|
@@ -0,0 +1,50 @@
|
|
|
1
|
+
import { JsBufferStrategy } from '../JsBufferStrategy.js';
|
|
2
|
+
import type { OpContextBinding } from '../opContext/types.js';
|
|
3
|
+
import { createTraceRoot } from '../traceRoot.universal.js';
|
|
4
|
+
import { StdioTracer, type StdioWritable } from '../tracers/StdioTracer.js';
|
|
5
|
+
import type { AnySpanBuffer } from '../types.js';
|
|
6
|
+
|
|
7
|
+
function isStdioWritable(value: unknown): value is StdioWritable {
|
|
8
|
+
return typeof value === 'object' && value !== null && typeof Reflect.get(value, 'write') === 'function';
|
|
9
|
+
}
|
|
10
|
+
|
|
11
|
+
function makeConsoleWriteStream(write: (line: string) => void): StdioWritable {
|
|
12
|
+
return {
|
|
13
|
+
write(chunk: string): boolean {
|
|
14
|
+
write(chunk.replace(/\n$/, ''));
|
|
15
|
+
return true;
|
|
16
|
+
},
|
|
17
|
+
};
|
|
18
|
+
}
|
|
19
|
+
|
|
20
|
+
function replayChildSpan(tracer: StdioTracer<OpContextBinding>, buffer: AnySpanBuffer): void {
|
|
21
|
+
tracer.onSpanStart(buffer);
|
|
22
|
+
for (const child of buffer._children) {
|
|
23
|
+
replayChildSpan(tracer, child);
|
|
24
|
+
}
|
|
25
|
+
tracer.onSpanEnd(buffer);
|
|
26
|
+
}
|
|
27
|
+
|
|
28
|
+
export function replayTraceToStdio(binding: OpContextBinding, rootBuffer: AnySpanBuffer): void {
|
|
29
|
+
const processRef = (globalThis as { process?: { stdout?: unknown; stderr?: unknown } }).process;
|
|
30
|
+
const out = isStdioWritable(processRef?.stdout)
|
|
31
|
+
? processRef.stdout
|
|
32
|
+
: makeConsoleWriteStream((line) => console.log(line));
|
|
33
|
+
const err = isStdioWritable(processRef?.stderr)
|
|
34
|
+
? processRef.stderr
|
|
35
|
+
: makeConsoleWriteStream((line) => console.error(line));
|
|
36
|
+
|
|
37
|
+
const tracer = new StdioTracer(binding, {
|
|
38
|
+
bufferStrategy: new JsBufferStrategy(),
|
|
39
|
+
createTraceRoot,
|
|
40
|
+
out,
|
|
41
|
+
err,
|
|
42
|
+
colorEnabled: processRef?.stdout !== undefined,
|
|
43
|
+
});
|
|
44
|
+
|
|
45
|
+
tracer.onTraceStart(rootBuffer);
|
|
46
|
+
for (const child of rootBuffer._children) {
|
|
47
|
+
replayChildSpan(tracer, child);
|
|
48
|
+
}
|
|
49
|
+
tracer.onTraceEnd(rootBuffer);
|
|
50
|
+
}
|
|
@@ -0,0 +1,329 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* TraceQuery - Post-run query API for the SQLite trace database.
|
|
3
|
+
*
|
|
4
|
+
* Queries a single flat `spans` table where each row is a buffer entry.
|
|
5
|
+
* Status and duration are derived from entry_type and timestamps via self-joins.
|
|
6
|
+
* Tree structure uses span_id / parent_span_id (no depth column).
|
|
7
|
+
*
|
|
8
|
+
* Platform-agnostic: accepts a SyncSQLiteDatabase instance from either
|
|
9
|
+
* bun:sqlite or better-sqlite3.
|
|
10
|
+
*
|
|
11
|
+
* @example
|
|
12
|
+
* ```typescript
|
|
13
|
+
* import { Database } from 'bun:sqlite';
|
|
14
|
+
* import { TraceQuery } from '@smoothbricks/lmao/testing';
|
|
15
|
+
*
|
|
16
|
+
* const query = new TraceQuery(new Database('.trace-results.db'));
|
|
17
|
+
* console.log(query.failures());
|
|
18
|
+
* console.log(query.slowest(undefined, 10));
|
|
19
|
+
* query.close();
|
|
20
|
+
* ```
|
|
21
|
+
*
|
|
22
|
+
* @module trace-query
|
|
23
|
+
*/
|
|
24
|
+
|
|
25
|
+
import typia from 'typia';
|
|
26
|
+
import type { SyncSQLiteDatabase } from '../sqlite/sqlite-db.js';
|
|
27
|
+
|
|
28
|
+
export interface TraceQueryResult {
|
|
29
|
+
spanName: string;
|
|
30
|
+
status: 'ok' | 'err' | 'exception' | 'running';
|
|
31
|
+
errorCode?: string;
|
|
32
|
+
durationNs?: number;
|
|
33
|
+
describe?: string;
|
|
34
|
+
parentSpanId?: number;
|
|
35
|
+
}
|
|
36
|
+
|
|
37
|
+
type TraceRun = { traceId: string; spanName: string; startedAt: number };
|
|
38
|
+
type LatestTraceRun = { traceId: string };
|
|
39
|
+
|
|
40
|
+
type TraceRunRow = {
|
|
41
|
+
readonly traceId: string;
|
|
42
|
+
readonly spanName: string;
|
|
43
|
+
readonly startedAt: number;
|
|
44
|
+
};
|
|
45
|
+
|
|
46
|
+
type LatestTraceRunRow = {
|
|
47
|
+
readonly traceId: string;
|
|
48
|
+
};
|
|
49
|
+
|
|
50
|
+
type RootSpanRow = {
|
|
51
|
+
readonly span_id: number;
|
|
52
|
+
};
|
|
53
|
+
|
|
54
|
+
type TraceQueryResultRow = {
|
|
55
|
+
readonly spanName: string;
|
|
56
|
+
readonly status: 'ok' | 'err' | 'exception' | 'running';
|
|
57
|
+
readonly durationNs: number | null;
|
|
58
|
+
readonly describe: string | null;
|
|
59
|
+
readonly parentSpanId: number;
|
|
60
|
+
};
|
|
61
|
+
|
|
62
|
+
let validateTraceRunRow: ((input: unknown) => typia.IValidation<TraceRunRow>) | undefined;
|
|
63
|
+
let validateLatestTraceRunRow: ((input: unknown) => typia.IValidation<LatestTraceRunRow>) | undefined;
|
|
64
|
+
let validateRootSpanRow: ((input: unknown) => typia.IValidation<RootSpanRow>) | undefined;
|
|
65
|
+
let validateTraceQueryResultRow: ((input: unknown) => typia.IValidation<TraceQueryResultRow>) | undefined;
|
|
66
|
+
|
|
67
|
+
function getValidateTraceRunRow(): (input: unknown) => typia.IValidation<TraceRunRow> {
|
|
68
|
+
validateTraceRunRow ??= typia.createValidateEquals<TraceRunRow>();
|
|
69
|
+
return validateTraceRunRow;
|
|
70
|
+
}
|
|
71
|
+
|
|
72
|
+
function getValidateLatestTraceRunRow(): (input: unknown) => typia.IValidation<LatestTraceRunRow> {
|
|
73
|
+
validateLatestTraceRunRow ??= typia.createValidateEquals<LatestTraceRunRow>();
|
|
74
|
+
return validateLatestTraceRunRow;
|
|
75
|
+
}
|
|
76
|
+
|
|
77
|
+
function getValidateRootSpanRow(): (input: unknown) => typia.IValidation<RootSpanRow> {
|
|
78
|
+
validateRootSpanRow ??= typia.createValidateEquals<RootSpanRow>();
|
|
79
|
+
return validateRootSpanRow;
|
|
80
|
+
}
|
|
81
|
+
|
|
82
|
+
function getValidateTraceQueryResultRow(): (input: unknown) => typia.IValidation<TraceQueryResultRow> {
|
|
83
|
+
validateTraceQueryResultRow ??= typia.createValidateEquals<TraceQueryResultRow>();
|
|
84
|
+
return validateTraceQueryResultRow;
|
|
85
|
+
}
|
|
86
|
+
|
|
87
|
+
function describeSqliteBoundaryError(
|
|
88
|
+
boundary: string,
|
|
89
|
+
errors: readonly { path: string; expected: string }[],
|
|
90
|
+
rowIndex?: number,
|
|
91
|
+
): string {
|
|
92
|
+
const firstError = errors[0];
|
|
93
|
+
const rowDetail = rowIndex === undefined ? '' : ` row ${rowIndex}`;
|
|
94
|
+
if (!firstError) {
|
|
95
|
+
return `${boundary} returned an invalid SQLite${rowDetail} result`;
|
|
96
|
+
}
|
|
97
|
+
|
|
98
|
+
return `${boundary} returned an invalid SQLite${rowDetail} result at ${firstError.path}: expected ${firstError.expected}`;
|
|
99
|
+
}
|
|
100
|
+
|
|
101
|
+
function parseOptionalSqliteRow<T>(
|
|
102
|
+
boundary: string,
|
|
103
|
+
row: unknown,
|
|
104
|
+
validate: (input: unknown) => typia.IValidation<T>,
|
|
105
|
+
): T | undefined {
|
|
106
|
+
if (row == null) {
|
|
107
|
+
return undefined;
|
|
108
|
+
}
|
|
109
|
+
|
|
110
|
+
const validation = validate(row);
|
|
111
|
+
if (!validation.success) {
|
|
112
|
+
throw new Error(describeSqliteBoundaryError(boundary, validation.errors));
|
|
113
|
+
}
|
|
114
|
+
|
|
115
|
+
return validation.data;
|
|
116
|
+
}
|
|
117
|
+
|
|
118
|
+
function parseSqliteRows<T>(
|
|
119
|
+
boundary: string,
|
|
120
|
+
rows: unknown[],
|
|
121
|
+
validate: (input: unknown) => typia.IValidation<T>,
|
|
122
|
+
): T[] {
|
|
123
|
+
return rows.map((row, rowIndex) => {
|
|
124
|
+
const validation = validate(row);
|
|
125
|
+
if (!validation.success) {
|
|
126
|
+
throw new Error(describeSqliteBoundaryError(boundary, validation.errors, rowIndex));
|
|
127
|
+
}
|
|
128
|
+
|
|
129
|
+
return validation.data;
|
|
130
|
+
});
|
|
131
|
+
}
|
|
132
|
+
|
|
133
|
+
function toTraceQueryResult(row: TraceQueryResultRow): TraceQueryResult {
|
|
134
|
+
return {
|
|
135
|
+
spanName: row.spanName,
|
|
136
|
+
status: row.status,
|
|
137
|
+
durationNs: row.durationNs ?? undefined,
|
|
138
|
+
describe: row.describe ?? undefined,
|
|
139
|
+
parentSpanId: row.parentSpanId,
|
|
140
|
+
};
|
|
141
|
+
}
|
|
142
|
+
|
|
143
|
+
export class TraceQuery {
|
|
144
|
+
constructor(private db: SyncSQLiteDatabase) {}
|
|
145
|
+
|
|
146
|
+
/** Get all trace runs (root spans), most recent first */
|
|
147
|
+
runs(): TraceRun[] {
|
|
148
|
+
return parseSqliteRows(
|
|
149
|
+
'TraceQuery.runs',
|
|
150
|
+
this.db
|
|
151
|
+
.prepare(
|
|
152
|
+
`SELECT trace_id AS traceId, message AS spanName, timestamp_ns AS startedAt
|
|
153
|
+
FROM spans
|
|
154
|
+
WHERE parent_span_id = 0 AND row_index = 0
|
|
155
|
+
ORDER BY timestamp_ns DESC`,
|
|
156
|
+
)
|
|
157
|
+
.all(),
|
|
158
|
+
getValidateTraceRunRow(),
|
|
159
|
+
);
|
|
160
|
+
}
|
|
161
|
+
|
|
162
|
+
/** Get the most recent trace_id (= run_id) */
|
|
163
|
+
latestRun(): LatestTraceRun | undefined {
|
|
164
|
+
return parseOptionalSqliteRow(
|
|
165
|
+
'TraceQuery.latestRun',
|
|
166
|
+
this.db
|
|
167
|
+
.prepare(
|
|
168
|
+
`SELECT trace_id AS traceId
|
|
169
|
+
FROM spans
|
|
170
|
+
WHERE parent_span_id = 0 AND row_index = 0
|
|
171
|
+
ORDER BY timestamp_ns DESC LIMIT 1`,
|
|
172
|
+
)
|
|
173
|
+
.get(),
|
|
174
|
+
getValidateLatestTraceRunRow(),
|
|
175
|
+
);
|
|
176
|
+
}
|
|
177
|
+
|
|
178
|
+
/** Get all failed tests in a run (defaults to latest run) */
|
|
179
|
+
failures(traceId?: string): TraceQueryResult[] {
|
|
180
|
+
const id = traceId ?? this.latestRun()?.traceId;
|
|
181
|
+
if (!id) return [];
|
|
182
|
+
|
|
183
|
+
// Find the root span_id for this trace
|
|
184
|
+
const root = parseOptionalSqliteRow(
|
|
185
|
+
'TraceQuery.failures root span',
|
|
186
|
+
this.db.prepare('SELECT span_id FROM spans WHERE trace_id = ? AND parent_span_id = 0 AND row_index = 0').get(id),
|
|
187
|
+
getValidateRootSpanRow(),
|
|
188
|
+
);
|
|
189
|
+
if (!root) return [];
|
|
190
|
+
|
|
191
|
+
// Self-join: row_index=0 for name, row_index=1 for status/duration
|
|
192
|
+
return parseSqliteRows(
|
|
193
|
+
'TraceQuery.failures rows',
|
|
194
|
+
this.db
|
|
195
|
+
.prepare(
|
|
196
|
+
`SELECT
|
|
197
|
+
s0.message AS spanName,
|
|
198
|
+
CASE WHEN s1.entry_type = 2 THEN 'ok'
|
|
199
|
+
WHEN s1.entry_type = 3 THEN 'err'
|
|
200
|
+
WHEN s1.entry_type = 4 THEN 'exception'
|
|
201
|
+
ELSE 'running' END AS status,
|
|
202
|
+
s1.timestamp_ns - s0.timestamp_ns AS durationNs,
|
|
203
|
+
s0.describe,
|
|
204
|
+
s0.parent_span_id AS parentSpanId
|
|
205
|
+
FROM spans s0
|
|
206
|
+
LEFT JOIN spans s1 ON s1.trace_id = s0.trace_id AND s1.span_id = s0.span_id AND s1.row_index = 1
|
|
207
|
+
WHERE s0.trace_id = ? AND s0.parent_span_id = ? AND s0.row_index = 0
|
|
208
|
+
AND s1.entry_type IN (3, 4)
|
|
209
|
+
ORDER BY s0.timestamp_ns ASC`,
|
|
210
|
+
)
|
|
211
|
+
.all(id, root.span_id),
|
|
212
|
+
getValidateTraceQueryResultRow(),
|
|
213
|
+
).map(toTraceQueryResult);
|
|
214
|
+
}
|
|
215
|
+
|
|
216
|
+
/** Get slowest tests in a run (defaults to latest run) */
|
|
217
|
+
slowest(traceId?: string, limit = 20): TraceQueryResult[] {
|
|
218
|
+
const id = traceId ?? this.latestRun()?.traceId;
|
|
219
|
+
if (!id) return [];
|
|
220
|
+
|
|
221
|
+
// Find the root span_id for this trace
|
|
222
|
+
const root = parseOptionalSqliteRow(
|
|
223
|
+
'TraceQuery.slowest root span',
|
|
224
|
+
this.db.prepare('SELECT span_id FROM spans WHERE trace_id = ? AND parent_span_id = 0 AND row_index = 0').get(id),
|
|
225
|
+
getValidateRootSpanRow(),
|
|
226
|
+
);
|
|
227
|
+
if (!root) return [];
|
|
228
|
+
|
|
229
|
+
return parseSqliteRows(
|
|
230
|
+
'TraceQuery.slowest rows',
|
|
231
|
+
this.db
|
|
232
|
+
.prepare(
|
|
233
|
+
`SELECT
|
|
234
|
+
s0.message AS spanName,
|
|
235
|
+
CASE WHEN s1.entry_type = 2 THEN 'ok'
|
|
236
|
+
WHEN s1.entry_type = 3 THEN 'err'
|
|
237
|
+
WHEN s1.entry_type = 4 THEN 'exception'
|
|
238
|
+
ELSE 'running' END AS status,
|
|
239
|
+
s1.timestamp_ns - s0.timestamp_ns AS durationNs,
|
|
240
|
+
s0.describe,
|
|
241
|
+
s0.parent_span_id AS parentSpanId
|
|
242
|
+
FROM spans s0
|
|
243
|
+
LEFT JOIN spans s1 ON s1.trace_id = s0.trace_id AND s1.span_id = s0.span_id AND s1.row_index = 1
|
|
244
|
+
WHERE s0.trace_id = ? AND s0.parent_span_id = ? AND s0.row_index = 0
|
|
245
|
+
AND s1.entry_type IS NOT NULL
|
|
246
|
+
ORDER BY durationNs DESC
|
|
247
|
+
LIMIT ?`,
|
|
248
|
+
)
|
|
249
|
+
.all(id, root.span_id, limit),
|
|
250
|
+
getValidateTraceQueryResultRow(),
|
|
251
|
+
).map(toTraceQueryResult);
|
|
252
|
+
}
|
|
253
|
+
|
|
254
|
+
/** Find spans by name pattern (SQL LIKE, defaults to latest run) */
|
|
255
|
+
findSpans(pattern: string, traceId?: string): TraceQueryResult[] {
|
|
256
|
+
const id = traceId ?? this.latestRun()?.traceId;
|
|
257
|
+
if (!id) return [];
|
|
258
|
+
|
|
259
|
+
return parseSqliteRows(
|
|
260
|
+
'TraceQuery.findSpans',
|
|
261
|
+
this.db
|
|
262
|
+
.prepare(
|
|
263
|
+
`SELECT
|
|
264
|
+
s0.message AS spanName,
|
|
265
|
+
CASE WHEN s1.entry_type = 2 THEN 'ok'
|
|
266
|
+
WHEN s1.entry_type = 3 THEN 'err'
|
|
267
|
+
WHEN s1.entry_type = 4 THEN 'exception'
|
|
268
|
+
ELSE 'running' END AS status,
|
|
269
|
+
s1.timestamp_ns - s0.timestamp_ns AS durationNs,
|
|
270
|
+
s0.describe,
|
|
271
|
+
s0.parent_span_id AS parentSpanId
|
|
272
|
+
FROM spans s0
|
|
273
|
+
LEFT JOIN spans s1 ON s1.trace_id = s0.trace_id AND s1.span_id = s0.span_id AND s1.row_index = 1
|
|
274
|
+
WHERE s0.trace_id = ? AND s0.row_index = 0 AND s0.message LIKE ?
|
|
275
|
+
ORDER BY s0.timestamp_ns ASC`,
|
|
276
|
+
)
|
|
277
|
+
.all(id, pattern),
|
|
278
|
+
getValidateTraceQueryResultRow(),
|
|
279
|
+
).map(toTraceQueryResult);
|
|
280
|
+
}
|
|
281
|
+
|
|
282
|
+
/** Get full span tree for a specific test (all descendants, defaults to latest run) */
|
|
283
|
+
testTree(testName: string, traceId?: string): TraceQueryResult[] {
|
|
284
|
+
const id = traceId ?? this.latestRun()?.traceId;
|
|
285
|
+
if (!id) return [];
|
|
286
|
+
|
|
287
|
+
// Recursive CTE on span_id/parent_span_id
|
|
288
|
+
return parseSqliteRows(
|
|
289
|
+
'TraceQuery.testTree',
|
|
290
|
+
this.db
|
|
291
|
+
.prepare(
|
|
292
|
+
`WITH RECURSIVE tree AS (
|
|
293
|
+
-- Anchor: find the span by name
|
|
294
|
+
SELECT span_id
|
|
295
|
+
FROM spans
|
|
296
|
+
WHERE trace_id = ? AND row_index = 0 AND message = ?
|
|
297
|
+
LIMIT 1
|
|
298
|
+
|
|
299
|
+
UNION ALL
|
|
300
|
+
|
|
301
|
+
-- Recurse: find children by parent_span_id
|
|
302
|
+
SELECT s.span_id
|
|
303
|
+
FROM spans s
|
|
304
|
+
INNER JOIN tree t ON s.parent_span_id = t.span_id
|
|
305
|
+
WHERE s.trace_id = ? AND s.row_index = 0
|
|
306
|
+
)
|
|
307
|
+
SELECT
|
|
308
|
+
s0.message AS spanName,
|
|
309
|
+
CASE WHEN s1.entry_type = 2 THEN 'ok'
|
|
310
|
+
WHEN s1.entry_type = 3 THEN 'err'
|
|
311
|
+
WHEN s1.entry_type = 4 THEN 'exception'
|
|
312
|
+
ELSE 'running' END AS status,
|
|
313
|
+
s1.timestamp_ns - s0.timestamp_ns AS durationNs,
|
|
314
|
+
s0.describe,
|
|
315
|
+
s0.parent_span_id AS parentSpanId
|
|
316
|
+
FROM tree
|
|
317
|
+
JOIN spans s0 ON s0.trace_id = ? AND s0.span_id = tree.span_id AND s0.row_index = 0
|
|
318
|
+
LEFT JOIN spans s1 ON s1.trace_id = s0.trace_id AND s1.span_id = s0.span_id AND s1.row_index = 1
|
|
319
|
+
ORDER BY s0.timestamp_ns ASC`,
|
|
320
|
+
)
|
|
321
|
+
.all(id, testName, id, id),
|
|
322
|
+
getValidateTraceQueryResultRow(),
|
|
323
|
+
).map(toTraceQueryResult);
|
|
324
|
+
}
|
|
325
|
+
|
|
326
|
+
close(): void {
|
|
327
|
+
this.db.close();
|
|
328
|
+
}
|
|
329
|
+
}
|