@critical-path/core 0.21.0 → 0.23.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 (55) hide show
  1. package/CHANGELOG.md +53 -0
  2. package/README.md +14 -0
  3. package/dist/domain/ddd.test.js +12 -0
  4. package/dist/domain/ddd.test.js.map +1 -1
  5. package/dist/domain/entities.d.ts.map +1 -1
  6. package/dist/domain/entities.js +3 -2
  7. package/dist/domain/entities.js.map +1 -1
  8. package/dist/domain/errors.d.ts +13 -0
  9. package/dist/domain/errors.d.ts.map +1 -0
  10. package/dist/domain/errors.js +19 -0
  11. package/dist/domain/errors.js.map +1 -0
  12. package/dist/domain/events.d.ts +9 -1
  13. package/dist/domain/events.d.ts.map +1 -1
  14. package/dist/domain/events.js.map +1 -1
  15. package/dist/domain/index.d.ts +1 -0
  16. package/dist/domain/index.d.ts.map +1 -1
  17. package/dist/domain/index.js +1 -0
  18. package/dist/domain/index.js.map +1 -1
  19. package/dist/engine/actor.test.d.ts +2 -0
  20. package/dist/engine/actor.test.d.ts.map +1 -0
  21. package/dist/engine/actor.test.js +53 -0
  22. package/dist/engine/actor.test.js.map +1 -0
  23. package/dist/engine/index.d.ts +23 -1
  24. package/dist/engine/index.d.ts.map +1 -1
  25. package/dist/engine/index.js +125 -29
  26. package/dist/engine/index.js.map +1 -1
  27. package/dist/index.test.js +20 -0
  28. package/dist/index.test.js.map +1 -1
  29. package/dist/store/sqlite.d.ts.map +1 -1
  30. package/dist/store/sqlite.js +5 -1
  31. package/dist/store/sqlite.js.map +1 -1
  32. package/dist/store/sqlite.test.js +20 -0
  33. package/dist/store/sqlite.test.js.map +1 -1
  34. package/dist/types/index.d.ts +7 -1
  35. package/dist/types/index.d.ts.map +1 -1
  36. package/dist/utils/fractional-index.d.ts.map +1 -1
  37. package/dist/utils/fractional-index.js +22 -26
  38. package/dist/utils/fractional-index.js.map +1 -1
  39. package/dist/utils/fractional-index.test.js +31 -0
  40. package/dist/utils/fractional-index.test.js.map +1 -1
  41. package/package.json +1 -5
  42. package/src/domain/ddd.test.ts +22 -0
  43. package/src/domain/entities.ts +3 -2
  44. package/src/domain/errors.ts +19 -0
  45. package/src/domain/events.ts +6 -0
  46. package/src/domain/index.ts +1 -0
  47. package/src/engine/actor.test.ts +62 -0
  48. package/src/engine/index.ts +134 -30
  49. package/src/index.test.ts +24 -0
  50. package/src/store/sqlite.test.ts +22 -0
  51. package/src/store/sqlite.ts +7 -1
  52. package/src/types/index.ts +8 -0
  53. package/src/utils/fractional-index.test.ts +37 -0
  54. package/src/utils/fractional-index.ts +20 -26
  55. package/tsconfig.tsbuildinfo +1 -1
@@ -108,40 +108,35 @@ export function getIntegerPart(key: string): string {
108
108
  }
109
109
 
110
110
  /**
111
- * Computes a fractional midpoint suffix between suffixA and suffixB.
111
+ * Computes a fractional suffix strictly between suffixes `a` and `b` (a < result < b).
112
+ * Missing digits in `a` are treated as '0', so `a` may be shorter than `b`.
113
+ * `b === null` means there is no upper bound.
112
114
  */
113
115
  function midpointSuffix(a: string, b: string | null): string {
114
- let i = 0;
115
- while (i < a.length && b !== null && i < b.length && a[i] === b[i]) {
116
- i++;
116
+ if (b !== null) {
117
+ let n = 0;
118
+ while (n < b.length && (a[n] ?? '0') === b[n]) {
119
+ n++;
120
+ }
121
+ if (n > 0) {
122
+ return b.slice(0, n) + midpointSuffix(a.slice(n), b.slice(n));
123
+ }
117
124
  }
118
125
 
119
- const common = a.slice(0, i);
120
- const charA = i < a.length ? a[i] : null;
121
- const charB = b !== null && i < b.length ? b[i] : null;
122
-
123
- const digitA = charA !== null ? BASE_62.indexOf(charA) : 0;
124
- const digitB = charB !== null ? BASE_62.indexOf(charB) : BASE_62.length;
126
+ const digitA = a.length > 0 ? BASE_62.indexOf(a[0]) : 0;
127
+ const digitB = b !== null ? BASE_62.indexOf(b[0]) : BASE_62.length;
125
128
 
126
129
  if (digitB - digitA > 1) {
127
- const mid = Math.floor((digitA + digitB) / 2);
128
- return common + BASE_62[mid];
130
+ return BASE_62[Math.floor((digitA + digitB) / 2)];
129
131
  }
130
132
 
131
- if (charA !== null) {
132
- const restA = a.slice(i + 1);
133
- const restB = b !== null && i < b.length && charA === charB ? b.slice(i + 1) : null;
134
- return common + charA + midpointSuffix(restA, restB);
135
- }
136
-
137
- if (b !== null && i < b.length) {
138
- if (digitB === 0) {
139
- const restB = b.slice(i + 1);
140
- return common + '0' + midpointSuffix('', restB);
141
- }
133
+ // Adjacent digits: if b has more digits, its first digit alone already sits between a and b.
134
+ if (b !== null && b.length > 1) {
135
+ return b[0];
142
136
  }
143
137
 
144
- return common + 'V';
138
+ // Otherwise keep a's digit and subdivide the remainder with no upper bound.
139
+ return BASE_62[digitA] + midpointSuffix(a.slice(1), null);
145
140
  }
146
141
 
147
142
  /**
@@ -185,8 +180,7 @@ export function generateKeyBetween(
185
180
 
186
181
  // Both a and b are present
187
182
  if (a! >= b!) {
188
- // Graceful fallback for inverted or equal keys
189
- return a! + 'V';
183
+ throw new RangeError(`generateKeyBetween: lower bound "${a}" must sort before upper bound "${b}"`);
190
184
  }
191
185
 
192
186
  const intA = getIntegerPart(a!);
@@ -1 +1 @@
1
- {"root":["./src/deliverables.test.ts","./src/index.test.ts","./src/index.ts","./src/status.test.ts","./src/task-state.test.ts","./src/use-case-validation.test.ts","./src/domain/calendar.test.ts","./src/domain/calendar.ts","./src/domain/cpm.test.ts","./src/domain/cpm.ts","./src/domain/custom-fields.ts","./src/domain/ddd.test.ts","./src/domain/entities.ts","./src/domain/events.ts","./src/domain/graph.ts","./src/domain/index.ts","./src/domain/ladder.test.ts","./src/domain/ladder.ts","./src/domain/metrics.test.ts","./src/domain/metrics.ts","./src/domain/task-duration.test.ts","./src/domain/workload.test.ts","./src/domain/workload.ts","./src/engine/index.ts","./src/plugins/index.ts","./src/storage/file-storage.ts","./src/storage/firebase-storage.ts","./src/storage/index.ts","./src/storage/s3.ts","./src/storage/storage.test.ts","./src/store/firebase.test.ts","./src/store/firebase.ts","./src/store/index.ts","./src/store/sqlite.test.ts","./src/store/sqlite.ts","./src/types/index.ts","./src/utils/fractional-index.test.ts","./src/utils/fractional-index.ts","./src/utils/index.ts","./src/utils/key.test.ts","./src/utils/key.ts","./src/utils/mentions.test.ts","./src/utils/mentions.ts","./src/utils/status.ts","./src/utils/workflow.ts"],"version":"5.9.3"}
1
+ {"root":["./src/deliverables.test.ts","./src/index.test.ts","./src/index.ts","./src/status.test.ts","./src/task-state.test.ts","./src/use-case-validation.test.ts","./src/domain/calendar.test.ts","./src/domain/calendar.ts","./src/domain/cpm.test.ts","./src/domain/cpm.ts","./src/domain/custom-fields.ts","./src/domain/ddd.test.ts","./src/domain/entities.ts","./src/domain/errors.ts","./src/domain/events.ts","./src/domain/graph.ts","./src/domain/index.ts","./src/domain/ladder.test.ts","./src/domain/ladder.ts","./src/domain/metrics.test.ts","./src/domain/metrics.ts","./src/domain/task-duration.test.ts","./src/domain/workload.test.ts","./src/domain/workload.ts","./src/engine/actor.test.ts","./src/engine/index.ts","./src/plugins/index.ts","./src/storage/file-storage.ts","./src/storage/firebase-storage.ts","./src/storage/index.ts","./src/storage/s3.ts","./src/storage/storage.test.ts","./src/store/firebase.test.ts","./src/store/firebase.ts","./src/store/index.ts","./src/store/sqlite.test.ts","./src/store/sqlite.ts","./src/types/index.ts","./src/utils/fractional-index.test.ts","./src/utils/fractional-index.ts","./src/utils/index.ts","./src/utils/key.test.ts","./src/utils/key.ts","./src/utils/mentions.test.ts","./src/utils/mentions.ts","./src/utils/status.ts","./src/utils/workflow.ts"],"version":"5.9.3"}