@smoothbricks/lmao 0.2.2 → 0.3.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.
Files changed (285) hide show
  1. package/README.md +206 -206
  2. package/dist/allocator.wasm +0 -0
  3. package/dist/index.d.ts +1 -0
  4. package/dist/index.d.ts.map +1 -1
  5. package/dist/index.js +1 -0
  6. package/dist/lib/JsBufferStrategy.d.ts +4 -3
  7. package/dist/lib/JsBufferStrategy.d.ts.map +1 -1
  8. package/dist/lib/JsBufferStrategy.js +18 -11
  9. package/dist/lib/arrow/lease.d.ts +10 -0
  10. package/dist/lib/arrow/lease.d.ts.map +1 -0
  11. package/dist/lib/arrow/lease.js +33 -0
  12. package/dist/lib/arrow/utils.d.ts +3 -4
  13. package/dist/lib/arrow/utils.d.ts.map +1 -1
  14. package/dist/lib/arrow/utils.js +12 -13
  15. package/dist/lib/arrow/vocabularyDictionary.d.ts +21 -0
  16. package/dist/lib/arrow/vocabularyDictionary.d.ts.map +1 -0
  17. package/dist/lib/arrow/vocabularyDictionary.js +95 -0
  18. package/dist/lib/bufferStrategy.d.ts +3 -2
  19. package/dist/lib/bufferStrategy.d.ts.map +1 -1
  20. package/dist/lib/cloudflare/traceRows.d.ts.map +1 -1
  21. package/dist/lib/cloudflare/traceRows.js +3 -2
  22. package/dist/lib/codegen/evaluatorGenerator.d.ts.map +1 -1
  23. package/dist/lib/codegen/evaluatorGenerator.js +12 -11
  24. package/dist/lib/codegen/fixedPositionWriterGenerator.d.ts +44 -82
  25. package/dist/lib/codegen/fixedPositionWriterGenerator.d.ts.map +1 -1
  26. package/dist/lib/codegen/fixedPositionWriterGenerator.js +223 -162
  27. package/dist/lib/codegen/spanLoggerClosureMaterializer.d.ts +63 -0
  28. package/dist/lib/codegen/spanLoggerClosureMaterializer.d.ts.map +1 -0
  29. package/dist/lib/codegen/spanLoggerClosureMaterializer.js +447 -0
  30. package/dist/lib/codegen/spanLoggerGenerator.d.ts +36 -19
  31. package/dist/lib/codegen/spanLoggerGenerator.d.ts.map +1 -1
  32. package/dist/lib/codegen/spanLoggerGenerator.js +164 -158
  33. package/dist/lib/convertToArrow.d.ts +7 -2
  34. package/dist/lib/convertToArrow.d.ts.map +1 -1
  35. package/dist/lib/convertToArrow.js +499 -285
  36. package/dist/lib/defineOpContext.js +1 -1
  37. package/dist/lib/enumMetadata.d.ts +19 -0
  38. package/dist/lib/enumMetadata.d.ts.map +1 -0
  39. package/dist/lib/enumMetadata.js +86 -0
  40. package/dist/lib/flushScheduler.d.ts.map +1 -1
  41. package/dist/lib/flushScheduler.js +13 -4
  42. package/dist/lib/library.d.ts +16 -98
  43. package/dist/lib/library.d.ts.map +1 -1
  44. package/dist/lib/library.js +32 -525
  45. package/dist/lib/logBinding.d.ts +21 -27
  46. package/dist/lib/logBinding.d.ts.map +1 -1
  47. package/dist/lib/op.d.ts +30 -30
  48. package/dist/lib/op.d.ts.map +1 -1
  49. package/dist/lib/op.js +15 -22
  50. package/dist/lib/opContext/createOpGroup.d.ts +1 -1
  51. package/dist/lib/opContext/createOpGroup.d.ts.map +1 -1
  52. package/dist/lib/opContext/createOpGroup.js +22 -29
  53. package/dist/lib/opContext/defineOp.d.ts +4 -4
  54. package/dist/lib/opContext/defineOp.d.ts.map +1 -1
  55. package/dist/lib/opContext/defineOp.js +53 -10
  56. package/dist/lib/opContext/opGroupTypes.d.ts +2 -2
  57. package/dist/lib/opContext/opTypes.d.ts +1 -1
  58. package/dist/lib/opContext/opTypes.d.ts.map +1 -1
  59. package/dist/lib/opContext/spanContextTypes.d.ts +33 -18
  60. package/dist/lib/opContext/spanContextTypes.d.ts.map +1 -1
  61. package/dist/lib/opContext/types.d.ts +4 -4
  62. package/dist/lib/opContext/types.d.ts.map +1 -1
  63. package/dist/lib/physicalLayoutPlan.d.ts +89 -0
  64. package/dist/lib/physicalLayoutPlan.d.ts.map +1 -0
  65. package/dist/lib/physicalLayoutPlan.js +442 -0
  66. package/dist/lib/resolveMessage.d.ts +9 -0
  67. package/dist/lib/resolveMessage.d.ts.map +1 -0
  68. package/dist/lib/resolveMessage.js +63 -0
  69. package/dist/lib/result.d.ts +5 -7
  70. package/dist/lib/result.d.ts.map +1 -1
  71. package/dist/lib/result.js +19 -26
  72. package/dist/lib/runtimeHint.d.ts +35 -0
  73. package/dist/lib/runtimeHint.d.ts.map +1 -0
  74. package/dist/lib/runtimeHint.js +79 -0
  75. package/dist/lib/schema/typeGuards.d.ts +7 -47
  76. package/dist/lib/schema/typeGuards.d.ts.map +1 -1
  77. package/dist/lib/schema/typeGuards.js +7 -123
  78. package/dist/lib/schema/types.d.ts +1 -1
  79. package/dist/lib/schema/types.d.ts.map +1 -1
  80. package/dist/lib/span-buffer/aot/v1.d.ts +2 -0
  81. package/dist/lib/span-buffer/aot/v1.d.ts.map +1 -0
  82. package/dist/lib/span-buffer/aot/v1.js +24 -0
  83. package/dist/lib/spanBuffer.d.ts +33 -4
  84. package/dist/lib/spanBuffer.d.ts.map +1 -1
  85. package/dist/lib/spanBuffer.js +583 -91
  86. package/dist/lib/spanBufferStats.d.ts +1 -1
  87. package/dist/lib/spanBufferStats.d.ts.map +1 -1
  88. package/dist/lib/spanContext.d.ts +27 -51
  89. package/dist/lib/spanContext.d.ts.map +1 -1
  90. package/dist/lib/spanContext.js +822 -344
  91. package/dist/lib/sqlite/sqlite-common.d.ts.map +1 -1
  92. package/dist/lib/sqlite/sqlite-common.js +20 -21
  93. package/dist/lib/testing/bun-harness.d.ts +8 -3
  94. package/dist/lib/testing/bun-harness.d.ts.map +1 -1
  95. package/dist/lib/testing/bun-harness.js +30 -18
  96. package/dist/lib/testing/extractFacts.d.ts +1 -1
  97. package/dist/lib/testing/extractFacts.d.ts.map +1 -1
  98. package/dist/lib/testing/extractFacts.js +55 -63
  99. package/dist/lib/testing/facts.d.ts +1 -1
  100. package/dist/lib/testing/facts.d.ts.map +1 -1
  101. package/dist/lib/testing/queryable-span.d.ts +1 -1
  102. package/dist/lib/testing/queryable-span.d.ts.map +1 -1
  103. package/dist/lib/testing/queryable-span.js +26 -28
  104. package/dist/lib/testing/span-query.d.ts.map +1 -1
  105. package/dist/lib/testing/span-query.js +19 -22
  106. package/dist/lib/testing/stdio-replay.d.ts.map +1 -1
  107. package/dist/lib/testing/stdio-replay.js +19 -8
  108. package/dist/lib/threadId.d.ts.map +1 -1
  109. package/dist/lib/threadId.js +6 -3
  110. package/dist/lib/traceContext.d.ts.map +1 -1
  111. package/dist/lib/traceContext.js +1 -4
  112. package/dist/lib/traceRoot.d.ts +30 -8
  113. package/dist/lib/traceRoot.d.ts.map +1 -1
  114. package/dist/lib/traceRoot.es.d.ts +17 -15
  115. package/dist/lib/traceRoot.es.d.ts.map +1 -1
  116. package/dist/lib/traceRoot.es.js +68 -34
  117. package/dist/lib/traceRoot.js +11 -0
  118. package/dist/lib/traceRoot.node.d.ts +17 -19
  119. package/dist/lib/traceRoot.node.d.ts.map +1 -1
  120. package/dist/lib/traceRoot.node.js +66 -38
  121. package/dist/lib/traceTopology.d.ts +42 -0
  122. package/dist/lib/traceTopology.d.ts.map +1 -0
  123. package/dist/lib/traceTopology.js +260 -0
  124. package/dist/lib/tracer.d.ts +9 -5
  125. package/dist/lib/tracer.d.ts.map +1 -1
  126. package/dist/lib/tracer.js +65 -71
  127. package/dist/lib/tracers/ArrayQueueTracer.d.ts +1 -1
  128. package/dist/lib/tracers/ArrayQueueTracer.js +1 -1
  129. package/dist/lib/tracers/StdioTracer.d.ts.map +1 -1
  130. package/dist/lib/tracers/StdioTracer.js +15 -13
  131. package/dist/lib/tracers/TestTracer.d.ts +4 -6
  132. package/dist/lib/tracers/TestTracer.d.ts.map +1 -1
  133. package/dist/lib/tracers/TestTracer.js +6 -8
  134. package/dist/lib/types.d.ts +49 -32
  135. package/dist/lib/types.d.ts.map +1 -1
  136. package/dist/lib/vocabularyRegistry.d.ts +25 -0
  137. package/dist/lib/vocabularyRegistry.d.ts.map +1 -0
  138. package/dist/lib/vocabularyRegistry.js +372 -0
  139. package/dist/lib/wasm/WasmBufferStrategy.d.ts +6 -10
  140. package/dist/lib/wasm/WasmBufferStrategy.d.ts.map +1 -1
  141. package/dist/lib/wasm/WasmBufferStrategy.js +44 -37
  142. package/dist/lib/wasm/wasmAllocator.d.ts +27 -22
  143. package/dist/lib/wasm/wasmAllocator.d.ts.map +1 -1
  144. package/dist/lib/wasm/wasmAllocator.js +66 -44
  145. package/dist/lib/wasm/wasmPhysicalLayout.d.ts +67 -0
  146. package/dist/lib/wasm/wasmPhysicalLayout.d.ts.map +1 -0
  147. package/dist/lib/wasm/wasmPhysicalLayout.js +179 -0
  148. package/dist/lib/wasm/wasmSpanBuffer.d.ts +79 -31
  149. package/dist/lib/wasm/wasmSpanBuffer.d.ts.map +1 -1
  150. package/dist/lib/wasm/wasmSpanBuffer.js +442 -272
  151. package/dist/lib/wasm/wasmTraceRoot.d.ts +24 -22
  152. package/dist/lib/wasm/wasmTraceRoot.d.ts.map +1 -1
  153. package/dist/lib/wasm/wasmTraceRoot.js +110 -71
  154. package/dist/vocabulary/register/v1.d.ts +2 -0
  155. package/dist/vocabulary/register/v1.d.ts.map +1 -0
  156. package/dist/vocabulary/register/v1.js +1 -0
  157. package/dist/wasm.d.ts +5 -0
  158. package/dist/wasm.d.ts.map +1 -0
  159. package/dist/wasm.js +4 -0
  160. package/package.json +54 -6
  161. package/src/index.ts +1 -0
  162. package/src/lib/JsBufferStrategy.ts +27 -9
  163. package/src/lib/__tests__/arrow-builder-integration/arrow-conversion.test.ts +335 -37
  164. package/src/lib/__tests__/arrow-builder-integration/binary-arrow-conversion.test.ts +97 -26
  165. package/src/lib/__tests__/arrow-builder-integration/binary-comparison.test.ts +75 -15
  166. package/src/lib/__tests__/arrow-builder-integration/binary-format-compliance.test.ts +30 -6
  167. package/src/lib/__tests__/arrow-builder-integration/buffer-chaining.test.ts +18 -21
  168. package/src/lib/__tests__/arrow-builder-integration/foundation.test.ts +5 -2
  169. package/src/lib/__tests__/arrow-builder-integration/integration.test.ts +25 -7
  170. package/src/lib/__tests__/arrow-builder-integration/lazy-columns.test.ts +3 -2
  171. package/src/lib/__tests__/buffer-overflow.test.ts +24 -18
  172. package/src/lib/__tests__/capability-span-context.test.ts +505 -0
  173. package/src/lib/__tests__/capacity-tuning.test.ts +5 -3
  174. package/src/lib/__tests__/eager-columns.test.ts +345 -0
  175. package/src/lib/__tests__/enum-metadata-aot.test.ts +153 -0
  176. package/src/lib/__tests__/enum-metadata.test.ts +177 -0
  177. package/src/lib/__tests__/fixtures/empty-vocabulary-runtime.fixture.ts +15 -0
  178. package/src/lib/__tests__/flushScheduler.test.ts +5 -1
  179. package/src/lib/__tests__/identity-view.property.test.ts +179 -0
  180. package/src/lib/__tests__/library.test.ts +19 -235
  181. package/src/lib/__tests__/message-buffer-families.test.ts +878 -0
  182. package/src/lib/__tests__/nested-library-tasks.test.ts +14 -15
  183. package/src/lib/__tests__/op-metadata.test.ts +1 -1
  184. package/src/lib/__tests__/op-type-safety.test.ts +5 -16
  185. package/src/lib/__tests__/physical-layout-plan.test.ts +333 -0
  186. package/src/lib/__tests__/remap-descriptor-integration.test.ts +381 -0
  187. package/src/lib/__tests__/root-context-construction.test.ts +414 -0
  188. package/src/lib/__tests__/span-auto-runtime.test.ts +386 -0
  189. package/src/lib/__tests__/span-buffer-segment-stats.test.ts +221 -0
  190. package/src/lib/__tests__/span-lifecycle.test.ts +53 -25
  191. package/src/lib/__tests__/spanbuffer-materializer-parity.test.ts +266 -0
  192. package/src/lib/__tests__/sync-async-trace.test.ts +24 -23
  193. package/src/lib/__tests__/tag-writer-aot.test.ts +214 -0
  194. package/src/lib/__tests__/test-helpers.ts +67 -12
  195. package/src/lib/__tests__/threadId.test.ts +62 -0
  196. package/src/lib/__tests__/timestamp.test.ts +221 -93
  197. package/src/lib/__tests__/traceTopology.property.test.ts +383 -0
  198. package/src/lib/__tests__/type-narrowing.test.ts +63 -0
  199. package/src/lib/__tests__/vocabulary-dense-decoding.test.ts +405 -0
  200. package/src/lib/__tests__/vocabularyRegistry.test.ts +313 -0
  201. package/src/lib/arrow/lease.ts +43 -0
  202. package/src/lib/arrow/utils.ts +10 -14
  203. package/src/lib/arrow/vocabularyDictionary.ts +123 -0
  204. package/src/lib/bufferStrategy.ts +9 -1
  205. package/src/lib/cloudflare/traceRows.ts +3 -2
  206. package/src/lib/codegen/__tests__/evaluatorGenerator.test.ts +21 -141
  207. package/src/lib/codegen/__tests__/fixedPositionWriter-parity.test.ts +273 -0
  208. package/src/lib/codegen/__tests__/fixedPositionWriter-uint64.test.ts +61 -34
  209. package/src/lib/codegen/__tests__/nullBitmap.test.ts +33 -37
  210. package/src/lib/codegen/__tests__/spanLoggerGenerator.test.ts +34 -18
  211. package/src/lib/codegen/__tests__/spanLoggerMaterializerParity.test.ts +503 -0
  212. package/src/lib/codegen/evaluatorGenerator.ts +18 -13
  213. package/src/lib/codegen/fixedPositionWriterGenerator.ts +329 -245
  214. package/src/lib/codegen/spanLoggerClosureMaterializer.ts +598 -0
  215. package/src/lib/codegen/spanLoggerGenerator.ts +241 -177
  216. package/src/lib/convertToArrow.ts +598 -311
  217. package/src/lib/defineOpContext.ts +1 -1
  218. package/src/lib/enumMetadata.ts +121 -0
  219. package/src/lib/flushScheduler.ts +11 -5
  220. package/src/lib/library.ts +37 -595
  221. package/src/lib/logBinding.ts +21 -27
  222. package/src/lib/op.ts +75 -18
  223. package/src/lib/opContext/__tests__/retry.test.ts +27 -21
  224. package/src/lib/opContext/createOpGroup.ts +33 -31
  225. package/src/lib/opContext/defineOp.ts +88 -11
  226. package/src/lib/opContext/opGroupTypes.ts +2 -2
  227. package/src/lib/opContext/opTypes.ts +1 -1
  228. package/src/lib/opContext/spanContextTypes.ts +122 -24
  229. package/src/lib/opContext/types.ts +7 -3
  230. package/src/lib/physicalLayoutPlan.ts +598 -0
  231. package/src/lib/resolveMessage.ts +67 -0
  232. package/src/lib/result.ts +20 -33
  233. package/src/lib/runtimeHint.ts +98 -0
  234. package/src/lib/schema/__tests__/featureFlags.test.ts +2 -1
  235. package/src/lib/schema/builder.ts +1 -1
  236. package/src/lib/schema/typeGuards.ts +7 -151
  237. package/src/lib/schema/types.ts +1 -1
  238. package/src/lib/span-buffer/aot/v1.ts +26 -0
  239. package/src/lib/spanBuffer.ts +658 -92
  240. package/src/lib/spanBufferStats.ts +1 -1
  241. package/src/lib/spanContext.ts +1350 -861
  242. package/src/lib/sqlite/sqlite-common.ts +20 -31
  243. package/src/lib/testing/__tests__/topology-traversal.test.ts +174 -0
  244. package/src/lib/testing/__tests__/vitest-harness.test.ts +2 -1
  245. package/src/lib/testing/bun-harness.ts +94 -43
  246. package/src/lib/testing/extractFacts.ts +64 -78
  247. package/src/lib/testing/facts.ts +1 -1
  248. package/src/lib/testing/queryable-span.ts +23 -30
  249. package/src/lib/testing/span-query.ts +16 -20
  250. package/src/lib/testing/stdio-replay.ts +25 -8
  251. package/src/lib/testing/vitest-harness.ts +1 -1
  252. package/src/lib/threadId.ts +6 -3
  253. package/src/lib/traceContext.ts +1 -6
  254. package/src/lib/traceRoot.es.ts +77 -42
  255. package/src/lib/traceRoot.node.ts +75 -46
  256. package/src/lib/traceRoot.ts +41 -14
  257. package/src/lib/traceTopology.ts +279 -0
  258. package/src/lib/tracer.ts +109 -98
  259. package/src/lib/tracers/ArrayQueueTracer.ts +1 -1
  260. package/src/lib/tracers/StdioTracer.ts +15 -13
  261. package/src/lib/tracers/TestTracer.ts +6 -8
  262. package/src/lib/tracers/__tests__/ArrayQueueTracer.test.ts +15 -10
  263. package/src/lib/tracers/__tests__/CompositeTracer.test.ts +150 -0
  264. package/src/lib/tracers/__tests__/TestTracer.test.ts +23 -13
  265. package/src/lib/types.ts +64 -33
  266. package/src/lib/vocabularyRegistry.ts +439 -0
  267. package/src/lib/wasm/WasmBufferStrategy.ts +56 -48
  268. package/src/lib/wasm/__tests__/WasmBufferStrategy.test.ts +215 -11
  269. package/src/lib/wasm/__tests__/allocatorFreeBlockClamp.test.ts +86 -0
  270. package/src/lib/wasm/__tests__/wasm-identity-view.test.ts +311 -0
  271. package/src/lib/wasm/__tests__/wasm-integration.test.ts +417 -44
  272. package/src/lib/wasm/__tests__/wasm-message-buffer-families.test.ts +588 -0
  273. package/src/lib/wasm/__tests__/wasmAllocator.test.ts +100 -668
  274. package/src/lib/wasm/__tests__/wasmSpanBuffer.test.ts +419 -63
  275. package/src/lib/wasm/__tests__/wasmTraceRoot.test.ts +24 -29
  276. package/src/lib/wasm/__tests__/wasmTracer.test.ts.disabled +2 -2
  277. package/src/lib/wasm/wasmAllocator.ts +131 -96
  278. package/src/lib/wasm/wasmPhysicalLayout.ts +309 -0
  279. package/src/lib/wasm/wasmSpanBuffer.ts +597 -341
  280. package/src/lib/wasm/wasmTraceRoot.ts +140 -78
  281. package/src/vocabulary/register/v1.ts +1 -0
  282. package/src/wasm.ts +19 -0
  283. package/src/lib/__tests__/remapped-buffer-view-integration.test.ts +0 -319
  284. package/src/lib/__tests__/remapped-buffer-view.test.ts +0 -635
  285. package/src/lib/wasm/allocator.zig +0 -948
@@ -11,7 +11,12 @@
11
11
 
12
12
  import { describe, expect, test } from 'bun:test';
13
13
  import type { CapacityStatsEntry } from '../../arrow/capacityStats.js';
14
- import { convertSpanTreeToArrowTable, convertToArrowTable } from '../../convertToArrow.js';
14
+ import {
15
+ convertSpanTreeToArrowTable,
16
+ convertSpanTreeToLeasedArrowTable,
17
+ convertToArrowTable,
18
+ convertToLeasedArrowTable,
19
+ } from '../../convertToArrow.js';
15
20
  import { DEFAULT_METADATA } from '../../opContext/defineOp.js';
16
21
  import { S } from '../../schema/builder.js';
17
22
  import {
@@ -28,7 +33,6 @@ import {
28
33
  ENTRY_TYPE_WARN,
29
34
  } from '../../schema/systemSchema.js';
30
35
  import { createChildSpanBuffer, createOverflowBuffer, createSpanBuffer, getSpanBufferClass } from '../../spanBuffer.js';
31
- import type { SpanBuffer } from '../../types.js';
32
36
  import { getColumnValue, getRawTimestamp } from '../arrow-test-helpers.js';
33
37
  import { createTestOpMetadata, createTestSchema, createTestTraceRoot } from '../test-helpers.js';
34
38
 
@@ -54,7 +58,11 @@ describe('Arrow Table Conversion', () => {
54
58
 
55
59
  // Write some test data
56
60
  buffer.timestamp[0] = 1000n;
57
- buffer.entry_type[0] = ENTRY_TYPE_SPAN_START;
61
+ {
62
+ const entryTypes = buffer.entry_type;
63
+ if (entryTypes === undefined) throw new Error('Expected split entry-type lane');
64
+ entryTypes[0] = ENTRY_TYPE_SPAN_START;
65
+ }
58
66
  buffer.message(0, 'test-span');
59
67
  buffer.httpStatus(0, 200);
60
68
  buffer.userId(0, 'user-123');
@@ -82,17 +90,29 @@ describe('Arrow Table Conversion', () => {
82
90
 
83
91
  // Write multiple rows
84
92
  buffer.timestamp[0] = 1000n;
85
- buffer.entry_type[0] = ENTRY_TYPE_SPAN_START;
93
+ {
94
+ const entryTypes = buffer.entry_type;
95
+ if (entryTypes === undefined) throw new Error('Expected split entry-type lane');
96
+ entryTypes[0] = ENTRY_TYPE_SPAN_START;
97
+ }
86
98
  buffer.message(0, 'span-1');
87
99
  buffer.level(0, 1); // INFO
88
100
 
89
101
  buffer.timestamp[1] = 2000n;
90
- buffer.entry_type[1] = ENTRY_TYPE_INFO;
102
+ {
103
+ const entryTypes = buffer.entry_type;
104
+ if (entryTypes === undefined) throw new Error('Expected split entry-type lane');
105
+ entryTypes[1] = ENTRY_TYPE_INFO;
106
+ }
91
107
  buffer.message(1, 'Log message');
92
108
  buffer.level(1, 0); // DEBUG
93
109
 
94
110
  buffer.timestamp[2] = 3000n;
95
- buffer.entry_type[2] = ENTRY_TYPE_SPAN_OK;
111
+ {
112
+ const entryTypes = buffer.entry_type;
113
+ if (entryTypes === undefined) throw new Error('Expected split entry-type lane');
114
+ entryTypes[2] = ENTRY_TYPE_SPAN_OK;
115
+ }
96
116
  buffer.message(2, 'span-1');
97
117
  buffer.level(2, 2); // WARN
98
118
 
@@ -125,7 +145,11 @@ describe('Arrow Table Conversion', () => {
125
145
 
126
146
  // Write row with only requiredField set
127
147
  buffer.timestamp[0] = 1000n;
128
- buffer.entry_type[0] = ENTRY_TYPE_SPAN_START;
148
+ {
149
+ const entryTypes = buffer.entry_type;
150
+ if (entryTypes === undefined) throw new Error('Expected split entry-type lane');
151
+ entryTypes[0] = ENTRY_TYPE_SPAN_START;
152
+ }
129
153
  buffer.message(0, 'test-span');
130
154
  buffer.requiredField(0, 42);
131
155
  // optionalField not set - should be null
@@ -150,7 +174,11 @@ describe('Arrow Table Conversion', () => {
150
174
 
151
175
  // Fill first buffer
152
176
  buffer1.timestamp[0] = 1000n;
153
- buffer1.entry_type[0] = ENTRY_TYPE_SPAN_START;
177
+ {
178
+ const entryTypes = buffer1.entry_type;
179
+ if (entryTypes === undefined) throw new Error('Expected split entry-type lane');
180
+ entryTypes[0] = ENTRY_TYPE_SPAN_START;
181
+ }
154
182
  buffer1.message(0, 'test-span');
155
183
  buffer1.counter(0, 1);
156
184
  buffer1._writeIndex = 1;
@@ -158,7 +186,11 @@ describe('Arrow Table Conversion', () => {
158
186
  // Create chained buffer
159
187
  const buffer2 = createOverflowBuffer(buffer1);
160
188
  buffer2.timestamp[0] = 2000n;
161
- buffer2.entry_type[0] = ENTRY_TYPE_INFO;
189
+ {
190
+ const entryTypes = buffer2.entry_type;
191
+ if (entryTypes === undefined) throw new Error('Expected split entry-type lane');
192
+ entryTypes[0] = ENTRY_TYPE_INFO;
193
+ }
162
194
  buffer2.message(0, 'Log in chain');
163
195
  buffer2.counter(0, 2);
164
196
  buffer2._writeIndex = 1;
@@ -182,21 +214,33 @@ describe('Arrow Table Conversion', () => {
182
214
  const buffer1 = createSpanBuffer(schema, createTestTraceRoot('trace-multi-chain'), DEFAULT_METADATA, undefined);
183
215
 
184
216
  buffer1.timestamp[0] = 1000n;
185
- buffer1.entry_type[0] = ENTRY_TYPE_SPAN_START;
217
+ {
218
+ const entryTypes = buffer1.entry_type;
219
+ if (entryTypes === undefined) throw new Error('Expected split entry-type lane');
220
+ entryTypes[0] = ENTRY_TYPE_SPAN_START;
221
+ }
186
222
  buffer1.message(0, 'test');
187
223
  buffer1.value(0, 1);
188
224
  buffer1._writeIndex = 1;
189
225
 
190
226
  const buffer2 = createOverflowBuffer(buffer1);
191
227
  buffer2.timestamp[0] = 2000n;
192
- buffer2.entry_type[0] = ENTRY_TYPE_INFO;
228
+ {
229
+ const entryTypes = buffer2.entry_type;
230
+ if (entryTypes === undefined) throw new Error('Expected split entry-type lane');
231
+ entryTypes[0] = ENTRY_TYPE_INFO;
232
+ }
193
233
  buffer2.message(0, 'log-1');
194
234
  buffer2.value(0, 2);
195
235
  buffer2._writeIndex = 1;
196
236
 
197
237
  const buffer3 = createOverflowBuffer(buffer2);
198
238
  buffer3.timestamp[0] = 3000n;
199
- buffer3.entry_type[0] = ENTRY_TYPE_SPAN_OK;
239
+ {
240
+ const entryTypes = buffer3.entry_type;
241
+ if (entryTypes === undefined) throw new Error('Expected split entry-type lane');
242
+ entryTypes[0] = ENTRY_TYPE_SPAN_OK;
243
+ }
200
244
  buffer3.message(0, 'test');
201
245
  buffer3.value(0, 3);
202
246
  buffer3._writeIndex = 1;
@@ -244,35 +288,45 @@ describe('Arrow Table Conversion', () => {
244
288
  const parentBuffer = createSpanBuffer(schema, createTestTraceRoot('trace-tree'), DEFAULT_METADATA, undefined);
245
289
 
246
290
  parentBuffer.timestamp[0] = 1000n;
247
- parentBuffer.entry_type[0] = ENTRY_TYPE_SPAN_START;
291
+ {
292
+ const entryTypes = parentBuffer.entry_type;
293
+ if (entryTypes === undefined) throw new Error('Expected split entry-type lane');
294
+ entryTypes[0] = ENTRY_TYPE_SPAN_START;
295
+ }
248
296
  parentBuffer.message(0, 'parent-span');
249
297
  parentBuffer.spanType(0, 'parent');
250
298
  parentBuffer._writeIndex = 1;
251
299
 
252
- // Create child span and register with parent
253
- const childBuffer = createChildSpanBuffer(
254
- parentBuffer,
255
- SpanBufferClass,
256
- DEFAULT_METADATA,
257
- DEFAULT_METADATA,
258
- ) as SpanBuffer<typeof schema>;
259
- parentBuffer._children.push(childBuffer); // Explicit registration per spanBuffer.ts
300
+ // Create child span; the factory registers it with the parent topology.
301
+ const childBuffer = createChildSpanBuffer(parentBuffer, SpanBufferClass, DEFAULT_METADATA, DEFAULT_METADATA);
260
302
 
261
303
  childBuffer.timestamp[0] = 1500n;
262
- childBuffer.entry_type[0] = ENTRY_TYPE_SPAN_START;
304
+ {
305
+ const entryTypes = childBuffer.entry_type;
306
+ if (entryTypes === undefined) throw new Error('Expected split entry-type lane');
307
+ entryTypes[0] = ENTRY_TYPE_SPAN_START;
308
+ }
263
309
  childBuffer.message(0, 'child-span');
264
310
  childBuffer.spanType(0, 'child');
265
311
  childBuffer._writeIndex = 1;
266
312
 
267
313
  // Complete child span
268
314
  childBuffer.timestamp[1] = 1800n;
269
- childBuffer.entry_type[1] = ENTRY_TYPE_SPAN_OK;
315
+ {
316
+ const entryTypes = childBuffer.entry_type;
317
+ if (entryTypes === undefined) throw new Error('Expected split entry-type lane');
318
+ entryTypes[1] = ENTRY_TYPE_SPAN_OK;
319
+ }
270
320
  childBuffer.message(1, 'child-span');
271
321
  childBuffer._writeIndex = 2;
272
322
 
273
323
  // Complete parent span
274
324
  parentBuffer.timestamp[1] = 2000n;
275
- parentBuffer.entry_type[1] = ENTRY_TYPE_SPAN_OK;
325
+ {
326
+ const entryTypes = parentBuffer.entry_type;
327
+ if (entryTypes === undefined) throw new Error('Expected split entry-type lane');
328
+ entryTypes[1] = ENTRY_TYPE_SPAN_OK;
329
+ }
276
330
  parentBuffer.message(1, 'parent-span');
277
331
  parentBuffer._writeIndex = 2;
278
332
 
@@ -302,35 +356,57 @@ describe('Arrow Table Conversion', () => {
302
356
  const parentBuffer = createSpanBuffer(schema, createTestTraceRoot('trace-siblings'), DEFAULT_METADATA, undefined);
303
357
 
304
358
  parentBuffer.timestamp[0] = 1000n;
305
- parentBuffer.entry_type[0] = ENTRY_TYPE_SPAN_START;
359
+ {
360
+ const entryTypes = parentBuffer.entry_type;
361
+ if (entryTypes === undefined) throw new Error('Expected split entry-type lane');
362
+ entryTypes[0] = ENTRY_TYPE_SPAN_START;
363
+ }
306
364
  parentBuffer.message(0, 'parent');
307
365
  parentBuffer._writeIndex = 1;
308
366
 
309
- // Create first child and register with parent
367
+ // Create first child; the factory registers it with the parent topology.
310
368
  const child1Buffer = createChildSpanBuffer(parentBuffer, SpanBufferClass, DEFAULT_METADATA, DEFAULT_METADATA);
311
- parentBuffer._children.push(child1Buffer); // Explicit registration per spanBuffer.ts
312
369
  child1Buffer.timestamp[0] = 1100n;
313
- child1Buffer.entry_type[0] = ENTRY_TYPE_SPAN_START;
370
+ {
371
+ const entryTypes = child1Buffer.entry_type;
372
+ if (entryTypes === undefined) throw new Error('Expected split entry-type lane');
373
+ entryTypes[0] = ENTRY_TYPE_SPAN_START;
374
+ }
314
375
  child1Buffer.message(0, 'child-1');
315
376
  child1Buffer.timestamp[1] = 1200n;
316
- child1Buffer.entry_type[1] = ENTRY_TYPE_SPAN_OK;
377
+ {
378
+ const entryTypes = child1Buffer.entry_type;
379
+ if (entryTypes === undefined) throw new Error('Expected split entry-type lane');
380
+ entryTypes[1] = ENTRY_TYPE_SPAN_OK;
381
+ }
317
382
  child1Buffer.message(1, 'child-1');
318
383
  child1Buffer._writeIndex = 2;
319
384
 
320
- // Create second child and register with parent
385
+ // Create second child; the factory preserves sibling insertion order.
321
386
  const child2Buffer = createChildSpanBuffer(parentBuffer, SpanBufferClass, DEFAULT_METADATA, DEFAULT_METADATA);
322
- parentBuffer._children.push(child2Buffer); // Explicit registration per spanBuffer.ts
323
387
  child2Buffer.timestamp[0] = 1300n;
324
- child2Buffer.entry_type[0] = ENTRY_TYPE_SPAN_START;
388
+ {
389
+ const entryTypes = child2Buffer.entry_type;
390
+ if (entryTypes === undefined) throw new Error('Expected split entry-type lane');
391
+ entryTypes[0] = ENTRY_TYPE_SPAN_START;
392
+ }
325
393
  child2Buffer.message(0, 'child-2');
326
394
  child2Buffer.timestamp[1] = 1400n;
327
- child2Buffer.entry_type[1] = ENTRY_TYPE_SPAN_OK;
395
+ {
396
+ const entryTypes = child2Buffer.entry_type;
397
+ if (entryTypes === undefined) throw new Error('Expected split entry-type lane');
398
+ entryTypes[1] = ENTRY_TYPE_SPAN_OK;
399
+ }
328
400
  child2Buffer.message(1, 'child-2');
329
401
  child2Buffer._writeIndex = 2;
330
402
 
331
403
  // Complete parent
332
404
  parentBuffer.timestamp[1] = 1500n;
333
- parentBuffer.entry_type[1] = ENTRY_TYPE_SPAN_OK;
405
+ {
406
+ const entryTypes = parentBuffer.entry_type;
407
+ if (entryTypes === undefined) throw new Error('Expected split entry-type lane');
408
+ entryTypes[1] = ENTRY_TYPE_SPAN_OK;
409
+ }
334
410
  parentBuffer.message(1, 'parent');
335
411
  parentBuffer._writeIndex = 2;
336
412
 
@@ -379,7 +455,11 @@ describe('Arrow Table Conversion', () => {
379
455
  // Write one row for each entry type
380
456
  for (let i = 0; i < entryTypes.length; i++) {
381
457
  buffer.timestamp[i] = BigInt(1000 + i * 100);
382
- buffer.entry_type[i] = entryTypes[i];
458
+ {
459
+ const physicalEntryTypes = buffer.entry_type;
460
+ if (physicalEntryTypes === undefined) throw new Error('Expected split entry-type lane');
461
+ physicalEntryTypes[i] = entryTypes[i];
462
+ }
383
463
  buffer.message(i, `entry-${i}`);
384
464
  }
385
465
  buffer._writeIndex = entryTypes.length;
@@ -404,12 +484,20 @@ describe('Arrow Table Conversion', () => {
404
484
 
405
485
  // Write some span entries
406
486
  buffer.timestamp[0] = 1000n;
407
- buffer.entry_type[0] = ENTRY_TYPE_SPAN_START;
487
+ {
488
+ const entryTypes = buffer.entry_type;
489
+ if (entryTypes === undefined) throw new Error('Expected split entry-type lane');
490
+ entryTypes[0] = ENTRY_TYPE_SPAN_START;
491
+ }
408
492
  buffer.message(0, 'test-span');
409
493
  buffer._writeIndex = 1;
410
494
 
411
495
  buffer.timestamp[1] = 2000n;
412
- buffer.entry_type[1] = ENTRY_TYPE_INFO;
496
+ {
497
+ const entryTypes = buffer.entry_type;
498
+ if (entryTypes === undefined) throw new Error('Expected split entry-type lane');
499
+ entryTypes[1] = ENTRY_TYPE_INFO;
500
+ }
413
501
  buffer.message(1, 'Test log message');
414
502
  buffer._writeIndex = 2;
415
503
 
@@ -482,4 +570,214 @@ describe('Arrow Table Conversion', () => {
482
570
  expect(toBigInt(getColumnValue(table, 'uint64_value', 3))).toBe(64n); // capacity
483
571
  });
484
572
  });
573
+
574
+ describe('leased chunked conversion', () => {
575
+ test('pins source chunks until idempotent release and preserves exact schema, nulls, and tree preorder', () => {
576
+ const schema = createTestSchema({ value: S.number(), label: S.category() });
577
+ const SpanBufferClass = getSpanBufferClass(schema);
578
+ const root = createSpanBuffer(schema, createTestTraceRoot('leased-tree'), DEFAULT_METADATA, 8);
579
+ root.timestamp[0] = 1000n;
580
+ {
581
+ const entryTypes = root.entry_type;
582
+ if (entryTypes === undefined) throw new Error('Expected split entry-type lane');
583
+ entryTypes[0] = ENTRY_TYPE_SPAN_START;
584
+ }
585
+ root.message(0, 'root-start');
586
+ root.value(0, 11);
587
+ root.label(0, 'root');
588
+ root.timestamp[1] = 1100n;
589
+ {
590
+ const entryTypes = root.entry_type;
591
+ if (entryTypes === undefined) throw new Error('Expected split entry-type lane');
592
+ entryTypes[1] = ENTRY_TYPE_SPAN_OK;
593
+ }
594
+ root._writeIndex = 2;
595
+
596
+ const overflow = createOverflowBuffer(root);
597
+ overflow.timestamp[0] = 1200n;
598
+ {
599
+ const entryTypes = overflow.entry_type;
600
+ if (entryTypes === undefined) throw new Error('Expected split entry-type lane');
601
+ entryTypes[0] = ENTRY_TYPE_INFO;
602
+ }
603
+ overflow.message(0, 'overflow-log');
604
+ overflow.value(0, 22);
605
+ overflow._writeIndex = 1;
606
+
607
+ const child = createChildSpanBuffer(root, SpanBufferClass, DEFAULT_METADATA, DEFAULT_METADATA);
608
+ child.timestamp[0] = 1300n;
609
+ {
610
+ const entryTypes = child.entry_type;
611
+ if (entryTypes === undefined) throw new Error('Expected split entry-type lane');
612
+ entryTypes[0] = ENTRY_TYPE_SPAN_START;
613
+ }
614
+ child.message(0, 'child-start');
615
+ child.label(0, 'child');
616
+ child.value(0, 0);
617
+ const childValueNulls = child.getNullsIfAllocated('value');
618
+ if (!(childValueNulls instanceof Uint8Array)) throw new Error('Expected child value validity');
619
+ childValueNulls[0] &= ~1;
620
+ child._writeIndex = 1;
621
+
622
+ const topology = root._traceRoot._topology;
623
+ const generation = topology.generation;
624
+ const lease = convertSpanTreeToLeasedArrowTable(root);
625
+ expect(lease.released).toBe(false);
626
+ expect(lease.table.names).toEqual([
627
+ 'timestamp',
628
+ 'trace_id',
629
+ 'thread_id',
630
+ 'span_id',
631
+ 'parent_thread_id',
632
+ 'parent_span_id',
633
+ 'entry_type',
634
+ 'package_name',
635
+ 'package_file',
636
+ 'git_sha',
637
+ 'message',
638
+ 'uint64_value',
639
+ 'value',
640
+ 'label',
641
+ ]);
642
+ const timestampColumn = lease.table.getChild('timestamp');
643
+ if (!timestampColumn) throw new Error('Missing leased timestamp column');
644
+ const rawTimestamps = timestampColumn.data.flatMap((batch) => {
645
+ if (!(batch.values instanceof BigInt64Array)) throw new Error('Expected raw BigInt64Array timestamps');
646
+ return Array.from(batch.values.subarray(0, batch.length));
647
+ });
648
+ expect(rawTimestamps).toEqual([1000n, 1100n, 1200n, 1300n]);
649
+ expect(
650
+ Array.from({ length: lease.table.numRows }, (_, row) => getColumnValue(lease.table, 'message', row)),
651
+ ).toEqual(['root-start', null, 'overflow-log', 'child-start']);
652
+ expect(
653
+ Array.from({ length: lease.table.numRows }, (_, row) => getColumnValue(lease.table, 'value', row)),
654
+ ).toEqual([11, null, 22, null]);
655
+ expect(
656
+ Array.from({ length: lease.table.numRows }, (_, row) => getColumnValue(lease.table, 'label', row)),
657
+ ).toEqual(['root', null, null, 'child']);
658
+
659
+ const valueColumn = lease.table.getChild('value');
660
+ if (!valueColumn) throw new Error('Missing leased value column');
661
+ const sourceColumns = [root, overflow, child].map((buffer) => {
662
+ const source = buffer.getColumnIfAllocated('value');
663
+ if (!(source instanceof Float64Array)) throw new Error('Expected source Float64Array');
664
+ return source;
665
+ });
666
+ expect(valueColumn.data).toHaveLength(3);
667
+ expect(valueColumn.data.map((batch) => batch.values.buffer)).toEqual(
668
+ sourceColumns.map((source) => source.buffer),
669
+ );
670
+ expect(topology.generation).toBe(generation);
671
+ expect(() => topology.assertLive(root)).not.toThrow();
672
+
673
+ root._traceRoot.tracer.bufferStrategy.releaseBuffer(root);
674
+ expect(topology.generation).toBe(generation);
675
+ expect(() => topology.assertLive(root)).toThrow('stale');
676
+ expect(getColumnValue(lease.table, 'message', 2)).toBe('overflow-log');
677
+ lease.release();
678
+ expect(lease.released).toBe(true);
679
+ expect(topology.generation).toBe(generation + 1);
680
+ expect(() => topology.assertLive(root)).toThrow('stale');
681
+ expect(() => lease.release()).not.toThrow();
682
+ expect(() => lease[Symbol.dispose]()).not.toThrow();
683
+ });
684
+
685
+ test('borrows nonpacked entry types but derives packed entry types without aliasing row headers', () => {
686
+ const schema = createTestSchema({ value: S.number() });
687
+ for (const physicalLayout of ['current', 'specialized', 'packed'] as const) {
688
+ const SpanBufferClass = getSpanBufferClass(schema, 'mixed', physicalLayout);
689
+ const root = createSpanBuffer(
690
+ schema,
691
+ createTestTraceRoot(`leased-entry-${physicalLayout}`),
692
+ DEFAULT_METADATA,
693
+ 8,
694
+ SpanBufferClass,
695
+ );
696
+ root.timestamp[0] = 1000n;
697
+ root.timestamp[1] = 1100n;
698
+ root.timestamp[2] = 1200n;
699
+ if (physicalLayout !== 'packed') {
700
+ if (root.entry_type === undefined) throw new Error('Expected split entry-type lane');
701
+ {
702
+ const entryTypes = root.entry_type;
703
+ if (entryTypes === undefined) throw new Error('Expected split entry-type lane');
704
+ entryTypes[0] = ENTRY_TYPE_SPAN_START;
705
+ }
706
+ {
707
+ const entryTypes = root.entry_type;
708
+ if (entryTypes === undefined) throw new Error('Expected split entry-type lane');
709
+ entryTypes[1] = ENTRY_TYPE_INFO;
710
+ }
711
+ {
712
+ const entryTypes = root.entry_type;
713
+ if (entryTypes === undefined) throw new Error('Expected split entry-type lane');
714
+ entryTypes[2] = ENTRY_TYPE_SPAN_OK;
715
+ }
716
+ } else {
717
+ if (root._rowHeaders === undefined) throw new Error('Expected packed row-header lane');
718
+ root._rowHeaders[0] = ENTRY_TYPE_SPAN_START;
719
+ root._rowHeaders[1] = ENTRY_TYPE_INFO;
720
+ root._rowHeaders[2] = ENTRY_TYPE_SPAN_OK;
721
+ }
722
+ root.message(0, `${physicalLayout}-root`);
723
+ root.message(1, `${physicalLayout}-raw`);
724
+ root.value(1, 42);
725
+ root._writeIndex = 3;
726
+
727
+ const lease = convertToLeasedArrowTable(root);
728
+ expect(Array.from({ length: 3 }, (_, row) => getColumnValue(lease.table, 'entry_type', row))).toEqual([
729
+ 'span-start',
730
+ 'info',
731
+ 'span-ok',
732
+ ]);
733
+ expect(Array.from({ length: 3 }, (_, row) => getColumnValue(lease.table, 'message', row))).toEqual([
734
+ `${physicalLayout}-root`,
735
+ `${physicalLayout}-raw`,
736
+ null,
737
+ ]);
738
+ const entryTypes = lease.table.getChild('entry_type');
739
+ if (!entryTypes) throw new Error('Missing leased entry_type column');
740
+ const values = entryTypes.data[0]?.values;
741
+ if (!(values instanceof Int8Array)) throw new Error('Expected dictionary entry-type indices');
742
+ if (physicalLayout !== 'packed') {
743
+ if (root.entry_type === undefined) throw new Error('Expected split entry-type lane');
744
+ expect(values.buffer).toBe(root.entry_type.buffer);
745
+ } else {
746
+ if (root._rowHeaders === undefined) throw new Error('Expected packed row-header lane');
747
+ expect(values.buffer).not.toBe(root._rowHeaders.buffer);
748
+ }
749
+ lease.release();
750
+ }
751
+ });
752
+
753
+ test('keeps the single-buffer Table API semantically identical while exposing leased source reuse', () => {
754
+ const schema = createTestSchema({ value: S.number() });
755
+ const root = createSpanBuffer(schema, createTestTraceRoot('leased-single'), DEFAULT_METADATA, 8);
756
+ root.timestamp[0] = 2000n;
757
+ {
758
+ const entryTypes = root.entry_type;
759
+ if (entryTypes === undefined) throw new Error('Expected split entry-type lane');
760
+ entryTypes[0] = ENTRY_TYPE_INFO;
761
+ }
762
+ root.message(0, 'single');
763
+ root.value(0, 42);
764
+ root._writeIndex = 1;
765
+
766
+ const legacy = convertToArrowTable(root);
767
+ const lease = convertToLeasedArrowTable(root);
768
+ expect(lease.table.names).toEqual(legacy.names);
769
+ expect(lease.table.numRows).toBe(legacy.numRows);
770
+ for (const name of ['timestamp', 'entry_type', 'message', 'value']) {
771
+ expect(getColumnValue(lease.table, name, 0)).toEqual(getColumnValue(legacy, name, 0));
772
+ }
773
+ const source = root.getColumnIfAllocated('value');
774
+ if (!(source instanceof Float64Array)) throw new Error('Expected source Float64Array');
775
+ const valueColumn = lease.table.getChild('value');
776
+ if (!valueColumn) throw new Error('Missing leased value column');
777
+ expect(valueColumn.data[0]?.values.buffer).toBe(source.buffer);
778
+ root._traceRoot.tracer.bufferStrategy.releaseBuffer(root);
779
+ lease[Symbol.dispose]();
780
+ expect(lease.released).toBe(true);
781
+ });
782
+ });
485
783
  });