@aneuhold/core-ts-db-lib 4.1.12 → 4.1.14

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 (58) hide show
  1. package/CHANGELOG.md +38 -0
  2. package/lib/browser.d.ts +11 -8
  3. package/lib/browser.d.ts.map +1 -1
  4. package/lib/browser.js +6 -4
  5. package/lib/browser.js.map +1 -1
  6. package/lib/browser.ts +23 -9
  7. package/lib/ctos/workout/WorkoutMuscleGroupVolumeCTO.d.ts +14 -0
  8. package/lib/ctos/workout/WorkoutMuscleGroupVolumeCTO.d.ts.map +1 -1
  9. package/lib/ctos/workout/WorkoutMuscleGroupVolumeCTO.ts +18 -0
  10. package/lib/documents/workout/README.md +43 -9
  11. package/lib/documents/workout/WorkoutSet.d.ts +8 -0
  12. package/lib/documents/workout/WorkoutSet.d.ts.map +1 -1
  13. package/lib/documents/workout/WorkoutSet.ts +9 -0
  14. package/lib/services/workout/Exercise/WorkoutExerciseService.d.ts +40 -0
  15. package/lib/services/workout/Exercise/WorkoutExerciseService.d.ts.map +1 -1
  16. package/lib/services/workout/Exercise/WorkoutExerciseService.js +134 -1
  17. package/lib/services/workout/Exercise/WorkoutExerciseService.js.map +1 -1
  18. package/lib/services/workout/Exercise/WorkoutExerciseService.ts +204 -1
  19. package/lib/services/workout/ExerciseCalibration/WorkoutExerciseCalibrationService.d.ts +15 -0
  20. package/lib/services/workout/ExerciseCalibration/WorkoutExerciseCalibrationService.d.ts.map +1 -1
  21. package/lib/services/workout/ExerciseCalibration/WorkoutExerciseCalibrationService.js +18 -1
  22. package/lib/services/workout/ExerciseCalibration/WorkoutExerciseCalibrationService.js.map +1 -1
  23. package/lib/services/workout/ExerciseCalibration/WorkoutExerciseCalibrationService.ts +19 -1
  24. package/lib/services/workout/Mesocycle/WorkoutMesocyclePlanContext.d.ts +30 -4
  25. package/lib/services/workout/Mesocycle/WorkoutMesocyclePlanContext.d.ts.map +1 -1
  26. package/lib/services/workout/Mesocycle/WorkoutMesocyclePlanContext.js +58 -4
  27. package/lib/services/workout/Mesocycle/WorkoutMesocyclePlanContext.js.map +1 -1
  28. package/lib/services/workout/Mesocycle/WorkoutMesocyclePlanContext.ts +69 -3
  29. package/lib/services/workout/Mesocycle/WorkoutMesocycleService.d.ts +45 -1
  30. package/lib/services/workout/Mesocycle/WorkoutMesocycleService.d.ts.map +1 -1
  31. package/lib/services/workout/Mesocycle/WorkoutMesocycleService.js +201 -11
  32. package/lib/services/workout/Mesocycle/WorkoutMesocycleService.js.map +1 -1
  33. package/lib/services/workout/Mesocycle/WorkoutMesocycleService.ts +285 -9
  34. package/lib/services/workout/Mesocycle/WorkoutMesocycleService.types.d.ts +33 -0
  35. package/lib/services/workout/Mesocycle/WorkoutMesocycleService.types.d.ts.map +1 -0
  36. package/lib/services/workout/Mesocycle/WorkoutMesocycleService.types.js +24 -0
  37. package/lib/services/workout/Mesocycle/WorkoutMesocycleService.types.js.map +1 -0
  38. package/lib/services/workout/Mesocycle/WorkoutMesocycleService.types.ts +36 -0
  39. package/lib/services/workout/Session/WorkoutSessionService.d.ts.map +1 -1
  40. package/lib/services/workout/Session/WorkoutSessionService.js +1 -11
  41. package/lib/services/workout/Session/WorkoutSessionService.js.map +1 -1
  42. package/lib/services/workout/Session/WorkoutSessionService.ts +1 -17
  43. package/lib/services/workout/SessionExercise/WorkoutSessionExerciseService.d.ts +14 -2
  44. package/lib/services/workout/SessionExercise/WorkoutSessionExerciseService.d.ts.map +1 -1
  45. package/lib/services/workout/SessionExercise/WorkoutSessionExerciseService.js +17 -3
  46. package/lib/services/workout/SessionExercise/WorkoutSessionExerciseService.js.map +1 -1
  47. package/lib/services/workout/SessionExercise/WorkoutSessionExerciseService.ts +28 -3
  48. package/lib/services/workout/Set/WorkoutSetService.d.ts +17 -5
  49. package/lib/services/workout/Set/WorkoutSetService.d.ts.map +1 -1
  50. package/lib/services/workout/Set/WorkoutSetService.js +83 -16
  51. package/lib/services/workout/Set/WorkoutSetService.js.map +1 -1
  52. package/lib/services/workout/Set/WorkoutSetService.ts +107 -24
  53. package/lib/services/workout/util/VolumePlanning/WorkoutVolumePlanningService.d.ts +161 -11
  54. package/lib/services/workout/util/VolumePlanning/WorkoutVolumePlanningService.d.ts.map +1 -1
  55. package/lib/services/workout/util/VolumePlanning/WorkoutVolumePlanningService.js +364 -127
  56. package/lib/services/workout/util/VolumePlanning/WorkoutVolumePlanningService.js.map +1 -1
  57. package/lib/services/workout/util/VolumePlanning/WorkoutVolumePlanningService.ts +551 -160
  58. package/package.json +1 -1
@@ -1,10 +1,9 @@
1
1
  import type { UUID } from 'crypto';
2
+ import type { WorkoutMuscleGroupVolumeCTO, WorkoutVolumeLandmarkEstimate } from '../../../../ctos/workout/WorkoutMuscleGroupVolumeCTO.js';
2
3
  import type WorkoutMesocyclePlanContext from '../../Mesocycle/WorkoutMesocyclePlanContext.js';
3
4
  /**
4
5
  * A service for handling volume planning operations across microcycles.
5
6
  *
6
- * SCOPE: Microcycle-level volume distribution (calculating set counts per exercise)
7
- *
8
7
  * RESPONSIBILITIES:
9
8
  * - Calculate set counts for exercises across a microcycle
10
9
  * - Apply progressive overload rules (baseline + historical adjustments)
@@ -17,8 +16,39 @@ import type WorkoutMesocyclePlanContext from '../../Mesocycle/WorkoutMesocyclePl
17
16
  * - {@link WorkoutSessionExerciseService} - Used to calculate SFR and recovery recommendations
18
17
  */
19
18
  export default class WorkoutVolumePlanningService {
19
+ /**
20
+ * Controls the volume *progression rate* across accumulation microcycles.
21
+ *
22
+ * Both modes start at estimated MEV when historical volume data exists
23
+ * (falling back to 2 sets per exercise when no history is available).
24
+ *
25
+ * When `false` (default): legacy progression — adds 1 set per muscle group
26
+ * every `progressionInterval` microcycles from the MEV starting point.
27
+ *
28
+ * When `true`: MEV-to-MRV interpolation — linearly distributes sets from
29
+ * estimated MEV to estimated MRV across all accumulation microcycles.
30
+ *
31
+ * This flag exists to allow toggling between the two progression algorithms
32
+ * while the MEV-to-MRV approach is validated in practice. Once confidence is
33
+ * established, the flag and legacy path should be removed.
34
+ */
35
+ static USE_VOLUME_LANDMARK_PROGRESSION: boolean;
20
36
  private static readonly MAX_SETS_PER_EXERCISE;
21
37
  private static readonly MAX_SETS_PER_MUSCLE_GROUP_PER_SESSION;
38
+ /** Minimum average RSM required for a mesocycle to count toward MEV estimation. */
39
+ private static readonly MEV_RSM_THRESHOLD;
40
+ /** Default estimated MEV when no qualifying mesocycle history exists. Per-exercise value. */
41
+ private static readonly DEFAULT_MEV_PER_EXERCISE;
42
+ /** Minimum average performance score (or recovery presence) to count a mesocycle toward MRV estimation. */
43
+ private static readonly MRV_PERFORMANCE_THRESHOLD;
44
+ /** Extra sets added above the historical peak when no stressed mesocycles exist, to estimate MRV. */
45
+ private static readonly MRV_HEADROOM;
46
+ /** Default estimated MRV when no mesocycle history exists at all. Per-exercise value. */
47
+ private static readonly DEFAULT_MRV_PER_EXERCISE;
48
+ /** Maximum sets that can be added to a single exercise in one progression step. */
49
+ private static readonly MAX_SET_ADDITION_PER_EXERCISE;
50
+ /** Maximum total sets to distribute across a muscle group in one progression step. */
51
+ private static readonly MAX_TOTAL_SET_ADDITIONS;
22
52
  /**
23
53
  * Calculates the set plan for an entire microcycle.
24
54
  */
@@ -26,23 +56,143 @@ export default class WorkoutVolumePlanningService {
26
56
  exerciseIdToSetCount: Map<UUID, number>;
27
57
  recoveryExerciseIds: Set<UUID>;
28
58
  };
59
+ /**
60
+ * Estimates MEV, MRV, and MAV for a muscle group based on historical data
61
+ * across completed mesocycles.
62
+ *
63
+ * @param volumeCTO The WorkoutMuscleGroupVolumeCTO containing mesocycle
64
+ * history for this muscle group.
65
+ */
66
+ static estimateVolumeLandmarks(volumeCTO: WorkoutMuscleGroupVolumeCTO): WorkoutVolumeLandmarkEstimate;
29
67
  /**
30
68
  * Calculates the set count for each exercise in a particular muscle group for this microcycle.
31
69
  *
32
- * If there is no previous microcycle data for the muscle group, this falls back to
33
- * the baseline progression rules.
70
+ * Pipeline:
71
+ * 1. **Volume targets** — Determine start/end volume from landmarks or defaults
72
+ * 2. **Baseline** — Calculate default set counts from progression rules
73
+ * 3. **Resolve history** — Find the most recent session exercise data for each exercise
74
+ * 4. **Apply history** — Override baselines with historical set counts (or MAV for recovery returns)
75
+ * 5. **Evaluate SFR** — Determine recovery exercises and candidates for set additions
76
+ * 6. **Distribute sets** — Allocate added sets to candidates by SFR quality
77
+ *
78
+ * Falls back to baseline when no previous microcycle data exists.
34
79
  */
35
80
  private static calculateSetCountForEachExerciseInMuscleGroup;
36
81
  /**
37
- * Calculates the default number of sets for an exercise based on microcycle progression.
82
+ * Determines the start and end volume targets for a muscle group based on
83
+ * historical volume landmarks and cycle type.
38
84
  *
39
- * Key rule: set progression is distributed across exercises that share the same primary muscle group
40
- * for the entire microcycle, regardless of which session those exercises are in.
85
+ * @param volumeLandmark Volume landmark estimate from historical data, if available.
86
+ * @param exerciseCount Number of exercises in the muscle group.
87
+ * @param progressionInterval Cycle-type progression interval (1=MuscleGain, 2=Cut, 0=Resensitization).
88
+ */
89
+ private static getVolumeTargetsForMuscleGroup;
90
+ /**
91
+ * Calculates the baseline set counts for all exercises in a muscle group for a given microcycle.
92
+ *
93
+ * When {@link USE_VOLUME_LANDMARK_PROGRESSION} is `false` (default), uses the legacy progression
94
+ * rate: +1 set per muscle group every `progressionInterval` microcycles from the starting volume.
95
+ *
96
+ * When `true`, linearly interpolates from `startVolume` to `endVolume` across accumulation
97
+ * microcycles.
98
+ *
99
+ * @param microcycleIndex The index of the current microcycle.
100
+ * @param accumulationMicrocycleCount Number of accumulation (non-deload) microcycles.
101
+ * @param exerciseCount Number of exercises in the muscle group.
102
+ * @param startVolume Total muscle-group volume at microcycle 0.
103
+ * @param endVolume Total muscle-group volume target at the last accumulation microcycle.
104
+ * @param isDeloadMicrocycle Whether this is a deload microcycle.
105
+ * @param progressionInterval Microcycles between each set addition (0 = no progression).
106
+ */
107
+ private static calculateBaselineSetCounts;
108
+ /**
109
+ * Distributes a total evenly across N slots, with remainder going to earlier slots.
110
+ *
111
+ * @param total The total to distribute.
112
+ * @param slots The number of slots to distribute across.
113
+ */
114
+ private static distributeEvenly;
115
+ /**
116
+ * Walks backward through completed microcycles to find the most recent non-recovery
117
+ * session exercise for each exercise in the muscle group.
118
+ *
119
+ * Returns `null` when no usable historical data exists (no previous microcycle, or
120
+ * previous microcycles are incomplete/have no matching exercises).
121
+ *
122
+ * @param context The mesocycle planning context.
123
+ * @param microcycleIndex The current microcycle index.
124
+ * @param exerciseIds The exercise IDs to search for.
125
+ */
126
+ private static resolveHistoricalExerciseData;
127
+ /**
128
+ * Overrides baseline set counts with historical data from the previous microcycle.
129
+ *
130
+ * For exercises returning from recovery, distributes the estimated MAV from volume
131
+ * landmarks proportionally across exercises. For deload microcycles, halves the
132
+ * historical count (minimum 1 set).
133
+ *
134
+ * @param muscleGroupExerciseCTOs Exercises in this muscle group.
135
+ * @param exerciseIdToPrevSessionExercise Map from exercise ID to its previous session exercise.
136
+ * @param exercisesThatWerePreviouslyInRecovery Exercises returning from recovery.
137
+ * @param exerciseIdToSetCount Current set count assignments (mutated).
138
+ * @param isDeloadMicrocycle Whether this is a deload microcycle.
139
+ * @param volumeLandmark Volume landmark estimate for the primary muscle group, if available.
140
+ */
141
+ private static applyHistoricalSetCounts;
142
+ /**
143
+ * Evaluates each exercise's performance feedback to determine recovery exercises,
144
+ * set addition recommendations, and candidates for volume increases.
145
+ *
146
+ * @param context The mesocycle planning context.
147
+ * @param muscleGroupExerciseCTOs Exercises in this muscle group.
148
+ * @param exerciseIdToPrevSessionExercise Map from exercise ID to its previous session exercise.
149
+ * @param exercisesThatWerePreviouslyInRecovery Exercises returning from recovery.
150
+ * @param exerciseIdToSetCount Current set count assignments (mutated for recovery exercises).
151
+ * @param recoveryExerciseIds Set of exercise IDs flagged for recovery (mutated).
152
+ * @param sessionIndexToExerciseIds Map from session index to exercise IDs in that session.
153
+ */
154
+ private static evaluateSfrRecommendations;
155
+ /**
156
+ * Distributes added sets across candidate exercises, prioritizing higher SFR scores.
157
+ * Respects per-exercise, per-session, and per-addition caps.
158
+ *
159
+ * @param candidates Exercises eligible for set additions, with SFR scores.
160
+ * @param totalSetsToAdd Total sets recommended for addition (before capping).
161
+ * @param exerciseIdToSetCount Current set count assignments (mutated).
162
+ * @param exerciseIdToSessionIndex Map from exercise ID to its session index.
163
+ * @param sessionIndexToExerciseIds Map from session index to exercise IDs in that session.
164
+ */
165
+ private static distributeSetsToExercises;
166
+ /**
167
+ * Determines if the session containing the given exercise is already at the
168
+ * per-muscle-group-per-session cap, based on previous microcycle set counts.
169
+ *
170
+ * @param exerciseId The exercise to check.
171
+ * @param exerciseIdToSessionIndex Map from exercise ID to its session index.
172
+ * @param sessionIndexToExerciseIds Map from session index to exercise IDs in that session.
173
+ * @param exerciseIdToPrevSessionExercise Map from exercise ID to its previous session exercise.
174
+ */
175
+ private static sessionIsCapped;
176
+ /**
177
+ * Gets the total sets currently planned for a session containing the given exercise.
178
+ *
179
+ * @param exerciseId The exercise whose session total to compute.
180
+ * @param exerciseIdToSetCount Current set count assignments.
181
+ * @param exerciseIdToSessionIndex Map from exercise ID to its session index.
182
+ * @param sessionIndexToExerciseIds Map from session index to exercise IDs in that session.
183
+ */
184
+ private static getSessionSetTotal;
185
+ /**
186
+ * Attempts to add sets to an exercise, respecting per-exercise, per-session, and
187
+ * per-addition caps. Mutates `exerciseIdToSetCount` in place.
41
188
  *
42
- * Baseline: 2 sets per exercise in the muscle group.
43
- * Progression: add 1 total set per microcycle per muscle group (distributed to earlier exercises
44
- * in the muscle-group-wide ordering).
189
+ * @param exerciseId The exercise to add sets to.
190
+ * @param setsToAdd The desired number of sets to add.
191
+ * @param exerciseIdToSetCount Current set count assignments (mutated).
192
+ * @param exerciseIdToSessionIndex Map from exercise ID to its session index.
193
+ * @param sessionIndexToExerciseIds Map from session index to exercise IDs in that session.
194
+ * @returns The number of sets actually added.
45
195
  */
46
- private static calculateBaselineSetCount;
196
+ private static addSetsToExercise;
47
197
  }
48
198
  //# sourceMappingURL=WorkoutVolumePlanningService.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"WorkoutVolumePlanningService.d.ts","sourceRoot":"","sources":["../../../../../src/services/workout/util/VolumePlanning/WorkoutVolumePlanningService.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,IAAI,EAAE,MAAM,QAAQ,CAAC;AAGnC,OAAO,KAAK,2BAA2B,MAAM,gDAAgD,CAAC;AAG9F;;;;;;;;;;;;;;;GAeG;AACH,MAAM,CAAC,OAAO,OAAO,4BAA4B;IAC/C,OAAO,CAAC,MAAM,CAAC,QAAQ,CAAC,qBAAqB,CAAK;IAClD,OAAO,CAAC,MAAM,CAAC,QAAQ,CAAC,qCAAqC,CAAM;IAEnE;;OAEG;IACH,MAAM,CAAC,6BAA6B,CAClC,OAAO,EAAE,2BAA2B,EACpC,eAAe,EAAE,MAAM,EACvB,kBAAkB,EAAE,OAAO,GAC1B;QAAE,oBAAoB,EAAE,GAAG,CAAC,IAAI,EAAE,MAAM,CAAC,CAAC;QAAC,mBAAmB,EAAE,GAAG,CAAC,IAAI,CAAC,CAAA;KAAE;IA4B9E;;;;;OAKG;IACH,OAAO,CAAC,MAAM,CAAC,6CAA6C;IAoP5D;;;;;;;;;OASG;IACH,OAAO,CAAC,MAAM,CAAC,yBAAyB;CA6BzC"}
1
+ {"version":3,"file":"WorkoutVolumePlanningService.d.ts","sourceRoot":"","sources":["../../../../../src/services/workout/util/VolumePlanning/WorkoutVolumePlanningService.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,IAAI,EAAE,MAAM,QAAQ,CAAC;AAEnC,OAAO,KAAK,EACV,2BAA2B,EAC3B,6BAA6B,EAC9B,MAAM,yDAAyD,CAAC;AAEjE,OAAO,KAAK,2BAA2B,MAAM,gDAAgD,CAAC;AAW9F;;;;;;;;;;;;;GAaG;AACH,MAAM,CAAC,OAAO,OAAO,4BAA4B;IAC/C;;;;;;;;;;;;;;;OAeG;IACH,MAAM,CAAC,+BAA+B,UAAS;IAE/C,OAAO,CAAC,MAAM,CAAC,QAAQ,CAAC,qBAAqB,CAAK;IAClD,OAAO,CAAC,MAAM,CAAC,QAAQ,CAAC,qCAAqC,CAAM;IAEnE,mFAAmF;IACnF,OAAO,CAAC,MAAM,CAAC,QAAQ,CAAC,iBAAiB,CAAK;IAE9C,6FAA6F;IAC7F,OAAO,CAAC,MAAM,CAAC,QAAQ,CAAC,wBAAwB,CAAK;IAErD,2GAA2G;IAC3G,OAAO,CAAC,MAAM,CAAC,QAAQ,CAAC,yBAAyB,CAAO;IAExD,qGAAqG;IACrG,OAAO,CAAC,MAAM,CAAC,QAAQ,CAAC,YAAY,CAAK;IAEzC,yFAAyF;IACzF,OAAO,CAAC,MAAM,CAAC,QAAQ,CAAC,wBAAwB,CAAK;IAErD,mFAAmF;IACnF,OAAO,CAAC,MAAM,CAAC,QAAQ,CAAC,6BAA6B,CAAK;IAE1D,sFAAsF;IACtF,OAAO,CAAC,MAAM,CAAC,QAAQ,CAAC,uBAAuB,CAAK;IAEpD;;OAEG;IACH,MAAM,CAAC,6BAA6B,CAClC,OAAO,EAAE,2BAA2B,EACpC,eAAe,EAAE,MAAM,EACvB,kBAAkB,EAAE,OAAO,GAC1B;QAAE,oBAAoB,EAAE,GAAG,CAAC,IAAI,EAAE,MAAM,CAAC,CAAC;QAAC,mBAAmB,EAAE,GAAG,CAAC,IAAI,CAAC,CAAA;KAAE;IA4B9E;;;;;;OAMG;IACH,MAAM,CAAC,uBAAuB,CAC5B,SAAS,EAAE,2BAA2B,GACrC,6BAA6B;IA+ChC;;;;;;;;;;;;OAYG;IACH,OAAO,CAAC,MAAM,CAAC,6CAA6C;IAqG5D;;;;;;;OAOG;IACH,OAAO,CAAC,MAAM,CAAC,8BAA8B;IAuC7C;;;;;;;;;;;;;;;;OAgBG;IACH,OAAO,CAAC,MAAM,CAAC,0BAA0B;IA4CzC;;;;;OAKG;IACH,OAAO,CAAC,MAAM,CAAC,gBAAgB;IAM/B;;;;;;;;;;OAUG;IACH,OAAO,CAAC,MAAM,CAAC,6BAA6B;IAuD5C;;;;;;;;;;;;;OAaG;IACH,OAAO,CAAC,MAAM,CAAC,wBAAwB;IAwCvC;;;;;;;;;;;OAWG;IACH,OAAO,CAAC,MAAM,CAAC,0BAA0B;IAgEzC;;;;;;;;;OASG;IACH,OAAO,CAAC,MAAM,CAAC,yBAAyB;IAkCxC;;;;;;;;OAQG;IACH,OAAO,CAAC,MAAM,CAAC,eAAe;IAuB9B;;;;;;;OAOG;IACH,OAAO,CAAC,MAAM,CAAC,kBAAkB;IAoBjC;;;;;;;;;;OAUG;IACH,OAAO,CAAC,MAAM,CAAC,iBAAiB;CA8BjC"}