@bitcobblers/wod-wiki-lang 0.42.2148 → 0.43.2149

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/dist/index.cjs CHANGED
@@ -4960,6 +4960,284 @@ var ExecutionContext = class {
4960
4960
  }
4961
4961
  }
4962
4962
  };
4963
+
4964
+ // src/runtime/RuntimeLogFormat.ts
4965
+ var RUNTIME_LOG_SUBJECT_WIDTH = 24;
4966
+ var pad2 = (n) => String(n).padStart(2, "0");
4967
+ var pad3 = (n) => String(n).padStart(3, "0");
4968
+ function formatRuntimeTimestamp(d) {
4969
+ return `${pad2(d.getHours())}:${pad2(d.getMinutes())}:${pad2(d.getSeconds())}.${pad3(d.getMilliseconds())}`;
4970
+ }
4971
+ function padRuntimeLogEvent(event) {
4972
+ return (event + " ").slice(0, 5);
4973
+ }
4974
+ function padRuntimeLogSubject(subject) {
4975
+ return (subject + " ".repeat(RUNTIME_LOG_SUBJECT_WIDTH)).slice(0, RUNTIME_LOG_SUBJECT_WIDTH);
4976
+ }
4977
+ function formatRuntimeLogLine(timestamp, event, subject, payload) {
4978
+ return `${formatRuntimeTimestamp(timestamp)} ${padRuntimeLogEvent(event)} ${padRuntimeLogSubject(subject)}${payload ? " " + payload : ""}`;
4979
+ }
4980
+ function formatRuntimeLogRule(label) {
4981
+ const width = 52;
4982
+ if (!label) return "\u2500".repeat(width);
4983
+ const inner = ` ${label} `;
4984
+ const left = Math.max(0, Math.floor((width - inner.length) / 2));
4985
+ const right = Math.max(0, width - inner.length - left);
4986
+ return `${"\u2500".repeat(left)}${inner}${"\u2500".repeat(right)}`;
4987
+ }
4988
+
4989
+ // src/runtime/RuntimeLogger.ts
4990
+ var RuntimeLoggerImpl = class {
4991
+ // Console is this logger's designated output sink; all writes funnel
4992
+ // through this single reference so the no-console rule is waived once.
4993
+ // eslint-disable-next-line no-console
4994
+ _console = console;
4995
+ _enabled = false;
4996
+ _history = [];
4997
+ _maxHistory = 500;
4998
+ EVENT_STYLES = {
4999
+ BOOT: "color: #3b82f6; font-weight: bold",
5000
+ // primary
5001
+ PUSH: "color: #a855f7; font-weight: bold",
5002
+ // rounds violet
5003
+ POP: "color: #64748b",
5004
+ // muted
5005
+ NEXT: "color: #b45309; font-weight: bold",
5006
+ // action ochre
5007
+ EVNT: "color: #a855f7; font-weight: bold",
5008
+ // violet
5009
+ OUT: "color: #16a34a; font-weight: bold",
5010
+ // effort green
5011
+ MEM: "color: #f59e0b",
5012
+ // amber
5013
+ TIME: "color: #3b82f6; font-weight: bold",
5014
+ // time slate
5015
+ HALT: "color: #ef4444; font-weight: bold",
5016
+ // destructive
5017
+ WARN: "color: #f59e0b; font-weight: bold",
5018
+ ERR: "color: #ef4444; font-weight: bold"
5019
+ };
5020
+ constructor() {
5021
+ if (typeof window !== "undefined") {
5022
+ const debugWindow = window;
5023
+ this._enabled = !!debugWindow.__WOD_DEBUG__;
5024
+ }
5025
+ }
5026
+ get enabled() {
5027
+ return this._enabled;
5028
+ }
5029
+ enable() {
5030
+ this._enabled = true;
5031
+ this.writeLine("BOOT", "runtime:ready", "logging enabled");
5032
+ }
5033
+ disable() {
5034
+ this.writeLine("HALT", "runtime:logger", "logging disabled");
5035
+ this._enabled = false;
5036
+ }
5037
+ getHistory() {
5038
+ return [...this._history];
5039
+ }
5040
+ clearHistory() {
5041
+ this._history = [];
5042
+ }
5043
+ // ============================================================================
5044
+ // Logging Methods
5045
+ // ============================================================================
5046
+ /**
5047
+ * Log runtime construction. Called once by ScriptRuntime's constructor;
5048
+ * dropped when logging is disabled, so cheap to leave wired.
5049
+ */
5050
+ logBoot(detail) {
5051
+ if (!this._enabled) return;
5052
+ this.writeLine("BOOT", "runtime:ready", detail);
5053
+ }
5054
+ /**
5055
+ * Log when a block is pushed onto the stack. `depth` is the 1-based
5056
+ * stack depth the block landed at (prototype's `dN` column).
5057
+ */
5058
+ logPush(block, parentKey, depth) {
5059
+ if (!this._enabled) return;
5060
+ const behaviors = this.getBehaviorNames(block);
5061
+ const payload = [
5062
+ `d${depth ?? "?"} ${block.blockType ?? "block"}`,
5063
+ behaviors.length > 0 ? `behaviors [${behaviors.join(", ")}]` : void 0,
5064
+ parentKey ? `parent ${parentKey.slice(0, 8)}` : void 0
5065
+ ].filter(Boolean).join(" \xB7 ");
5066
+ this.writeLine("PUSH", block.label || block.blockType || "Block", payload);
5067
+ this.addToHistory("info", "push", `PUSH ${block.label}`, {
5068
+ key: block.key.toString(),
5069
+ parentKey,
5070
+ behaviors,
5071
+ sourceIds: block.sourceIds
5072
+ });
5073
+ }
5074
+ /**
5075
+ * Log when a block is popped from the stack. `depth` is the 1-based
5076
+ * depth the block occupied (prototype's `dN` column).
5077
+ */
5078
+ logPop(block, reason, depth) {
5079
+ if (!this._enabled) return;
5080
+ this.writeLine("POP", block.label || block.blockType || "Block", `d${depth ?? "?"}${reason ? " " + reason : ""}`);
5081
+ this.addToHistory("info", "pop", `POP ${block.label}`, {
5082
+ key: block.key.toString(),
5083
+ reason
5084
+ });
5085
+ }
5086
+ /**
5087
+ * Log when next() is called on a block
5088
+ */
5089
+ logNext(block, actions) {
5090
+ if (!this._enabled) return;
5091
+ if (actions.length === 0) return;
5092
+ const actionNames = actions.map((a) => a.type || a.constructor?.name || "Action");
5093
+ this.writeLine("NEXT", block.label || "Block", `${actionNames.length} action(s): [${actionNames.join(", ")}]`);
5094
+ this.addToHistory("info", "next", `NEXT ${block.label}`, {
5095
+ key: block.key.toString(),
5096
+ actions: actionNames
5097
+ });
5098
+ }
5099
+ /**
5100
+ * Log when an event produces actions
5101
+ */
5102
+ logEvent(event, actions) {
5103
+ if (!this._enabled) return;
5104
+ if (actions.length === 0) return;
5105
+ const actionNames = actions.map((a) => a.type || a.constructor?.name || "Action");
5106
+ this.writeLine("EVNT", event.name, `${actionNames.length} action(s): [${actionNames.join(", ")}]`);
5107
+ this.addToHistory("info", "event", `EVENT ${event.name}`, {
5108
+ eventName: event.name,
5109
+ eventData: event.data,
5110
+ actions: actionNames
5111
+ });
5112
+ }
5113
+ /**
5114
+ * Log an output statement (segment / milestone). Called by OutputEmitter
5115
+ * on every published output. 'system' outputs (sound cues etc.) and
5116
+ * label-less structural outputs (the boot 'load' statement) are skipped —
5117
+ * volume stays proportional to what the athlete did.
5118
+ */
5119
+ logOutput(output) {
5120
+ if (!this._enabled) return;
5121
+ if (output.outputType !== "segment" && output.outputType !== "milestone") return;
5122
+ const subject = output.text || this.outputSubject(output.metrics);
5123
+ if (!subject) return;
5124
+ this.writeLine("OUT", subject, output.outputType);
5125
+ this.addToHistory("info", "output", `OUT ${subject}`, {
5126
+ outputType: output.outputType,
5127
+ label: subject
5128
+ });
5129
+ }
5130
+ /** No `label` field exists on outputs — fall back to the explicit Label
5131
+ * metric (image, then value), matching the UI's naming convention. */
5132
+ outputSubject(metrics) {
5133
+ if (!metrics) return void 0;
5134
+ for (const m of metrics) {
5135
+ if (m.type === "label") return m.image || (m.value != null ? String(m.value) : "") || void 0;
5136
+ }
5137
+ return void 0;
5138
+ }
5139
+ /**
5140
+ * Log when memory is updated on a block
5141
+ */
5142
+ logMemoryUpdate(blockKey, memoryType, value) {
5143
+ if (!this._enabled) return;
5144
+ const displayValue = typeof value === "object" && value !== null ? this.summarizeObject(value) : value;
5145
+ this.writeLine("MEM", memoryType, `[${blockKey.slice(0, 8)}] ${safeJson(displayValue)}`);
5146
+ this.addToHistory("debug", "memory", `MEMORY ${memoryType}`, {
5147
+ blockKey,
5148
+ memoryType,
5149
+ value: displayValue
5150
+ });
5151
+ }
5152
+ /**
5153
+ * Log action execution
5154
+ */
5155
+ logAction(action, depth) {
5156
+ if (!this._enabled) return;
5157
+ const actionName = action.type || action.constructor?.name || "Action";
5158
+ this.writeLine("EVNT", actionName, `d${depth}`);
5159
+ }
5160
+ /**
5161
+ * General-purpose message log for runtime consumers.
5162
+ * Gates on _enabled; writes to the console sink and history.
5163
+ */
5164
+ logMessage(level, category, message, data) {
5165
+ if (!this._enabled) return;
5166
+ this.writeLine(level === "error" ? "ERR" : level === "warn" ? "WARN" : "EVNT", category, message);
5167
+ this.addToHistory(level, category, message, data);
5168
+ }
5169
+ /**
5170
+ * Always-on variant of `logMessage`. Use sparingly for errors/warnings that
5171
+ * must be visible even when debug logging is disabled.
5172
+ */
5173
+ logAlways(level, category, message, data) {
5174
+ this.writeLine(level === "error" ? "ERR" : level === "warn" ? "WARN" : "EVNT", category, message);
5175
+ this.addToHistory(level, category, message, data);
5176
+ }
5177
+ /** A round-boundary rule in the paper format (prototype tier 04). */
5178
+ logRule(label) {
5179
+ if (!this._enabled) return;
5180
+ this._console.log(`%c${formatRuntimeLogRule(label)}`, "color: #94a3b8");
5181
+ }
5182
+ // ============================================================================
5183
+ // Helpers
5184
+ // ============================================================================
5185
+ /**
5186
+ * The one console write path: a single paper line with the event code
5187
+ * tinted. `addToHistory` stays separate — entries carry structured data,
5188
+ * lines carry display text.
5189
+ */
5190
+ writeLine(code, subject, payload) {
5191
+ const ts = formatRuntimeTimestamp(/* @__PURE__ */ new Date());
5192
+ this._console.log(
5193
+ `${ts} %c${padRuntimeLogEvent(code)}%c ${padRuntimeLogSubject(subject)}${payload ? " " + payload : ""}`,
5194
+ this.EVENT_STYLES[code],
5195
+ "color: inherit"
5196
+ );
5197
+ }
5198
+ getBehaviorNames(block) {
5199
+ const blockWithBehaviors = block;
5200
+ const behaviors = blockWithBehaviors.behaviors;
5201
+ if (!behaviors || !Array.isArray(behaviors)) return [];
5202
+ return behaviors.map((b) => b.constructor?.name || "Behavior");
5203
+ }
5204
+ summarizeObject(obj) {
5205
+ const summary = {};
5206
+ for (const [key, val] of Object.entries(obj)) {
5207
+ if (Array.isArray(val)) {
5208
+ summary[key] = `[${val.length} items]`;
5209
+ } else if (typeof val === "object" && val !== null) {
5210
+ summary[key] = "{...}";
5211
+ } else {
5212
+ summary[key] = val;
5213
+ }
5214
+ }
5215
+ return summary;
5216
+ }
5217
+ addToHistory(level, category, message, data) {
5218
+ this._history.push({
5219
+ timestamp: /* @__PURE__ */ new Date(),
5220
+ level,
5221
+ category,
5222
+ message,
5223
+ data
5224
+ });
5225
+ if (this._history.length > this._maxHistory) {
5226
+ this._history = this._history.slice(-this._maxHistory);
5227
+ }
5228
+ }
5229
+ };
5230
+ function safeJson(value) {
5231
+ try {
5232
+ return JSON.stringify(value) ?? "";
5233
+ } catch {
5234
+ return String(value);
5235
+ }
5236
+ }
5237
+ var RuntimeLogger = new RuntimeLoggerImpl();
5238
+ if (typeof window !== "undefined") {
5239
+ window.RuntimeLogger = RuntimeLogger;
5240
+ }
4963
5241
  var OutputEmitter = class {
4964
5242
  _outputStatements = [];
4965
5243
  _outputListeners = /* @__PURE__ */ new Set();
@@ -5013,6 +5291,7 @@ var OutputEmitter = class {
5013
5291
  }
5014
5292
  const processed = this._analyticsEngine ? this._analyticsEngine.run(output) : output;
5015
5293
  this._propagateSourceLine(processed);
5294
+ RuntimeLogger.logOutput(processed);
5016
5295
  this._outputStatements.push(processed);
5017
5296
  for (const listener of this._outputListeners) {
5018
5297
  try {
@@ -5358,249 +5637,6 @@ var RuntimeObservers = class {
5358
5637
  }
5359
5638
  };
5360
5639
 
5361
- // src/runtime/RuntimeLogger.ts
5362
- var RuntimeLoggerImpl = class {
5363
- // Console is this logger's designated output sink; all writes funnel
5364
- // through this single reference so the no-console rule is waived once.
5365
- // eslint-disable-next-line no-console
5366
- _console = console;
5367
- _enabled = false;
5368
- _history = [];
5369
- _maxHistory = 500;
5370
- // Style constants for console output
5371
- STYLES = {
5372
- push: "color: #22c55e; font-weight: bold",
5373
- // green
5374
- pop: "color: #ef4444; font-weight: bold",
5375
- // red
5376
- next: "color: #3b82f6; font-weight: bold",
5377
- // blue
5378
- event: "color: #a855f7; font-weight: bold",
5379
- // purple
5380
- memory: "color: #f59e0b; font-weight: bold",
5381
- // amber
5382
- action: "color: #6366f1; font-weight: normal",
5383
- // indigo
5384
- origin: "color: #64748b; font-weight: normal"
5385
- // slate
5386
- };
5387
- constructor() {
5388
- if (typeof window !== "undefined") {
5389
- const debugWindow = window;
5390
- this._enabled = !!debugWindow.__WOD_DEBUG__;
5391
- }
5392
- }
5393
- get enabled() {
5394
- return this._enabled;
5395
- }
5396
- enable() {
5397
- this._enabled = true;
5398
- this._console.log("%c[RT] \u{1F527} Runtime logging ENABLED", "color: #22c55e; font-weight: bold");
5399
- }
5400
- disable() {
5401
- this._enabled = false;
5402
- this._console.log("%c[RT] Runtime logging disabled", "color: #64748b");
5403
- }
5404
- getHistory() {
5405
- return [...this._history];
5406
- }
5407
- clearHistory() {
5408
- this._history = [];
5409
- }
5410
- // ============================================================================
5411
- // Logging Methods
5412
- // ============================================================================
5413
- /**
5414
- * Log when a block is pushed onto the stack
5415
- */
5416
- logPush(block, parentKey) {
5417
- if (!this._enabled) return;
5418
- const behaviors = this.getBehaviorNames(block);
5419
- const memoryTypes = block.getAllMemory?.().map((loc) => loc.tag) ?? [];
5420
- this._console.groupCollapsed(
5421
- `%c[RT] \u25B6 PUSH %c${block.label || block.blockType || "Block"}%c [${block.key.toString().slice(0, 8)}]`,
5422
- this.STYLES.push,
5423
- "color: inherit; font-weight: bold",
5424
- "color: #64748b; font-weight: normal"
5425
- );
5426
- this._console.log("Key:", block.key.toString());
5427
- if (parentKey) this._console.log("Parent:", parentKey);
5428
- this._console.log("Source IDs:", block.sourceIds);
5429
- this._console.log("Behaviors:", behaviors);
5430
- if (memoryTypes.length > 0) this._console.log("Memory Types:", memoryTypes);
5431
- this._console.groupEnd();
5432
- this.addToHistory("info", "push", `PUSH ${block.label}`, {
5433
- key: block.key.toString(),
5434
- parentKey,
5435
- behaviors,
5436
- sourceIds: block.sourceIds
5437
- });
5438
- }
5439
- /**
5440
- * Log when a block is popped from the stack
5441
- */
5442
- logPop(block, reason) {
5443
- if (!this._enabled) return;
5444
- this._console.log(
5445
- `%c[RT] \u25C0 POP %c${block.label || block.blockType || "Block"}%c [${block.key.toString().slice(0, 8)}]${reason ? ` (${reason})` : ""}`,
5446
- this.STYLES.pop,
5447
- "color: inherit; font-weight: bold",
5448
- "color: #64748b; font-weight: normal"
5449
- );
5450
- this.addToHistory("info", "pop", `POP ${block.label}`, {
5451
- key: block.key.toString(),
5452
- reason
5453
- });
5454
- }
5455
- /**
5456
- * Log when next() is called on a block
5457
- */
5458
- logNext(block, actions) {
5459
- if (!this._enabled) return;
5460
- const actionNames = actions.map((a) => a.type || a.constructor?.name || "Action");
5461
- if (actions.length === 0) {
5462
- return;
5463
- }
5464
- this._console.groupCollapsed(
5465
- `%c[RT] \u2192 NEXT %c${block.label || "Block"}%c \u2192 ${actions.length} action(s)`,
5466
- this.STYLES.next,
5467
- "color: inherit; font-weight: bold",
5468
- "color: #64748b; font-weight: normal"
5469
- );
5470
- this._console.log("Block:", block.key.toString());
5471
- this._console.log("Actions:", actionNames);
5472
- this._console.groupEnd();
5473
- this.addToHistory("info", "next", `NEXT ${block.label}`, {
5474
- key: block.key.toString(),
5475
- actions: actionNames
5476
- });
5477
- }
5478
- /**
5479
- * Log when an event produces actions
5480
- */
5481
- logEvent(event, actions) {
5482
- if (!this._enabled) return;
5483
- if (actions.length === 0) return;
5484
- const actionNames = actions.map((a) => a.type || a.constructor?.name || "Action");
5485
- this._console.groupCollapsed(
5486
- `%c[RT] \u26A1 EVENT %c${event.name}%c \u2192 ${actions.length} action(s)`,
5487
- this.STYLES.event,
5488
- "color: inherit; font-weight: bold",
5489
- "color: #64748b; font-weight: normal"
5490
- );
5491
- this._console.log("Event Data:", event.data);
5492
- this._console.log("Actions:", actionNames);
5493
- this._console.groupEnd();
5494
- this.addToHistory("info", "event", `EVENT ${event.name}`, {
5495
- eventName: event.name,
5496
- eventData: event.data,
5497
- actions: actionNames
5498
- });
5499
- }
5500
- /**
5501
- * Log when memory is updated on a block
5502
- */
5503
- logMemoryUpdate(blockKey, memoryType, value) {
5504
- if (!this._enabled) return;
5505
- let displayValue = value;
5506
- if (typeof value === "object" && value !== null) {
5507
- displayValue = this.summarizeObject(value);
5508
- }
5509
- this._console.log(
5510
- `%c[RT] \u{1F4DD} MEMORY %c${memoryType}%c on [${blockKey.slice(0, 8)}]:`,
5511
- this.STYLES.memory,
5512
- "color: inherit; font-weight: bold",
5513
- "color: #64748b; font-weight: normal",
5514
- displayValue
5515
- );
5516
- this.addToHistory("debug", "memory", `MEMORY ${memoryType}`, {
5517
- blockKey,
5518
- memoryType,
5519
- value: displayValue
5520
- });
5521
- }
5522
- /**
5523
- * Log action execution (verbose, under a group)
5524
- */
5525
- logAction(action, depth) {
5526
- if (!this._enabled) return;
5527
- const indent = " ".repeat(depth);
5528
- const actionName = action.type || action.constructor?.name || "Action";
5529
- this._console.log(
5530
- `%c[RT] ${indent}\u2699 %c${actionName}`,
5531
- this.STYLES.action,
5532
- "color: inherit"
5533
- );
5534
- }
5535
- /**
5536
- * General-purpose message log for runtime consumers.
5537
- * Gates on _enabled; writes to the console sink and history.
5538
- */
5539
- logMessage(level, category, message, data) {
5540
- if (!this._enabled) return;
5541
- this._console.log(`%c[RT] ${category} %c${message}`, this.styleFor(level), "color: inherit");
5542
- this.addToHistory(level, category, message, data);
5543
- }
5544
- /**
5545
- * Always-on variant of `logMessage`. Use sparingly for errors/warnings that
5546
- * must be visible even when debug logging is disabled.
5547
- */
5548
- logAlways(level, category, message, data) {
5549
- this._console.log(`%c[RT] ${category} %c${message}`, this.styleFor(level), "color: inherit");
5550
- this.addToHistory(level, category, message, data);
5551
- }
5552
- // ============================================================================
5553
- // Helpers
5554
- // ============================================================================
5555
- getBehaviorNames(block) {
5556
- const blockWithBehaviors = block;
5557
- const behaviors = blockWithBehaviors.behaviors;
5558
- if (!behaviors || !Array.isArray(behaviors)) return [];
5559
- return behaviors.map((b) => b.constructor?.name || "Behavior");
5560
- }
5561
- summarizeObject(obj) {
5562
- const summary = {};
5563
- for (const [key, val] of Object.entries(obj)) {
5564
- if (Array.isArray(val)) {
5565
- summary[key] = `[${val.length} items]`;
5566
- } else if (typeof val === "object" && val !== null) {
5567
- summary[key] = "{...}";
5568
- } else {
5569
- summary[key] = val;
5570
- }
5571
- }
5572
- return summary;
5573
- }
5574
- styleFor(level) {
5575
- switch (level) {
5576
- case "error":
5577
- return "color: #ef4444; font-weight: bold";
5578
- case "warn":
5579
- return "color: #f59e0b; font-weight: bold";
5580
- case "info":
5581
- return "color: #3b82f6; font-weight: bold";
5582
- default:
5583
- return "color: #64748b";
5584
- }
5585
- }
5586
- addToHistory(level, category, message, data) {
5587
- this._history.push({
5588
- timestamp: /* @__PURE__ */ new Date(),
5589
- level,
5590
- category,
5591
- message,
5592
- data
5593
- });
5594
- if (this._history.length > this._maxHistory) {
5595
- this._history = this._history.slice(-this._maxHistory);
5596
- }
5597
- }
5598
- };
5599
- var RuntimeLogger = new RuntimeLoggerImpl();
5600
- if (typeof window !== "undefined") {
5601
- window.RuntimeLogger = RuntimeLogger;
5602
- }
5603
-
5604
5640
  // src/runtime/actions/stack/PushBlockAction.ts
5605
5641
  var PushBlockAction = class {
5606
5642
  constructor(block, options = {}) {
@@ -5634,7 +5670,7 @@ var PushBlockAction = class {
5634
5670
  runtime.stack.push(this.block);
5635
5671
  const mountActions = this.block.mount(runtime, lifecycle);
5636
5672
  const parentKey = runtime.stack.blocks.length > 1 ? runtime.stack.blocks[1]?.key.toString() : void 0;
5637
- RuntimeLogger.logPush(this.block, parentKey);
5673
+ RuntimeLogger.logPush(this.block, parentKey, runtime.stack.blocks.length);
5638
5674
  return mountActions;
5639
5675
  } catch (error) {
5640
5676
  const runtimeWithSetError = runtime;
@@ -5665,7 +5701,7 @@ var PopBlockAction = class {
5665
5701
  }
5666
5702
  if (!current.isComplete && typeof current.markComplete === "function") {
5667
5703
  current.markComplete("forced-pop");
5668
- RuntimeLogger.logPop(current, "forced-pop (incomplete block popped without next)");
5704
+ RuntimeLogger.logPop(current, "forced-pop (incomplete block popped without next)", runtime.stack.blocks.length);
5669
5705
  }
5670
5706
  const unmountActions = current.unmount(runtime, lifecycleOptions) ?? [];
5671
5707
  const popped = runtime.stack.pop();
@@ -5675,7 +5711,7 @@ var PopBlockAction = class {
5675
5711
  popped.dispose(runtime);
5676
5712
  popped.context?.release?.();
5677
5713
  if (popped.completionReason !== "forced-pop") {
5678
- RuntimeLogger.logPop(popped, popped.completionReason);
5714
+ RuntimeLogger.logPop(popped, popped.completionReason, runtime.stack.blocks.length + 1);
5679
5715
  }
5680
5716
  const parent = runtime.stack.current;
5681
5717
  return parent ? [...unmountActions, new NextAction(lifecycleOptions, runtime.nowProvider)] : unmountActions;
@@ -5714,6 +5750,7 @@ var ScriptRuntime = class {
5714
5750
  });
5715
5751
  this.clock.start();
5716
5752
  this._output.emitLoad();
5753
+ RuntimeLogger.logBoot(`statements ${this.script.statements.length}`);
5717
5754
  }
5718
5755
  script;
5719
5756
  eventBus;
@@ -8451,6 +8488,10 @@ var ReportOutputBehavior = class {
8451
8488
  writeResultMemory(ctx, resultFragments) {
8452
8489
  const existing = ctx.block.getMemoryByTag("metric:result");
8453
8490
  if (existing.length > 0) {
8491
+ const preserved = collectUserOriginMetrics(existing);
8492
+ if (preserved.length > 0) {
8493
+ resultFragments = resultFragments.clone().add(...preserved);
8494
+ }
8454
8495
  ctx.updateMemory("metric:result", resultFragments.toArray());
8455
8496
  return;
8456
8497
  }
@@ -8458,11 +8499,22 @@ var ReportOutputBehavior = class {
8458
8499
  }
8459
8500
  writeResultGroups(ctx, resultGroups) {
8460
8501
  const existing = ctx.block.getMemoryByTag("metric:result");
8461
- if (existing.length > 0) {
8502
+ if (existing.length === 0) {
8503
+ for (const group of resultGroups) {
8504
+ ctx.pushMemory("metric:result", group.toArray());
8505
+ }
8462
8506
  return;
8463
8507
  }
8464
- for (const group of resultGroups) {
8465
- ctx.pushMemory("metric:result", group.toArray());
8508
+ const count = Math.max(existing.length, resultGroups.length);
8509
+ for (let i = 0; i < count; i++) {
8510
+ const base = resultGroups[i] ? resultGroups[i].clone() : existing[i].metrics.clone();
8511
+ const userMetrics = resultGroups[i] && i < existing.length ? collectUserOriginMetrics([existing[i]]) : [];
8512
+ const merged = base.add(...userMetrics);
8513
+ if (i < existing.length) {
8514
+ existing[i].update(merged);
8515
+ } else {
8516
+ ctx.pushMemory("metric:result", merged.toArray());
8517
+ }
8466
8518
  }
8467
8519
  }
8468
8520
  formatLabel(ctx) {
@@ -8472,6 +8524,15 @@ var ReportOutputBehavior = class {
8472
8524
  return round.total !== void 0 ? `Round ${round.current} of ${round.total}` : `Round ${round.current}`;
8473
8525
  }
8474
8526
  };
8527
+ function collectUserOriginMetrics(locations) {
8528
+ const userMetrics = [];
8529
+ for (const loc of locations) {
8530
+ for (const m of loc.metrics) {
8531
+ if (m.origin === "user") userMetrics.push(m);
8532
+ }
8533
+ }
8534
+ return userMetrics;
8535
+ }
8475
8536
  var SoundMetric = class {
8476
8537
  constructor(sound, trigger, options = {}) {
8477
8538
  this.sound = sound;
@@ -10801,8 +10862,7 @@ var CalcEngine = class {
10801
10862
  for (const segment of segments) {
10802
10863
  if (segment.outputType !== "segment") continue;
10803
10864
  if (exclusion && matchesExclusion(effortOf(segment).slug, exclusion)) continue;
10804
- for (const metric of segment.metrics.rawMetrics) {
10805
- if (metric.type !== metricType) continue;
10865
+ for (const metric of segment.getDisplayMetrics({ types: [metricType] })) {
10806
10866
  const value = numericMetricValue(metric);
10807
10867
  if (value === void 0) continue;
10808
10868
  values.push(value);
@@ -14869,6 +14929,7 @@ exports.PushBlockAction = PushBlockAction;
14869
14929
  exports.PushRestBlockAction = PushRestBlockAction;
14870
14930
  exports.REST_EXCLUSION = REST_EXCLUSION;
14871
14931
  exports.RPE_LABELS = RPE_LABELS;
14932
+ exports.RUNTIME_LOG_SUBJECT_WIDTH = RUNTIME_LOG_SUBJECT_WIDTH;
14872
14933
  exports.RegisterEventHandlerAction = RegisterEventHandlerAction;
14873
14934
  exports.Registry = Registry;
14874
14935
  exports.ReportOutputBehavior = ReportOutputBehavior;
@@ -14984,6 +15045,9 @@ exports.fixtureUserCustom = fixtureUserCustom;
14984
15045
  exports.fixtureUserOverride = fixtureUserOverride;
14985
15046
  exports.formatDim = formatDim;
14986
15047
  exports.formatDuration = formatDuration;
15048
+ exports.formatRuntimeLogLine = formatRuntimeLogLine;
15049
+ exports.formatRuntimeLogRule = formatRuntimeLogRule;
15050
+ exports.formatRuntimeTimestamp = formatRuntimeTimestamp;
14987
15051
  exports.fragmentsToLabel = metricsToLabel;
14988
15052
  exports.frozenNow = frozenNow;
14989
15053
  exports.fullFixtureSet = fullFixtureSet;
@@ -15014,6 +15078,8 @@ exports.num = num;
15014
15078
  exports.openSpan = openSpan;
15015
15079
  exports.outputNodeId = outputNodeId;
15016
15080
  exports.outputNodeIds = outputNodeIds;
15081
+ exports.padRuntimeLogEvent = padRuntimeLogEvent;
15082
+ exports.padRuntimeLogSubject = padRuntimeLogSubject;
15017
15083
  exports.parseCalcLine = parseCalcLine;
15018
15084
  exports.parseCalculateBlock = parseCalculateBlock;
15019
15085
  exports.parseEffortFile = parseEffortFile;