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,107 @@
1
+ import { FhirPathEngine } from '../api/engine.ts'
2
+ import type { ElementInfo, ModelProvider } from '../model/provider.ts'
3
+ import { R4_RESOURCES } from './generated/resources-data.ts'
4
+ import { R4_DATA_TYPES } from './generated/types-data.ts'
5
+ import type { GeneratedElement, GeneratedType } from './model-data.ts'
6
+
7
+ // One canonical FHIR-primitive → System map lives in values/typed-value.ts;
8
+ // re-exported here because the model subpath is where consumers look for it.
9
+ export { FHIR_PRIMITIVE_TO_SYSTEM as PRIMITIVE_TO_SYSTEM } from '../values/typed-value.ts'
10
+ export type { GeneratedElement, GeneratedType } from './model-data.ts'
11
+
12
+ const NAMESPACE = 'FHIR'
13
+ const PREFIX = `${NAMESPACE}.`
14
+
15
+ function lookupType(name: string): GeneratedType | undefined {
16
+ return R4_RESOURCES[name] ?? R4_DATA_TYPES[name]
17
+ }
18
+
19
+ function localName(canonical: string): string {
20
+ return canonical.startsWith(PREFIX) ? canonical.slice(PREFIX.length) : canonical
21
+ }
22
+
23
+ /**
24
+ * Walk a type and its ancestors for an element. Backbone elements are typed by
25
+ * their path (`Patient.contact`), which is itself a key in the generated tables.
26
+ */
27
+ function findElement(typeName: string, element: string): GeneratedElement | undefined {
28
+ let current: string | undefined = typeName
29
+ const visited = new Set<string>()
30
+ while (current !== undefined && !visited.has(current)) {
31
+ visited.add(current)
32
+ const definition = lookupType(current)
33
+ if (!definition) {
34
+ return undefined
35
+ }
36
+ const found: GeneratedElement | undefined = definition.e[element]
37
+ if (found) {
38
+ return found
39
+ }
40
+ current = definition.b
41
+ }
42
+ return undefined
43
+ }
44
+
45
+ /** The generated R4 model: type resolution, element lookup, and the type hierarchy. */
46
+ export const r4Model: ModelProvider = {
47
+ namespace: NAMESPACE,
48
+
49
+ resolveType(name: string): string | undefined {
50
+ return lookupType(name) ? `${PREFIX}${name}` : undefined
51
+ },
52
+
53
+ getElement(type: string, element: string): ElementInfo | undefined {
54
+ const found = findElement(localName(type), element)
55
+ if (!found) {
56
+ return undefined
57
+ }
58
+ return {
59
+ types: found.t,
60
+ isCollection: found.a === 1,
61
+ isChoice: found.c === 1,
62
+ ...(found.r !== undefined && { referenceTargets: found.r }),
63
+ }
64
+ },
65
+
66
+ listElements(type: string): string[] | undefined {
67
+ let current: string | undefined = localName(type)
68
+ if (!lookupType(current)) {
69
+ return undefined
70
+ }
71
+ const names: string[] = []
72
+ const seen = new Set<string>()
73
+ const visited = new Set<string>()
74
+ while (current !== undefined && !visited.has(current)) {
75
+ visited.add(current)
76
+ const definition = lookupType(current)
77
+ if (!definition) {
78
+ break
79
+ }
80
+ for (const name of Object.keys(definition.e)) {
81
+ if (!seen.has(name)) {
82
+ seen.add(name)
83
+ names.push(name)
84
+ }
85
+ }
86
+ current = definition.b
87
+ }
88
+ return names
89
+ },
90
+
91
+ isSubtypeOf(type: string, base: string): boolean {
92
+ const target = localName(base)
93
+ let current: string | undefined = localName(type)
94
+ const visited = new Set<string>()
95
+ while (current !== undefined && !visited.has(current)) {
96
+ if (current === target) {
97
+ return true
98
+ }
99
+ visited.add(current)
100
+ current = lookupType(current)?.b
101
+ }
102
+ return false
103
+ },
104
+ }
105
+
106
+ /** A ready-made engine with the R4 model bound: `r4.evaluate('Patient.name.given', patient)`. */
107
+ export const r4 = new FhirPathEngine({ model: r4Model })
@@ -0,0 +1,17 @@
1
+ /** Shapes of the generated R4 model data (see scripts/generate-r4-model.ts). */
2
+ export interface GeneratedElement {
3
+ /** Element types; several entries for choice elements (`value[x]`). */
4
+ t: string[]
5
+ /** Present (1) when max cardinality is above 1. */
6
+ a?: 1
7
+ /** Present (1) for choice elements: JSON keys carry a type suffix (valueQuantity). */
8
+ c?: 1
9
+ /** Resource names a Reference element may point to (targetProfile); absent when unconstrained. */
10
+ r?: string[]
11
+ }
12
+
13
+ export interface GeneratedType {
14
+ /** Base type local name, absent for the roots (Base, Element). */
15
+ b?: string
16
+ e: Record<string, GeneratedElement>
17
+ }
@@ -0,0 +1,285 @@
1
+ /**
2
+ * Finds FHIRPath expressions in a TypeScript AST. The caller supplies TypeScript,
3
+ * which keeps this entry point free of runtime dependencies. The ESLint rule has
4
+ * a separate ESTree walker that uses the same expression policy.
5
+ */
6
+ // A default import, not `* as TS`. Under Node's ESM resolution a namespace
7
+ // import of `typescript` (a CommonJS `export =` module) carries a synthetic
8
+ // `default` property that a caller's own `import ts from 'typescript'` does not,
9
+ // so `typeof TS` would reject the very value callers pass. The default form
10
+ // names the same namespace — `TS.Node` still resolves — and accepts both.
11
+ import type TS from 'typescript'
12
+
13
+ import {
14
+ CALL_SITES,
15
+ type ClassHeritage,
16
+ columnFunctionDeclaration,
17
+ constructsEngine,
18
+ declaredColumnOverloads,
19
+ DTO_BASE_NAME,
20
+ dtoRootsOf,
21
+ type ExpressionAst,
22
+ expressionEntries,
23
+ type FileColumnFunction,
24
+ isCheckedCall,
25
+ isCheckedTag,
26
+ isForeignModule,
27
+ type LocalModuleOptions,
28
+ rootOf,
29
+ type SiteContext,
30
+ siteContext,
31
+ type SourceBindings,
32
+ TAG_NAME,
33
+ } from '../analyzer/expression-policy.ts'
34
+
35
+ /** The TypeScript namespace accepted by `createSiteFinder`. */
36
+ export type TypeScriptApi = typeof TS
37
+
38
+ export interface ExpressionSite {
39
+ expression: string
40
+ /** 0-based offset of the expression text inside the file. */
41
+ start: number
42
+ line: number
43
+ column: number
44
+ /** The DTO fhirType the expression is analyzed against, when the site fixes one. */
45
+ inputType?: string
46
+ /** A DTO member site, which `analyzeSite` checks with source-only limits. */
47
+ dto?: true
48
+ /** Callable DTO columns declared in the same file. */
49
+ functions?: Readonly<Record<string, FileColumnFunction>>
50
+ }
51
+
52
+ /** Finds every static FHIRPath expression in one source file. */
53
+ export type SiteFinder = (sourceText: string, fileName: string, options?: LocalModuleOptions) => ExpressionSite[]
54
+
55
+ /**
56
+ * Creates a finder for the calls and tags in `CALL_SITES`. DTO fields include a
57
+ * root type when the class declares one, and each column is exposed as a local
58
+ * function declaration. Dynamic expressions are skipped.
59
+ */
60
+ export function createSiteFinder(ts: TypeScriptApi): SiteFinder {
61
+ /** How the shared shape extractor reads TypeScript AST nodes. */
62
+ const tsAst: ExpressionAst<TS.Node> = {
63
+ string: node => (ts.isStringLiteralLike(node) ? { node, expression: node.text } : undefined),
64
+ boolean: node =>
65
+ node.kind === ts.SyntaxKind.TrueKeyword ? true : node.kind === ts.SyntaxKind.FalseKeyword ? false : undefined,
66
+ properties: node =>
67
+ ts.isObjectLiteralExpression(node)
68
+ ? node.properties
69
+ .filter(ts.isPropertyAssignment)
70
+ .map(property => ({ name: propertyKeyName(property.name), value: property.initializer }))
71
+ : undefined,
72
+ elements: node => (ts.isArrayLiteralExpression(node) ? [...node.elements] : undefined),
73
+ }
74
+
75
+ /** Statically-known property key (`path` in `{ path: ... }` or `{ 'path': ... }`), undefined when computed. */
76
+ function propertyKeyName(name: TS.PropertyName): string | undefined {
77
+ return ts.isIdentifier(name) || ts.isStringLiteral(name) ? name.text : undefined
78
+ }
79
+
80
+ /** The name of the field a `@column(...)` decorator belongs to. */
81
+ function decoratedFieldName(call: TS.CallExpression): string | undefined {
82
+ const decorator = call.parent
83
+ const member = decorator?.parent
84
+ if (
85
+ decorator === undefined ||
86
+ !ts.isDecorator(decorator) ||
87
+ member === undefined ||
88
+ !ts.isPropertyDeclaration(member) ||
89
+ !(ts.isIdentifier(member.name) || ts.isStringLiteral(member.name))
90
+ ) {
91
+ return undefined
92
+ }
93
+ return member.name.text
94
+ }
95
+
96
+ /** A class's heritage, as `dtoRootsOf` reads it: its own DTO root, or the name of the class it extends. */
97
+ function heritageOf(node: TS.ClassLikeDeclaration): ClassHeritage {
98
+ const heritage: ClassHeritage = { name: node.name?.text, ownRoot: undefined, baseName: undefined }
99
+ for (const clause of node.heritageClauses ?? []) {
100
+ if (clause.token !== ts.SyntaxKind.ExtendsKeyword) {
101
+ continue
102
+ }
103
+ for (const type of clause.types) {
104
+ const base = type.expression
105
+ if (ts.isCallExpression(base)) {
106
+ if (nameOf(base.expression) === DTO_BASE_NAME) {
107
+ const root = base.arguments[0]
108
+ heritage.ownRoot = root === undefined ? undefined : tsAst.string(root)?.expression
109
+ }
110
+ } else if (ts.isIdentifier(base)) {
111
+ heritage.baseName = base.text
112
+ }
113
+ }
114
+ }
115
+ return heritage
116
+ }
117
+
118
+ /** Collects imports, engine locals, rebound names, and DTO class roots before extracting sites. */
119
+ function collectFile(
120
+ source: TS.SourceFile,
121
+ options: LocalModuleOptions
122
+ ): {
123
+ bindings: SourceBindings
124
+ dtoRoots: ReadonlyMap<string, string>
125
+ heritage: ReadonlyMap<TS.Node, ClassHeritage>
126
+ } {
127
+ const foreign = new Set<string>()
128
+ const trusted = new Set<string>()
129
+ const rebound = new Set<string>()
130
+ for (const statement of source.statements) {
131
+ if (!(ts.isImportDeclaration(statement) && ts.isStringLiteral(statement.moduleSpecifier))) {
132
+ continue
133
+ }
134
+ const names = isForeignModule(statement.moduleSpecifier.text, options) ? foreign : trusted
135
+ const clause = statement.importClause
136
+ if (!clause) {
137
+ continue
138
+ }
139
+ if (clause.name) {
140
+ names.add(clause.name.text)
141
+ }
142
+ if (clause.namedBindings) {
143
+ if (ts.isNamedImports(clause.namedBindings)) {
144
+ for (const element of clause.namedBindings.elements) {
145
+ names.add(element.name.text)
146
+ }
147
+ } else {
148
+ names.add(clause.namedBindings.name.text)
149
+ }
150
+ }
151
+ }
152
+ const bindings = { foreign, trusted, rebound }
153
+ const heritage = new Map<TS.Node, ClassHeritage>()
154
+ const collectLocals = (node: TS.Node): void => {
155
+ if (ts.isClassLike(node)) {
156
+ heritage.set(node, heritageOf(node))
157
+ }
158
+ if (ts.isVariableDeclaration(node)) {
159
+ if (
160
+ ts.isIdentifier(node.name) &&
161
+ node.initializer !== undefined &&
162
+ ts.isNewExpression(node.initializer) &&
163
+ ts.isIdentifier(node.initializer.expression)
164
+ ) {
165
+ const set = constructsEngine(node.initializer.expression.text, bindings) ? trusted : rebound
166
+ set.add(node.name.text)
167
+ } else {
168
+ // Catch clauses reach here too: `catch (r4)` is a VariableDeclaration.
169
+ addBindingNames(node.name, rebound)
170
+ }
171
+ } else if (ts.isParameter(node)) {
172
+ addBindingNames(node.name, rebound)
173
+ } else if (
174
+ (ts.isFunctionDeclaration(node) ||
175
+ ts.isFunctionExpression(node) ||
176
+ ts.isClassDeclaration(node) ||
177
+ ts.isClassExpression(node)) &&
178
+ node.name !== undefined
179
+ ) {
180
+ rebound.add(node.name.text)
181
+ }
182
+ ts.forEachChild(node, collectLocals)
183
+ }
184
+ collectLocals(source)
185
+ return { bindings, dtoRoots: dtoRootsOf([...heritage.values()]), heritage }
186
+ }
187
+
188
+ /** Add every identifier a binding name declares (`x`, `{ r4 }`, `[a, ...rest]`). */
189
+ function addBindingNames(name: TS.BindingName, into: Set<string>): void {
190
+ if (ts.isIdentifier(name)) {
191
+ into.add(name.text)
192
+ return
193
+ }
194
+ for (const element of name.elements) {
195
+ if (ts.isBindingElement(element)) {
196
+ addBindingNames(element.name, into)
197
+ }
198
+ }
199
+ }
200
+
201
+ function nameOf(node: TS.Expression): string | undefined {
202
+ if (ts.isIdentifier(node)) {
203
+ return node.text
204
+ }
205
+ if (ts.isPropertyAccessExpression(node)) {
206
+ return node.name.text
207
+ }
208
+ return undefined
209
+ }
210
+
211
+ /** Leftmost identifier of a member-access callee (`Handlebars` in `Handlebars.compile`). */
212
+ function receiverRoot(callee: TS.Expression): string | undefined {
213
+ if (!ts.isPropertyAccessExpression(callee)) {
214
+ return undefined
215
+ }
216
+ let current: TS.Expression = callee.expression
217
+ while (ts.isPropertyAccessExpression(current) || ts.isElementAccessExpression(current)) {
218
+ current = current.expression
219
+ }
220
+ return ts.isIdentifier(current) ? current.text : undefined
221
+ }
222
+
223
+ return function findExpressionSites(
224
+ sourceText: string,
225
+ fileName: string,
226
+ options: LocalModuleOptions = {}
227
+ ): ExpressionSite[] {
228
+ const source = ts.createSourceFile(fileName, sourceText, ts.ScriptTarget.Latest, true)
229
+ const { bindings, dtoRoots, heritage } = collectFile(source, options)
230
+ const sites: ExpressionSite[] = []
231
+ const functions: Record<string, FileColumnFunction> = {}
232
+ // A site points at the first character inside the quote/backtick (node start
233
+ // + 1), so fhirpath-check can add a diagnostic's span offsets directly. The
234
+ // ESLint rule reports on the literal node itself, one column earlier.
235
+ const record = (text: string, literalNode: TS.Node, context: SiteContext = {}): void => {
236
+ const literalStart = literalNode.getStart(source) + 1
237
+ const { line, character } = source.getLineAndCharacterOfPosition(literalStart)
238
+ sites.push({
239
+ expression: text,
240
+ start: literalStart,
241
+ line: line + 1,
242
+ column: character + 1,
243
+ ...context,
244
+ })
245
+ }
246
+ const visit = (node: TS.Node, classRoot: string | undefined): void => {
247
+ if (
248
+ ts.isTaggedTemplateExpression(node) &&
249
+ nameOf(node.tag) === TAG_NAME &&
250
+ isCheckedTag(receiverRoot(node.tag), bindings)
251
+ ) {
252
+ if (ts.isNoSubstitutionTemplateLiteral(node.template)) {
253
+ record(node.template.text, node.template)
254
+ }
255
+ } else if (ts.isCallExpression(node)) {
256
+ const callee = nameOf(node.expression)
257
+ const policy = callee === undefined ? undefined : CALL_SITES.get(callee)
258
+ const argument = policy && (node.arguments[policy.argIndex] as TS.Expression | undefined)
259
+ if (
260
+ callee !== undefined &&
261
+ policy !== undefined &&
262
+ argument !== undefined &&
263
+ isCheckedCall(policy, callee, receiverRoot(node.expression), bindings)
264
+ ) {
265
+ const declares = policy.declaresField
266
+ const field = declares === undefined ? undefined : decoratedFieldName(node)
267
+ if (declares !== undefined && field !== undefined) {
268
+ functions[field] = declaredColumnOverloads(
269
+ functions[field],
270
+ columnFunctionDeclaration<TS.Node>(declares, node.arguments[1], tsAst, classRoot)
271
+ )
272
+ }
273
+ const context = siteContext<TS.Node>(policy, index => node.arguments[index], classRoot, tsAst)
274
+ for (const entry of expressionEntries<TS.Node>(argument, policy.shape, tsAst)) {
275
+ record(entry.expression, entry.node, context)
276
+ }
277
+ }
278
+ }
279
+ const nested = ts.isClassLike(node) ? rootOf(heritage.get(node), dtoRoots) : classRoot
280
+ ts.forEachChild(node, child => visit(child, nested))
281
+ }
282
+ visit(source, undefined)
283
+ return Object.keys(functions).length === 0 ? sites : sites.map(site => ({ ...site, functions }))
284
+ }
285
+ }