@bitcobblers/wod-wiki-lang 0.43.2153 → 0.44.2155
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/{browserRuntimeNow-M4hQ_DTl.d.cts → browserRuntimeNow-_zhhbzoE.d.cts} +294 -2
- package/dist/{browserRuntimeNow-M4hQ_DTl.d.ts → browserRuntimeNow-_zhhbzoE.d.ts} +294 -2
- package/dist/index.cjs +1497 -1116
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +246 -325
- package/dist/index.d.ts +246 -325
- package/dist/index.mjs +1483 -1115
- package/dist/index.mjs.map +1 -1
- package/dist/react.cjs.map +1 -1
- package/dist/react.d.cts +2 -2
- package/dist/react.d.ts +2 -2
- package/dist/react.mjs.map +1 -1
- package/package.json +2 -2
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { ReferenceMatchKind, ReferenceRef, ReferenceDiagnostic, ICodeStatement, ParseError, MetricContainer, IMetric, BlockKey, TimeSpan as TimeSpan$1, OutputStatementType, MetricType, IOutputStatement, MetricOrigin } from '@bitcobblers/wod-wiki-core';
|
|
1
|
+
import { ReferenceMatchKind, ReferenceRef, ReferenceDiagnostic, ICodeStatement, ParseError, TagIndex, MetricContainer, IMetric, BlockKey, TimeSpan as TimeSpan$1, OutputStatementType, TagReferenceMetadata, MetricType, IOutputStatement, MetricOrigin } from '@bitcobblers/wod-wiki-core';
|
|
2
2
|
|
|
3
3
|
/**
|
|
4
4
|
* Canonical discipline vocabulary — the single source of truth for effort
|
|
@@ -587,6 +587,260 @@ interface TestableBlockConfig {
|
|
|
587
587
|
disposeOverride?: (runtime: IRuntimeActionable) => void;
|
|
588
588
|
}
|
|
589
589
|
|
|
590
|
+
/**
|
|
591
|
+
* Sound profiles — user-defined rule sets that drive workout audio.
|
|
592
|
+
*
|
|
593
|
+
* A profile is a list of rules. Each rule names a **trigger point** (an offset
|
|
594
|
+
* relative to the block's own duration) and the **sound** to play there. The
|
|
595
|
+
* profile therefore decides both *when* a sound fires and *what* it is.
|
|
596
|
+
*
|
|
597
|
+
* ## Trigger notation
|
|
598
|
+
*
|
|
599
|
+
* A trigger is a duration offset written in the whiteboard duration notation,
|
|
600
|
+
* with a leading anchor that says which end of the block it counts from:
|
|
601
|
+
*
|
|
602
|
+
* - `:00` — the **start** of the block (elapsed = 0).
|
|
603
|
+
* - `-:00` — the **end** of the block (remaining = 0).
|
|
604
|
+
* - `-:03` — three seconds before the end (remaining).
|
|
605
|
+
* - `:05:00` — five minutes after the start (elapsed).
|
|
606
|
+
*
|
|
607
|
+
* The magnitude accepts every duration spelling the language already
|
|
608
|
+
* understands — `05:00`, `5:00`, `00:05:00` and `5` all mean the same
|
|
609
|
+
* duration. The anchor is what distinguishes the two families:
|
|
610
|
+
*
|
|
611
|
+
* | Anchor | Counts from | Fires when |
|
|
612
|
+
* |--------|-------------|------------|
|
|
613
|
+
* | `:` | block start | elapsed reaches the offset |
|
|
614
|
+
* | `-:` | block end | remaining falls to the offset |
|
|
615
|
+
*
|
|
616
|
+
* Because the offset is relative to the block's own duration, one profile
|
|
617
|
+
* works for any block length: the same `-:03` rule beeps three seconds
|
|
618
|
+
* before the end of a 5:00 run and three seconds before the end of a 1:00
|
|
619
|
+
* rest.
|
|
620
|
+
*/
|
|
621
|
+
/** Which end of the block a trigger counts from. */
|
|
622
|
+
type SoundTriggerAnchor = 'start' | 'end';
|
|
623
|
+
/** A trigger point: an anchor plus an offset from that anchor. */
|
|
624
|
+
interface SoundTriggerPoint {
|
|
625
|
+
/** Counts from the block's start (`start`) or its end (`end`). */
|
|
626
|
+
readonly anchor: SoundTriggerAnchor;
|
|
627
|
+
/** Offset from the anchor, in milliseconds. Never negative. */
|
|
628
|
+
readonly offsetMs: number;
|
|
629
|
+
}
|
|
630
|
+
/** One rule in a profile: a trigger point plus the sound to play there. */
|
|
631
|
+
interface SoundRule {
|
|
632
|
+
/** When the sound fires. */
|
|
633
|
+
readonly trigger: SoundTriggerPoint;
|
|
634
|
+
/** Name of the sound to play. Resolved against the app's sound table. */
|
|
635
|
+
readonly sound: string;
|
|
636
|
+
}
|
|
637
|
+
/** A named, user-defined set of sound rules. */
|
|
638
|
+
interface SoundProfile {
|
|
639
|
+
/** Stable identifier (slug). Unique across profiles. */
|
|
640
|
+
readonly id: string;
|
|
641
|
+
/** Human-readable name shown in Settings. */
|
|
642
|
+
readonly name: string;
|
|
643
|
+
/** The rules, in declaration order. */
|
|
644
|
+
readonly rules: readonly SoundRule[];
|
|
645
|
+
}
|
|
646
|
+
/**
|
|
647
|
+
* Parse a trigger notation into a {@link SoundTriggerPoint}.
|
|
648
|
+
*
|
|
649
|
+
* The anchor says which end of the block the offset counts from:
|
|
650
|
+
*
|
|
651
|
+
* - `:` — from the block's start (elapsed). This is the default, so the
|
|
652
|
+
* magnitude may be written with or without it: `:05:00`, `05:00`,
|
|
653
|
+
* `00:05:00` and `5:00` all mean five minutes from the start.
|
|
654
|
+
* - `-` — from the block's end (remaining). The colon is optional here
|
|
655
|
+
* too: `-:03` and `-03` both mean three seconds remaining.
|
|
656
|
+
*
|
|
657
|
+
* The magnitude accepts every duration spelling the language already
|
|
658
|
+
* understands: `5` (seconds), `5:00` (minutes), `00:05:00` (hours).
|
|
659
|
+
*
|
|
660
|
+
* @returns the parsed trigger, or `undefined` when the notation is malformed.
|
|
661
|
+
*/
|
|
662
|
+
declare function parseSoundTrigger(notation: string): SoundTriggerPoint | undefined;
|
|
663
|
+
/**
|
|
664
|
+
* Format a trigger back into its canonical notation.
|
|
665
|
+
*
|
|
666
|
+
* `:00` for the start, `-:00` for the end, `-:03` for three seconds before
|
|
667
|
+
* the end, `:05:00` for five minutes after the start.
|
|
668
|
+
*/
|
|
669
|
+
declare function formatSoundTrigger(trigger: SoundTriggerPoint): string;
|
|
670
|
+
/**
|
|
671
|
+
* Resolve a profile's rules against a block's duration, dropping any rule
|
|
672
|
+
* whose trigger point can never be reached.
|
|
673
|
+
*
|
|
674
|
+
* - A rule anchored to the **start** measures elapsed time, so it always
|
|
675
|
+
* applies — no duration needed.
|
|
676
|
+
* - A rule anchored to the **end** with no offset means "when the block
|
|
677
|
+
* ends", so it always applies too.
|
|
678
|
+
* - A rule anchored to the **end** with an offset needs a duration to count
|
|
679
|
+
* down from. It applies only when the block's duration is known and long
|
|
680
|
+
* enough to reach it.
|
|
681
|
+
*
|
|
682
|
+
* A rule that cannot be reached is dropped silently — an unreachable trigger
|
|
683
|
+
* is not an authoring error, it is simply a rule that does not apply to this
|
|
684
|
+
* block.
|
|
685
|
+
*
|
|
686
|
+
* @param profile the profile whose rules to resolve
|
|
687
|
+
* @param durationMs the block's duration in milliseconds, when known
|
|
688
|
+
*/
|
|
689
|
+
declare function resolveProfileRules(profile: SoundProfile, durationMs: number | undefined): SoundRule[];
|
|
690
|
+
/**
|
|
691
|
+
* The profile applied when nothing selects one.
|
|
692
|
+
*
|
|
693
|
+
* A three-two-one countdown into a completion cue — the behaviour the app
|
|
694
|
+
* has always implied but never actually played.
|
|
695
|
+
*/
|
|
696
|
+
declare const DEFAULT_SOUND_PROFILE: SoundProfile;
|
|
697
|
+
|
|
698
|
+
/**
|
|
699
|
+
* AST for the composed-calculation expression language (spec §2).
|
|
700
|
+
*
|
|
701
|
+
* One expression language across all three scopes; scope only changes how
|
|
702
|
+
* atoms resolve. `wql` atoms are legal in store scope only (executed by
|
|
703
|
+
* QueryService); stream aggregates (`sum(reps)`) are builtin calls resolved
|
|
704
|
+
* by the engine, not by this core.
|
|
705
|
+
*/
|
|
706
|
+
type BinaryOp = '+' | '-' | '*' | '/' | '==' | '!=' | '<' | '<=' | '>' | '>=' | 'and' | 'or';
|
|
707
|
+
type ExprNode = {
|
|
708
|
+
kind: 'literal';
|
|
709
|
+
value: number;
|
|
710
|
+
} | {
|
|
711
|
+
kind: 'period';
|
|
712
|
+
days: number;
|
|
713
|
+
} | {
|
|
714
|
+
kind: 'string';
|
|
715
|
+
value: string;
|
|
716
|
+
}
|
|
717
|
+
/** Metric ref, context node (`session.duration`), or library node ref. */
|
|
718
|
+
| {
|
|
719
|
+
kind: 'ref';
|
|
720
|
+
name: string;
|
|
721
|
+
} | {
|
|
722
|
+
kind: 'call';
|
|
723
|
+
name: string;
|
|
724
|
+
args: ExprNode[];
|
|
725
|
+
}
|
|
726
|
+
/** Effort-exclusion filter argument: `without: rest|pause|rest-*`. */
|
|
727
|
+
| {
|
|
728
|
+
kind: 'filter';
|
|
729
|
+
value: string;
|
|
730
|
+
} | {
|
|
731
|
+
kind: 'unary';
|
|
732
|
+
op: '-' | 'not';
|
|
733
|
+
arg: ExprNode;
|
|
734
|
+
} | {
|
|
735
|
+
kind: 'binary';
|
|
736
|
+
op: BinaryOp;
|
|
737
|
+
left: ExprNode;
|
|
738
|
+
right: ExprNode;
|
|
739
|
+
}
|
|
740
|
+
/** Store-scope WQL selection, e.g. `sum:sessionLoad{} by {day}`. */
|
|
741
|
+
| {
|
|
742
|
+
kind: 'wql';
|
|
743
|
+
aggregator: string;
|
|
744
|
+
metric: string;
|
|
745
|
+
filters?: string;
|
|
746
|
+
groupBy?: string[];
|
|
747
|
+
};
|
|
748
|
+
/** A parsed calc line: `name = expr -> unit when predicate`. */
|
|
749
|
+
interface CalcLine {
|
|
750
|
+
name: string;
|
|
751
|
+
expr: ExprNode;
|
|
752
|
+
unit?: string;
|
|
753
|
+
when?: ExprNode;
|
|
754
|
+
}
|
|
755
|
+
|
|
756
|
+
/**
|
|
757
|
+
* Exponent-vector dimension model for the composed calculations layer.
|
|
758
|
+
*
|
|
759
|
+
* Dimensions are 5-element exponent vectors over base physical quantities:
|
|
760
|
+
* [L, M, T, C, E] = [length, mass, time, count(reps), energy(cal)]
|
|
761
|
+
*
|
|
762
|
+
* Algebra (docs/composed-calculations-spec.md §5.1):
|
|
763
|
+
* Dim(a * b) = Dim(a) + Dim(b)
|
|
764
|
+
* Dim(a / b) = Dim(a) − Dim(b)
|
|
765
|
+
* Dim(a ± b) requires Dim(a) = Dim(b) (static registration failure otherwise)
|
|
766
|
+
*/
|
|
767
|
+
type DimVector = readonly [number, number, number, number, number];
|
|
768
|
+
declare const DIM_ZERO: DimVector;
|
|
769
|
+
declare const DIM_LENGTH: DimVector;
|
|
770
|
+
declare const DIM_MASS: DimVector;
|
|
771
|
+
declare const DIM_TIME: DimVector;
|
|
772
|
+
declare const DIM_COUNT: DimVector;
|
|
773
|
+
declare const DIM_ENERGY: DimVector;
|
|
774
|
+
declare function addDim(a: DimVector, b: DimVector): DimVector;
|
|
775
|
+
declare function subDim(a: DimVector, b: DimVector): DimVector;
|
|
776
|
+
declare function dimEquals(a: DimVector, b: DimVector): boolean;
|
|
777
|
+
declare function isDimensionless(d: DimVector): boolean;
|
|
778
|
+
/** Human-readable vector, e.g. "T·L⁻¹" for pace. */
|
|
779
|
+
declare function formatDim(d: DimVector): string;
|
|
780
|
+
/**
|
|
781
|
+
* Named compound dimension registry (spec §5.2). Used for diagnostics and
|
|
782
|
+
* dimension-filtered unit suggestions — not required for evaluation.
|
|
783
|
+
*/
|
|
784
|
+
declare const NAMED_COMPOUNDS: Record<string, {
|
|
785
|
+
dim: DimVector;
|
|
786
|
+
preferredUnits: string[];
|
|
787
|
+
}>;
|
|
788
|
+
/** Reverse lookup: find the compound name for a vector, if one exists. */
|
|
789
|
+
declare function compoundName(d: DimVector): string | undefined;
|
|
790
|
+
|
|
791
|
+
/**
|
|
792
|
+
* Canonical Node DAG records (spec §2.2) — the storage/registration form for
|
|
793
|
+
* calculations. Seeds are TS object literals (#849); the line-form parser
|
|
794
|
+
* (#863) must round-trip these losslessly.
|
|
795
|
+
*/
|
|
796
|
+
|
|
797
|
+
type CalcOrigin = 'analyzed' | 'analyzed-estimated' | 'user';
|
|
798
|
+
type CalcScope = 'segment' | 'workout' | 'store';
|
|
799
|
+
interface CalcNode {
|
|
800
|
+
id: string;
|
|
801
|
+
kind: 'metric' | 'lookup' | 'builtin' | 'wql' | 'expr';
|
|
802
|
+
expression?: string;
|
|
803
|
+
ast?: ExprNode;
|
|
804
|
+
/**
|
|
805
|
+
* Declared node unit. Named zero-vector casts (AU, pts, MET-min, ratio)
|
|
806
|
+
* override the computed vector (§5.3 applied to intermediate nodes —
|
|
807
|
+
* required by TIS-shaped formulas that fold time into a score); any other
|
|
808
|
+
* unit must match the computed vector.
|
|
809
|
+
*/
|
|
810
|
+
unit?: string;
|
|
811
|
+
}
|
|
812
|
+
interface CalcVariant {
|
|
813
|
+
id: string;
|
|
814
|
+
priority: number;
|
|
815
|
+
when?: string;
|
|
816
|
+
whenAst?: ExprNode;
|
|
817
|
+
origin: CalcOrigin;
|
|
818
|
+
nodes: Record<string, CalcNode>;
|
|
819
|
+
/** Node dimensions computed at registration (static check output). */
|
|
820
|
+
nodeDims?: Record<string, DimVector>;
|
|
821
|
+
}
|
|
822
|
+
interface CalculationDefinition {
|
|
823
|
+
id: string;
|
|
824
|
+
kind: 'output' | 'library';
|
|
825
|
+
scope: CalcScope;
|
|
826
|
+
fences?: string[];
|
|
827
|
+
when?: string;
|
|
828
|
+
whenAst?: ExprNode;
|
|
829
|
+
variants: CalcVariant[];
|
|
830
|
+
output?: {
|
|
831
|
+
nodeId: string | string[];
|
|
832
|
+
key?: string;
|
|
833
|
+
emitType?: string;
|
|
834
|
+
unit?: string;
|
|
835
|
+
isGrouped?: boolean;
|
|
836
|
+
/** Group dimensions for grouped emission (e.g. ['effort']). */
|
|
837
|
+
groupBy?: string[];
|
|
838
|
+
publishMetadataNodes?: string[];
|
|
839
|
+
/** Display label for published facts (store-scope rollups). */
|
|
840
|
+
label?: string;
|
|
841
|
+
};
|
|
842
|
+
}
|
|
843
|
+
|
|
590
844
|
/**
|
|
591
845
|
* Factory function type for wrapping blocks in debug mode.
|
|
592
846
|
* Receives the original block and returns a wrapped version.
|
|
@@ -673,6 +927,35 @@ interface RuntimeStackOptions extends IRuntimeOptions {
|
|
|
673
927
|
userProfile?: {
|
|
674
928
|
vo2max?: number;
|
|
675
929
|
};
|
|
930
|
+
/**
|
|
931
|
+
* The functions available to the run — user-authored calculations,
|
|
932
|
+
* registered after the built-ins.
|
|
933
|
+
*/
|
|
934
|
+
calcs?: CalculationDefinition[];
|
|
935
|
+
/**
|
|
936
|
+
* The tag catalogue: the tags a script can reference with `#slug`
|
|
937
|
+
* and the functions they carry.
|
|
938
|
+
*/
|
|
939
|
+
tags?: TagIndex;
|
|
940
|
+
/**
|
|
941
|
+
* Tags active for the whole run, whatever the segments say — the
|
|
942
|
+
* bundle a profile applies.
|
|
943
|
+
*/
|
|
944
|
+
activeTags?: readonly string[];
|
|
945
|
+
};
|
|
946
|
+
/**
|
|
947
|
+
* Sound configuration for this run.
|
|
948
|
+
*
|
|
949
|
+
* `profiles` are the user's sound profiles, available for selection.
|
|
950
|
+
* `noteProfileId` is the profile selected for the note as a whole — the
|
|
951
|
+
* note-level `sound-{profile}` tag, resolved by the host before the
|
|
952
|
+
* runtime starts. A block that names its own profile overrides it.
|
|
953
|
+
*
|
|
954
|
+
* With neither, blocks fall back to the default profile.
|
|
955
|
+
*/
|
|
956
|
+
soundOptions?: {
|
|
957
|
+
profiles?: readonly SoundProfile[];
|
|
958
|
+
noteProfileId?: string;
|
|
676
959
|
};
|
|
677
960
|
}
|
|
678
961
|
|
|
@@ -1687,6 +1970,15 @@ interface CompletionDecision {
|
|
|
1687
1970
|
* - Memory usage should be minimized during execution
|
|
1688
1971
|
*/
|
|
1689
1972
|
interface IRuntimeBlock extends IBlockRef {
|
|
1973
|
+
/**
|
|
1974
|
+
* The tag composition of this block — the tags its statements referenced,
|
|
1975
|
+
* and what each carried (the functions it activates, the sound profile it
|
|
1976
|
+
* names).
|
|
1977
|
+
*
|
|
1978
|
+
* Resolved at compile time, so the runtime and the surfaces that show a
|
|
1979
|
+
* block know which tags shaped it without re-reading the catalogue.
|
|
1980
|
+
*/
|
|
1981
|
+
readonly tagComposition?: readonly TagReferenceMetadata[];
|
|
1690
1982
|
/**
|
|
1691
1983
|
* Execution timing metadata propagated by the runtime (start/completion timestamps).
|
|
1692
1984
|
* Implementations can rely on RuntimeStack/PushBlockAction to set this.
|
|
@@ -2521,4 +2813,4 @@ declare function getRuntimeNowMs(): number;
|
|
|
2521
2813
|
/** Creates an INowProvider that reads the browser sender-clock when available. */
|
|
2522
2814
|
declare function createBrowserRuntimeNow(): INowProvider;
|
|
2523
2815
|
|
|
2524
|
-
export { type
|
|
2816
|
+
export { type IEventHandler as $, type AnalyticsContext as A, type BehaviorEventType as B, type IBlockContext as C, type MetricVisibility as D, type EffortResolverOptions as E, type BlockLifecycleOptions as F, type CompletionDecision as G, type IRuntimeMemory as H, type IEquipment as I, TypedMemoryReference as J, type MemorySearchCriteria as K, type IMemoryReference as L, type MemoryTag as M, type RuntimeStackLogger as N, type OutputListener as O, type StackObserver as P, type StackSnapshot as Q, type ReferenceIndex as R, type SubscribeOptions as S, TimeSpan as T, type Unsubscribe as U, type StackListener as V, WhiteboardScript as W, MemoryTypeEnum as X, type IAnchorValue as Y, type SoundProfile as Z, type ButtonConfig as _, type ReferenceResolutionDefaults as a, type ScriptRuntimeDependencies as a$, type HandlerScope as a0, type IScriptRuntime as a1, type TestableBlockConfig as a2, type IRuntimeOptions as a3, ScriptRuntime as a4, type EventHandlerOptions as a5, type EventCallback as a6, type TimerState as a7, type CalculationDefinition as a8, type IRealtimeProcessor as a9, type DisplayState as aA, EFFORT_DISCIPLINES as aB, EFFORT_REGISTRY_ORIGINS as aC, type EffortBaseAttributes as aD, type EffortDerivation as aE, type EffortDiscipline as aF, type EffortMaterializer as aG, type EffortResolvedFrom as aH, type EquipmentStorageAdapter as aI, type FenceDialect as aJ, type FragmentDisplayState as aK, type FragmentState as aL, type IAnalyticsProcessorDescriptor as aM, type IEquipmentRegistry as aN, INTENSITY_TIERS as aO, type IScript as aP, type IntensityTier as aQ, type InterceptMode as aR, MemoryLocation as aS, type MemoryType as aT, type MemoryTypeMap as aU, type MemoryValueOf as aV, NAMED_COMPOUNDS as aW, type ReferenceCatalog as aX, type ResolvedReferences as aY, type RoundState as aZ, type RuntimeState as a_, type ISummaryProcessor as aa, type ProjectionResult as ab, type DimVector as ac, type CalcLine as ad, type ExprNode as ae, type CalcScope as af, type BinaryOp as ag, type ButtonVariant as ah, type ButtonsState as ai, CATALOG_PRECEDENCE_RANK as aj, type CalcNode as ak, type CalcOrigin as al, type CalcVariant as am, type CatalogPrecedenceTier as an, type ChildrenStatusState as ao, type CompletionState as ap, DEFAULT_RESOLVER_OPTIONS as aq, DEFAULT_RUNTIME_OPTIONS as ar, DEFAULT_SOUND_PROFILE as as, DIM_COUNT as at, DIM_ENERGY as au, DIM_LENGTH as av, DIM_MASS as aw, DIM_TIME as ax, DIM_ZERO as ay, DISCIPLINE_FACTORS as az, type IEffort as b, type SoundRule as b0, type SoundTriggerAnchor as b1, type SoundTriggerPoint as b2, type StackEvent as b3, type TimerDirection as b4, VISIBILITY_ICONS as b5, VISIBILITY_LABELS as b6, addDim as b7, compoundName as b8, createBrowserRuntimeNow as b9, createReferenceIndex as ba, dedupeEntitiesByPrecedence as bb, dimEquals as bc, disciplineFactorFor as bd, extractStatementRefs as be, filterTagsByVisibility as bf, formatDim as bg, formatSoundTrigger as bh, frozenNow as bi, getMetricVisibility as bj, getRuntimeNowMs as bk, isDimensionless as bl, isEffortDiscipline as bm, isFragmentTag as bn, parseSoundTrigger as bo, resolveEntityRank as bp, resolveEntityTier as bq, resolveProfileRules as br, resolveSourceRank as bs, resolveSourceTier as bt, slugifyRefLabel as bu, subDim as bv, wallClockNow as bw, type IEffortResolver as c, type IEffortRegistry as d, type EffortResolutionOptions as e, type ResolvedEffort as f, type EffortRegistrySource as g, type EffortStorageAdapter as h, type IRuntimeActionable as i, type IEventBus as j, type IRuntimeStack as k, type IRuntimeClock as l, type IJitCompiler as m, type INowProvider as n, type RuntimeStackOptions as o, type RuntimeError as p, type IEvent as q, type IRuntimeAction as r, type IAnalyticsEngine as s, type IRuntimeBlock as t, type IBehaviorContext as u, type BehaviorEventListener as v, type Unsubscribe$1 as w, type OutputOptions as x, type IMemoryLocation as y, type IRuntimeBehavior as z };
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { ReferenceMatchKind, ReferenceRef, ReferenceDiagnostic, ICodeStatement, ParseError, MetricContainer, IMetric, BlockKey, TimeSpan as TimeSpan$1, OutputStatementType, MetricType, IOutputStatement, MetricOrigin } from '@bitcobblers/wod-wiki-core';
|
|
1
|
+
import { ReferenceMatchKind, ReferenceRef, ReferenceDiagnostic, ICodeStatement, ParseError, TagIndex, MetricContainer, IMetric, BlockKey, TimeSpan as TimeSpan$1, OutputStatementType, TagReferenceMetadata, MetricType, IOutputStatement, MetricOrigin } from '@bitcobblers/wod-wiki-core';
|
|
2
2
|
|
|
3
3
|
/**
|
|
4
4
|
* Canonical discipline vocabulary — the single source of truth for effort
|
|
@@ -587,6 +587,260 @@ interface TestableBlockConfig {
|
|
|
587
587
|
disposeOverride?: (runtime: IRuntimeActionable) => void;
|
|
588
588
|
}
|
|
589
589
|
|
|
590
|
+
/**
|
|
591
|
+
* Sound profiles — user-defined rule sets that drive workout audio.
|
|
592
|
+
*
|
|
593
|
+
* A profile is a list of rules. Each rule names a **trigger point** (an offset
|
|
594
|
+
* relative to the block's own duration) and the **sound** to play there. The
|
|
595
|
+
* profile therefore decides both *when* a sound fires and *what* it is.
|
|
596
|
+
*
|
|
597
|
+
* ## Trigger notation
|
|
598
|
+
*
|
|
599
|
+
* A trigger is a duration offset written in the whiteboard duration notation,
|
|
600
|
+
* with a leading anchor that says which end of the block it counts from:
|
|
601
|
+
*
|
|
602
|
+
* - `:00` — the **start** of the block (elapsed = 0).
|
|
603
|
+
* - `-:00` — the **end** of the block (remaining = 0).
|
|
604
|
+
* - `-:03` — three seconds before the end (remaining).
|
|
605
|
+
* - `:05:00` — five minutes after the start (elapsed).
|
|
606
|
+
*
|
|
607
|
+
* The magnitude accepts every duration spelling the language already
|
|
608
|
+
* understands — `05:00`, `5:00`, `00:05:00` and `5` all mean the same
|
|
609
|
+
* duration. The anchor is what distinguishes the two families:
|
|
610
|
+
*
|
|
611
|
+
* | Anchor | Counts from | Fires when |
|
|
612
|
+
* |--------|-------------|------------|
|
|
613
|
+
* | `:` | block start | elapsed reaches the offset |
|
|
614
|
+
* | `-:` | block end | remaining falls to the offset |
|
|
615
|
+
*
|
|
616
|
+
* Because the offset is relative to the block's own duration, one profile
|
|
617
|
+
* works for any block length: the same `-:03` rule beeps three seconds
|
|
618
|
+
* before the end of a 5:00 run and three seconds before the end of a 1:00
|
|
619
|
+
* rest.
|
|
620
|
+
*/
|
|
621
|
+
/** Which end of the block a trigger counts from. */
|
|
622
|
+
type SoundTriggerAnchor = 'start' | 'end';
|
|
623
|
+
/** A trigger point: an anchor plus an offset from that anchor. */
|
|
624
|
+
interface SoundTriggerPoint {
|
|
625
|
+
/** Counts from the block's start (`start`) or its end (`end`). */
|
|
626
|
+
readonly anchor: SoundTriggerAnchor;
|
|
627
|
+
/** Offset from the anchor, in milliseconds. Never negative. */
|
|
628
|
+
readonly offsetMs: number;
|
|
629
|
+
}
|
|
630
|
+
/** One rule in a profile: a trigger point plus the sound to play there. */
|
|
631
|
+
interface SoundRule {
|
|
632
|
+
/** When the sound fires. */
|
|
633
|
+
readonly trigger: SoundTriggerPoint;
|
|
634
|
+
/** Name of the sound to play. Resolved against the app's sound table. */
|
|
635
|
+
readonly sound: string;
|
|
636
|
+
}
|
|
637
|
+
/** A named, user-defined set of sound rules. */
|
|
638
|
+
interface SoundProfile {
|
|
639
|
+
/** Stable identifier (slug). Unique across profiles. */
|
|
640
|
+
readonly id: string;
|
|
641
|
+
/** Human-readable name shown in Settings. */
|
|
642
|
+
readonly name: string;
|
|
643
|
+
/** The rules, in declaration order. */
|
|
644
|
+
readonly rules: readonly SoundRule[];
|
|
645
|
+
}
|
|
646
|
+
/**
|
|
647
|
+
* Parse a trigger notation into a {@link SoundTriggerPoint}.
|
|
648
|
+
*
|
|
649
|
+
* The anchor says which end of the block the offset counts from:
|
|
650
|
+
*
|
|
651
|
+
* - `:` — from the block's start (elapsed). This is the default, so the
|
|
652
|
+
* magnitude may be written with or without it: `:05:00`, `05:00`,
|
|
653
|
+
* `00:05:00` and `5:00` all mean five minutes from the start.
|
|
654
|
+
* - `-` — from the block's end (remaining). The colon is optional here
|
|
655
|
+
* too: `-:03` and `-03` both mean three seconds remaining.
|
|
656
|
+
*
|
|
657
|
+
* The magnitude accepts every duration spelling the language already
|
|
658
|
+
* understands: `5` (seconds), `5:00` (minutes), `00:05:00` (hours).
|
|
659
|
+
*
|
|
660
|
+
* @returns the parsed trigger, or `undefined` when the notation is malformed.
|
|
661
|
+
*/
|
|
662
|
+
declare function parseSoundTrigger(notation: string): SoundTriggerPoint | undefined;
|
|
663
|
+
/**
|
|
664
|
+
* Format a trigger back into its canonical notation.
|
|
665
|
+
*
|
|
666
|
+
* `:00` for the start, `-:00` for the end, `-:03` for three seconds before
|
|
667
|
+
* the end, `:05:00` for five minutes after the start.
|
|
668
|
+
*/
|
|
669
|
+
declare function formatSoundTrigger(trigger: SoundTriggerPoint): string;
|
|
670
|
+
/**
|
|
671
|
+
* Resolve a profile's rules against a block's duration, dropping any rule
|
|
672
|
+
* whose trigger point can never be reached.
|
|
673
|
+
*
|
|
674
|
+
* - A rule anchored to the **start** measures elapsed time, so it always
|
|
675
|
+
* applies — no duration needed.
|
|
676
|
+
* - A rule anchored to the **end** with no offset means "when the block
|
|
677
|
+
* ends", so it always applies too.
|
|
678
|
+
* - A rule anchored to the **end** with an offset needs a duration to count
|
|
679
|
+
* down from. It applies only when the block's duration is known and long
|
|
680
|
+
* enough to reach it.
|
|
681
|
+
*
|
|
682
|
+
* A rule that cannot be reached is dropped silently — an unreachable trigger
|
|
683
|
+
* is not an authoring error, it is simply a rule that does not apply to this
|
|
684
|
+
* block.
|
|
685
|
+
*
|
|
686
|
+
* @param profile the profile whose rules to resolve
|
|
687
|
+
* @param durationMs the block's duration in milliseconds, when known
|
|
688
|
+
*/
|
|
689
|
+
declare function resolveProfileRules(profile: SoundProfile, durationMs: number | undefined): SoundRule[];
|
|
690
|
+
/**
|
|
691
|
+
* The profile applied when nothing selects one.
|
|
692
|
+
*
|
|
693
|
+
* A three-two-one countdown into a completion cue — the behaviour the app
|
|
694
|
+
* has always implied but never actually played.
|
|
695
|
+
*/
|
|
696
|
+
declare const DEFAULT_SOUND_PROFILE: SoundProfile;
|
|
697
|
+
|
|
698
|
+
/**
|
|
699
|
+
* AST for the composed-calculation expression language (spec §2).
|
|
700
|
+
*
|
|
701
|
+
* One expression language across all three scopes; scope only changes how
|
|
702
|
+
* atoms resolve. `wql` atoms are legal in store scope only (executed by
|
|
703
|
+
* QueryService); stream aggregates (`sum(reps)`) are builtin calls resolved
|
|
704
|
+
* by the engine, not by this core.
|
|
705
|
+
*/
|
|
706
|
+
type BinaryOp = '+' | '-' | '*' | '/' | '==' | '!=' | '<' | '<=' | '>' | '>=' | 'and' | 'or';
|
|
707
|
+
type ExprNode = {
|
|
708
|
+
kind: 'literal';
|
|
709
|
+
value: number;
|
|
710
|
+
} | {
|
|
711
|
+
kind: 'period';
|
|
712
|
+
days: number;
|
|
713
|
+
} | {
|
|
714
|
+
kind: 'string';
|
|
715
|
+
value: string;
|
|
716
|
+
}
|
|
717
|
+
/** Metric ref, context node (`session.duration`), or library node ref. */
|
|
718
|
+
| {
|
|
719
|
+
kind: 'ref';
|
|
720
|
+
name: string;
|
|
721
|
+
} | {
|
|
722
|
+
kind: 'call';
|
|
723
|
+
name: string;
|
|
724
|
+
args: ExprNode[];
|
|
725
|
+
}
|
|
726
|
+
/** Effort-exclusion filter argument: `without: rest|pause|rest-*`. */
|
|
727
|
+
| {
|
|
728
|
+
kind: 'filter';
|
|
729
|
+
value: string;
|
|
730
|
+
} | {
|
|
731
|
+
kind: 'unary';
|
|
732
|
+
op: '-' | 'not';
|
|
733
|
+
arg: ExprNode;
|
|
734
|
+
} | {
|
|
735
|
+
kind: 'binary';
|
|
736
|
+
op: BinaryOp;
|
|
737
|
+
left: ExprNode;
|
|
738
|
+
right: ExprNode;
|
|
739
|
+
}
|
|
740
|
+
/** Store-scope WQL selection, e.g. `sum:sessionLoad{} by {day}`. */
|
|
741
|
+
| {
|
|
742
|
+
kind: 'wql';
|
|
743
|
+
aggregator: string;
|
|
744
|
+
metric: string;
|
|
745
|
+
filters?: string;
|
|
746
|
+
groupBy?: string[];
|
|
747
|
+
};
|
|
748
|
+
/** A parsed calc line: `name = expr -> unit when predicate`. */
|
|
749
|
+
interface CalcLine {
|
|
750
|
+
name: string;
|
|
751
|
+
expr: ExprNode;
|
|
752
|
+
unit?: string;
|
|
753
|
+
when?: ExprNode;
|
|
754
|
+
}
|
|
755
|
+
|
|
756
|
+
/**
|
|
757
|
+
* Exponent-vector dimension model for the composed calculations layer.
|
|
758
|
+
*
|
|
759
|
+
* Dimensions are 5-element exponent vectors over base physical quantities:
|
|
760
|
+
* [L, M, T, C, E] = [length, mass, time, count(reps), energy(cal)]
|
|
761
|
+
*
|
|
762
|
+
* Algebra (docs/composed-calculations-spec.md §5.1):
|
|
763
|
+
* Dim(a * b) = Dim(a) + Dim(b)
|
|
764
|
+
* Dim(a / b) = Dim(a) − Dim(b)
|
|
765
|
+
* Dim(a ± b) requires Dim(a) = Dim(b) (static registration failure otherwise)
|
|
766
|
+
*/
|
|
767
|
+
type DimVector = readonly [number, number, number, number, number];
|
|
768
|
+
declare const DIM_ZERO: DimVector;
|
|
769
|
+
declare const DIM_LENGTH: DimVector;
|
|
770
|
+
declare const DIM_MASS: DimVector;
|
|
771
|
+
declare const DIM_TIME: DimVector;
|
|
772
|
+
declare const DIM_COUNT: DimVector;
|
|
773
|
+
declare const DIM_ENERGY: DimVector;
|
|
774
|
+
declare function addDim(a: DimVector, b: DimVector): DimVector;
|
|
775
|
+
declare function subDim(a: DimVector, b: DimVector): DimVector;
|
|
776
|
+
declare function dimEquals(a: DimVector, b: DimVector): boolean;
|
|
777
|
+
declare function isDimensionless(d: DimVector): boolean;
|
|
778
|
+
/** Human-readable vector, e.g. "T·L⁻¹" for pace. */
|
|
779
|
+
declare function formatDim(d: DimVector): string;
|
|
780
|
+
/**
|
|
781
|
+
* Named compound dimension registry (spec §5.2). Used for diagnostics and
|
|
782
|
+
* dimension-filtered unit suggestions — not required for evaluation.
|
|
783
|
+
*/
|
|
784
|
+
declare const NAMED_COMPOUNDS: Record<string, {
|
|
785
|
+
dim: DimVector;
|
|
786
|
+
preferredUnits: string[];
|
|
787
|
+
}>;
|
|
788
|
+
/** Reverse lookup: find the compound name for a vector, if one exists. */
|
|
789
|
+
declare function compoundName(d: DimVector): string | undefined;
|
|
790
|
+
|
|
791
|
+
/**
|
|
792
|
+
* Canonical Node DAG records (spec §2.2) — the storage/registration form for
|
|
793
|
+
* calculations. Seeds are TS object literals (#849); the line-form parser
|
|
794
|
+
* (#863) must round-trip these losslessly.
|
|
795
|
+
*/
|
|
796
|
+
|
|
797
|
+
type CalcOrigin = 'analyzed' | 'analyzed-estimated' | 'user';
|
|
798
|
+
type CalcScope = 'segment' | 'workout' | 'store';
|
|
799
|
+
interface CalcNode {
|
|
800
|
+
id: string;
|
|
801
|
+
kind: 'metric' | 'lookup' | 'builtin' | 'wql' | 'expr';
|
|
802
|
+
expression?: string;
|
|
803
|
+
ast?: ExprNode;
|
|
804
|
+
/**
|
|
805
|
+
* Declared node unit. Named zero-vector casts (AU, pts, MET-min, ratio)
|
|
806
|
+
* override the computed vector (§5.3 applied to intermediate nodes —
|
|
807
|
+
* required by TIS-shaped formulas that fold time into a score); any other
|
|
808
|
+
* unit must match the computed vector.
|
|
809
|
+
*/
|
|
810
|
+
unit?: string;
|
|
811
|
+
}
|
|
812
|
+
interface CalcVariant {
|
|
813
|
+
id: string;
|
|
814
|
+
priority: number;
|
|
815
|
+
when?: string;
|
|
816
|
+
whenAst?: ExprNode;
|
|
817
|
+
origin: CalcOrigin;
|
|
818
|
+
nodes: Record<string, CalcNode>;
|
|
819
|
+
/** Node dimensions computed at registration (static check output). */
|
|
820
|
+
nodeDims?: Record<string, DimVector>;
|
|
821
|
+
}
|
|
822
|
+
interface CalculationDefinition {
|
|
823
|
+
id: string;
|
|
824
|
+
kind: 'output' | 'library';
|
|
825
|
+
scope: CalcScope;
|
|
826
|
+
fences?: string[];
|
|
827
|
+
when?: string;
|
|
828
|
+
whenAst?: ExprNode;
|
|
829
|
+
variants: CalcVariant[];
|
|
830
|
+
output?: {
|
|
831
|
+
nodeId: string | string[];
|
|
832
|
+
key?: string;
|
|
833
|
+
emitType?: string;
|
|
834
|
+
unit?: string;
|
|
835
|
+
isGrouped?: boolean;
|
|
836
|
+
/** Group dimensions for grouped emission (e.g. ['effort']). */
|
|
837
|
+
groupBy?: string[];
|
|
838
|
+
publishMetadataNodes?: string[];
|
|
839
|
+
/** Display label for published facts (store-scope rollups). */
|
|
840
|
+
label?: string;
|
|
841
|
+
};
|
|
842
|
+
}
|
|
843
|
+
|
|
590
844
|
/**
|
|
591
845
|
* Factory function type for wrapping blocks in debug mode.
|
|
592
846
|
* Receives the original block and returns a wrapped version.
|
|
@@ -673,6 +927,35 @@ interface RuntimeStackOptions extends IRuntimeOptions {
|
|
|
673
927
|
userProfile?: {
|
|
674
928
|
vo2max?: number;
|
|
675
929
|
};
|
|
930
|
+
/**
|
|
931
|
+
* The functions available to the run — user-authored calculations,
|
|
932
|
+
* registered after the built-ins.
|
|
933
|
+
*/
|
|
934
|
+
calcs?: CalculationDefinition[];
|
|
935
|
+
/**
|
|
936
|
+
* The tag catalogue: the tags a script can reference with `#slug`
|
|
937
|
+
* and the functions they carry.
|
|
938
|
+
*/
|
|
939
|
+
tags?: TagIndex;
|
|
940
|
+
/**
|
|
941
|
+
* Tags active for the whole run, whatever the segments say — the
|
|
942
|
+
* bundle a profile applies.
|
|
943
|
+
*/
|
|
944
|
+
activeTags?: readonly string[];
|
|
945
|
+
};
|
|
946
|
+
/**
|
|
947
|
+
* Sound configuration for this run.
|
|
948
|
+
*
|
|
949
|
+
* `profiles` are the user's sound profiles, available for selection.
|
|
950
|
+
* `noteProfileId` is the profile selected for the note as a whole — the
|
|
951
|
+
* note-level `sound-{profile}` tag, resolved by the host before the
|
|
952
|
+
* runtime starts. A block that names its own profile overrides it.
|
|
953
|
+
*
|
|
954
|
+
* With neither, blocks fall back to the default profile.
|
|
955
|
+
*/
|
|
956
|
+
soundOptions?: {
|
|
957
|
+
profiles?: readonly SoundProfile[];
|
|
958
|
+
noteProfileId?: string;
|
|
676
959
|
};
|
|
677
960
|
}
|
|
678
961
|
|
|
@@ -1687,6 +1970,15 @@ interface CompletionDecision {
|
|
|
1687
1970
|
* - Memory usage should be minimized during execution
|
|
1688
1971
|
*/
|
|
1689
1972
|
interface IRuntimeBlock extends IBlockRef {
|
|
1973
|
+
/**
|
|
1974
|
+
* The tag composition of this block — the tags its statements referenced,
|
|
1975
|
+
* and what each carried (the functions it activates, the sound profile it
|
|
1976
|
+
* names).
|
|
1977
|
+
*
|
|
1978
|
+
* Resolved at compile time, so the runtime and the surfaces that show a
|
|
1979
|
+
* block know which tags shaped it without re-reading the catalogue.
|
|
1980
|
+
*/
|
|
1981
|
+
readonly tagComposition?: readonly TagReferenceMetadata[];
|
|
1690
1982
|
/**
|
|
1691
1983
|
* Execution timing metadata propagated by the runtime (start/completion timestamps).
|
|
1692
1984
|
* Implementations can rely on RuntimeStack/PushBlockAction to set this.
|
|
@@ -2521,4 +2813,4 @@ declare function getRuntimeNowMs(): number;
|
|
|
2521
2813
|
/** Creates an INowProvider that reads the browser sender-clock when available. */
|
|
2522
2814
|
declare function createBrowserRuntimeNow(): INowProvider;
|
|
2523
2815
|
|
|
2524
|
-
export { type
|
|
2816
|
+
export { type IEventHandler as $, type AnalyticsContext as A, type BehaviorEventType as B, type IBlockContext as C, type MetricVisibility as D, type EffortResolverOptions as E, type BlockLifecycleOptions as F, type CompletionDecision as G, type IRuntimeMemory as H, type IEquipment as I, TypedMemoryReference as J, type MemorySearchCriteria as K, type IMemoryReference as L, type MemoryTag as M, type RuntimeStackLogger as N, type OutputListener as O, type StackObserver as P, type StackSnapshot as Q, type ReferenceIndex as R, type SubscribeOptions as S, TimeSpan as T, type Unsubscribe as U, type StackListener as V, WhiteboardScript as W, MemoryTypeEnum as X, type IAnchorValue as Y, type SoundProfile as Z, type ButtonConfig as _, type ReferenceResolutionDefaults as a, type ScriptRuntimeDependencies as a$, type HandlerScope as a0, type IScriptRuntime as a1, type TestableBlockConfig as a2, type IRuntimeOptions as a3, ScriptRuntime as a4, type EventHandlerOptions as a5, type EventCallback as a6, type TimerState as a7, type CalculationDefinition as a8, type IRealtimeProcessor as a9, type DisplayState as aA, EFFORT_DISCIPLINES as aB, EFFORT_REGISTRY_ORIGINS as aC, type EffortBaseAttributes as aD, type EffortDerivation as aE, type EffortDiscipline as aF, type EffortMaterializer as aG, type EffortResolvedFrom as aH, type EquipmentStorageAdapter as aI, type FenceDialect as aJ, type FragmentDisplayState as aK, type FragmentState as aL, type IAnalyticsProcessorDescriptor as aM, type IEquipmentRegistry as aN, INTENSITY_TIERS as aO, type IScript as aP, type IntensityTier as aQ, type InterceptMode as aR, MemoryLocation as aS, type MemoryType as aT, type MemoryTypeMap as aU, type MemoryValueOf as aV, NAMED_COMPOUNDS as aW, type ReferenceCatalog as aX, type ResolvedReferences as aY, type RoundState as aZ, type RuntimeState as a_, type ISummaryProcessor as aa, type ProjectionResult as ab, type DimVector as ac, type CalcLine as ad, type ExprNode as ae, type CalcScope as af, type BinaryOp as ag, type ButtonVariant as ah, type ButtonsState as ai, CATALOG_PRECEDENCE_RANK as aj, type CalcNode as ak, type CalcOrigin as al, type CalcVariant as am, type CatalogPrecedenceTier as an, type ChildrenStatusState as ao, type CompletionState as ap, DEFAULT_RESOLVER_OPTIONS as aq, DEFAULT_RUNTIME_OPTIONS as ar, DEFAULT_SOUND_PROFILE as as, DIM_COUNT as at, DIM_ENERGY as au, DIM_LENGTH as av, DIM_MASS as aw, DIM_TIME as ax, DIM_ZERO as ay, DISCIPLINE_FACTORS as az, type IEffort as b, type SoundRule as b0, type SoundTriggerAnchor as b1, type SoundTriggerPoint as b2, type StackEvent as b3, type TimerDirection as b4, VISIBILITY_ICONS as b5, VISIBILITY_LABELS as b6, addDim as b7, compoundName as b8, createBrowserRuntimeNow as b9, createReferenceIndex as ba, dedupeEntitiesByPrecedence as bb, dimEquals as bc, disciplineFactorFor as bd, extractStatementRefs as be, filterTagsByVisibility as bf, formatDim as bg, formatSoundTrigger as bh, frozenNow as bi, getMetricVisibility as bj, getRuntimeNowMs as bk, isDimensionless as bl, isEffortDiscipline as bm, isFragmentTag as bn, parseSoundTrigger as bo, resolveEntityRank as bp, resolveEntityTier as bq, resolveProfileRules as br, resolveSourceRank as bs, resolveSourceTier as bt, slugifyRefLabel as bu, subDim as bv, wallClockNow as bw, type IEffortResolver as c, type IEffortRegistry as d, type EffortResolutionOptions as e, type ResolvedEffort as f, type EffortRegistrySource as g, type EffortStorageAdapter as h, type IRuntimeActionable as i, type IEventBus as j, type IRuntimeStack as k, type IRuntimeClock as l, type IJitCompiler as m, type INowProvider as n, type RuntimeStackOptions as o, type RuntimeError as p, type IEvent as q, type IRuntimeAction as r, type IAnalyticsEngine as s, type IRuntimeBlock as t, type IBehaviorContext as u, type BehaviorEventListener as v, type Unsubscribe$1 as w, type OutputOptions as x, type IMemoryLocation as y, type IRuntimeBehavior as z };
|