universal-physics-tensor 0.47.0 → 1.0.1

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 (591) hide show
  1. package/LICENSE +21 -21
  2. package/README.md +396 -383
  3. package/bin/upt.mjs +28 -22
  4. package/dist/atlas/benchmark/hybrid-retrieval.d.ts +108 -0
  5. package/dist/atlas/benchmark/hybrid-retrieval.d.ts.map +1 -0
  6. package/dist/atlas/benchmark/hybrid-retrieval.js +241 -0
  7. package/dist/atlas/benchmark/hybrid-retrieval.js.map +1 -0
  8. package/dist/atlas/catalog-formal-ref.d.ts +24 -0
  9. package/dist/atlas/catalog-formal-ref.d.ts.map +1 -0
  10. package/dist/atlas/catalog-formal-ref.js +36 -0
  11. package/dist/atlas/catalog-formal-ref.js.map +1 -0
  12. package/dist/atlas/composition-table.d.ts +11 -46
  13. package/dist/atlas/composition-table.d.ts.map +1 -1
  14. package/dist/atlas/composition-table.js +7 -124
  15. package/dist/atlas/composition-table.js.map +1 -1
  16. package/dist/atlas/conventions.d.ts +4 -58
  17. package/dist/atlas/conventions.d.ts.map +1 -1
  18. package/dist/atlas/conventions.js +3 -88
  19. package/dist/atlas/conventions.js.map +1 -1
  20. package/dist/atlas/derive-evidence.d.ts +50 -3
  21. package/dist/atlas/derive-evidence.d.ts.map +1 -1
  22. package/dist/atlas/derive-evidence.js +73 -4
  23. package/dist/atlas/derive-evidence.js.map +1 -1
  24. package/dist/atlas/diffusion/bridges-closure.d.ts.map +1 -1
  25. package/dist/atlas/diffusion/bridges-closure.js +5 -1
  26. package/dist/atlas/diffusion/bridges-closure.js.map +1 -1
  27. package/dist/atlas/index.d.ts +9 -7
  28. package/dist/atlas/index.d.ts.map +1 -1
  29. package/dist/atlas/index.js +6 -5
  30. package/dist/atlas/index.js.map +1 -1
  31. package/dist/atlas/oscillators/bridges-exact.d.ts.map +1 -1
  32. package/dist/atlas/oscillators/bridges-exact.js +6 -0
  33. package/dist/atlas/oscillators/bridges-exact.js.map +1 -1
  34. package/dist/atlas/oscillators/bridges-limits.d.ts +2 -0
  35. package/dist/atlas/oscillators/bridges-limits.d.ts.map +1 -1
  36. package/dist/atlas/oscillators/bridges-limits.js +20 -19
  37. package/dist/atlas/oscillators/bridges-limits.js.map +1 -1
  38. package/dist/atlas/oscillators/limit-witnesses.d.ts +93 -0
  39. package/dist/atlas/oscillators/limit-witnesses.d.ts.map +1 -0
  40. package/dist/atlas/oscillators/limit-witnesses.js +152 -0
  41. package/dist/atlas/oscillators/limit-witnesses.js.map +1 -0
  42. package/dist/atlas/oscillators/models.d.ts +2 -1
  43. package/dist/atlas/oscillators/models.d.ts.map +1 -1
  44. package/dist/atlas/oscillators/models.js +4 -3
  45. package/dist/atlas/oscillators/models.js.map +1 -1
  46. package/dist/atlas/oscillators/norm-transport-witness.d.ts +37 -0
  47. package/dist/atlas/oscillators/norm-transport-witness.d.ts.map +1 -0
  48. package/dist/atlas/oscillators/norm-transport-witness.js +58 -0
  49. package/dist/atlas/oscillators/norm-transport-witness.js.map +1 -0
  50. package/dist/atlas/oscillators/norm-transport.d.ts +44 -0
  51. package/dist/atlas/oscillators/norm-transport.d.ts.map +1 -0
  52. package/dist/atlas/oscillators/norm-transport.js +66 -0
  53. package/dist/atlas/oscillators/norm-transport.js.map +1 -0
  54. package/dist/atlas/oscillators/norms.d.ts +11 -0
  55. package/dist/atlas/oscillators/norms.d.ts.map +1 -0
  56. package/dist/atlas/oscillators/norms.js +11 -0
  57. package/dist/atlas/oscillators/norms.js.map +1 -0
  58. package/dist/atlas/oscillators/pendulum-motion.d.ts +38 -0
  59. package/dist/atlas/oscillators/pendulum-motion.d.ts.map +1 -0
  60. package/dist/atlas/oscillators/pendulum-motion.js +122 -0
  61. package/dist/atlas/oscillators/pendulum-motion.js.map +1 -0
  62. package/dist/atlas/oscillators/phase-carriage.d.ts +38 -0
  63. package/dist/atlas/oscillators/phase-carriage.d.ts.map +1 -0
  64. package/dist/atlas/oscillators/phase-carriage.js +96 -0
  65. package/dist/atlas/oscillators/phase-carriage.js.map +1 -0
  66. package/dist/atlas/oscillators/phase-translation.d.ts +46 -0
  67. package/dist/atlas/oscillators/phase-translation.d.ts.map +1 -0
  68. package/dist/atlas/oscillators/phase-translation.js +178 -0
  69. package/dist/atlas/oscillators/phase-translation.js.map +1 -0
  70. package/dist/atlas/oscillators/position-translation.d.ts +59 -0
  71. package/dist/atlas/oscillators/position-translation.d.ts.map +1 -0
  72. package/dist/atlas/oscillators/position-translation.js +254 -0
  73. package/dist/atlas/oscillators/position-translation.js.map +1 -0
  74. package/dist/atlas/path-bound.d.ts +126 -9
  75. package/dist/atlas/path-bound.d.ts.map +1 -1
  76. package/dist/atlas/path-bound.js +372 -23
  77. package/dist/atlas/path-bound.js.map +1 -1
  78. package/dist/atlas/physjs-ref.d.ts +112 -0
  79. package/dist/atlas/physjs-ref.d.ts.map +1 -0
  80. package/dist/atlas/physjs-ref.js +842 -0
  81. package/dist/atlas/physjs-ref.js.map +1 -0
  82. package/dist/atlas/regime.d.ts +12 -136
  83. package/dist/atlas/regime.d.ts.map +1 -1
  84. package/dist/atlas/regime.js +8 -254
  85. package/dist/atlas/regime.js.map +1 -1
  86. package/dist/atlas/serialize.d.ts.map +1 -1
  87. package/dist/atlas/serialize.js +25 -0
  88. package/dist/atlas/serialize.js.map +1 -1
  89. package/dist/atlas/translation-registry.d.ts +22 -0
  90. package/dist/atlas/translation-registry.d.ts.map +1 -0
  91. package/dist/atlas/translation-registry.js +31 -0
  92. package/dist/atlas/translation-registry.js.map +1 -0
  93. package/dist/atlas/translation.d.ts +116 -0
  94. package/dist/atlas/translation.d.ts.map +1 -0
  95. package/dist/atlas/translation.js +34 -0
  96. package/dist/atlas/translation.js.map +1 -0
  97. package/dist/atlas/types.d.ts +74 -240
  98. package/dist/atlas/types.d.ts.map +1 -1
  99. package/dist/atlas/types.js +5 -37
  100. package/dist/atlas/types.js.map +1 -1
  101. package/dist/atlas/waves/bridges-closure.d.ts.map +1 -1
  102. package/dist/atlas/waves/bridges-closure.js +4 -0
  103. package/dist/atlas/waves/bridges-closure.js.map +1 -1
  104. package/dist/atlas/waves/bridges.d.ts.map +1 -1
  105. package/dist/atlas/waves/bridges.js +3 -0
  106. package/dist/atlas/waves/bridges.js.map +1 -1
  107. package/dist/atlas/waves/models.js +1 -1
  108. package/dist/atlas/waves/models.js.map +1 -1
  109. package/dist/atlas/witness-dominance.d.ts +50 -0
  110. package/dist/atlas/witness-dominance.d.ts.map +1 -0
  111. package/dist/atlas/witness-dominance.js +86 -0
  112. package/dist/atlas/witness-dominance.js.map +1 -0
  113. package/dist/atlas/witness-specs.d.ts +30 -0
  114. package/dist/atlas/witness-specs.d.ts.map +1 -1
  115. package/dist/atlas/witness-specs.js +107 -0
  116. package/dist/atlas/witness-specs.js.map +1 -1
  117. package/dist/bridges/be53-yang-mills-confrontation.d.ts +81 -0
  118. package/dist/bridges/be53-yang-mills-confrontation.d.ts.map +1 -0
  119. package/dist/bridges/be53-yang-mills-confrontation.js +110 -0
  120. package/dist/bridges/be53-yang-mills-confrontation.js.map +1 -0
  121. package/dist/bridges/confrontations.d.ts +1 -1
  122. package/dist/bridges/confrontations.d.ts.map +1 -1
  123. package/dist/bridges/confrontations.js +291 -3
  124. package/dist/bridges/confrontations.js.map +1 -1
  125. package/dist/bridges/equations/be-13-einstein-trace.d.ts +2 -3
  126. package/dist/bridges/equations/be-13-einstein-trace.d.ts.map +1 -1
  127. package/dist/bridges/equations/be-13-einstein-trace.js +2 -3
  128. package/dist/bridges/equations/be-13-einstein-trace.js.map +1 -1
  129. package/dist/bridges/equations/be-38-mond.d.ts +7 -5
  130. package/dist/bridges/equations/be-38-mond.d.ts.map +1 -1
  131. package/dist/bridges/equations/be-38-mond.js +7 -5
  132. package/dist/bridges/equations/be-38-mond.js.map +1 -1
  133. package/dist/bridges/equations/be-53-yang-mills-beta.d.ts +21 -0
  134. package/dist/bridges/equations/be-53-yang-mills-beta.d.ts.map +1 -1
  135. package/dist/bridges/equations/be-53-yang-mills-beta.js +12 -0
  136. package/dist/bridges/equations/be-53-yang-mills-beta.js.map +1 -1
  137. package/dist/bridges/evaluator-inputs.d.ts +21 -0
  138. package/dist/bridges/evaluator-inputs.d.ts.map +1 -0
  139. package/dist/bridges/evaluator-inputs.js +75 -0
  140. package/dist/bridges/evaluator-inputs.js.map +1 -0
  141. package/dist/bridges/evaluators.d.ts +38 -0
  142. package/dist/bridges/evaluators.d.ts.map +1 -1
  143. package/dist/bridges/evaluators.js +41 -15
  144. package/dist/bridges/evaluators.js.map +1 -1
  145. package/dist/bridges/gravitational-lensing.d.ts +1 -1
  146. package/dist/bridges/gravitational-lensing.js +1 -1
  147. package/dist/bridges/index.d.ts +1 -1
  148. package/dist/bridges/index.d.ts.map +1 -1
  149. package/dist/bridges/index.js +13 -13
  150. package/dist/bridges/index.js.map +1 -1
  151. package/dist/bridges/observations/types.d.ts +110 -2
  152. package/dist/bridges/observations/types.d.ts.map +1 -1
  153. package/dist/bridges/observations/types.js +29 -0
  154. package/dist/bridges/observations/types.js.map +1 -1
  155. package/dist/bridges/perihelion-precession.d.ts +1 -1
  156. package/dist/bridges/perihelion-precession.js +1 -1
  157. package/dist/canonical/canonical-equation.d.ts +1 -1
  158. package/dist/canonical/canonical-equation.d.ts.map +1 -1
  159. package/dist/canonical/entries/atomic.d.ts.map +1 -1
  160. package/dist/canonical/entries/atomic.js +32 -10
  161. package/dist/canonical/entries/atomic.js.map +1 -1
  162. package/dist/canonical/entries/dimensional-classics.js +2 -2
  163. package/dist/canonical/entries/dimensional-classics.js.map +1 -1
  164. package/dist/canonical/entries/mechanics.d.ts.map +1 -1
  165. package/dist/canonical/entries/mechanics.js +10 -6
  166. package/dist/canonical/entries/mechanics.js.map +1 -1
  167. package/dist/canonical/entries/relativity.d.ts.map +1 -1
  168. package/dist/canonical/entries/relativity.js +41 -8
  169. package/dist/canonical/entries/relativity.js.map +1 -1
  170. package/dist/canonical/entries/thermo-nuclear-cosmo.js +5 -5
  171. package/dist/canonical/entries/thermo-nuclear-cosmo.js.map +1 -1
  172. package/dist/canonical/linkage.d.ts.map +1 -1
  173. package/dist/canonical/linkage.js +14 -8
  174. package/dist/canonical/linkage.js.map +1 -1
  175. package/dist/canonical/normal-form.d.ts +17 -0
  176. package/dist/canonical/normal-form.d.ts.map +1 -1
  177. package/dist/canonical/normal-form.js +21 -4
  178. package/dist/canonical/normal-form.js.map +1 -1
  179. package/dist/cases/brownian-sphere.d.ts +68 -0
  180. package/dist/cases/brownian-sphere.d.ts.map +1 -0
  181. package/dist/cases/brownian-sphere.js +353 -0
  182. package/dist/cases/brownian-sphere.js.map +1 -0
  183. package/dist/cases/damped-resonator.d.ts +23 -0
  184. package/dist/cases/damped-resonator.d.ts.map +1 -0
  185. package/dist/cases/damped-resonator.js +224 -0
  186. package/dist/cases/damped-resonator.js.map +1 -0
  187. package/dist/cases/index.d.ts +11 -0
  188. package/dist/cases/index.d.ts.map +1 -0
  189. package/dist/cases/index.js +29 -0
  190. package/dist/cases/index.js.map +1 -0
  191. package/dist/cases/kepler-rv.d.ts +13 -0
  192. package/dist/cases/kepler-rv.d.ts.map +1 -0
  193. package/dist/cases/kepler-rv.js +168 -0
  194. package/dist/cases/kepler-rv.js.map +1 -0
  195. package/dist/cases/lumped-cooling.d.ts +46 -0
  196. package/dist/cases/lumped-cooling.d.ts.map +1 -0
  197. package/dist/cases/lumped-cooling.js +261 -0
  198. package/dist/cases/lumped-cooling.js.map +1 -0
  199. package/dist/cases/quadrature.d.ts +14 -0
  200. package/dist/cases/quadrature.d.ts.map +1 -0
  201. package/dist/cases/quadrature.js +41 -0
  202. package/dist/cases/quadrature.js.map +1 -0
  203. package/dist/cases/resistor-noise.d.ts +14 -0
  204. package/dist/cases/resistor-noise.d.ts.map +1 -0
  205. package/dist/cases/resistor-noise.js +210 -0
  206. package/dist/cases/resistor-noise.js.map +1 -0
  207. package/dist/cases/skin-depth.d.ts +21 -0
  208. package/dist/cases/skin-depth.d.ts.map +1 -0
  209. package/dist/cases/skin-depth.js +174 -0
  210. package/dist/cases/skin-depth.js.map +1 -0
  211. package/dist/cases/types.d.ts +115 -0
  212. package/dist/cases/types.d.ts.map +1 -0
  213. package/dist/cases/types.js +20 -0
  214. package/dist/cases/types.js.map +1 -0
  215. package/dist/cli/commands/_atlas-map.d.ts +409 -0
  216. package/dist/cli/commands/_atlas-map.d.ts.map +1 -0
  217. package/dist/cli/commands/_atlas-map.js +1014 -0
  218. package/dist/cli/commands/_atlas-map.js.map +1 -0
  219. package/dist/cli/commands/_atlas-route.d.ts +111 -0
  220. package/dist/cli/commands/_atlas-route.d.ts.map +1 -0
  221. package/dist/cli/commands/_atlas-route.js +140 -0
  222. package/dist/cli/commands/_atlas-route.js.map +1 -0
  223. package/dist/cli/commands/_discovery-opts.d.ts.map +1 -1
  224. package/dist/cli/commands/_discovery-opts.js +10 -1
  225. package/dist/cli/commands/_discovery-opts.js.map +1 -1
  226. package/dist/cli/commands/atlas.d.ts +20 -0
  227. package/dist/cli/commands/atlas.d.ts.map +1 -1
  228. package/dist/cli/commands/atlas.js +333 -19
  229. package/dist/cli/commands/atlas.js.map +1 -1
  230. package/dist/cli/commands/audit.d.ts.map +1 -1
  231. package/dist/cli/commands/audit.js +14 -5
  232. package/dist/cli/commands/audit.js.map +1 -1
  233. package/dist/cli/commands/axes.js +4 -4
  234. package/dist/cli/commands/candidates.d.ts.map +1 -1
  235. package/dist/cli/commands/candidates.js +6 -5
  236. package/dist/cli/commands/candidates.js.map +1 -1
  237. package/dist/cli/commands/canonical.d.ts.map +1 -1
  238. package/dist/cli/commands/canonical.js +41 -12
  239. package/dist/cli/commands/canonical.js.map +1 -1
  240. package/dist/cli/commands/confront.d.ts.map +1 -1
  241. package/dist/cli/commands/confront.js +210 -28
  242. package/dist/cli/commands/confront.js.map +1 -1
  243. package/dist/cli/commands/connectors.d.ts.map +1 -1
  244. package/dist/cli/commands/connectors.js +11 -10
  245. package/dist/cli/commands/connectors.js.map +1 -1
  246. package/dist/cli/commands/coverage.js +3 -3
  247. package/dist/cli/commands/derive.d.ts.map +1 -1
  248. package/dist/cli/commands/derive.js +22 -10
  249. package/dist/cli/commands/derive.js.map +1 -1
  250. package/dist/cli/commands/discover.d.ts.map +1 -1
  251. package/dist/cli/commands/discover.js +149 -32
  252. package/dist/cli/commands/discover.js.map +1 -1
  253. package/dist/cli/commands/eval.d.ts.map +1 -1
  254. package/dist/cli/commands/eval.js +76 -17
  255. package/dist/cli/commands/eval.js.map +1 -1
  256. package/dist/cli/commands/evaluate.d.ts +30 -0
  257. package/dist/cli/commands/evaluate.d.ts.map +1 -1
  258. package/dist/cli/commands/evaluate.js +440 -25
  259. package/dist/cli/commands/evaluate.js.map +1 -1
  260. package/dist/cli/commands/explain.d.ts.map +1 -1
  261. package/dist/cli/commands/explain.js +38 -11
  262. package/dist/cli/commands/explain.js.map +1 -1
  263. package/dist/cli/commands/frontier.d.ts +3 -0
  264. package/dist/cli/commands/frontier.d.ts.map +1 -0
  265. package/dist/cli/commands/frontier.js +28 -0
  266. package/dist/cli/commands/frontier.js.map +1 -0
  267. package/dist/cli/commands/ground.d.ts.map +1 -1
  268. package/dist/cli/commands/ground.js +37 -12
  269. package/dist/cli/commands/ground.js.map +1 -1
  270. package/dist/cli/commands/index.d.ts +5 -0
  271. package/dist/cli/commands/index.d.ts.map +1 -1
  272. package/dist/cli/commands/index.js +5 -0
  273. package/dist/cli/commands/index.js.map +1 -1
  274. package/dist/cli/commands/map.d.ts +8 -0
  275. package/dist/cli/commands/map.d.ts.map +1 -1
  276. package/dist/cli/commands/map.js +401 -64
  277. package/dist/cli/commands/map.js.map +1 -1
  278. package/dist/cli/commands/metric.d.ts +3 -0
  279. package/dist/cli/commands/metric.d.ts.map +1 -0
  280. package/dist/cli/commands/metric.js +136 -0
  281. package/dist/cli/commands/metric.js.map +1 -0
  282. package/dist/cli/commands/path.d.ts +109 -1
  283. package/dist/cli/commands/path.d.ts.map +1 -1
  284. package/dist/cli/commands/path.js +1019 -109
  285. package/dist/cli/commands/path.js.map +1 -1
  286. package/dist/cli/commands/predict.d.ts.map +1 -1
  287. package/dist/cli/commands/predict.js +6 -5
  288. package/dist/cli/commands/predict.js.map +1 -1
  289. package/dist/cli/commands/priority.d.ts.map +1 -1
  290. package/dist/cli/commands/priority.js +4 -3
  291. package/dist/cli/commands/priority.js.map +1 -1
  292. package/dist/cli/commands/probe.d.ts +7 -0
  293. package/dist/cli/commands/probe.d.ts.map +1 -1
  294. package/dist/cli/commands/probe.js +234 -52
  295. package/dist/cli/commands/probe.js.map +1 -1
  296. package/dist/cli/commands/recover.d.ts.map +1 -1
  297. package/dist/cli/commands/recover.js +17 -6
  298. package/dist/cli/commands/recover.js.map +1 -1
  299. package/dist/cli/commands/regime.d.ts +1 -1
  300. package/dist/cli/commands/regime.d.ts.map +1 -1
  301. package/dist/cli/commands/regime.js +134 -33
  302. package/dist/cli/commands/regime.js.map +1 -1
  303. package/dist/cli/commands/retrieve.d.ts +3 -0
  304. package/dist/cli/commands/retrieve.d.ts.map +1 -0
  305. package/dist/cli/commands/retrieve.js +65 -0
  306. package/dist/cli/commands/retrieve.js.map +1 -0
  307. package/dist/cli/commands/search.d.ts +3 -0
  308. package/dist/cli/commands/search.d.ts.map +1 -0
  309. package/dist/cli/commands/search.js +70 -0
  310. package/dist/cli/commands/search.js.map +1 -0
  311. package/dist/cli/commands/symbolic.d.ts.map +1 -1
  312. package/dist/cli/commands/symbolic.js +112 -21
  313. package/dist/cli/commands/symbolic.js.map +1 -1
  314. package/dist/cli/commands/testplan.d.ts +3 -0
  315. package/dist/cli/commands/testplan.d.ts.map +1 -0
  316. package/dist/cli/commands/testplan.js +131 -0
  317. package/dist/cli/commands/testplan.js.map +1 -0
  318. package/dist/cli/conventions.d.ts +22 -0
  319. package/dist/cli/conventions.d.ts.map +1 -0
  320. package/dist/cli/conventions.js +48 -0
  321. package/dist/cli/conventions.js.map +1 -0
  322. package/dist/cli/euler-guard.d.ts +9 -0
  323. package/dist/cli/euler-guard.d.ts.map +1 -0
  324. package/dist/cli/euler-guard.js +11 -0
  325. package/dist/cli/euler-guard.js.map +1 -0
  326. package/dist/cli/eval-numbers.d.ts +26 -0
  327. package/dist/cli/eval-numbers.d.ts.map +1 -0
  328. package/dist/cli/eval-numbers.js +49 -0
  329. package/dist/cli/eval-numbers.js.map +1 -0
  330. package/dist/cli/expr-print.d.ts +25 -0
  331. package/dist/cli/expr-print.d.ts.map +1 -0
  332. package/dist/cli/expr-print.js +123 -0
  333. package/dist/cli/expr-print.js.map +1 -0
  334. package/dist/cli/graphs.d.ts +26 -0
  335. package/dist/cli/graphs.d.ts.map +1 -1
  336. package/dist/cli/graphs.js +19 -0
  337. package/dist/cli/graphs.js.map +1 -1
  338. package/dist/cli/main.d.ts +4 -10
  339. package/dist/cli/main.d.ts.map +1 -1
  340. package/dist/cli/main.js +370 -167
  341. package/dist/cli/main.js.map +1 -1
  342. package/dist/cli/map-evidence.d.ts +47 -0
  343. package/dist/cli/map-evidence.d.ts.map +1 -0
  344. package/dist/cli/map-evidence.js +53 -0
  345. package/dist/cli/map-evidence.js.map +1 -0
  346. package/dist/cli/output.d.ts +21 -1
  347. package/dist/cli/output.d.ts.map +1 -1
  348. package/dist/cli/output.js +5 -1
  349. package/dist/cli/output.js.map +1 -1
  350. package/dist/{composition → cli}/poster-source.d.ts +3 -2
  351. package/dist/cli/poster-source.d.ts.map +1 -0
  352. package/dist/{composition → cli}/poster-source.js +2 -1
  353. package/dist/cli/poster-source.js.map +1 -0
  354. package/dist/cli/record-reach.d.ts +44 -0
  355. package/dist/cli/record-reach.d.ts.map +1 -0
  356. package/dist/cli/record-reach.js +228 -0
  357. package/dist/cli/record-reach.js.map +1 -0
  358. package/dist/cli/record-tables.d.ts +38 -0
  359. package/dist/cli/record-tables.d.ts.map +1 -0
  360. package/dist/cli/record-tables.js +110 -0
  361. package/dist/cli/record-tables.js.map +1 -0
  362. package/dist/cli/record.d.ts +141 -0
  363. package/dist/cli/record.d.ts.map +1 -0
  364. package/dist/cli/record.js +612 -0
  365. package/dist/cli/record.js.map +1 -0
  366. package/dist/cli/search-index.d.ts +56 -0
  367. package/dist/cli/search-index.d.ts.map +1 -0
  368. package/dist/cli/search-index.js +190 -0
  369. package/dist/cli/search-index.js.map +1 -0
  370. package/dist/cli/statuses.d.ts +25 -0
  371. package/dist/cli/statuses.d.ts.map +1 -0
  372. package/dist/cli/statuses.js +276 -0
  373. package/dist/cli/statuses.js.map +1 -0
  374. package/dist/cli/version.d.ts +8 -0
  375. package/dist/cli/version.d.ts.map +1 -1
  376. package/dist/cli/version.js +32 -1
  377. package/dist/cli/version.js.map +1 -1
  378. package/dist/cli-api.d.ts +33 -15
  379. package/dist/cli-api.d.ts.map +1 -1
  380. package/dist/cli-api.js +31 -11
  381. package/dist/cli-api.js.map +1 -1
  382. package/dist/composition/bridge-analysis.d.ts.map +1 -1
  383. package/dist/composition/bridge-analysis.js +2 -1
  384. package/dist/composition/bridge-analysis.js.map +1 -1
  385. package/dist/composition/canonical-compare.d.ts +36 -11
  386. package/dist/composition/canonical-compare.d.ts.map +1 -1
  387. package/dist/composition/canonical-compare.js +424 -56
  388. package/dist/composition/canonical-compare.js.map +1 -1
  389. package/dist/composition/canonical-graph.d.ts +2 -2
  390. package/dist/composition/canonical-graph.js +3 -3
  391. package/dist/composition/canonical-graph.js.map +1 -1
  392. package/dist/composition/canonical-prefactors.d.ts +24 -1
  393. package/dist/composition/canonical-prefactors.d.ts.map +1 -1
  394. package/dist/composition/canonical-prefactors.js +97 -1
  395. package/dist/composition/canonical-prefactors.js.map +1 -1
  396. package/dist/composition/compose-symbolic.js +1 -1
  397. package/dist/composition/compose-symbolic.js.map +1 -1
  398. package/dist/composition/compose.d.ts.map +1 -1
  399. package/dist/composition/compose.js +17 -9
  400. package/dist/composition/compose.js.map +1 -1
  401. package/dist/composition/composition-recovery.d.ts +47 -0
  402. package/dist/composition/composition-recovery.d.ts.map +1 -0
  403. package/dist/composition/composition-recovery.js +77 -0
  404. package/dist/composition/composition-recovery.js.map +1 -0
  405. package/dist/composition/consequence.d.ts +39 -0
  406. package/dist/composition/consequence.d.ts.map +1 -1
  407. package/dist/composition/consequence.js +37 -0
  408. package/dist/composition/consequence.js.map +1 -1
  409. package/dist/composition/discovery.d.ts +20 -0
  410. package/dist/composition/discovery.d.ts.map +1 -1
  411. package/dist/composition/discovery.js +27 -5
  412. package/dist/composition/discovery.js.map +1 -1
  413. package/dist/composition/edge.d.ts +1 -1
  414. package/dist/composition/edge.d.ts.map +1 -1
  415. package/dist/composition/edge.js.map +1 -1
  416. package/dist/composition/edges/_catalog-helpers.d.ts +4 -0
  417. package/dist/composition/edges/_catalog-helpers.d.ts.map +1 -1
  418. package/dist/composition/edges/_catalog-helpers.js +15 -0
  419. package/dist/composition/edges/_catalog-helpers.js.map +1 -1
  420. package/dist/composition/edges/calibration.d.ts.map +1 -1
  421. package/dist/composition/edges/calibration.js +57 -0
  422. package/dist/composition/edges/calibration.js.map +1 -1
  423. package/dist/composition/edges/catalog-fields.d.ts.map +1 -1
  424. package/dist/composition/edges/catalog-fields.js +2 -1
  425. package/dist/composition/edges/catalog-fields.js.map +1 -1
  426. package/dist/composition/edges/catalog-gravitation-cosmology.d.ts.map +1 -1
  427. package/dist/composition/edges/catalog-gravitation-cosmology.js +2 -1
  428. package/dist/composition/edges/catalog-gravitation-cosmology.js.map +1 -1
  429. package/dist/composition/edges/catalog-quantum.d.ts.map +1 -1
  430. package/dist/composition/edges/catalog-quantum.js +26 -0
  431. package/dist/composition/edges/catalog-quantum.js.map +1 -1
  432. package/dist/composition/edges/catalog-tranche.d.ts.map +1 -1
  433. package/dist/composition/edges/catalog-tranche.js +2 -1
  434. package/dist/composition/edges/catalog-tranche.js.map +1 -1
  435. package/dist/composition/expr-eval.d.ts.map +1 -1
  436. package/dist/composition/expr-eval.js +4 -1
  437. package/dist/composition/expr-eval.js.map +1 -1
  438. package/dist/composition/expr-simplify.js +1 -1
  439. package/dist/composition/expr-simplify.js.map +1 -1
  440. package/dist/composition/frontier-account.d.ts +78 -0
  441. package/dist/composition/frontier-account.d.ts.map +1 -0
  442. package/dist/composition/frontier-account.js +127 -0
  443. package/dist/composition/frontier-account.js.map +1 -0
  444. package/dist/composition/graph-viz.d.ts +7 -22
  445. package/dist/composition/graph-viz.d.ts.map +1 -1
  446. package/dist/composition/graph-viz.js +4 -27
  447. package/dist/composition/graph-viz.js.map +1 -1
  448. package/dist/composition/grounding.d.ts +49 -0
  449. package/dist/composition/grounding.d.ts.map +1 -1
  450. package/dist/composition/grounding.js +38 -0
  451. package/dist/composition/grounding.js.map +1 -1
  452. package/dist/composition/index.d.ts +0 -2
  453. package/dist/composition/index.d.ts.map +1 -1
  454. package/dist/composition/index.js +1 -1
  455. package/dist/composition/index.js.map +1 -1
  456. package/dist/composition/probe/expression-gaps.d.ts +27 -0
  457. package/dist/composition/probe/expression-gaps.d.ts.map +1 -0
  458. package/dist/composition/probe/expression-gaps.js +47 -0
  459. package/dist/composition/probe/expression-gaps.js.map +1 -0
  460. package/dist/composition/probe/frontier.d.ts +2 -1
  461. package/dist/composition/probe/frontier.d.ts.map +1 -1
  462. package/dist/composition/probe/frontier.js +3 -2
  463. package/dist/composition/probe/frontier.js.map +1 -1
  464. package/dist/composition/probe/index.d.ts +4 -1
  465. package/dist/composition/probe/index.d.ts.map +1 -1
  466. package/dist/composition/probe/index.js +3 -1
  467. package/dist/composition/probe/index.js.map +1 -1
  468. package/dist/composition/probe/pipeline.d.ts +2 -0
  469. package/dist/composition/probe/pipeline.d.ts.map +1 -1
  470. package/dist/composition/probe/pipeline.js +6 -2
  471. package/dist/composition/probe/pipeline.js.map +1 -1
  472. package/dist/composition/probe/problem.d.ts +7 -0
  473. package/dist/composition/probe/problem.d.ts.map +1 -1
  474. package/dist/composition/probe/problem.js +15 -5
  475. package/dist/composition/probe/problem.js.map +1 -1
  476. package/dist/composition/probe/search-budget.d.ts.map +1 -1
  477. package/dist/composition/probe/search-budget.js +6 -2
  478. package/dist/composition/probe/search-budget.js.map +1 -1
  479. package/dist/composition/probe/study.d.ts +340 -0
  480. package/dist/composition/probe/study.d.ts.map +1 -0
  481. package/dist/composition/probe/study.js +1519 -0
  482. package/dist/composition/probe/study.js.map +1 -0
  483. package/dist/composition/proposed-bridges.js +1 -1
  484. package/dist/composition/proposed-bridges.js.map +1 -1
  485. package/dist/composition/quantities.d.ts +4 -16
  486. package/dist/composition/quantities.d.ts.map +1 -1
  487. package/dist/composition/quantities.js +4 -16
  488. package/dist/composition/quantities.js.map +1 -1
  489. package/dist/composition/retrodiction.d.ts.map +1 -1
  490. package/dist/composition/retrodiction.js +6 -2
  491. package/dist/composition/retrodiction.js.map +1 -1
  492. package/dist/composition/uncertainty.d.ts +1 -1
  493. package/dist/composition/uncertainty.d.ts.map +1 -1
  494. package/dist/composition/user-equation.d.ts +87 -14
  495. package/dist/composition/user-equation.d.ts.map +1 -1
  496. package/dist/composition/user-equation.js +266 -59
  497. package/dist/composition/user-equation.js.map +1 -1
  498. package/dist/core/constants.d.ts +9 -4
  499. package/dist/core/constants.d.ts.map +1 -1
  500. package/dist/core/constants.js +9 -4
  501. package/dist/core/constants.js.map +1 -1
  502. package/dist/core/types.d.ts +1 -1
  503. package/dist/core/types.d.ts.map +1 -1
  504. package/dist/core/types.js +2 -1
  505. package/dist/core/types.js.map +1 -1
  506. package/dist/dimensional/curvature.d.ts +7 -56
  507. package/dist/dimensional/curvature.d.ts.map +1 -1
  508. package/dist/dimensional/curvature.js +7 -76
  509. package/dist/dimensional/curvature.js.map +1 -1
  510. package/dist/dimensional/dimension-spec.d.ts +7 -1
  511. package/dist/dimensional/dimension-spec.d.ts.map +1 -1
  512. package/dist/dimensional/dimension-spec.js +131 -3
  513. package/dist/dimensional/dimension-spec.js.map +1 -1
  514. package/dist/dimensional/formula-names.d.ts +30 -0
  515. package/dist/dimensional/formula-names.d.ts.map +1 -0
  516. package/dist/dimensional/formula-names.js +37 -0
  517. package/dist/dimensional/formula-names.js.map +1 -0
  518. package/dist/dimensional/natural-units.d.ts +33 -0
  519. package/dist/dimensional/natural-units.d.ts.map +1 -0
  520. package/dist/dimensional/natural-units.js +58 -0
  521. package/dist/dimensional/natural-units.js.map +1 -0
  522. package/dist/{composition → dimensional}/symbolic-constants.d.ts +21 -2
  523. package/dist/dimensional/symbolic-constants.d.ts.map +1 -0
  524. package/dist/dimensional/symbolic-constants.js +116 -0
  525. package/dist/dimensional/symbolic-constants.js.map +1 -0
  526. package/dist/dimensional/unit-convention.d.ts +30 -0
  527. package/dist/dimensional/unit-convention.d.ts.map +1 -0
  528. package/dist/dimensional/unit-convention.js +60 -0
  529. package/dist/dimensional/unit-convention.js.map +1 -0
  530. package/dist/dimensional/units.d.ts +43 -0
  531. package/dist/dimensional/units.d.ts.map +1 -0
  532. package/dist/dimensional/units.js +197 -0
  533. package/dist/dimensional/units.js.map +1 -0
  534. package/dist/index.d.ts +8 -4
  535. package/dist/index.d.ts.map +1 -1
  536. package/dist/index.js +7 -3
  537. package/dist/index.js.map +1 -1
  538. package/dist/numerical/bianchi-residual.d.ts +55 -0
  539. package/dist/numerical/bianchi-residual.d.ts.map +1 -0
  540. package/dist/numerical/bianchi-residual.js +79 -0
  541. package/dist/numerical/bianchi-residual.js.map +1 -0
  542. package/dist/numerical/binding-value.d.ts +67 -0
  543. package/dist/numerical/binding-value.d.ts.map +1 -0
  544. package/dist/numerical/binding-value.js +347 -0
  545. package/dist/numerical/binding-value.js.map +1 -0
  546. package/dist/numerical/connection-lowering-helpers.d.ts.map +1 -1
  547. package/dist/numerical/connection-lowering-helpers.js +13 -26
  548. package/dist/numerical/connection-lowering-helpers.js.map +1 -1
  549. package/dist/numerical/curvature-lowering-helpers.d.ts.map +1 -1
  550. package/dist/numerical/curvature-lowering-helpers.js +9 -0
  551. package/dist/numerical/curvature-lowering-helpers.js.map +1 -1
  552. package/dist/numerical/float64-engine.d.ts.map +1 -1
  553. package/dist/numerical/float64-engine.js +23 -16
  554. package/dist/numerical/float64-engine.js.map +1 -1
  555. package/dist/numerical/formula-dimension.d.ts +7 -0
  556. package/dist/numerical/formula-dimension.d.ts.map +1 -1
  557. package/dist/numerical/formula-dimension.js +23 -6
  558. package/dist/numerical/formula-dimension.js.map +1 -1
  559. package/dist/numerical/formula-mathts.d.ts.map +1 -1
  560. package/dist/numerical/formula-mathts.js +68 -6
  561. package/dist/numerical/formula-mathts.js.map +1 -1
  562. package/dist/numerical/formula.d.ts +27 -0
  563. package/dist/numerical/formula.d.ts.map +1 -1
  564. package/dist/numerical/formula.js +68 -6
  565. package/dist/numerical/formula.js.map +1 -1
  566. package/dist/numerical/spacetime-metrics.d.ts +243 -0
  567. package/dist/numerical/spacetime-metrics.d.ts.map +1 -0
  568. package/dist/numerical/spacetime-metrics.js +1056 -0
  569. package/dist/numerical/spacetime-metrics.js.map +1 -0
  570. package/dist/relations/composition-table.d.ts +61 -0
  571. package/dist/relations/composition-table.d.ts.map +1 -0
  572. package/dist/relations/composition-table.js +140 -0
  573. package/dist/relations/composition-table.js.map +1 -0
  574. package/dist/relations/conventions.d.ts +63 -0
  575. package/dist/relations/conventions.d.ts.map +1 -0
  576. package/dist/relations/conventions.js +93 -0
  577. package/dist/relations/conventions.js.map +1 -0
  578. package/dist/relations/regime.d.ts +159 -0
  579. package/dist/relations/regime.d.ts.map +1 -0
  580. package/dist/relations/regime.js +304 -0
  581. package/dist/relations/regime.js.map +1 -0
  582. package/dist/relations/types.d.ts +259 -0
  583. package/dist/relations/types.d.ts.map +1 -0
  584. package/dist/relations/types.js +37 -0
  585. package/dist/relations/types.js.map +1 -0
  586. package/package.json +166 -163
  587. package/dist/composition/poster-source.d.ts.map +0 -1
  588. package/dist/composition/poster-source.js.map +0 -1
  589. package/dist/composition/symbolic-constants.d.ts.map +0 -1
  590. package/dist/composition/symbolic-constants.js +0 -65
  591. package/dist/composition/symbolic-constants.js.map +0 -1
@@ -0,0 +1,1014 @@
1
+ /**
2
+ * `upt map --route=FROM,TO` and `upt map --family=NAME` — focused maps of the
3
+ * ATLAS (models and the bridges between them), as opposed to the rest of `map`,
4
+ * which draws the equation graph by shared quantities. The two graphs are
5
+ * different facts: a shared quantity is connectivity, a bridge is a recorded
6
+ * transformation between models, and neither is drawn as the other.
7
+ *
8
+ * Every view states its denominator (how many of the atlas's models and
9
+ * bridges it shows) and its source.
10
+ *
11
+ * ## The join to the equation graph
12
+ *
13
+ * A model is joined to a canonical equation ONLY through the model's own
14
+ * `canonicalRefs` field. Nothing is inferred from a shared dimension, a shared
15
+ * quantity or a similar name, and a model with no recorded reference is shown
16
+ * as having none recorded — an absent link, not a finding that none exists.
17
+ *
18
+ * ## Evidence, and the witness results it is derived from
19
+ *
20
+ * Which witnesses pass is decided by runs the view may or may not observe.
21
+ * Every tag `deriveEvidence` emits is monotone in the passing set except
22
+ * `proposed`, which is antitone, so deriving under the witnesses KNOWN to pass
23
+ * and under those plus every witness with NO observed result brackets every
24
+ * possible result: a tag in both is derived whatever the unobserved results
25
+ * are, a tag in neither cannot be, and a tag in exactly one is undecided here.
26
+ * An undecided bridge is counted apart from one that does not match.
27
+ *
28
+ * With no results source every witness is unobserved. `--stored` observes the
29
+ * committed artifact (`data/atlas/witness-results.json`); `--run` observes the
30
+ * in-process registered witnesses, run by this invocation. Only a `'checked'`
31
+ * row is a pass. A `'refuted'` or `'unresolved'` row is observed and not
32
+ * passing, and the two are counted apart; a witness with no row stays
33
+ * unobserved, whatever its name.
34
+ */
35
+ import { execFileSync } from 'node:child_process';
36
+ import { readFileSync } from 'node:fs';
37
+ import { join } from 'node:path';
38
+ import { fileURLToPath } from 'node:url';
39
+ import { CliError } from '../errors.js';
40
+ import { showInequality } from './regime.js';
41
+ import { claimReport, explainsRefusal, missingForComposite, routeClaim, selectRoute, transportReport, } from './_atlas-route.js';
42
+ export const ATLAS_SOURCE = 'atlas (ATLAS_FAMILIES, src/atlas/families.ts)';
43
+ export const LINK_SOURCE = 'AtlasModel.canonicalRefs';
44
+ const NO_LINK = 'no canonical equation recorded in its canonicalRefs (an absent link, not a finding that none exists; ' +
45
+ 'nothing is inferred from shared quantities or names)';
46
+ const EPISTEMICS = 'bridges are recorded transformations between models; the equation links are only those a model records. ' +
47
+ 'A route existing is not a warrant: the composed claim is.';
48
+ export const STORED_RESULTS_PATH = 'data/atlas/witness-results.json';
49
+ const ARTIFACT_CARRIES = 'the artifact records no commit or date of its own';
50
+ /** The repository root, when this module runs from a checkout (src/ or dist/). */
51
+ function repoRoot() {
52
+ return fileURLToPath(new URL('../../../', import.meta.url));
53
+ }
54
+ /** The absolute path `--stored` reads, which an experiment record hashes as an input. */
55
+ export function storedResultsFile() {
56
+ return join(repoRoot(), STORED_RESULTS_PATH);
57
+ }
58
+ function git(args, cwd) {
59
+ try {
60
+ return execFileSync('git', args, { cwd, encoding: 'utf8', stdio: ['ignore', 'pipe', 'ignore'], timeout: 5000 }).trim();
61
+ }
62
+ catch {
63
+ return null;
64
+ }
65
+ }
66
+ /**
67
+ * The committed witness-results artifact. It is a repository file, not shipped
68
+ * in the package, so its absence is refused rather than read as "no results":
69
+ * an empty source would render every tag exactly as the default view does,
70
+ * under a label claiming it had been observed.
71
+ */
72
+ export function loadStoredResults(command = 'upt map') {
73
+ const root = repoRoot();
74
+ const file = storedResultsFile();
75
+ let raw;
76
+ try {
77
+ raw = readFileSync(file, 'utf8');
78
+ }
79
+ catch {
80
+ throw new CliError(`${command}: --stored reads ${STORED_RESULTS_PATH}, a repository artifact not shipped in the package, and it is not ` +
81
+ 'present here; --run executes the in-process registered witnesses instead');
82
+ }
83
+ const artifact = JSON.parse(raw);
84
+ if (artifact.schemaVersion !== '0' || !Array.isArray(artifact.results)) {
85
+ throw new CliError(`${command}: ${STORED_RESULTS_PATH} has schemaVersion '${String(artifact.schemaVersion)}'; this command reads '0'`);
86
+ }
87
+ const log = git(['log', '-1', '--format=%H %cI', '--', STORED_RESULTS_PATH], root);
88
+ const [hash, date] = log === null || log === '' ? [] : log.split(' ');
89
+ const lastCommit = hash !== undefined && date !== undefined ? { hash, date } : null;
90
+ const status = lastCommit === null ? null : git(['status', '--porcelain', '--', STORED_RESULTS_PATH], root);
91
+ return {
92
+ mode: 'stored',
93
+ provenance: {
94
+ path: STORED_RESULTS_PATH,
95
+ schemaVersion: artifact.schemaVersion,
96
+ carries: ARTIFACT_CARRIES,
97
+ lastCommit,
98
+ modifiedSinceCommit: status === null ? null : status !== '',
99
+ },
100
+ rows: artifact.results.map((r) => ({
101
+ recordId: r.recordId,
102
+ witnessId: r.witnessId,
103
+ status: r.status,
104
+ ...(r.reason === undefined ? {} : { reason: r.reason }),
105
+ })),
106
+ };
107
+ }
108
+ /**
109
+ * Run the in-process registered witnesses of `bridgeIds`, now, and those of
110
+ * the norm transports the bridges declare (registered under the transport id).
111
+ */
112
+ export async function runResults(api, bridgeIds) {
113
+ const transportIds = api.ATLAS_FAMILIES.flatMap((f) => f.bridges)
114
+ .filter((b) => bridgeIds.has(b.id))
115
+ .flatMap((b) => (b.normTransports ?? []).map((nt) => nt.id));
116
+ const ids = new Set([...bridgeIds, ...transportIds]);
117
+ const registered = api.WITNESS_REGISTRY.filter((e) => ids.has(e.recordId));
118
+ const artifact = await api.runWitnessRegistry(registered);
119
+ return {
120
+ mode: 'run',
121
+ provenance: { ran: 'runWitnessRegistry, in-process, by this invocation', registered: registered.length },
122
+ rows: artifact.results.map((r) => ({
123
+ recordId: r.recordId,
124
+ witnessId: r.witnessId,
125
+ status: r.status,
126
+ ...(r.reason === undefined ? {} : { reason: r.reason }),
127
+ })),
128
+ };
129
+ }
130
+ function outcomes(b, results) {
131
+ const rows = results.rows.filter((r) => r.recordId === b.id);
132
+ const o = { source: results.mode, checked: [], refuted: [], unresolved: [], notObserved: [] };
133
+ for (const w of b.witnesses) {
134
+ const row = rows.find((r) => r.witnessId === w.id);
135
+ if (row === undefined)
136
+ o.notObserved.push(w.id);
137
+ else if (row.status === 'checked')
138
+ o.checked.push(w.id);
139
+ else if (row.status === 'refuted')
140
+ o.refuted.push(w.id);
141
+ else
142
+ o.unresolved.push({ id: w.id, reason: row.reason ?? null });
143
+ }
144
+ return o;
145
+ }
146
+ function tally(results, bridges) {
147
+ if (results === null)
148
+ return undefined;
149
+ const seen = new Map(bridges.map((b) => [b.id, b.evidence.results]));
150
+ const sum = (f) => [...seen.values()].reduce((n, o) => n + f(o), 0);
151
+ return {
152
+ mode: results.mode,
153
+ provenance: results.provenance,
154
+ witnesses: {
155
+ checked: sum((o) => o.checked.length),
156
+ refuted: sum((o) => o.refuted.length),
157
+ unresolved: sum((o) => o.unresolved.length),
158
+ notObserved: sum((o) => o.notObserved.length),
159
+ },
160
+ };
161
+ }
162
+ function allModels(api) {
163
+ return new Map(api.ATLAS_FAMILIES.flatMap((f) => f.models.map((m) => [m.id, m])));
164
+ }
165
+ function totals(api) {
166
+ return {
167
+ families: api.ATLAS_FAMILIES.length,
168
+ models: api.ATLAS_FAMILIES.reduce((n, f) => n + f.models.length, 0),
169
+ bridges: api.ATLAS_FAMILIES.reduce((n, f) => n + f.bridges.length, 0),
170
+ };
171
+ }
172
+ function modelView(api, m) {
173
+ return {
174
+ id: m.id,
175
+ family: m.family,
176
+ dynamics: m.dynamics,
177
+ equationLinks: m.canonicalRefs.map((ref) => {
178
+ const eq = api.CANONICAL_EQUATIONS.find((e) => e.id === ref);
179
+ const edge = api.CANONICAL_GRAPH.find((e) => e.id === ref);
180
+ return {
181
+ id: ref,
182
+ name: eq?.name ?? null,
183
+ formula: eq?.formula_latex ?? null,
184
+ graphEdge: edge === undefined ? null : { sources: edge.sources.map((q) => q.name), target: edge.target.name },
185
+ };
186
+ }),
187
+ };
188
+ }
189
+ function evidenceView(api, b, results) {
190
+ const o = results === null ? null : outcomes(b, results);
191
+ const passing = o === null ? api.NO_PASSING_WITNESSES : new Set(o.checked);
192
+ const open = o === null ? b.witnesses.map((w) => w.id) : o.notObserved;
193
+ const low = api.deriveEvidence(b, passing);
194
+ const high = api.deriveEvidence(b, new Set([...passing, ...open]));
195
+ const tags = [...new Set([...low, ...high])].sort();
196
+ return {
197
+ derived: tags.filter((t) => low.has(t) && high.has(t)),
198
+ undecided: tags.filter((t) => low.has(t) !== high.has(t)),
199
+ formalRef: b.formalRef === undefined
200
+ ? null
201
+ : {
202
+ system: b.formalRef.system,
203
+ fidelity: b.formalRef.fidelity,
204
+ kind: b.formalRef.kind,
205
+ url: b.formalRef.url,
206
+ },
207
+ witnesses: b.witnesses.length,
208
+ ...(o === null ? {} : { results: o }),
209
+ };
210
+ }
211
+ function bridgeView(api, b, family, models, results = null) {
212
+ const at = (id) => ({ id, family: models.get(id)?.family ?? 'UNKNOWN' });
213
+ return {
214
+ id: b.id,
215
+ family,
216
+ relation: b.relation,
217
+ premises: b.premises.map(at),
218
+ conclusion: at(b.conclusion),
219
+ transformation: b.transformation,
220
+ assumptions: [...b.sideConditions],
221
+ regime: { inequalities: b.regime.inequalities.map(showInequality), vacuous: b.regime.inequalities.length === 0 },
222
+ bound: b.bound === undefined
223
+ ? null
224
+ : { K: b.bound.K, delta: b.bound.delta, norm: b.bound.norm, horizon: b.bound.horizon },
225
+ evidence: evidenceView(api, b, results),
226
+ };
227
+ }
228
+ function familyOfBridge(api, id) {
229
+ return api.ATLAS_FAMILIES.find((f) => f.bridges.some((b) => b.id === id))?.family ?? 'UNKNOWN';
230
+ }
231
+ function linkSummary(models) {
232
+ const withLink = models.filter((m) => m.equationLinks.length > 0).length;
233
+ return { source: LINK_SOURCE, withLink, withoutLink: models.length - withLink, of: models.length };
234
+ }
235
+ const SELECTION = 'the shortest route by bridge count (the one `upt path` reports); other routes between the endpoints, if any, are not shown';
236
+ /** Parse a FROM,TO route flag into atlas model ids. */
237
+ export function parseRoute(raw) {
238
+ const parts = raw.split(',').map((s) => s.trim());
239
+ if (parts.length !== 2 || parts.some((p) => p === '')) {
240
+ throw new CliError(`upt map: --route='${raw}' must be FROM,TO (two model ids), e.g. --route=model-pendulum,model-lc`);
241
+ }
242
+ return parts;
243
+ }
244
+ function checkEndpoints(models, from, to) {
245
+ for (const id of [from, to]) {
246
+ if (!models.has(id)) {
247
+ throw new CliError(`upt map: '${id}' is not a model of any atlas family (run \`upt map --family=NAME\` to list one family's models)`);
248
+ }
249
+ }
250
+ }
251
+ /** The models a route visits, in route order: an exact equivalence may be walked conclusion → premise. */
252
+ function routeModelIds(from, bridges) {
253
+ const ids = [from];
254
+ for (const b of bridges) {
255
+ const at = ids[ids.length - 1];
256
+ ids.push(b.conclusion === at && b.relation === 'exact-equivalence' ? b.premises[0] : b.conclusion);
257
+ }
258
+ return ids;
259
+ }
260
+ const COMPOSITE_RULE = 'derived from the parts (every step and every transport applied): a positive tag survives only if every part ' +
261
+ "carries it, contradicted if any part does; a transport contributes its basis when its witness checks, else 'proposed' " +
262
+ '(docs/planning/ADR-transported-norm-composition.md §4)';
263
+ function transportResult(nt, results) {
264
+ const row = results?.rows.find((r) => r.recordId === nt.id && r.witnessId === nt.witness.id);
265
+ return row === undefined ? 'no result' : row.status;
266
+ }
267
+ /** The composite evidence of a bound route, bracketed over the unobserved witness results like one bridge's. */
268
+ function compositeEvidence(api, bridges, transports, results) {
269
+ const lows = [];
270
+ const highs = [];
271
+ for (const b of bridges) {
272
+ const o = results === null ? null : outcomes(b, results);
273
+ const passing = o === null ? api.NO_PASSING_WITNESSES : new Set(o.checked);
274
+ const open = o === null ? b.witnesses.map((w) => w.id) : o.notObserved;
275
+ lows.push(api.deriveEvidence(b, passing));
276
+ highs.push(api.deriveEvidence(b, new Set([...passing, ...open])));
277
+ }
278
+ for (const { transport } of transports) {
279
+ const r = transportResult(transport, results);
280
+ lows.push(new Set([r === 'checked' ? transport.basis : 'proposed']));
281
+ highs.push(new Set([r === 'checked' || r === 'no result' ? transport.basis : 'proposed']));
282
+ }
283
+ const low = api.deriveCompositeEvidence(lows);
284
+ const high = api.deriveCompositeEvidence(highs);
285
+ const tags = [...new Set([...low, ...high])].sort();
286
+ return {
287
+ derived: tags.filter((t) => low.has(t) && high.has(t)),
288
+ undecided: tags.filter((t) => low.has(t) !== high.has(t)),
289
+ rule: COMPOSITE_RULE,
290
+ };
291
+ }
292
+ /** The composition table folded along a non-empty route, and what the route supports. */
293
+ function composeSteps(api, bridges, results) {
294
+ const running = [];
295
+ let breaksAt = null;
296
+ let rel = bridges[0].relation;
297
+ running.push({ after: bridges[0].id, relation: rel });
298
+ for (let i = 1; i < bridges.length; i++) {
299
+ if (rel === null || rel === 'no-composite-claim')
300
+ rel = null;
301
+ else {
302
+ rel = api.composeRelation(rel, bridges[i].relation);
303
+ if (rel === 'no-composite-claim')
304
+ breaksAt = i;
305
+ }
306
+ running.push({ after: bridges[i].id, relation: rel });
307
+ }
308
+ const claim = routeClaim(api, bridges);
309
+ const missing = explainsRefusal(claim) ? missingForComposite(api, bridges) : [];
310
+ const applied = claim.kind === 'bound' ? (claim.transports ?? []) : [];
311
+ const transports = applied.map((a) => ({ ...transportReport(a), result: transportResult(a.transport, results) }));
312
+ const evidence = claim.kind === 'bound' ? compositeEvidence(api, bridges, applied, results) : null;
313
+ return { running, breaksAt, claim: claimReport(claim), missing, transports, evidence };
314
+ }
315
+ /** Build the focused atlas route view for two model ids. */
316
+ export function buildRouteView(api, from, to, results = null) {
317
+ const models = allModels(api);
318
+ checkEndpoints(models, from, to);
319
+ const { bridges } = selectRoute(api, from, to, 'map');
320
+ const t = totals(api);
321
+ const steps = bridges === null ? null : bridges.map((b) => bridgeView(api, b, familyOfBridge(api, b.id), models, results));
322
+ const routeModels = bridges === null ? [from, to] : routeModelIds(from, bridges);
323
+ const mv = routeModels.map((id) => modelView(api, models.get(id)));
324
+ const { running, breaksAt, claim, missing, transports, evidence } = bridges === null || bridges.length === 0
325
+ ? { running: [], breaksAt: null, claim: null, missing: [], transports: [], evidence: null }
326
+ : composeSteps(api, bridges, results);
327
+ const witnessResults = tally(results, steps ?? []);
328
+ return {
329
+ view: 'route',
330
+ from,
331
+ to,
332
+ source: ATLAS_SOURCE,
333
+ steps,
334
+ models: mv,
335
+ denominator: {
336
+ bridges: { shown: steps?.length ?? 0, of: t.bridges },
337
+ models: { shown: mv.length, of: t.models },
338
+ },
339
+ selection: SELECTION,
340
+ composition: { running, breaksAt, claim, missing, transports, evidence },
341
+ equationLinks: linkSummary(mv),
342
+ ...(witnessResults === undefined ? {} : { witnessResults }),
343
+ epistemics: EPISTEMICS,
344
+ };
345
+ }
346
+ // ── all routes ─────────────────────────────────────────────────────────────
347
+ export const DEFAULT_MAX_ROUTES = 20;
348
+ export const MAX_ROUTES_CEILING = 1000;
349
+ const ROUTES_SELECTION = 'every simple route (no model visited twice), ordered by bridge count and then atlas order; the same traversal as ' +
350
+ '`upt path`: an exact equivalence both ways, every other relation forward only, multi-premise bridges not followed';
351
+ /** Build the simple-route atlas view between two model ids up to the requested limit. */
352
+ export function buildRoutesView(api, from, to, limit, results = null) {
353
+ const models = allModels(api);
354
+ checkEndpoints(models, from, to);
355
+ const found = api.enumerateAtlasRoutes(from, to, limit);
356
+ const reported = selectRoute(api, from, to, 'map').bridges;
357
+ const reportedKey = reported === null ? null : reported.map((b) => b.id).join(' ');
358
+ const routes = found.routes
359
+ .filter((r) => r.length > 0)
360
+ .map((r) => ({
361
+ bridges: r.map((b) => b.id),
362
+ models: routeModelIds(from, r),
363
+ composition: composeSteps(api, r, results),
364
+ reported: r.map((b) => b.id).join(' ') === reportedKey,
365
+ }));
366
+ const used = new Set(routes.flatMap((r) => r.bridges));
367
+ const bridges = api.ATLAS_FAMILIES.flatMap((f) => f.bridges.filter((b) => used.has(b.id)).map((b) => bridgeView(api, b, f.family, models, results)));
368
+ const visited = new Set(routes.flatMap((r) => r.models));
369
+ const mv = [...models.values()].filter((m) => visited.has(m.id) || (routes.length === 0 && (m.id === from || m.id === to))).map((m) => modelView(api, m));
370
+ const noClaim = {};
371
+ for (const r of routes) {
372
+ const c = r.composition.claim;
373
+ if (c.kind === 'no-claim')
374
+ noClaim[c.reason] = (noClaim[c.reason] ?? 0) + 1;
375
+ }
376
+ const t = totals(api);
377
+ const witnessResults = tally(results, bridges);
378
+ return {
379
+ view: 'routes',
380
+ from,
381
+ to,
382
+ source: ATLAS_SOURCE,
383
+ routes,
384
+ bridges,
385
+ models: mv,
386
+ count: {
387
+ shown: routes.length,
388
+ limit,
389
+ exhausted: found.exhausted,
390
+ completeThrough: found.completeThrough,
391
+ stoppedBy: found.stoppedBy,
392
+ },
393
+ claims: { bound: routes.filter((r) => r.composition.claim.kind === 'bound').length, noClaim },
394
+ denominator: { bridges: { shown: bridges.length, of: t.bridges }, models: { shown: mv.length, of: t.models } },
395
+ selection: ROUTES_SELECTION,
396
+ equationLinks: linkSummary(mv),
397
+ ...(witnessResults === undefined ? {} : { witnessResults }),
398
+ epistemics: EPISTEMICS,
399
+ };
400
+ }
401
+ const OBSERVABLE_MATCH = "a case-insensitive whole-word text match against each bridge's recorded `preserves` and `doesNotPreserve` strings " +
402
+ 'and the observable names of its declared bound translations; nothing is inferred from dimensions, quantities or ' +
403
+ 'the transformation, and a bridge that records nothing about the observable is counted apart from one that records ' +
404
+ 'it as not preserved';
405
+ function wordMatcher(term) {
406
+ const escaped = term.replace(/[.*+?^${}()|[\]\\]/g, '\\$&');
407
+ const re = new RegExp(`(^|[^\\p{L}\\p{N}])${escaped}($|[^\\p{L}\\p{N}])`, 'iu');
408
+ return (text) => re.test(text);
409
+ }
410
+ /** Build an observable-focused atlas view by matching recorded observable text and translations. */
411
+ export function buildObservableView(api, observable, filter, results = null) {
412
+ const term = observable.trim();
413
+ if (term.length < 2)
414
+ throw new CliError(`upt map: --observable='${observable}' must name an observable (two characters or more)`);
415
+ const hit = wordMatcher(term);
416
+ const models = allModels(api);
417
+ const rows = api.ATLAS_FAMILIES.flatMap((f) => f.bridges.map((b) => ({ family: f.family, b })));
418
+ const matched = rows.map(({ family, b }) => ({
419
+ family,
420
+ b,
421
+ preserves: b.preserves.filter(hit),
422
+ translations: api.translationsOf(b.id).map((x) => x.observable).filter(hit),
423
+ doesNot: b.doesNotPreserve.filter(hit),
424
+ }));
425
+ const candidates = matched
426
+ .filter((m) => m.preserves.length > 0 || m.translations.length > 0)
427
+ .map((m) => ({ ...bridgeView(api, m.b, m.family, models, results), preservesMatched: m.preserves, translationsMatched: m.translations }));
428
+ const filtering = filter.relation !== undefined || filter.evidence !== undefined;
429
+ const verdicts = candidates.map((b) => (filtering ? judge(b, filter) : 'kept'));
430
+ const kept = candidates.filter((_, i) => verdicts[i] === 'kept');
431
+ const n = (v) => verdicts.filter((x) => x === v).length;
432
+ const onKept = new Set(kept.flatMap((b) => [...b.premises.map((p) => p.id), b.conclusion.id]));
433
+ const mv = [...models.values()].filter((m) => onKept.has(m.id)).map((m) => modelView(api, m));
434
+ const t = totals(api);
435
+ const witnessResults = tally(results, kept);
436
+ return {
437
+ view: 'observable',
438
+ observable: term,
439
+ source: ATLAS_SOURCE,
440
+ match: OBSERVABLE_MATCH,
441
+ bridges: kept,
442
+ notPreserved: matched
443
+ .filter((m) => m.doesNot.length > 0)
444
+ .map((m) => ({ id: m.b.id, family: m.family, relation: m.b.relation, matched: m.doesNot })),
445
+ models: mv,
446
+ denominator: {
447
+ bridges: {
448
+ preserves: matched.filter((m) => m.preserves.length > 0).length,
449
+ translates: matched.filter((m) => m.translations.length > 0).length,
450
+ doesNotPreserve: matched.filter((m) => m.doesNot.length > 0).length,
451
+ recordsNothing: matched.filter((m) => m.preserves.length + m.translations.length + m.doesNot.length === 0).length,
452
+ of: t.bridges,
453
+ },
454
+ models: { shown: mv.length, of: t.models },
455
+ },
456
+ filter: filtering
457
+ ? {
458
+ ...filter,
459
+ total: candidates.length,
460
+ kept: kept.length,
461
+ droppedNotMatching: n('not-matching'),
462
+ droppedUndecided: n('undecided'),
463
+ ...(results === null ? {} : { results: results.mode }),
464
+ }
465
+ : null,
466
+ equationLinks: linkSummary(mv),
467
+ ...(witnessResults === undefined ? {} : { witnessResults }),
468
+ epistemics: EPISTEMICS,
469
+ };
470
+ }
471
+ /** Every bridge of every family, with its derived evidence: the atlas-wide view of `upt atlas --evidence`. */
472
+ export function buildAtlasEvidenceView(api, results = null) {
473
+ const models = allModels(api);
474
+ const views = api.ATLAS_FAMILIES.flatMap((f) => f.bridges.map((b) => bridgeView(api, b, f.family, models, results)));
475
+ const derived = api.summarizeEvidence(views.map((v) => new Set(v.evidence.derived)));
476
+ const undecided = api.summarizeEvidence(views.map((v) => new Set(v.evidence.undecided)));
477
+ const witnessResults = tally(results, views);
478
+ return {
479
+ view: 'atlas-evidence',
480
+ source: ATLAS_SOURCE,
481
+ denominator: {
482
+ families: api.ATLAS_FAMILIES.length,
483
+ bridges: views.length,
484
+ witnesses: views.reduce((n, v) => n + v.evidence.witnesses, 0),
485
+ },
486
+ bridges: views.map((v) => ({ id: v.id, family: v.family, relation: v.relation, evidence: v.evidence })),
487
+ byTag: api.ALL_EVIDENCE_TAGS.map((tag) => ({ tag, derived: derived.byTag[tag], undecided: undecided.byTag[tag] })),
488
+ normTransports: api.ATLAS_FAMILIES.flatMap((f) => f.bridges).flatMap((b) => (b.normTransports ?? []).map((nt) => ({ id: nt.id, bridge: b.id, witness: nt.witness.id, status: transportResult(nt, results) }))),
489
+ ...(witnessResults === undefined ? {} : { witnessResults }),
490
+ epistemics: 'evidence is derived from each record and the witness results the view observes, never read from a stored tag; ' +
491
+ 'a tag is undecided when unobserved witness results could give it or withhold it. Only a checked witness is a pass.',
492
+ };
493
+ }
494
+ /** The text lines `upt atlas --evidence` prints for the view `v`. */
495
+ export function atlasEvidenceText(v) {
496
+ const d = v.denominator;
497
+ const out = [`\nAtlas evidence — ${d.bridges} bridges across ${d.families} families, ${d.witnesses} recorded witnesses [source: ${v.source}]`];
498
+ const r = resultsLine(v.witnessResults);
499
+ out.push(` ${r ?? 'witness results: none observed (every witness is a name, not a result); --stored reads the committed artifact, --run runs them now'}`);
500
+ out.push(` by tag (bridges; a bridge carries several tags, so the counts do not sum to ${d.bridges}):`);
501
+ for (const t of v.byTag)
502
+ out.push(` ${t.tag.padEnd(22)} derived ${String(t.derived).padStart(2)} · undecided ${String(t.undecided).padStart(2)}`);
503
+ for (const family of [...new Set(v.bridges.map((b) => b.family))]) {
504
+ const bs = v.bridges.filter((b) => b.family === family);
505
+ out.push(` ${family} (${bs.length} bridge${bs.length === 1 ? '' : 's'}):`);
506
+ for (const b of bs) {
507
+ out.push(` ${b.id} — ${b.relation}`);
508
+ out.push(` ${evidenceLine(b.evidence, b.id)}`);
509
+ if (b.evidence.results !== undefined)
510
+ out.push(` ${outcomeLine(b.evidence.results)}`);
511
+ }
512
+ }
513
+ out.push(` norm transports (${v.normTransports.length}):`);
514
+ if (v.normTransports.length === 0)
515
+ out.push(' none declared');
516
+ for (const nt of v.normTransports)
517
+ out.push(` ${nt.id} on ${nt.bridge}: witness ${nt.witness} — ${nt.status}`);
518
+ out.push(' Refuted and unresolved are counted apart; neither is a pass. `upt atlas <bridge-id>` shows one bridge by claim.');
519
+ return out;
520
+ }
521
+ function judge(b, f) {
522
+ if (f.relation !== undefined && b.relation !== f.relation)
523
+ return 'not-matching';
524
+ if (f.evidence === undefined || b.evidence.derived.includes(f.evidence))
525
+ return 'kept';
526
+ return b.evidence.undecided.includes(f.evidence) ? 'undecided' : 'not-matching';
527
+ }
528
+ /** Format the bridge-filter counts shown in text and diagram legends. */
529
+ export function formatAtlasFilterLegend(s) {
530
+ if (s === null)
531
+ return null;
532
+ const terms = [
533
+ ...(s.relation !== undefined ? [`relation=${s.relation}`] : []),
534
+ ...(s.evidence !== undefined ? [`evidence=${s.evidence}`] : []),
535
+ ];
536
+ return (`filter: ${terms.join(' ')} — ${s.kept} of ${s.total} bridges kept; ` +
537
+ `${s.droppedNotMatching} dropped (did not match); ` +
538
+ `${s.droppedUndecided} dropped (undecided: ${UNOBSERVED[s.results ?? 'none']})`);
539
+ }
540
+ const UNOBSERVED = {
541
+ none: 'depends on witness results this command does not observe',
542
+ stored: `depends on witnesses with no result in ${STORED_RESULTS_PATH}`,
543
+ run: 'depends on witnesses not registered to run in-process',
544
+ };
545
+ /** Every bridge a view draws on, for running their witnesses before the view is built with the results. */
546
+ export function bridgeIdsOf(v) {
547
+ if (v.view === 'route')
548
+ return new Set((v.steps ?? []).map((b) => b.id));
549
+ return new Set(v.bridges.map((b) => b.id));
550
+ }
551
+ /** Build a family-focused atlas map, applying relation and evidence filters to its bridges. */
552
+ export function buildFamilyView(api, name, filter, results = null) {
553
+ const fam = api.ATLAS_FAMILIES.find((f) => f.family === name);
554
+ if (fam === undefined) {
555
+ throw new CliError(`upt map: unknown --family='${name}' (expected: ${api.ATLAS_FAMILIES.map((f) => f.family).join(' | ')})`);
556
+ }
557
+ const models = allModels(api);
558
+ const own = new Set(fam.models.map((m) => m.id));
559
+ const filed = fam.bridges.map((b) => ({ ...bridgeView(api, b, fam.family, models, results), role: 'filed' }));
560
+ const touching = api.ATLAS_FAMILIES.filter((f) => f !== fam).flatMap((f) => f.bridges
561
+ .filter((b) => [...b.premises, b.conclusion].some((id) => own.has(id)))
562
+ .map((b) => ({ ...bridgeView(api, b, f.family, models, results), role: 'touching' })));
563
+ const all = [...filed, ...touching];
564
+ const filtering = filter.relation !== undefined || filter.evidence !== undefined;
565
+ const verdicts = all.map((b) => (filtering ? judge(b, filter) : 'kept'));
566
+ const kept = all.filter((_, i) => verdicts[i] === 'kept');
567
+ const n = (v) => verdicts.filter((x) => x === v).length;
568
+ const mv = fam.models.map((m) => modelView(api, m));
569
+ const t = totals(api);
570
+ const witnessResults = tally(results, kept);
571
+ return {
572
+ view: 'family',
573
+ family: fam.family,
574
+ source: ATLAS_SOURCE,
575
+ models: mv,
576
+ bridges: kept,
577
+ rejections: fam.rejections.map((r) => ({
578
+ id: r.id,
579
+ claimed: r.claimed,
580
+ premises: [...r.premises],
581
+ conclusion: r.conclusion,
582
+ reason: r.reason,
583
+ })),
584
+ denominator: {
585
+ models: { shown: mv.length, of: t.models },
586
+ bridgesFiled: { shown: kept.filter((b) => b.role === 'filed').length, of: t.bridges },
587
+ bridgesTouching: { shown: kept.filter((b) => b.role === 'touching').length, of: t.bridges },
588
+ rejections: fam.rejections.length,
589
+ },
590
+ filter: filtering
591
+ ? {
592
+ ...filter,
593
+ total: all.length,
594
+ kept: kept.length,
595
+ droppedNotMatching: n('not-matching'),
596
+ droppedUndecided: n('undecided'),
597
+ ...(results === null ? {} : { results: results.mode }),
598
+ }
599
+ : null,
600
+ equationLinks: linkSummary(mv),
601
+ ...(witnessResults === undefined ? {} : { witnessResults }),
602
+ epistemics: EPISTEMICS,
603
+ };
604
+ }
605
+ // ── text ───────────────────────────────────────────────────────────────────
606
+ const MODE_LABEL = { stored: 'stored', run: 'run now' };
607
+ const NO_RESULT = {
608
+ stored: 'with no stored result',
609
+ run: 'not run: no in-process runner is registered for them',
610
+ };
611
+ function evidenceLine(e, id) {
612
+ const derived = e.derived.length === 0 ? 'none' : e.derived.join(', ');
613
+ const formal = e.formalRef === null ? '' : ` [formalRef ${e.formalRef.system}, fidelity ${e.formalRef.fidelity}; covers its statement only]`;
614
+ const r = e.results;
615
+ if (r === undefined) {
616
+ const undecided = e.undecided.length === 0
617
+ ? ''
618
+ : `; undecided without witness results: ${e.undecided.join(', ')} (${e.witnesses} witness(es); \`upt atlas ${id} --run\`)`;
619
+ return `evidence (derived): ${derived}${formal}${undecided}`;
620
+ }
621
+ const undecided = e.undecided.length === 0
622
+ ? ''
623
+ : `; undecided: ${e.undecided.join(', ')} (${r.notObserved.length} witness(es) ${NO_RESULT[r.source]})`;
624
+ return `evidence (derived, witness results ${MODE_LABEL[r.source]}): ${derived}${formal}${undecided}`;
625
+ }
626
+ function outcomeLine(r) {
627
+ const ids = (xs) => (xs.length === 0 ? 'none' : xs.join(', '));
628
+ const unresolved = r.unresolved.length === 0 ? 'none' : r.unresolved.map((u) => `${u.id} (${u.reason ?? 'no reason recorded'})`).join(', ');
629
+ return (`witnesses (${MODE_LABEL[r.source]}): checked ${ids(r.checked)} · refuted ${ids(r.refuted)} · ` +
630
+ `unresolved ${unresolved} · no result ${ids(r.notObserved)}`);
631
+ }
632
+ /** Format witness-result provenance and counts for a rendered atlas view. */
633
+ export function resultsLine(t) {
634
+ if (t === undefined)
635
+ return null;
636
+ const w = t.witnesses;
637
+ const counts = `over the bridges shown: ${w.checked} checked · ${w.refuted} refuted · ${w.unresolved} unresolved · ` +
638
+ `${w.notObserved} with no result (not a pass)`;
639
+ if ('ran' in t.provenance) {
640
+ return `witness results: run now — ${t.provenance.ran} (${t.provenance.registered} registered witness(es) ran); ${counts}`;
641
+ }
642
+ const p = t.provenance;
643
+ const when = p.lastCommit === null
644
+ ? 'no commit of it found (git unavailable, or the file is not committed)'
645
+ : `last commit touching it ${p.lastCommit.hash.slice(0, 12)} (${p.lastCommit.date})` +
646
+ (p.modifiedSinceCommit === true ? ', and the working-tree file is MODIFIED since' : '');
647
+ return `witness results: stored — ${p.path} (schemaVersion ${p.schemaVersion}; ${p.carries}; ${when}); ${counts}`;
648
+ }
649
+ function bridgeLines(b, indent) {
650
+ const at = (m, home) => (m.family === home ? m.id : `${m.id} (${m.family})`);
651
+ const lines = [
652
+ `${b.premises.map((p) => at(p, b.family)).join(' + ')} --[${b.relation}]--> ${at(b.conclusion, b.family)} (${b.id}) [${b.family}]`,
653
+ `${indent}transformation: ${b.transformation}`,
654
+ `${indent}assumptions: ${b.assumptions.length === 0 ? 'none stated' : b.assumptions.join('; ')}`,
655
+ `${indent}regime: ${b.regime.vacuous ? 'VACUOUS — states no inequality' : b.regime.inequalities.join('; ')}`,
656
+ `${indent}bound: ${b.bound === null ? 'none stated' : `K = ${b.bound.K} · delta = ${b.bound.delta} (${b.bound.norm}); horizon ${b.bound.horizon}`}`,
657
+ `${indent}${evidenceLine(b.evidence, b.id)}`,
658
+ ...(b.evidence.results === undefined ? [] : [`${indent}${outcomeLine(b.evidence.results)}`]),
659
+ ];
660
+ return lines;
661
+ }
662
+ function modelLines(m, indent) {
663
+ const lines = [`${m.id} [${m.family}]: ${m.dynamics}`];
664
+ if (m.equationLinks.length === 0)
665
+ lines.push(`${indent}equations: ${NO_LINK}`);
666
+ for (const l of m.equationLinks) {
667
+ const eq = l.name === null ? `${l.id} (NOT in the canonical registry)` : `${l.id} — ${l.name}: ${l.formula}`;
668
+ const edge = l.graphEdge === null ? 'no edge by this id in the equation graph' : `graph edge {${l.graphEdge.sources.join(', ')}} → ${l.graphEdge.target}`;
669
+ lines.push(`${indent}equation: ${eq}; ${edge}`);
670
+ }
671
+ return lines;
672
+ }
673
+ function linkLine(s) {
674
+ return `equation links (source: ${s.source}): ${s.withLink} of ${s.of} models record one; ${s.withoutLink} record none`;
675
+ }
676
+ function compositionLines(c, relations, indent) {
677
+ const out = c.running.map((r, i) => {
678
+ const state = r.relation === null
679
+ ? 'not composed (an earlier step already yields no composite claim)'
680
+ : r.relation === 'no-composite-claim'
681
+ ? `NO COMPOSITE CLAIM — ${relations[i - 1]} then ${relations[i]} has no table cell`
682
+ : r.relation;
683
+ return `${indent}after step ${i + 1} (${r.after}): ${state}`;
684
+ });
685
+ const claim = c.claim;
686
+ if (claim.kind === 'bound') {
687
+ out.push(`${indent}route claim: ${claim.relation}, K = ${claim.bound.K} · delta = ${claim.bound.delta} (${claim.norm ?? 'no norm stated'})`);
688
+ for (const nt of c.transports) {
689
+ out.push(`${indent} across '${nt.bridgeId}' by its declared transport '${nt.id}' (${nt.fromModel} → ${nt.toModel}, ` +
690
+ `K = ${nt.K}, time map uniform): witness ${nt.witness.id} ${nt.result === 'no result' ? 'has no result here (not a pass)' : nt.result}`);
691
+ }
692
+ if (c.evidence !== null) {
693
+ const d = c.evidence.derived.length === 0 ? 'none' : c.evidence.derived.join(', ');
694
+ const u = c.evidence.undecided.length === 0 ? '' : `; undecided: ${c.evidence.undecided.join(', ')}`;
695
+ out.push(`${indent}composite evidence (derived): ${d}${u} — never stronger than the weakest part`);
696
+ }
697
+ }
698
+ else {
699
+ out.push(`${indent}route claim: no composite claim — reason '${claim.reason}': ${claim.detail}`);
700
+ if (c.missing.length > 0) {
701
+ out.push(`${indent}to compose, this route would need:`);
702
+ for (const m of c.missing)
703
+ out.push(`${indent} - ${m}`);
704
+ }
705
+ }
706
+ return out;
707
+ }
708
+ /** Render a focused route view as human-readable CLI output lines. */
709
+ export function routeText(v) {
710
+ const out = [`\nRoute map — ${v.from} → ${v.to} [source: ${v.source}]`];
711
+ if (v.steps === null) {
712
+ out.push(` shown: 0 of ${v.denominator.bridges.of} atlas bridges — no chain of bridges connects these models ` +
713
+ '(only an exact equivalence is followed in both directions); there is nothing to compose.');
714
+ out.push(' endpoints:');
715
+ for (const m of v.models)
716
+ out.push(...modelLines(m, ' ').map((l, i) => (i === 0 ? ` ${l}` : l)));
717
+ out.push(` ${linkLine(v.equationLinks)}`);
718
+ return out;
719
+ }
720
+ if (v.steps.length === 0) {
721
+ out.push(' the endpoints are the same model: the route is empty and composes nothing.');
722
+ return out;
723
+ }
724
+ out.push(` shown: ${v.denominator.bridges.shown} of ${v.denominator.bridges.of} atlas bridges, ` +
725
+ `${v.denominator.models.shown} of ${v.denominator.models.of} models — ${v.selection}`);
726
+ const results = resultsLine(v.witnessResults);
727
+ if (results !== null)
728
+ out.push(` ${results}`);
729
+ out.push('');
730
+ v.steps.forEach((b, i) => {
731
+ const [head, ...rest] = bridgeLines(b, ' ');
732
+ out.push(` step ${i + 1} ${head}`, ...rest);
733
+ });
734
+ out.push('');
735
+ out.push(' composition (the composition table, folded along the route):');
736
+ out.push(...compositionLines(v.composition, v.steps.map((b) => b.relation), ' '));
737
+ out.push('');
738
+ out.push(' models on the route, with the equations each records:');
739
+ for (const m of v.models) {
740
+ const [head, ...rest] = modelLines(m, ' ');
741
+ out.push(` ${head}`, ...rest);
742
+ }
743
+ out.push(` ${linkLine(v.equationLinks)}`);
744
+ out.push(`\n (${v.epistemics})`);
745
+ return out;
746
+ }
747
+ /** Render a family atlas view as human-readable CLI output lines. */
748
+ export function familyText(v) {
749
+ const d = v.denominator;
750
+ const out = [`\nFamily map — ${v.family} [source: ${v.source}]`];
751
+ out.push(` shown: ${d.models.shown} of ${d.models.of} atlas models; ${d.bridgesFiled.shown} bridge(s) filed under ${v.family} ` +
752
+ `and ${d.bridgesTouching.shown} filed elsewhere that touch its models, of ${d.bridgesFiled.of} atlas bridges; ` +
753
+ `${d.rejections} rejection(s)`);
754
+ const legend = formatAtlasFilterLegend(v.filter);
755
+ if (legend !== null)
756
+ out.push(` ${legend}`);
757
+ const results = resultsLine(v.witnessResults);
758
+ if (results !== null)
759
+ out.push(` ${results}`);
760
+ out.push('');
761
+ out.push(' models, with the equations each records:');
762
+ for (const m of v.models) {
763
+ const [head, ...rest] = modelLines(m, ' ');
764
+ out.push(` ${head}`, ...rest);
765
+ }
766
+ out.push(` ${linkLine(v.equationLinks)}`);
767
+ for (const role of ['filed', 'touching']) {
768
+ const bs = v.bridges.filter((b) => b.role === role);
769
+ out.push('');
770
+ out.push(role === 'filed' ? ` bridges filed under ${v.family} (${bs.length}):` : ` bridges filed in other families that touch ${v.family} models (${bs.length}):`);
771
+ if (bs.length === 0)
772
+ out.push(' none');
773
+ for (const b of bs) {
774
+ const [head, ...rest] = bridgeLines(b, ' ');
775
+ out.push(` ${head}`, ...rest);
776
+ }
777
+ }
778
+ out.push('');
779
+ out.push(` rejections (${v.rejections.length}) — claimed bridges the atlas refutes:`);
780
+ if (v.rejections.length === 0)
781
+ out.push(' none recorded');
782
+ for (const r of v.rejections)
783
+ out.push(` ${r.premises.join(' + ')} -x[${r.claimed}]-> ${r.conclusion} (${r.id}): ${r.reason}`);
784
+ out.push(`\n (${v.epistemics})`);
785
+ return out;
786
+ }
787
+ /** Render a multi-route atlas view as human-readable CLI output lines. */
788
+ export function routesText(v) {
789
+ const out = [`\nAll routes — ${v.from} → ${v.to} [source: ${v.source}]`];
790
+ const c = v.count;
791
+ if (v.from === v.to) {
792
+ out.push(' the endpoints are the same model: the route is empty and composes nothing.');
793
+ return out;
794
+ }
795
+ const scope = c.exhausted
796
+ ? `${c.shown} simple route(s): the search ran out of routes, so these are all of them`
797
+ : (c.stoppedBy === 'limit'
798
+ ? `the first ${c.shown} simple routes: the search stopped at the limit of ${c.limit} (--max-routes), so MORE exist; `
799
+ : `${c.shown} simple route(s) found before the search exhausted its work budget; whether more exist is UNKNOWN; `) +
800
+ `every route of at most ${c.completeThrough} bridge(s) is among these, and longer ones may be missing`;
801
+ out.push(` ${scope} — ${v.selection}`);
802
+ out.push(` shown: ${v.denominator.bridges.shown} of ${v.denominator.bridges.of} atlas bridges, ` +
803
+ `${v.denominator.models.shown} of ${v.denominator.models.of} models, over the routes shown`);
804
+ if (c.shown === 0) {
805
+ out.push(' no chain of bridges connects these models (only an exact equivalence is followed in both directions).');
806
+ return out;
807
+ }
808
+ const reasons = Object.entries(v.claims.noClaim).map(([r, n]) => `${n} '${r}'`);
809
+ out.push(` route claims: ${v.claims.bound} carry a bound; ${c.shown - v.claims.bound} carry no composite claim` +
810
+ (reasons.length === 0 ? '' : ` (${reasons.join(', ')})`));
811
+ const results = resultsLine(v.witnessResults);
812
+ if (results !== null)
813
+ out.push(` ${results}`);
814
+ const byId = new Map(v.bridges.map((b) => [b.id, b]));
815
+ v.routes.forEach((r, i) => {
816
+ out.push('');
817
+ const hops = r.bridges.map((id, k) => ` --[${byId.get(id).relation}: ${id}]--> ${r.models[k + 1]}`).join('');
818
+ out.push(` route ${i + 1} (${r.bridges.length} bridge(s))${r.reported ? ' — the route `upt path` reports' : ''}:`);
819
+ out.push(` ${r.models[0]}${hops}`);
820
+ out.push(...compositionLines(r.composition, r.bridges.map((id) => byId.get(id).relation), ' '));
821
+ });
822
+ out.push('');
823
+ out.push(` bridges on these routes (${v.bridges.length}), each once:`);
824
+ for (const b of v.bridges) {
825
+ const [head, ...rest] = bridgeLines(b, ' ');
826
+ out.push(` ${head}`, ...rest);
827
+ }
828
+ out.push('');
829
+ out.push(' models on these routes, with the equations each records:');
830
+ for (const m of v.models) {
831
+ const [head, ...rest] = modelLines(m, ' ');
832
+ out.push(` ${head}`, ...rest);
833
+ }
834
+ out.push(` ${linkLine(v.equationLinks)}`);
835
+ out.push(`\n (${v.epistemics})`);
836
+ return out;
837
+ }
838
+ /** Render an observable atlas view as human-readable CLI output lines. */
839
+ export function observableText(v) {
840
+ const d = v.denominator.bridges;
841
+ const out = [`\nObservable map — '${v.observable}' [source: ${v.source}]`];
842
+ out.push(` of ${d.of} atlas bridges: ${d.preserves} record it as preserved, ${d.translates} declare a bound translation into it, ` +
843
+ `${d.doesNotPreserve} record it as NOT preserved, ${d.recordsNothing} record nothing about it (an absent record, not a finding)`);
844
+ out.push(` match: ${v.match}`);
845
+ const legend = formatAtlasFilterLegend(v.filter);
846
+ if (legend !== null)
847
+ out.push(` ${legend}`);
848
+ const results = resultsLine(v.witnessResults);
849
+ if (results !== null)
850
+ out.push(` ${results}`);
851
+ out.push('');
852
+ out.push(` bridges that preserve or translate it (${v.bridges.length}):`);
853
+ if (v.bridges.length === 0)
854
+ out.push(' none');
855
+ for (const b of v.bridges) {
856
+ const [head, ...rest] = bridgeLines(b, ' ');
857
+ out.push(` ${head}`, ...rest);
858
+ if (b.preservesMatched.length > 0)
859
+ out.push(` preserves (recorded): ${b.preservesMatched.join('; ')}`);
860
+ if (b.translationsMatched.length > 0)
861
+ out.push(` bound translation declared into: ${b.translationsMatched.join(', ')}`);
862
+ }
863
+ out.push('');
864
+ out.push(` bridges that record it as NOT preserved (${v.notPreserved.length}):`);
865
+ if (v.notPreserved.length === 0)
866
+ out.push(' none');
867
+ for (const b of v.notPreserved)
868
+ out.push(` ${b.id} (${b.relation}) [${b.family}]: does not preserve ${b.matched.join('; ')}`);
869
+ out.push('');
870
+ out.push(` models these bridges connect (${v.denominator.models.shown} of ${v.denominator.models.of}):`);
871
+ for (const m of v.models) {
872
+ const [head, ...rest] = modelLines(m, ' ');
873
+ out.push(` ${head}`, ...rest);
874
+ }
875
+ out.push(` ${linkLine(v.equationLinks)}`);
876
+ out.push(`\n (${v.epistemics})`);
877
+ return out;
878
+ }
879
+ // ── diagrams ───────────────────────────────────────────────────────────────
880
+ const mm = (s) => s.replace(/\r\n|\r|\n/g, ' ').replace(/&/g, '&amp;').replace(/"/g, '&quot;').replace(/</g, '&lt;').replace(/>/g, '&gt;');
881
+ const dq = (s) => s.replace(/\r\n|\r|\n/g, ' ').replace(/\\/g, '\\\\').replace(/"/g, '\\"');
882
+ /** The one-line denominator every diagram carries in its title. */
883
+ export function viewLegend(v) {
884
+ const tail = v.witnessResults === undefined ? '' : `; witness results: ${MODE_LABEL[v.witnessResults.mode]}`;
885
+ if (v.view === 'route') {
886
+ const d = v.denominator;
887
+ return (`route ${v.from} → ${v.to}: ${d.bridges.shown} of ${d.bridges.of} atlas bridges, ${d.models.shown} of ${d.models.of} models ` +
888
+ `[source: ${v.source}; equation links: ${LINK_SOURCE}${tail}]`);
889
+ }
890
+ if (v.view === 'routes') {
891
+ const d = v.denominator;
892
+ const c = v.count;
893
+ const scope = c.exhausted ? `all ${c.shown} simple routes` : `the first ${c.shown} simple routes (search stopped by its ${c.stoppedBy}; more may exist)`;
894
+ return (`routes ${v.from} → ${v.to}: ${scope}, over ${d.bridges.shown} of ${d.bridges.of} atlas bridges and ${d.models.shown} of ` +
895
+ `${d.models.of} models [source: ${v.source}; equation links: ${LINK_SOURCE}${tail}]`);
896
+ }
897
+ if (v.view === 'observable') {
898
+ const d = v.denominator.bridges;
899
+ const f = formatAtlasFilterLegend(v.filter);
900
+ return (`observable '${v.observable}': ${v.bridges.length} bridge(s) shown; of ${d.of} atlas bridges ${d.preserves} record it preserved, ` +
901
+ `${d.translates} translate into it, ${d.doesNotPreserve} record it NOT preserved, ${d.recordsNothing} record nothing ` +
902
+ `[source: ${v.source}, recorded preserves/doesNotPreserve text and bound translations; equation links: ${LINK_SOURCE}${tail}]` +
903
+ (f === null ? '' : ` — ${f}`));
904
+ }
905
+ const d = v.denominator;
906
+ const f = formatAtlasFilterLegend(v.filter);
907
+ return (`family ${v.family}: ${d.models.shown} of ${d.models.of} atlas models, ${d.bridgesFiled.shown} filed + ` +
908
+ `${d.bridgesTouching.shown} touching of ${d.bridgesFiled.of} atlas bridges [source: ${v.source}; equation links: ${LINK_SOURCE}${tail}]` +
909
+ (f === null ? '' : ` — ${f}`));
910
+ }
911
+ function diagramOf(v) {
912
+ if (v.view === 'route') {
913
+ const steps = v.steps ?? [];
914
+ const br = v.composition.breaksAt;
915
+ return { title: viewLegend(v), models: v.models, bridges: steps, breaks: new Set(br === null ? [] : [steps[br].id]) };
916
+ }
917
+ // A route-specific break is not a property of a bridge shared by several routes, so none is drawn.
918
+ return { title: viewLegend(v), models: v.models, bridges: v.bridges, breaks: new Set() };
919
+ }
920
+ function idMaker() {
921
+ const seen = new Map();
922
+ const used = new Set();
923
+ return (prefix, key) => {
924
+ const k = `${prefix}:${key}`;
925
+ const hit = seen.get(k);
926
+ if (hit !== undefined)
927
+ return hit;
928
+ const base = `${prefix}_${key.replace(/[^A-Za-z0-9]/g, '_')}`;
929
+ let id = base;
930
+ for (let n = 1; used.has(id); n++)
931
+ id = `${base}_${n}`;
932
+ used.add(id);
933
+ seen.set(k, id);
934
+ return id;
935
+ };
936
+ }
937
+ /** Models not in the view but named by a drawn bridge (a touching bridge's far end). */
938
+ function endpointsOutside(d) {
939
+ const inView = new Set(d.models.map((m) => m.id));
940
+ return [...new Set(d.bridges.flatMap((b) => [...b.premises.map((p) => p.id), b.conclusion.id]))].filter((id) => !inView.has(id));
941
+ }
942
+ function edgeLabel(b, breaks) {
943
+ return `${b.relation} (${b.id})${breaks ? ' — no composite claim from here' : ''}`;
944
+ }
945
+ /** Render an atlas map view as a Mermaid flowchart. */
946
+ export function toMermaid(v) {
947
+ const d = diagramOf(v);
948
+ const id = idMaker();
949
+ const out = ['flowchart LR', `%% ${d.title}`, ` legend["${mm(d.title)}"]:::legend`];
950
+ for (const m of d.models)
951
+ out.push(` ${id('m', m.id)}["${mm(`${m.id}: ${m.dynamics}`)}"]:::model`);
952
+ for (const m of endpointsOutside(d))
953
+ out.push(` ${id('m', m)}["${mm(m)}"]:::outside`);
954
+ // linkStyle addresses links by definition order, so the bridge links are
955
+ // emitted before any canonicalRef link.
956
+ const breakIdx = [];
957
+ let link = 0;
958
+ for (const b of d.bridges) {
959
+ const arrow = b.relation === 'exact-equivalence' ? '<-->' : '-->';
960
+ for (const p of b.premises) {
961
+ if (d.breaks.has(b.id))
962
+ breakIdx.push(link);
963
+ link++;
964
+ out.push(` ${id('m', p.id)} ${arrow}|"${mm(edgeLabel(b, d.breaks.has(b.id)))}"| ${id('m', b.conclusion.id)}`);
965
+ }
966
+ }
967
+ for (const m of d.models) {
968
+ for (const l of m.equationLinks) {
969
+ out.push(` ${id('c', l.id)}(["${mm(l.name === null ? l.id : `${l.id}: ${l.formula}`)}"]):::equation`);
970
+ out.push(` ${id('m', m.id)} -.->|"canonicalRef"| ${id('c', l.id)}`);
971
+ }
972
+ }
973
+ for (const i of breakIdx)
974
+ out.push(` linkStyle ${i} stroke:#c0392b,stroke-width:2px`);
975
+ out.push(' classDef model fill:#cfe3f7,stroke:#3a6ea5');
976
+ out.push(' classDef outside fill:#ffffff,stroke:#999999,stroke-dasharray:4 3');
977
+ out.push(' classDef equation fill:#f3f0e7,stroke:#8d7b4f,stroke-dasharray:4 3');
978
+ out.push(' classDef legend fill:#ffffff,stroke:#333333');
979
+ return out.join('\n') + '\n';
980
+ }
981
+ /** Render an atlas map view as a DOT graph. */
982
+ export function toDot(v) {
983
+ const d = diagramOf(v);
984
+ const id = idMaker();
985
+ const out = [
986
+ 'digraph AtlasMap {',
987
+ ` label="${dq(d.title)}";`,
988
+ ' rankdir=LR;',
989
+ ' node [fontname="Helvetica"];',
990
+ ];
991
+ for (const m of d.models)
992
+ out.push(` ${id('m', m.id)} [shape=box,label="${dq(`${m.id}: ${m.dynamics}`)}"];`);
993
+ for (const m of endpointsOutside(d))
994
+ out.push(` ${id('m', m)} [shape=box,style=dashed,label="${dq(m)}"];`);
995
+ for (const b of d.bridges) {
996
+ const brk = d.breaks.has(b.id);
997
+ const attrs = [
998
+ `label="${dq(edgeLabel(b, brk))}"`,
999
+ ...(b.relation === 'exact-equivalence' ? ['dir=both'] : []),
1000
+ ...(brk ? ['color="#c0392b"', 'penwidth=2'] : []),
1001
+ ];
1002
+ for (const p of b.premises)
1003
+ out.push(` ${id('m', p.id)} -> ${id('m', b.conclusion.id)} [${attrs.join(',')}];`);
1004
+ }
1005
+ for (const m of d.models) {
1006
+ for (const l of m.equationLinks) {
1007
+ out.push(` ${id('c', l.id)} [shape=ellipse,style=dashed,label="${dq(l.name === null ? l.id : `${l.id}: ${l.formula}`)}"];`);
1008
+ out.push(` ${id('m', m.id)} -> ${id('c', l.id)} [style=dashed,label="canonicalRef"];`);
1009
+ }
1010
+ }
1011
+ out.push('}');
1012
+ return out.join('\n') + '\n';
1013
+ }
1014
+ //# sourceMappingURL=_atlas-map.js.map