fhirpath-ts 0.0.0-bootstrap.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 (414) hide show
  1. package/LICENSE +201 -0
  2. package/README.md +391 -0
  3. package/THIRD-PARTY-NOTICES.md +296 -0
  4. package/dist/analyzer/analyze-dto.d.ts +45 -0
  5. package/dist/analyzer/analyze-dto.d.ts.map +1 -0
  6. package/dist/analyzer/analyze-dto.js +147 -0
  7. package/dist/analyzer/analyze-dto.js.map +1 -0
  8. package/dist/analyzer/analyze.d.ts +98 -0
  9. package/dist/analyzer/analyze.d.ts.map +1 -0
  10. package/dist/analyzer/analyze.js +925 -0
  11. package/dist/analyzer/analyze.js.map +1 -0
  12. package/dist/analyzer/expression-policy.d.ts +210 -0
  13. package/dist/analyzer/expression-policy.d.ts.map +1 -0
  14. package/dist/analyzer/expression-policy.js +254 -0
  15. package/dist/analyzer/expression-policy.js.map +1 -0
  16. package/dist/analyzer/index.d.ts +3 -0
  17. package/dist/analyzer/index.d.ts.map +1 -0
  18. package/dist/analyzer/index.js +6 -0
  19. package/dist/analyzer/index.js.map +1 -0
  20. package/dist/analyzer/regex-safety.d.ts +10 -0
  21. package/dist/analyzer/regex-safety.d.ts.map +1 -0
  22. package/dist/analyzer/regex-safety.js +84 -0
  23. package/dist/analyzer/regex-safety.js.map +1 -0
  24. package/dist/analyzer/signatures.d.ts +72 -0
  25. package/dist/analyzer/signatures.d.ts.map +1 -0
  26. package/dist/analyzer/signatures.js +195 -0
  27. package/dist/analyzer/signatures.js.map +1 -0
  28. package/dist/api/bundle.d.ts +29 -0
  29. package/dist/api/bundle.d.ts.map +1 -0
  30. package/dist/api/bundle.js +108 -0
  31. package/dist/api/bundle.js.map +1 -0
  32. package/dist/api/cache.d.ts +10 -0
  33. package/dist/api/cache.d.ts.map +1 -0
  34. package/dist/api/cache.js +38 -0
  35. package/dist/api/cache.js.map +1 -0
  36. package/dist/api/column-signature.d.ts +53 -0
  37. package/dist/api/column-signature.d.ts.map +1 -0
  38. package/dist/api/column-signature.js +43 -0
  39. package/dist/api/column-signature.js.map +1 -0
  40. package/dist/api/compile.d.ts +120 -0
  41. package/dist/api/compile.d.ts.map +1 -0
  42. package/dist/api/compile.js +167 -0
  43. package/dist/api/compile.js.map +1 -0
  44. package/dist/api/constraints.d.ts +48 -0
  45. package/dist/api/constraints.d.ts.map +1 -0
  46. package/dist/api/constraints.js +52 -0
  47. package/dist/api/constraints.js.map +1 -0
  48. package/dist/api/dto.d.ts +134 -0
  49. package/dist/api/dto.d.ts.map +1 -0
  50. package/dist/api/dto.js +295 -0
  51. package/dist/api/dto.js.map +1 -0
  52. package/dist/api/engine.d.ts +136 -0
  53. package/dist/api/engine.d.ts.map +1 -0
  54. package/dist/api/engine.js +183 -0
  55. package/dist/api/engine.js.map +1 -0
  56. package/dist/api/evaluate.d.ts +7 -0
  57. package/dist/api/evaluate.d.ts.map +1 -0
  58. package/dist/api/evaluate.js +10 -0
  59. package/dist/api/evaluate.js.map +1 -0
  60. package/dist/api/project.d.ts +89 -0
  61. package/dist/api/project.d.ts.map +1 -0
  62. package/dist/api/project.js +150 -0
  63. package/dist/api/project.js.map +1 -0
  64. package/dist/api/tagged.d.ts +14 -0
  65. package/dist/api/tagged.d.ts.map +1 -0
  66. package/dist/api/tagged.js +13 -0
  67. package/dist/api/tagged.js.map +1 -0
  68. package/dist/cli/dto-check.d.ts +25 -0
  69. package/dist/cli/dto-check.d.ts.map +1 -0
  70. package/dist/cli/dto-check.js +77 -0
  71. package/dist/cli/dto-check.js.map +1 -0
  72. package/dist/cli/fhirpath-check.d.ts +3 -0
  73. package/dist/cli/fhirpath-check.d.ts.map +1 -0
  74. package/dist/cli/fhirpath-check.js +149 -0
  75. package/dist/cli/fhirpath-check.js.map +1 -0
  76. package/dist/cli/ts-loader.d.mts +3 -0
  77. package/dist/cli/ts-loader.d.mts.map +1 -0
  78. package/dist/cli/ts-loader.mjs +48 -0
  79. package/dist/cli/ts-loader.mjs.map +1 -0
  80. package/dist/engine/context.d.ts +173 -0
  81. package/dist/engine/context.d.ts.map +1 -0
  82. package/dist/engine/context.js +118 -0
  83. package/dist/engine/context.js.map +1 -0
  84. package/dist/engine/evaluator.d.ts +7 -0
  85. package/dist/engine/evaluator.d.ts.map +1 -0
  86. package/dist/engine/evaluator.js +196 -0
  87. package/dist/engine/evaluator.js.map +1 -0
  88. package/dist/engine/navigation.d.ts +11 -0
  89. package/dist/engine/navigation.d.ts.map +1 -0
  90. package/dist/engine/navigation.js +102 -0
  91. package/dist/engine/navigation.js.map +1 -0
  92. package/dist/engine/operators/collections.d.ts +12 -0
  93. package/dist/engine/operators/collections.d.ts.map +1 -0
  94. package/dist/engine/operators/collections.js +31 -0
  95. package/dist/engine/operators/collections.js.map +1 -0
  96. package/dist/engine/operators/comparison.d.ts +13 -0
  97. package/dist/engine/operators/comparison.d.ts.map +1 -0
  98. package/dist/engine/operators/comparison.js +77 -0
  99. package/dist/engine/operators/comparison.js.map +1 -0
  100. package/dist/engine/operators/equality.d.ts +19 -0
  101. package/dist/engine/operators/equality.d.ts.map +1 -0
  102. package/dist/engine/operators/equality.js +203 -0
  103. package/dist/engine/operators/equality.js.map +1 -0
  104. package/dist/engine/operators/index.d.ts +18 -0
  105. package/dist/engine/operators/index.d.ts.map +1 -0
  106. package/dist/engine/operators/index.js +30 -0
  107. package/dist/engine/operators/index.js.map +1 -0
  108. package/dist/engine/operators/logic.d.ts +8 -0
  109. package/dist/engine/operators/logic.d.ts.map +1 -0
  110. package/dist/engine/operators/logic.js +38 -0
  111. package/dist/engine/operators/logic.js.map +1 -0
  112. package/dist/engine/operators/math.d.ts +13 -0
  113. package/dist/engine/operators/math.d.ts.map +1 -0
  114. package/dist/engine/operators/math.js +198 -0
  115. package/dist/engine/operators/math.js.map +1 -0
  116. package/dist/engine/operators/strings.d.ts +8 -0
  117. package/dist/engine/operators/strings.d.ts.map +1 -0
  118. package/dist/engine/operators/strings.js +22 -0
  119. package/dist/engine/operators/strings.js.map +1 -0
  120. package/dist/engine/operators/types.d.ts +3 -0
  121. package/dist/engine/operators/types.d.ts.map +1 -0
  122. package/dist/engine/operators/types.js +15 -0
  123. package/dist/engine/operators/types.js.map +1 -0
  124. package/dist/engine/type-matching.d.ts +20 -0
  125. package/dist/engine/type-matching.d.ts.map +1 -0
  126. package/dist/engine/type-matching.js +122 -0
  127. package/dist/engine/type-matching.js.map +1 -0
  128. package/dist/errors.d.ts +25 -0
  129. package/dist/errors.d.ts.map +1 -0
  130. package/dist/errors.js +21 -0
  131. package/dist/errors.js.map +1 -0
  132. package/dist/eslint/index.d.ts +12 -0
  133. package/dist/eslint/index.d.ts.map +1 -0
  134. package/dist/eslint/index.js +316 -0
  135. package/dist/eslint/index.js.map +1 -0
  136. package/dist/fhir/html-checks.d.ts +7 -0
  137. package/dist/fhir/html-checks.d.ts.map +1 -0
  138. package/dist/fhir/html-checks.js +256 -0
  139. package/dist/fhir/html-checks.js.map +1 -0
  140. package/dist/fhir/model-navigation.d.ts +11 -0
  141. package/dist/fhir/model-navigation.d.ts.map +1 -0
  142. package/dist/fhir/model-navigation.js +142 -0
  143. package/dist/fhir/model-navigation.js.map +1 -0
  144. package/dist/functions/aggregate.d.ts +2 -0
  145. package/dist/functions/aggregate.d.ts.map +1 -0
  146. package/dist/functions/aggregate.js +127 -0
  147. package/dist/functions/aggregate.js.map +1 -0
  148. package/dist/functions/boundary.d.ts +2 -0
  149. package/dist/functions/boundary.d.ts.map +1 -0
  150. package/dist/functions/boundary.js +189 -0
  151. package/dist/functions/boundary.js.map +1 -0
  152. package/dist/functions/combining.d.ts +2 -0
  153. package/dist/functions/combining.d.ts.map +1 -0
  154. package/dist/functions/combining.js +13 -0
  155. package/dist/functions/combining.js.map +1 -0
  156. package/dist/functions/control.d.ts +2 -0
  157. package/dist/functions/control.d.ts.map +1 -0
  158. package/dist/functions/control.js +25 -0
  159. package/dist/functions/control.js.map +1 -0
  160. package/dist/functions/conversion.d.ts +3 -0
  161. package/dist/functions/conversion.d.ts.map +1 -0
  162. package/dist/functions/conversion.js +316 -0
  163. package/dist/functions/conversion.js.map +1 -0
  164. package/dist/functions/date-components.d.ts +2 -0
  165. package/dist/functions/date-components.d.ts.map +1 -0
  166. package/dist/functions/date-components.js +81 -0
  167. package/dist/functions/date-components.js.map +1 -0
  168. package/dist/functions/existence.d.ts +4 -0
  169. package/dist/functions/existence.d.ts.map +1 -0
  170. package/dist/functions/existence.js +97 -0
  171. package/dist/functions/existence.js.map +1 -0
  172. package/dist/functions/fhir.d.ts +2 -0
  173. package/dist/functions/fhir.d.ts.map +1 -0
  174. package/dist/functions/fhir.js +222 -0
  175. package/dist/functions/fhir.js.map +1 -0
  176. package/dist/functions/filtering.d.ts +2 -0
  177. package/dist/functions/filtering.d.ts.map +1 -0
  178. package/dist/functions/filtering.js +112 -0
  179. package/dist/functions/filtering.js.map +1 -0
  180. package/dist/functions/install.d.ts +18 -0
  181. package/dist/functions/install.d.ts.map +1 -0
  182. package/dist/functions/install.js +20 -0
  183. package/dist/functions/install.js.map +1 -0
  184. package/dist/functions/iteration.d.ts +7 -0
  185. package/dist/functions/iteration.d.ts.map +1 -0
  186. package/dist/functions/iteration.js +9 -0
  187. package/dist/functions/iteration.js.map +1 -0
  188. package/dist/functions/math.d.ts +2 -0
  189. package/dist/functions/math.d.ts.map +1 -0
  190. package/dist/functions/math.js +152 -0
  191. package/dist/functions/math.js.map +1 -0
  192. package/dist/functions/reflection.d.ts +2 -0
  193. package/dist/functions/reflection.d.ts.map +1 -0
  194. package/dist/functions/reflection.js +23 -0
  195. package/dist/functions/reflection.js.map +1 -0
  196. package/dist/functions/registry.d.ts +28 -0
  197. package/dist/functions/registry.d.ts.map +1 -0
  198. package/dist/functions/registry.js +46 -0
  199. package/dist/functions/registry.js.map +1 -0
  200. package/dist/functions/sort.d.ts +2 -0
  201. package/dist/functions/sort.d.ts.map +1 -0
  202. package/dist/functions/sort.js +48 -0
  203. package/dist/functions/sort.js.map +1 -0
  204. package/dist/functions/string.d.ts +2 -0
  205. package/dist/functions/string.d.ts.map +1 -0
  206. package/dist/functions/string.js +353 -0
  207. package/dist/functions/string.js.map +1 -0
  208. package/dist/functions/subsetting.d.ts +2 -0
  209. package/dist/functions/subsetting.d.ts.map +1 -0
  210. package/dist/functions/subsetting.js +72 -0
  211. package/dist/functions/subsetting.js.map +1 -0
  212. package/dist/functions/tree.d.ts +8 -0
  213. package/dist/functions/tree.d.ts.map +1 -0
  214. package/dist/functions/tree.js +109 -0
  215. package/dist/functions/tree.js.map +1 -0
  216. package/dist/functions/type-specifier.d.ts +8 -0
  217. package/dist/functions/type-specifier.d.ts.map +1 -0
  218. package/dist/functions/type-specifier.js +27 -0
  219. package/dist/functions/type-specifier.js.map +1 -0
  220. package/dist/functions/utility.d.ts +2 -0
  221. package/dist/functions/utility.d.ts.map +1 -0
  222. package/dist/functions/utility.js +76 -0
  223. package/dist/functions/utility.js.map +1 -0
  224. package/dist/functions/variables.d.ts +2 -0
  225. package/dist/functions/variables.d.ts.map +1 -0
  226. package/dist/functions/variables.js +35 -0
  227. package/dist/functions/variables.js.map +1 -0
  228. package/dist/index.d.ts +25 -0
  229. package/dist/index.d.ts.map +1 -0
  230. package/dist/index.js +11 -0
  231. package/dist/index.js.map +1 -0
  232. package/dist/lexer/lexer.d.ts +4 -0
  233. package/dist/lexer/lexer.d.ts.map +1 -0
  234. package/dist/lexer/lexer.js +318 -0
  235. package/dist/lexer/lexer.js.map +1 -0
  236. package/dist/lexer/tokens.d.ts +23 -0
  237. package/dist/lexer/tokens.d.ts.map +1 -0
  238. package/dist/lexer/tokens.js +40 -0
  239. package/dist/lexer/tokens.js.map +1 -0
  240. package/dist/model/provider.d.ts +36 -0
  241. package/dist/model/provider.d.ts.map +1 -0
  242. package/dist/model/provider.js +2 -0
  243. package/dist/model/provider.js.map +1 -0
  244. package/dist/parser/ast.d.ts +104 -0
  245. package/dist/parser/ast.d.ts.map +1 -0
  246. package/dist/parser/ast.js +2 -0
  247. package/dist/parser/ast.js.map +1 -0
  248. package/dist/parser/parser.d.ts +4 -0
  249. package/dist/parser/parser.d.ts.map +1 -0
  250. package/dist/parser/parser.js +299 -0
  251. package/dist/parser/parser.js.map +1 -0
  252. package/dist/parser/precedence.d.ts +24 -0
  253. package/dist/parser/precedence.d.ts.map +1 -0
  254. package/dist/parser/precedence.js +52 -0
  255. package/dist/parser/precedence.js.map +1 -0
  256. package/dist/parser/printer.d.ts +4 -0
  257. package/dist/parser/printer.d.ts.map +1 -0
  258. package/dist/parser/printer.js +112 -0
  259. package/dist/parser/printer.js.map +1 -0
  260. package/dist/r4/generated/resources-data.d.ts +3 -0
  261. package/dist/r4/generated/resources-data.d.ts.map +1 -0
  262. package/dist/r4/generated/resources-data.js +28628 -0
  263. package/dist/r4/generated/resources-data.js.map +1 -0
  264. package/dist/r4/generated/type-maps.d.ts +43153 -0
  265. package/dist/r4/generated/type-maps.d.ts.map +1 -0
  266. package/dist/r4/generated/type-maps.js +4 -0
  267. package/dist/r4/generated/type-maps.js.map +1 -0
  268. package/dist/r4/generated/types-data.d.ts +3 -0
  269. package/dist/r4/generated/types-data.d.ts.map +1 -0
  270. package/dist/r4/generated/types-data.js +2205 -0
  271. package/dist/r4/generated/types-data.js.map +1 -0
  272. package/dist/r4/index.d.ts +9 -0
  273. package/dist/r4/index.d.ts.map +1 -0
  274. package/dist/r4/index.js +94 -0
  275. package/dist/r4/index.js.map +1 -0
  276. package/dist/r4/model-data.d.ts +17 -0
  277. package/dist/r4/model-data.d.ts.map +1 -0
  278. package/dist/r4/model-data.js +2 -0
  279. package/dist/r4/model-data.js.map +1 -0
  280. package/dist/sites/index.d.ts +31 -0
  281. package/dist/sites/index.d.ts.map +1 -0
  282. package/dist/sites/index.js +205 -0
  283. package/dist/sites/index.js.map +1 -0
  284. package/dist/typed/infer.d.ts +234 -0
  285. package/dist/typed/infer.d.ts.map +1 -0
  286. package/dist/typed/infer.js +85 -0
  287. package/dist/typed/infer.js.map +1 -0
  288. package/dist/typed/perf-fixture.types.d.ts +136 -0
  289. package/dist/typed/perf-fixture.types.d.ts.map +1 -0
  290. package/dist/typed/perf-fixture.types.js +2 -0
  291. package/dist/typed/perf-fixture.types.js.map +1 -0
  292. package/dist/values/collection.d.ts +24 -0
  293. package/dist/values/collection.d.ts.map +1 -0
  294. package/dist/values/collection.js +51 -0
  295. package/dist/values/collection.js.map +1 -0
  296. package/dist/values/datetime.d.ts +54 -0
  297. package/dist/values/datetime.d.ts.map +1 -0
  298. package/dist/values/datetime.js +226 -0
  299. package/dist/values/datetime.js.map +1 -0
  300. package/dist/values/decimal.d.ts +48 -0
  301. package/dist/values/decimal.d.ts.map +1 -0
  302. package/dist/values/decimal.js +188 -0
  303. package/dist/values/decimal.js.map +1 -0
  304. package/dist/values/numeric.d.ts +24 -0
  305. package/dist/values/numeric.d.ts.map +1 -0
  306. package/dist/values/numeric.js +53 -0
  307. package/dist/values/numeric.js.map +1 -0
  308. package/dist/values/quantity.d.ts +49 -0
  309. package/dist/values/quantity.d.ts.map +1 -0
  310. package/dist/values/quantity.js +297 -0
  311. package/dist/values/quantity.js.map +1 -0
  312. package/dist/values/temporal-arithmetic.d.ts +17 -0
  313. package/dist/values/temporal-arithmetic.d.ts.map +1 -0
  314. package/dist/values/temporal-arithmetic.js +183 -0
  315. package/dist/values/temporal-arithmetic.js.map +1 -0
  316. package/dist/values/temporal-compare.d.ts +9 -0
  317. package/dist/values/temporal-compare.d.ts.map +1 -0
  318. package/dist/values/temporal-compare.js +59 -0
  319. package/dist/values/temporal-compare.js.map +1 -0
  320. package/dist/values/type-compat.d.ts +47 -0
  321. package/dist/values/type-compat.d.ts.map +1 -0
  322. package/dist/values/type-compat.js +100 -0
  323. package/dist/values/type-compat.js.map +1 -0
  324. package/dist/values/typed-value.d.ts +48 -0
  325. package/dist/values/typed-value.d.ts.map +1 -0
  326. package/dist/values/typed-value.js +117 -0
  327. package/dist/values/typed-value.js.map +1 -0
  328. package/dist/values/ucum.d.ts +14 -0
  329. package/dist/values/ucum.d.ts.map +1 -0
  330. package/dist/values/ucum.js +146 -0
  331. package/dist/values/ucum.js.map +1 -0
  332. package/package.json +137 -0
  333. package/src/analyzer/analyze-dto.ts +195 -0
  334. package/src/analyzer/analyze.ts +1181 -0
  335. package/src/analyzer/expression-policy.ts +434 -0
  336. package/src/analyzer/index.ts +23 -0
  337. package/src/analyzer/regex-safety.ts +85 -0
  338. package/src/analyzer/signatures.ts +260 -0
  339. package/src/api/bundle.ts +132 -0
  340. package/src/api/cache.ts +40 -0
  341. package/src/api/column-signature.ts +71 -0
  342. package/src/api/compile.ts +308 -0
  343. package/src/api/constraints.ts +104 -0
  344. package/src/api/dto.ts +445 -0
  345. package/src/api/engine.ts +328 -0
  346. package/src/api/evaluate.ts +11 -0
  347. package/src/api/project.ts +255 -0
  348. package/src/api/tagged.ts +35 -0
  349. package/src/cli/dto-check.ts +94 -0
  350. package/src/cli/fhirpath-check.ts +168 -0
  351. package/src/cli/ts-loader.mjs +49 -0
  352. package/src/engine/context.ts +282 -0
  353. package/src/engine/evaluator.ts +246 -0
  354. package/src/engine/navigation.ts +106 -0
  355. package/src/engine/operators/collections.ts +34 -0
  356. package/src/engine/operators/comparison.ts +82 -0
  357. package/src/engine/operators/equality.ts +232 -0
  358. package/src/engine/operators/index.ts +65 -0
  359. package/src/engine/operators/logic.ts +53 -0
  360. package/src/engine/operators/math.ts +225 -0
  361. package/src/engine/operators/strings.ts +25 -0
  362. package/src/engine/operators/types.ts +16 -0
  363. package/src/engine/type-matching.ts +148 -0
  364. package/src/errors.ts +33 -0
  365. package/src/eslint/index.ts +388 -0
  366. package/src/fhir/html-checks.ts +266 -0
  367. package/src/fhir/model-navigation.ts +148 -0
  368. package/src/functions/aggregate.ts +136 -0
  369. package/src/functions/boundary.ts +209 -0
  370. package/src/functions/combining.ts +15 -0
  371. package/src/functions/control.ts +25 -0
  372. package/src/functions/conversion.ts +349 -0
  373. package/src/functions/date-components.ts +88 -0
  374. package/src/functions/existence.ts +107 -0
  375. package/src/functions/fhir.ts +247 -0
  376. package/src/functions/filtering.ts +120 -0
  377. package/src/functions/install.ts +19 -0
  378. package/src/functions/iteration.ts +21 -0
  379. package/src/functions/math.ts +167 -0
  380. package/src/functions/reflection.ts +24 -0
  381. package/src/functions/registry.ts +72 -0
  382. package/src/functions/sort.ts +68 -0
  383. package/src/functions/string.ts +413 -0
  384. package/src/functions/subsetting.ts +89 -0
  385. package/src/functions/tree.ts +112 -0
  386. package/src/functions/type-specifier.ts +29 -0
  387. package/src/functions/utility.ts +82 -0
  388. package/src/functions/variables.ts +36 -0
  389. package/src/index.ts +30 -0
  390. package/src/lexer/lexer.ts +341 -0
  391. package/src/lexer/tokens.ts +69 -0
  392. package/src/model/provider.ts +36 -0
  393. package/src/parser/ast.ts +164 -0
  394. package/src/parser/parser.ts +321 -0
  395. package/src/parser/precedence.ts +52 -0
  396. package/src/parser/printer.ts +114 -0
  397. package/src/r4/generated/resources-data.ts +28631 -0
  398. package/src/r4/generated/type-maps.ts +22145 -0
  399. package/src/r4/generated/types-data.ts +2208 -0
  400. package/src/r4/index.ts +107 -0
  401. package/src/r4/model-data.ts +17 -0
  402. package/src/sites/index.ts +285 -0
  403. package/src/typed/infer.ts +433 -0
  404. package/src/typed/perf-fixture.types.ts +143 -0
  405. package/src/values/collection.ts +57 -0
  406. package/src/values/datetime.ts +285 -0
  407. package/src/values/decimal.ts +213 -0
  408. package/src/values/numeric.ts +63 -0
  409. package/src/values/quantity.ts +358 -0
  410. package/src/values/temporal-arithmetic.ts +231 -0
  411. package/src/values/temporal-compare.ts +65 -0
  412. package/src/values/type-compat.ts +133 -0
  413. package/src/values/typed-value.ts +151 -0
  414. package/src/values/ucum.ts +181 -0
@@ -0,0 +1,59 @@
1
+ import { GREGORIAN_UTC_YEAR_OFFSET } from "./datetime.js";
2
+ /**
3
+ * Precision levels for comparison. Seconds and milliseconds are one level: the spec
4
+ * treats the second field as a decimal, so `@T10:00:00` and `@T10:00:00.0` compare
5
+ * as equal values rather than as a precision mismatch.
6
+ */
7
+ const LEVELS = ['year', 'month', 'day', 'hour', 'minute', 'second'];
8
+ /**
9
+ * Compare two temporal values per spec §6.1/§6.4: equal at the shared precision but
10
+ * with different precisions → 'differentPrecision' (empty for `=` and `<`); a time
11
+ * never compares with a date/dateTime. Values without a timezone are treated as UTC.
12
+ */
13
+ export function compareTemporal(a, b) {
14
+ if ((a.kind === 'time') !== (b.kind === 'time')) {
15
+ return 'incompatible';
16
+ }
17
+ const levelA = comparisonLevel(a);
18
+ const levelB = comparisonLevel(b);
19
+ const shared = Math.min(levelA, levelB);
20
+ // At time precision, a value with a timezone and one without cannot be ordered (spec §6.1).
21
+ if (shared >= 3 && (a.timezoneOffsetMinutes === undefined) !== (b.timezoneOffsetMinutes === undefined)) {
22
+ return 'differentPrecision';
23
+ }
24
+ const rankA = rank(a, shared);
25
+ const rankB = rank(b, shared);
26
+ if (rankA < rankB) {
27
+ return -1;
28
+ }
29
+ if (rankA > rankB) {
30
+ return 1;
31
+ }
32
+ return levelA === levelB ? 0 : 'differentPrecision';
33
+ }
34
+ function comparisonLevel(value) {
35
+ const precision = value.precision === 'millisecond' ? 'second' : value.precision;
36
+ return LEVELS.indexOf(precision);
37
+ }
38
+ /**
39
+ * Milliseconds on a common axis, truncated to `level`. Years are shifted by +400 to
40
+ * dodge Date.UTC's 0-99 → 19xx mapping; the Gregorian calendar repeats exactly every
41
+ * 400 years, so ordering and equality are unaffected.
42
+ */
43
+ function rank(value, level) {
44
+ const year = (value.year ?? 1970) + GREGORIAN_UTC_YEAR_OFFSET;
45
+ const month = level >= 1 ? (value.month ?? 1) : 1;
46
+ const day = level >= 2 ? (value.day ?? 1) : 1;
47
+ const hour = level >= 3 ? (value.hour ?? 0) : 0;
48
+ let minute = level >= 4 ? (value.minute ?? 0) : 0;
49
+ let milliseconds = 0;
50
+ if (level >= 5) {
51
+ const fraction = value.fraction === undefined ? 0 : Number.parseFloat(`0.${value.fraction}`);
52
+ milliseconds = Math.round(((value.second ?? 0) + fraction) * 1000);
53
+ }
54
+ if (level >= 3 && value.timezoneOffsetMinutes !== undefined) {
55
+ minute -= value.timezoneOffsetMinutes;
56
+ }
57
+ return Date.UTC(year, month - 1, day, hour, minute, 0, milliseconds);
58
+ }
59
+ //# sourceMappingURL=temporal-compare.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"temporal-compare.js","sourceRoot":"","sources":["../../src/values/temporal-compare.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,47 @@
1
+ /** Shared, conservative type compatibility for runtime dispatch and static checks. */
2
+ import type { ModelProvider } from '../model/provider.ts';
3
+ /** Behavior families used by the static checks. */
4
+ export type ValueKind = 'Boolean' | 'String' | 'Numeric' | 'Temporal' | 'Quantity' | 'Complex';
5
+ export declare function valueKindOfTypeName(canonical: string): ValueKind;
6
+ /**
7
+ * Resolves a focus type through its full name, then its local name. Unknown names
8
+ * return undefined so callers can skip claims the model cannot support.
9
+ */
10
+ export declare function canonicalFocusType(model: ModelProvider, raw: string): string | undefined;
11
+ /**
12
+ * Returns whether one value may have both types. Compatible value kinds and
13
+ * either direction of the model hierarchy count. The model check must still run
14
+ * when kinds differ because `SimpleQuantity` and `Quantity` use different kinds.
15
+ */
16
+ export declare function typesOverlap(model: ModelProvider, a: string, b: string): boolean;
17
+ /**
18
+ * The proof that a call is on the wrong focus: `wanted` lists the declared
19
+ * types and `found` lists the focus types, both as canonical names with
20
+ * duplicates removed. Callers report those two lists and add nothing of their
21
+ * own.
22
+ */
23
+ export interface UnsatisfiedInput {
24
+ wanted: string[];
25
+ found: string[];
26
+ }
27
+ /**
28
+ * Returns proof only when every known focus type is incompatible with every
29
+ * declared input type. Missing models, unknown types, empty focus, and any
30
+ * matching type remain allowed. Runtime dispatch and the analyzer share this
31
+ * decision and report it in their own way.
32
+ */
33
+ export declare function unsatisfiedInput(model: ModelProvider | undefined, declared: readonly string[] | undefined, focus: Iterable<string>): UnsatisfiedInput | undefined;
34
+ /** Either the declaration a call resolves to, or the proof that none of them fits. */
35
+ export type InputResolution<T> = {
36
+ resolved: T;
37
+ } | {
38
+ unsatisfied: UnsatisfiedInput;
39
+ };
40
+ /**
41
+ * Selects the first same-name declaration accepted by the focus. If none fits,
42
+ * the result combines their expected and found types into one error. Unknown or
43
+ * empty focus selects the first declaration; registration prevents ambiguous
44
+ * known focus types.
45
+ */
46
+ export declare function resolveByInput<T>(model: ModelProvider | undefined, candidates: readonly T[], declaredTypesOf: (candidate: T) => readonly string[] | undefined, focus: readonly string[]): InputResolution<T>;
47
+ //# sourceMappingURL=type-compat.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"type-compat.d.ts","sourceRoot":"","sources":["../../src/values/type-compat.ts"],"names":[],"mappings":"AAAA,sFAAsF;AACtF,OAAO,KAAK,EAAE,aAAa,EAAE,MAAM,sBAAsB,CAAA;AAGzD,mDAAmD;AACnD,MAAM,MAAM,SAAS,GAAG,SAAS,GAAG,QAAQ,GAAG,SAAS,GAAG,UAAU,GAAG,UAAU,GAAG,SAAS,CAAA;AAE9F,wBAAgB,mBAAmB,CAAC,SAAS,EAAE,MAAM,GAAG,SAAS,CAoBhE;AAED;;;GAGG;AACH,wBAAgB,kBAAkB,CAAC,KAAK,EAAE,aAAa,EAAE,GAAG,EAAE,MAAM,GAAG,MAAM,GAAG,SAAS,CAKxF;AAUD;;;;GAIG;AACH,wBAAgB,YAAY,CAAC,KAAK,EAAE,aAAa,EAAE,CAAC,EAAE,MAAM,EAAE,CAAC,EAAE,MAAM,GAAG,OAAO,CAMhF;AAED;;;;;GAKG;AACH,MAAM,WAAW,gBAAgB;IAC/B,MAAM,EAAE,MAAM,EAAE,CAAA;IAChB,KAAK,EAAE,MAAM,EAAE,CAAA;CAChB;AAED;;;;;GAKG;AACH,wBAAgB,gBAAgB,CAC9B,KAAK,EAAE,aAAa,GAAG,SAAS,EAChC,QAAQ,EAAE,SAAS,MAAM,EAAE,GAAG,SAAS,EACvC,KAAK,EAAE,QAAQ,CAAC,MAAM,CAAC,GACtB,gBAAgB,GAAG,SAAS,CAmB9B;AAED,sFAAsF;AACtF,MAAM,MAAM,eAAe,CAAC,CAAC,IAAI;IAAE,QAAQ,EAAE,CAAC,CAAA;CAAE,GAAG;IAAE,WAAW,EAAE,gBAAgB,CAAA;CAAE,CAAA;AAEpF;;;;;GAKG;AACH,wBAAgB,cAAc,CAAC,CAAC,EAC9B,KAAK,EAAE,aAAa,GAAG,SAAS,EAChC,UAAU,EAAE,SAAS,CAAC,EAAE,EACxB,eAAe,EAAE,CAAC,SAAS,EAAE,CAAC,KAAK,SAAS,MAAM,EAAE,GAAG,SAAS,EAChE,KAAK,EAAE,SAAS,MAAM,EAAE,GACvB,eAAe,CAAC,CAAC,CAAC,CAepB"}
@@ -0,0 +1,100 @@
1
+ import { FHIR_PRIMITIVE_TO_SYSTEM, typeLocalName } from "./typed-value.js";
2
+ export function valueKindOfTypeName(canonical) {
3
+ const system = canonical.startsWith('System.') ? canonical : FHIR_PRIMITIVE_TO_SYSTEM[typeLocalName(canonical)];
4
+ switch (system) {
5
+ case 'System.Boolean':
6
+ return 'Boolean';
7
+ case 'System.String':
8
+ return 'String';
9
+ case 'System.Integer':
10
+ case 'System.Long':
11
+ case 'System.Decimal':
12
+ return 'Numeric';
13
+ case 'System.Date':
14
+ case 'System.DateTime':
15
+ case 'System.Time':
16
+ return 'Temporal';
17
+ case 'System.Quantity':
18
+ return 'Quantity';
19
+ default:
20
+ return canonical === 'FHIR.Quantity' || typeLocalName(canonical) === 'Quantity' ? 'Quantity' : 'Complex';
21
+ }
22
+ }
23
+ /**
24
+ * Resolves a focus type through its full name, then its local name. Unknown names
25
+ * return undefined so callers can skip claims the model cannot support.
26
+ */
27
+ export function canonicalFocusType(model, raw) {
28
+ if (raw.startsWith('System.')) {
29
+ return raw;
30
+ }
31
+ return model.resolveType(raw) ?? model.resolveType(typeLocalName(raw));
32
+ }
33
+ /** True when every `type` value is a `base` value, including FHIR-primitive → System subtyping. */
34
+ function typeSatisfies(model, type, base) {
35
+ if (type === base || model.isSubtypeOf(type, base)) {
36
+ return true;
37
+ }
38
+ return base.startsWith('System.') && FHIR_PRIMITIVE_TO_SYSTEM[typeLocalName(type)] === base;
39
+ }
40
+ /**
41
+ * Returns whether one value may have both types. Compatible value kinds and
42
+ * either direction of the model hierarchy count. The model check must still run
43
+ * when kinds differ because `SimpleQuantity` and `Quantity` use different kinds.
44
+ */
45
+ export function typesOverlap(model, a, b) {
46
+ const kind = valueKindOfTypeName(a);
47
+ if (kind !== 'Complex' && kind === valueKindOfTypeName(b)) {
48
+ return true;
49
+ }
50
+ return typeSatisfies(model, a, b) || typeSatisfies(model, b, a);
51
+ }
52
+ /**
53
+ * Returns proof only when every known focus type is incompatible with every
54
+ * declared input type. Missing models, unknown types, empty focus, and any
55
+ * matching type remain allowed. Runtime dispatch and the analyzer share this
56
+ * decision and report it in their own way.
57
+ */
58
+ export function unsatisfiedInput(model, declared, focus) {
59
+ if (model === undefined || declared === undefined) {
60
+ return undefined;
61
+ }
62
+ const wanted = declared
63
+ .map(type => canonicalFocusType(model, type))
64
+ .filter((type) => type !== undefined);
65
+ if (wanted.length === 0) {
66
+ return undefined;
67
+ }
68
+ const found = new Set();
69
+ for (const type of focus) {
70
+ const canonical = canonicalFocusType(model, type);
71
+ if (canonical === undefined || wanted.some(want => typesOverlap(model, canonical, want))) {
72
+ return undefined;
73
+ }
74
+ found.add(canonical);
75
+ }
76
+ return found.size === 0 ? undefined : { wanted, found: [...found] };
77
+ }
78
+ /**
79
+ * Selects the first same-name declaration accepted by the focus. If none fits,
80
+ * the result combines their expected and found types into one error. Unknown or
81
+ * empty focus selects the first declaration; registration prevents ambiguous
82
+ * known focus types.
83
+ */
84
+ export function resolveByInput(model, candidates, declaredTypesOf, focus) {
85
+ const misses = [];
86
+ for (const candidate of candidates) {
87
+ const miss = unsatisfiedInput(model, declaredTypesOf(candidate), focus);
88
+ if (miss === undefined) {
89
+ return { resolved: candidate };
90
+ }
91
+ misses.push(miss);
92
+ }
93
+ return {
94
+ unsatisfied: {
95
+ wanted: [...new Set(misses.flatMap(miss => miss.wanted))],
96
+ found: [...new Set(misses.flatMap(miss => miss.found))],
97
+ },
98
+ };
99
+ }
100
+ //# sourceMappingURL=type-compat.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"type-compat.js","sourceRoot":"","sources":["../../src/values/type-compat.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,48 @@
1
+ import { Decimal } from './decimal.ts';
2
+ export declare const SYSTEM_BOOLEAN = "System.Boolean";
3
+ export declare const SYSTEM_STRING = "System.String";
4
+ export declare const SYSTEM_INTEGER = "System.Integer";
5
+ export declare const SYSTEM_LONG = "System.Long";
6
+ export declare const SYSTEM_DECIMAL = "System.Decimal";
7
+ export declare const SYSTEM_DATE = "System.Date";
8
+ export declare const SYSTEM_DATETIME = "System.DateTime";
9
+ export declare const SYSTEM_TIME = "System.Time";
10
+ export declare const SYSTEM_QUANTITY = "System.Quantity";
11
+ /** Placeholder type for plain objects when no model knows better. */
12
+ export declare const OBJECT_TYPE = "Object";
13
+ /** A minimal Quantity value; unit algebra and UCUM conversion land in the quantity phase. */
14
+ export interface QuantityValue {
15
+ value: Decimal;
16
+ unit: string;
17
+ /** True for calendar duration units (`4 days`), false for UCUM strings (`4 'd'`). */
18
+ calendar: boolean;
19
+ }
20
+ /**
21
+ * A value paired with its type name, e.g. `System.Integer` or `FHIR.Patient`.
22
+ * Runtime representations: Boolean → boolean, String → string, Integer → number,
23
+ * Long → bigint, Decimal → Decimal, Date/DateTime/Time → Temporal,
24
+ * Quantity → QuantityValue, complex types → raw JSON.
25
+ */
26
+ export interface TypedValue {
27
+ type: string;
28
+ value: unknown;
29
+ /** For FHIR primitives navigated with a model: the `_field` sibling (id/extension). */
30
+ primitiveElement?: unknown;
31
+ }
32
+ /** FHIR primitive type names to their System twins (FHIR spec "types" page). */
33
+ export declare const FHIR_PRIMITIVE_TO_SYSTEM: Readonly<Record<string, string>>;
34
+ /**
35
+ * The System type a value behaves as: System types answer themselves, FHIR
36
+ * primitives answer their twin (`FHIR.code` → `System.String`), everything else
37
+ * undefined. Operators dispatch on this so FHIR-typed primitives keep working.
38
+ */
39
+ export declare function systemTypeOf(item: TypedValue): string | undefined;
40
+ /** The local part of a qualified type name: `System.Boolean` → `Boolean`. */
41
+ export declare function typeLocalName(type: string): string;
42
+ /** Wrap a raw JSON value, inferring System types where possible. */
43
+ export declare function toTypedValue(value: unknown): TypedValue;
44
+ /** Wrap an input (single value, array, or undefined) as a collection. */
45
+ export declare function toCollection(value: unknown): TypedValue[];
46
+ /** Unwrap for the public API: internal value objects become plain JS values. */
47
+ export declare function unwrap(typed: TypedValue): unknown;
48
+ //# sourceMappingURL=typed-value.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"typed-value.d.ts","sourceRoot":"","sources":["../../src/values/typed-value.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,OAAO,EAAE,MAAM,cAAc,CAAA;AAEtC,eAAO,MAAM,cAAc,mBAAmB,CAAA;AAC9C,eAAO,MAAM,aAAa,kBAAkB,CAAA;AAC5C,eAAO,MAAM,cAAc,mBAAmB,CAAA;AAC9C,eAAO,MAAM,WAAW,gBAAgB,CAAA;AACxC,eAAO,MAAM,cAAc,mBAAmB,CAAA;AAC9C,eAAO,MAAM,WAAW,gBAAgB,CAAA;AACxC,eAAO,MAAM,eAAe,oBAAoB,CAAA;AAChD,eAAO,MAAM,WAAW,gBAAgB,CAAA;AACxC,eAAO,MAAM,eAAe,oBAAoB,CAAA;AAEhD,qEAAqE;AACrE,eAAO,MAAM,WAAW,WAAW,CAAA;AAEnC,6FAA6F;AAC7F,MAAM,WAAW,aAAa;IAC5B,KAAK,EAAE,OAAO,CAAA;IACd,IAAI,EAAE,MAAM,CAAA;IACZ,qFAAqF;IACrF,QAAQ,EAAE,OAAO,CAAA;CAClB;AAED;;;;;GAKG;AACH,MAAM,WAAW,UAAU;IACzB,IAAI,EAAE,MAAM,CAAA;IACZ,KAAK,EAAE,OAAO,CAAA;IACd,uFAAuF;IACvF,gBAAgB,CAAC,EAAE,OAAO,CAAA;CAC3B;AAED,gFAAgF;AAChF,eAAO,MAAM,wBAAwB,EAAE,QAAQ,CAAC,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAsBrE,CAAA;AAED;;;;GAIG;AACH,wBAAgB,YAAY,CAAC,IAAI,EAAE,UAAU,GAAG,MAAM,GAAG,SAAS,CAKjE;AAED,6EAA6E;AAC7E,wBAAgB,aAAa,CAAC,IAAI,EAAE,MAAM,GAAG,MAAM,CAGlD;AAED,oEAAoE;AACpE,wBAAgB,YAAY,CAAC,KAAK,EAAE,OAAO,GAAG,UAAU,CA0BvD;AAUD,yEAAyE;AACzE,wBAAgB,YAAY,CAAC,KAAK,EAAE,OAAO,GAAG,UAAU,EAAE,CAQzD;AAED,gFAAgF;AAChF,wBAAgB,MAAM,CAAC,KAAK,EAAE,UAAU,GAAG,OAAO,CAajD"}
@@ -0,0 +1,117 @@
1
+ import { Decimal } from "./decimal.js";
2
+ export const SYSTEM_BOOLEAN = 'System.Boolean';
3
+ export const SYSTEM_STRING = 'System.String';
4
+ export const SYSTEM_INTEGER = 'System.Integer';
5
+ export const SYSTEM_LONG = 'System.Long';
6
+ export const SYSTEM_DECIMAL = 'System.Decimal';
7
+ export const SYSTEM_DATE = 'System.Date';
8
+ export const SYSTEM_DATETIME = 'System.DateTime';
9
+ export const SYSTEM_TIME = 'System.Time';
10
+ export const SYSTEM_QUANTITY = 'System.Quantity';
11
+ /** Placeholder type for plain objects when no model knows better. */
12
+ export const OBJECT_TYPE = 'Object';
13
+ /** FHIR primitive type names to their System twins (FHIR spec "types" page). */
14
+ export const FHIR_PRIMITIVE_TO_SYSTEM = {
15
+ boolean: 'System.Boolean',
16
+ integer: 'System.Integer',
17
+ positiveInt: 'System.Integer',
18
+ unsignedInt: 'System.Integer',
19
+ integer64: 'System.Long',
20
+ decimal: 'System.Decimal',
21
+ date: 'System.Date',
22
+ dateTime: 'System.DateTime',
23
+ instant: 'System.DateTime',
24
+ time: 'System.Time',
25
+ string: 'System.String',
26
+ code: 'System.String',
27
+ id: 'System.String',
28
+ markdown: 'System.String',
29
+ uri: 'System.String',
30
+ url: 'System.String',
31
+ canonical: 'System.String',
32
+ oid: 'System.String',
33
+ uuid: 'System.String',
34
+ base64Binary: 'System.String',
35
+ xhtml: 'System.String',
36
+ };
37
+ /**
38
+ * The System type a value behaves as: System types answer themselves, FHIR
39
+ * primitives answer their twin (`FHIR.code` → `System.String`), everything else
40
+ * undefined. Operators dispatch on this so FHIR-typed primitives keep working.
41
+ */
42
+ export function systemTypeOf(item) {
43
+ if (item.type.startsWith('System.')) {
44
+ return item.type;
45
+ }
46
+ return FHIR_PRIMITIVE_TO_SYSTEM[typeLocalName(item.type)];
47
+ }
48
+ /** The local part of a qualified type name: `System.Boolean` → `Boolean`. */
49
+ export function typeLocalName(type) {
50
+ const separator = type.lastIndexOf('.');
51
+ return separator === -1 ? type : type.slice(separator + 1);
52
+ }
53
+ /** Wrap a raw JSON value, inferring System types where possible. */
54
+ export function toTypedValue(value) {
55
+ if (typeof value === 'boolean') {
56
+ return { type: SYSTEM_BOOLEAN, value };
57
+ }
58
+ if (typeof value === 'string') {
59
+ return { type: SYSTEM_STRING, value };
60
+ }
61
+ if (typeof value === 'bigint') {
62
+ return { type: SYSTEM_LONG, value };
63
+ }
64
+ if (typeof value === 'number') {
65
+ if (Number.isSafeInteger(value)) {
66
+ return { type: SYSTEM_INTEGER, value };
67
+ }
68
+ const decimal = Decimal.fromNumber(value);
69
+ // NaN/Infinity have no FHIRPath representation; keep them opaque so operations
70
+ // against them fail with a clean type error instead of a raw TypeError.
71
+ return decimal === undefined ? { type: OBJECT_TYPE, value } : { type: SYSTEM_DECIMAL, value: decimal };
72
+ }
73
+ if (value instanceof Decimal) {
74
+ return { type: SYSTEM_DECIMAL, value };
75
+ }
76
+ if (isResource(value)) {
77
+ return { type: `FHIR.${value.resourceType}`, value };
78
+ }
79
+ return { type: OBJECT_TYPE, value };
80
+ }
81
+ function isResource(value) {
82
+ return (typeof value === 'object' &&
83
+ value !== null &&
84
+ typeof value.resourceType === 'string');
85
+ }
86
+ /** Wrap an input (single value, array, or undefined) as a collection. */
87
+ export function toCollection(value) {
88
+ if (value === undefined || value === null) {
89
+ return [];
90
+ }
91
+ if (Array.isArray(value)) {
92
+ return value.flatMap(item => toCollection(item));
93
+ }
94
+ return [toTypedValue(value)];
95
+ }
96
+ /** Unwrap for the public API: internal value objects become plain JS values. */
97
+ export function unwrap(typed) {
98
+ const value = typed.value;
99
+ if (value instanceof Decimal) {
100
+ return value.toNumber();
101
+ }
102
+ if (isTemporal(value)) {
103
+ return value.toString();
104
+ }
105
+ if (isQuantity(typed)) {
106
+ const quantity = value;
107
+ return { value: quantity.value.toNumber(), unit: quantity.unit };
108
+ }
109
+ return value;
110
+ }
111
+ function isTemporal(value) {
112
+ return typeof value === 'object' && value !== null && 'kind' in value && 'toLiteralString' in value;
113
+ }
114
+ function isQuantity(typed) {
115
+ return typed.type === SYSTEM_QUANTITY;
116
+ }
117
+ //# sourceMappingURL=typed-value.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"typed-value.js","sourceRoot":"","sources":["../../src/values/typed-value.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,OAAO,EAAE,MAAM,cAAc,CAAA;AAEtC,MAAM,CAAC,MAAM,cAAc,GAAG,gBAAgB,CAAA;AAC9C,MAAM,CAAC,MAAM,aAAa,GAAG,eAAe,CAAA;AAC5C,MAAM,CAAC,MAAM,cAAc,GAAG,gBAAgB,CAAA;AAC9C,MAAM,CAAC,MAAM,WAAW,GAAG,aAAa,CAAA;AACxC,MAAM,CAAC,MAAM,cAAc,GAAG,gBAAgB,CAAA;AAC9C,MAAM,CAAC,MAAM,WAAW,GAAG,aAAa,CAAA;AACxC,MAAM,CAAC,MAAM,eAAe,GAAG,iBAAiB,CAAA;AAChD,MAAM,CAAC,MAAM,WAAW,GAAG,aAAa,CAAA;AACxC,MAAM,CAAC,MAAM,eAAe,GAAG,iBAAiB,CAAA;AAEhD,qEAAqE;AACrE,MAAM,CAAC,MAAM,WAAW,GAAG,QAAQ,CAAA;AAuBnC,gFAAgF;AAChF,MAAM,CAAC,MAAM,wBAAwB,GAAqC;IACxE,OAAO,EAAE,gBAAgB;IACzB,OAAO,EAAE,gBAAgB;IACzB,WAAW,EAAE,gBAAgB;IAC7B,WAAW,EAAE,gBAAgB;IAC7B,SAAS,EAAE,aAAa;IACxB,OAAO,EAAE,gBAAgB;IACzB,IAAI,EAAE,aAAa;IACnB,QAAQ,EAAE,iBAAiB;IAC3B,OAAO,EAAE,iBAAiB;IAC1B,IAAI,EAAE,aAAa;IACnB,MAAM,EAAE,eAAe;IACvB,IAAI,EAAE,eAAe;IACrB,EAAE,EAAE,eAAe;IACnB,QAAQ,EAAE,eAAe;IACzB,GAAG,EAAE,eAAe;IACpB,GAAG,EAAE,eAAe;IACpB,SAAS,EAAE,eAAe;IAC1B,GAAG,EAAE,eAAe;IACpB,IAAI,EAAE,eAAe;IACrB,YAAY,EAAE,eAAe;IAC7B,KAAK,EAAE,eAAe;CACvB,CAAA;AAED;;;;GAIG;AACH,MAAM,UAAU,YAAY,CAAC,IAAgB;IAC3C,IAAI,IAAI,CAAC,IAAI,CAAC,UAAU,CAAC,SAAS,CAAC,EAAE,CAAC;QACpC,OAAO,IAAI,CAAC,IAAI,CAAA;IAClB,CAAC;IACD,OAAO,wBAAwB,CAAC,aAAa,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC,CAAA;AAC3D,CAAC;AAED,6EAA6E;AAC7E,MAAM,UAAU,aAAa,CAAC,IAAY;IACxC,MAAM,SAAS,GAAG,IAAI,CAAC,WAAW,CAAC,GAAG,CAAC,CAAA;IACvC,OAAO,SAAS,KAAK,CAAC,CAAC,CAAC,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,IAAI,CAAC,KAAK,CAAC,SAAS,GAAG,CAAC,CAAC,CAAA;AAC5D,CAAC;AAED,oEAAoE;AACpE,MAAM,UAAU,YAAY,CAAC,KAAc;IACzC,IAAI,OAAO,KAAK,KAAK,SAAS,EAAE,CAAC;QAC/B,OAAO,EAAE,IAAI,EAAE,cAAc,EAAE,KAAK,EAAE,CAAA;IACxC,CAAC;IACD,IAAI,OAAO,KAAK,KAAK,QAAQ,EAAE,CAAC;QAC9B,OAAO,EAAE,IAAI,EAAE,aAAa,EAAE,KAAK,EAAE,CAAA;IACvC,CAAC;IACD,IAAI,OAAO,KAAK,KAAK,QAAQ,EAAE,CAAC;QAC9B,OAAO,EAAE,IAAI,EAAE,WAAW,EAAE,KAAK,EAAE,CAAA;IACrC,CAAC;IACD,IAAI,OAAO,KAAK,KAAK,QAAQ,EAAE,CAAC;QAC9B,IAAI,MAAM,CAAC,aAAa,CAAC,KAAK,CAAC,EAAE,CAAC;YAChC,OAAO,EAAE,IAAI,EAAE,cAAc,EAAE,KAAK,EAAE,CAAA;QACxC,CAAC;QACD,MAAM,OAAO,GAAG,OAAO,CAAC,UAAU,CAAC,KAAK,CAAC,CAAA;QACzC,+EAA+E;QAC/E,wEAAwE;QACxE,OAAO,OAAO,KAAK,SAAS,CAAC,CAAC,CAAC,EAAE,IAAI,EAAE,WAAW,EAAE,KAAK,EAAE,CAAC,CAAC,CAAC,EAAE,IAAI,EAAE,cAAc,EAAE,KAAK,EAAE,OAAO,EAAE,CAAA;IACxG,CAAC;IACD,IAAI,KAAK,YAAY,OAAO,EAAE,CAAC;QAC7B,OAAO,EAAE,IAAI,EAAE,cAAc,EAAE,KAAK,EAAE,CAAA;IACxC,CAAC;IACD,IAAI,UAAU,CAAC,KAAK,CAAC,EAAE,CAAC;QACtB,OAAO,EAAE,IAAI,EAAE,QAAQ,KAAK,CAAC,YAAY,EAAE,EAAE,KAAK,EAAE,CAAA;IACtD,CAAC;IACD,OAAO,EAAE,IAAI,EAAE,WAAW,EAAE,KAAK,EAAE,CAAA;AACrC,CAAC;AAED,SAAS,UAAU,CAAC,KAAc;IAChC,OAAO,CACL,OAAO,KAAK,KAAK,QAAQ;QACzB,KAAK,KAAK,IAAI;QACd,OAAQ,KAAoC,CAAC,YAAY,KAAK,QAAQ,CACvE,CAAA;AACH,CAAC;AAED,yEAAyE;AACzE,MAAM,UAAU,YAAY,CAAC,KAAc;IACzC,IAAI,KAAK,KAAK,SAAS,IAAI,KAAK,KAAK,IAAI,EAAE,CAAC;QAC1C,OAAO,EAAE,CAAA;IACX,CAAC;IACD,IAAI,KAAK,CAAC,OAAO,CAAC,KAAK,CAAC,EAAE,CAAC;QACzB,OAAO,KAAK,CAAC,OAAO,CAAC,IAAI,CAAC,EAAE,CAAC,YAAY,CAAC,IAAI,CAAC,CAAC,CAAA;IAClD,CAAC;IACD,OAAO,CAAC,YAAY,CAAC,KAAK,CAAC,CAAC,CAAA;AAC9B,CAAC;AAED,gFAAgF;AAChF,MAAM,UAAU,MAAM,CAAC,KAAiB;IACtC,MAAM,KAAK,GAAG,KAAK,CAAC,KAAK,CAAA;IACzB,IAAI,KAAK,YAAY,OAAO,EAAE,CAAC;QAC7B,OAAO,KAAK,CAAC,QAAQ,EAAE,CAAA;IACzB,CAAC;IACD,IAAI,UAAU,CAAC,KAAK,CAAC,EAAE,CAAC;QACtB,OAAO,KAAK,CAAC,QAAQ,EAAE,CAAA;IACzB,CAAC;IACD,IAAI,UAAU,CAAC,KAAK,CAAC,EAAE,CAAC;QACtB,MAAM,QAAQ,GAAG,KAAsB,CAAA;QACvC,OAAO,EAAE,KAAK,EAAE,QAAQ,CAAC,KAAK,CAAC,QAAQ,EAAE,EAAE,IAAI,EAAE,QAAQ,CAAC,IAAI,EAAE,CAAA;IAClE,CAAC;IACD,OAAO,KAAK,CAAA;AACd,CAAC;AAED,SAAS,UAAU,CAAC,KAAc;IAChC,OAAO,OAAO,KAAK,KAAK,QAAQ,IAAI,KAAK,KAAK,IAAI,IAAI,MAAM,IAAI,KAAK,IAAI,iBAAiB,IAAI,KAAK,CAAA;AACrG,CAAC;AAED,SAAS,UAAU,CAAC,KAAiB;IACnC,OAAO,KAAK,CAAC,IAAI,KAAK,eAAe,CAAA;AACvC,CAAC"}
@@ -0,0 +1,14 @@
1
+ import { Decimal } from './decimal.ts';
2
+ export interface CanonicalUnit {
3
+ /** Multiplier to base units, exact. */
4
+ factor: Decimal;
5
+ /** Dimension exponents, e.g. `g/m` → { g: 1, m: -1 }. Dimensionless entries are dropped. */
6
+ dimensions: Readonly<Record<string, number>>;
7
+ }
8
+ /**
9
+ * Reduce a UCUM expression (`mg`, `m2`, `g/m`, `kg.m/s2`) to base dimensions.
10
+ * Undefined for units outside the table — they stay opaque.
11
+ */
12
+ export declare function canonicalizeUnit(unit: string): CanonicalUnit | undefined;
13
+ export declare function sameDimensions(a: CanonicalUnit, b: CanonicalUnit): boolean;
14
+ //# sourceMappingURL=ucum.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"ucum.d.ts","sourceRoot":"","sources":["../../src/values/ucum.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,OAAO,EAAE,MAAM,cAAc,CAAA;AA6DtC,MAAM,WAAW,aAAa;IAC5B,uCAAuC;IACvC,MAAM,EAAE,OAAO,CAAA;IACf,4FAA4F;IAC5F,UAAU,EAAE,QAAQ,CAAC,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC,CAAA;CAC7C;AAuED;;;GAGG;AACH,wBAAgB,gBAAgB,CAAC,IAAI,EAAE,MAAM,GAAG,aAAa,GAAG,SAAS,CAiCxE;AAED,wBAAgB,cAAc,CAAC,CAAC,EAAE,aAAa,EAAE,CAAC,EAAE,aAAa,GAAG,OAAO,CAI1E"}
@@ -0,0 +1,146 @@
1
+ import { Decimal } from "./decimal.js";
2
+ const ATOMS = {
3
+ m: { dimension: 'm', factor: '1', prefixable: true },
4
+ g: { dimension: 'g', factor: '1', prefixable: true },
5
+ s: { dimension: 's', factor: '1', prefixable: true },
6
+ mol: { dimension: 'mol', factor: '1', prefixable: true },
7
+ L: { dimension: 'm', factor: '0.001', prefixable: true }, // handled as m^3 via exponent bump below
8
+ l: { dimension: 'm', factor: '0.001', prefixable: true },
9
+ min: { dimension: 's', factor: '60', prefixable: false },
10
+ h: { dimension: 's', factor: '3600', prefixable: false },
11
+ d: { dimension: 's', factor: '86400', prefixable: false },
12
+ wk: { dimension: 's', factor: '604800', prefixable: false },
13
+ // UCUM's annum is the Julian year; the Julian month is a twelfth of it.
14
+ a: { dimension: 's', factor: '31557600', prefixable: false },
15
+ mo: { dimension: 's', factor: '2629800', prefixable: false },
16
+ '[lb_av]': { dimension: 'g', factor: '453.59237', prefixable: false },
17
+ '[oz_av]': { dimension: 'g', factor: '28.349523125', prefixable: false },
18
+ '[in_i]': { dimension: 'm', factor: '0.0254', prefixable: false },
19
+ '[ft_i]': { dimension: 'm', factor: '0.3048', prefixable: false },
20
+ '1': { dimension: '1', factor: '1', prefixable: false },
21
+ '%': { dimension: '1', factor: '0.01', prefixable: false },
22
+ };
23
+ /** Units that are volumes even though their atom row reduces through meters. */
24
+ const VOLUME_ATOMS = new Set(['L', 'l']);
25
+ const PREFIXES = {
26
+ T: '1000000000000',
27
+ G: '1000000000',
28
+ M: '1000000',
29
+ k: '1000',
30
+ h: '100',
31
+ da: '10',
32
+ d: '0.1',
33
+ c: '0.01',
34
+ m: '0.001',
35
+ u: '0.000001',
36
+ n: '0.000000001',
37
+ p: '0.000000000001',
38
+ };
39
+ /**
40
+ * Real UCUM exponents are single-digit (m2, cm3, s2). Larger ones would make
41
+ * powDecimal multiply huge exact BigInts — a tiny expression could hang the
42
+ * process — so anything past this stays an opaque unit.
43
+ */
44
+ const MAX_EXPONENT_MAGNITUDE = 9;
45
+ /** One `atom` optionally followed by an integer exponent, e.g. `m2` or `cm3`. */
46
+ function parseComponent(text) {
47
+ // Whole-text atoms first, so '1' is the unity unit rather than an empty atom with exponent 1.
48
+ const whole = resolveAtom(text);
49
+ if (whole) {
50
+ const volumeBump = VOLUME_ATOMS.has(whole.atomKey) ? 3 : 1;
51
+ return { factor: whole.factor, dimension: whole.atom.dimension, exponent: volumeBump };
52
+ }
53
+ const match = /^(.*?)(-?\d+)?$/.exec(text);
54
+ /* v8 ignore next 3 -- the regex cannot fail on any string */
55
+ if (!match) {
56
+ return undefined;
57
+ }
58
+ const [, atomText = '', exponentText] = match;
59
+ const exponent = exponentText === undefined ? 1 : Number.parseInt(exponentText, 10);
60
+ if (Math.abs(exponent) > MAX_EXPONENT_MAGNITUDE) {
61
+ return undefined;
62
+ }
63
+ const resolved = resolveAtom(atomText);
64
+ if (!resolved) {
65
+ return undefined;
66
+ }
67
+ const volumeBump = VOLUME_ATOMS.has(resolved.atomKey) ? 3 : 1;
68
+ const factor = powDecimal(resolved.factor, exponent);
69
+ return { factor, dimension: resolved.atom.dimension, exponent: exponent * volumeBump };
70
+ }
71
+ function resolveAtom(text) {
72
+ const direct = ATOMS[text];
73
+ if (direct) {
74
+ return { atom: direct, atomKey: text, factor: Decimal.fromString(direct.factor) };
75
+ }
76
+ for (const [prefix, prefixFactor] of Object.entries(PREFIXES)) {
77
+ if (text.startsWith(prefix)) {
78
+ const rest = text.slice(prefix.length);
79
+ const atom = ATOMS[rest];
80
+ if (atom?.prefixable) {
81
+ const factor = Decimal.fromString(atom.factor).multiply(Decimal.fromString(prefixFactor));
82
+ return { atom, atomKey: rest, factor };
83
+ }
84
+ }
85
+ }
86
+ return undefined;
87
+ }
88
+ function powDecimal(base, exponent) {
89
+ if (exponent === 0) {
90
+ return new Decimal(1n, 0);
91
+ }
92
+ let result = new Decimal(1n, 0);
93
+ for (let i = 0; i < Math.abs(exponent); i++) {
94
+ result = result.multiply(base);
95
+ }
96
+ if (exponent < 0) {
97
+ // Factors are exact positive decimals, so the inverse always exists.
98
+ return new Decimal(1n, 0).divide(result);
99
+ }
100
+ return result;
101
+ }
102
+ /**
103
+ * Reduce a UCUM expression (`mg`, `m2`, `g/m`, `kg.m/s2`) to base dimensions.
104
+ * Undefined for units outside the table — they stay opaque.
105
+ */
106
+ export function canonicalizeUnit(unit) {
107
+ const [numerator, ...denominators] = unit.split('/');
108
+ let factor = new Decimal(1n, 0);
109
+ const dimensions = {};
110
+ const apply = (componentText, sign) => {
111
+ const component = parseComponent(componentText);
112
+ if (!component) {
113
+ return false;
114
+ }
115
+ factor = sign === 1 ? factor.multiply(component.factor) : factor.divide(component.factor);
116
+ if (component.dimension !== '1') {
117
+ const next = (dimensions[component.dimension] ?? 0) + sign * component.exponent;
118
+ if (next === 0) {
119
+ delete dimensions[component.dimension];
120
+ }
121
+ else {
122
+ dimensions[component.dimension] = next;
123
+ }
124
+ }
125
+ return true;
126
+ };
127
+ for (const part of (numerator ?? '').split('.')) {
128
+ if (!apply(part, 1)) {
129
+ return undefined;
130
+ }
131
+ }
132
+ for (const denominator of denominators) {
133
+ for (const part of denominator.split('.')) {
134
+ if (!apply(part, -1)) {
135
+ return undefined;
136
+ }
137
+ }
138
+ }
139
+ return { factor, dimensions };
140
+ }
141
+ export function sameDimensions(a, b) {
142
+ const keysA = Object.keys(a.dimensions);
143
+ const keysB = Object.keys(b.dimensions);
144
+ return keysA.length === keysB.length && keysA.every(key => a.dimensions[key] === b.dimensions[key]);
145
+ }
146
+ //# sourceMappingURL=ucum.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"ucum.js","sourceRoot":"","sources":["../../src/values/ucum.ts"],"names":[],"mappings":"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"}