@prisma-next/cli 0.12.0 → 0.13.0-dev.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 (213) hide show
  1. package/README.md +2 -2
  2. package/dist/cli.mjs +180 -163
  3. package/dist/cli.mjs.map +1 -1
  4. package/dist/{client-KgJorIvG.mjs → client-CJzuo5wX.mjs} +222 -107
  5. package/dist/client-CJzuo5wX.mjs.map +1 -0
  6. package/dist/{command-helpers-Bbw1GbwL.mjs → command-helpers-DGMvGBeX.mjs} +318 -25
  7. package/dist/command-helpers-DGMvGBeX.mjs.map +1 -0
  8. package/dist/commands/contract-emit.d.mts.map +1 -1
  9. package/dist/commands/contract-emit.mjs +1 -1
  10. package/dist/commands/contract-infer.d.mts.map +1 -1
  11. package/dist/commands/contract-infer.mjs +1 -1
  12. package/dist/commands/db-init.d.mts.map +1 -1
  13. package/dist/commands/db-init.mjs +4 -5
  14. package/dist/commands/db-init.mjs.map +1 -1
  15. package/dist/commands/db-schema.d.mts.map +1 -1
  16. package/dist/commands/db-schema.mjs +3 -3
  17. package/dist/commands/db-schema.mjs.map +1 -1
  18. package/dist/commands/db-sign.d.mts.map +1 -1
  19. package/dist/commands/db-sign.mjs +6 -6
  20. package/dist/commands/db-sign.mjs.map +1 -1
  21. package/dist/commands/db-update.d.mts.map +1 -1
  22. package/dist/commands/db-update.mjs +10 -7
  23. package/dist/commands/db-update.mjs.map +1 -1
  24. package/dist/commands/db-verify.d.mts.map +1 -1
  25. package/dist/commands/db-verify.mjs +1 -1
  26. package/dist/commands/migrate.d.mts +37 -3
  27. package/dist/commands/migrate.d.mts.map +1 -1
  28. package/dist/commands/migrate.mjs +298 -12
  29. package/dist/commands/migrate.mjs.map +1 -1
  30. package/dist/commands/migration-check.d.mts +55 -13
  31. package/dist/commands/migration-check.d.mts.map +1 -1
  32. package/dist/commands/migration-check.mjs +3 -2
  33. package/dist/commands/migration-graph.d.mts +17 -8
  34. package/dist/commands/migration-graph.d.mts.map +1 -1
  35. package/dist/commands/migration-graph.mjs +185 -2
  36. package/dist/commands/migration-graph.mjs.map +1 -0
  37. package/dist/commands/migration-list.d.mts +26 -27
  38. package/dist/commands/migration-list.d.mts.map +1 -1
  39. package/dist/commands/migration-list.mjs +2 -190
  40. package/dist/commands/migration-log.d.mts +9 -19
  41. package/dist/commands/migration-log.d.mts.map +1 -1
  42. package/dist/commands/migration-log.mjs +1 -137
  43. package/dist/commands/migration-new.d.mts.map +1 -1
  44. package/dist/commands/migration-new.mjs +6 -5
  45. package/dist/commands/migration-new.mjs.map +1 -1
  46. package/dist/commands/migration-plan.d.mts +1 -1
  47. package/dist/commands/migration-plan.d.mts.map +1 -1
  48. package/dist/commands/migration-plan.mjs +1 -1
  49. package/dist/commands/migration-show.d.mts +17 -21
  50. package/dist/commands/migration-show.d.mts.map +1 -1
  51. package/dist/commands/migration-show.mjs +24 -36
  52. package/dist/commands/migration-show.mjs.map +1 -1
  53. package/dist/commands/migration-status.d.mts +42 -144
  54. package/dist/commands/migration-status.d.mts.map +1 -1
  55. package/dist/commands/migration-status.mjs +3 -759
  56. package/dist/commands/ref.d.mts +1 -1
  57. package/dist/commands/ref.d.mts.map +1 -1
  58. package/dist/commands/ref.mjs +4 -4
  59. package/dist/commands/ref.mjs.map +1 -1
  60. package/dist/commands/telemetry/index.d.mts +7 -0
  61. package/dist/commands/telemetry/index.d.mts.map +1 -0
  62. package/dist/commands/telemetry/index.mjs +2 -0
  63. package/dist/{config-loader-B6sJjXTv.mjs → config-loader-p9JMrekQ.mjs} +1 -1
  64. package/dist/{config-loader-B6sJjXTv.mjs.map → config-loader-p9JMrekQ.mjs.map} +1 -1
  65. package/dist/config-loader.mjs +1 -1
  66. package/dist/{contract-at-errors-BxP-TOMl.mjs → contract-at-errors-CFXsstzm.mjs} +2 -2
  67. package/dist/{contract-at-errors-BxP-TOMl.mjs.map → contract-at-errors-CFXsstzm.mjs.map} +1 -1
  68. package/dist/{contract-emit-DxcGl4Uq.mjs → contract-emit-B_qriF8B.mjs} +5 -5
  69. package/dist/{contract-emit-DxcGl4Uq.mjs.map → contract-emit-B_qriF8B.mjs.map} +1 -1
  70. package/dist/{contract-emit-D-4jrNve.mjs → contract-emit-C8HmtboH.mjs} +12 -7
  71. package/dist/contract-emit-C8HmtboH.mjs.map +1 -0
  72. package/dist/{contract-enrichment-a0V5Y_mL.mjs → contract-enrichment-gn9sWbPw.mjs} +1 -1
  73. package/dist/{contract-enrichment-a0V5Y_mL.mjs.map → contract-enrichment-gn9sWbPw.mjs.map} +1 -1
  74. package/dist/{contract-infer-D8uEbJuu.mjs → contract-infer-BYT_ra_U.mjs} +5 -5
  75. package/dist/contract-infer-BYT_ra_U.mjs.map +1 -0
  76. package/dist/{contract-space-aggregate-loader-DvZwdkrr.mjs → contract-space-aggregate-loader-ClI1KN6d.mjs} +5 -5
  77. package/dist/{contract-space-aggregate-loader-DvZwdkrr.mjs.map → contract-space-aggregate-loader-ClI1KN6d.mjs.map} +1 -1
  78. package/dist/{db-verify-v_vUKXTU.mjs → db-verify-C24FKhb7.mjs} +6 -6
  79. package/dist/{db-verify-v_vUKXTU.mjs.map → db-verify-C24FKhb7.mjs.map} +1 -1
  80. package/dist/exports/control-api.d.mts +5 -3
  81. package/dist/exports/control-api.d.mts.map +1 -1
  82. package/dist/exports/control-api.mjs +3 -3
  83. package/dist/exports/index.mjs +1 -1
  84. package/dist/exports/index.mjs.map +1 -1
  85. package/dist/exports/init-output.d.mts +1 -3
  86. package/dist/exports/init-output.d.mts.map +1 -1
  87. package/dist/exports/init-output.mjs +1 -1
  88. package/dist/{extension-pack-inputs-IDvjRCi3.mjs → extension-pack-inputs-1ySHqxKG.mjs} +1 -1
  89. package/dist/{extension-pack-inputs-IDvjRCi3.mjs.map → extension-pack-inputs-1ySHqxKG.mjs.map} +1 -1
  90. package/dist/{framework-components-fYXjz_in.mjs → framework-components-YVQHhPH7.mjs} +2 -2
  91. package/dist/{framework-components-fYXjz_in.mjs.map → framework-components-YVQHhPH7.mjs.map} +1 -1
  92. package/dist/{global-flags-DEHjV8_s.d.mts → global-flags-BpoOYtNZ.d.mts} +1 -1
  93. package/dist/{global-flags-DEHjV8_s.d.mts.map → global-flags-BpoOYtNZ.d.mts.map} +1 -1
  94. package/dist/{init-Cv9UzWL5.mjs → init-0HwB-Vh8.mjs} +5 -58
  95. package/dist/init-0HwB-Vh8.mjs.map +1 -0
  96. package/dist/{inspect-live-schema-C6ohV_oQ.mjs → inspect-live-schema-DF6IwcDl.mjs} +7 -5
  97. package/dist/inspect-live-schema-DF6IwcDl.mjs.map +1 -0
  98. package/dist/migration-check-soB5uZEQ.mjs +573 -0
  99. package/dist/migration-check-soB5uZEQ.mjs.map +1 -0
  100. package/dist/migration-cli.mjs +1 -1
  101. package/dist/migration-cli.mjs.map +1 -1
  102. package/dist/{migration-command-scaffold-CjvwO6at.mjs → migration-command-scaffold-DA-Lhx6o.mjs} +5 -5
  103. package/dist/{migration-command-scaffold-CjvwO6at.mjs.map → migration-command-scaffold-DA-Lhx6o.mjs.map} +1 -1
  104. package/dist/migration-graph-command-render-CEez7YUK.mjs +1960 -0
  105. package/dist/migration-graph-command-render-CEez7YUK.mjs.map +1 -0
  106. package/dist/migration-list-DlJJ_38Z.mjs +230 -0
  107. package/dist/migration-list-DlJJ_38Z.mjs.map +1 -0
  108. package/dist/migration-log-CG0qQAFm.mjs +222 -0
  109. package/dist/migration-log-CG0qQAFm.mjs.map +1 -0
  110. package/dist/migration-path-target-Ce6OZImp.mjs +38 -0
  111. package/dist/migration-path-target-Ce6OZImp.mjs.map +1 -0
  112. package/dist/{migration-plan-9DJ7q7_z.mjs → migration-plan-z5Ing-TD.mjs} +9 -8
  113. package/dist/migration-plan-z5Ing-TD.mjs.map +1 -0
  114. package/dist/migration-status-CgWSoI_g.mjs +446 -0
  115. package/dist/migration-status-CgWSoI_g.mjs.map +1 -0
  116. package/dist/{output-B60Gw5fu.mjs → output-mEQ74_nd.mjs} +1 -1
  117. package/dist/{output-B60Gw5fu.mjs.map → output-mEQ74_nd.mjs.map} +1 -1
  118. package/dist/{progress-adapter-C644QK8l.mjs → progress-adapter-CjAeTxY_.mjs} +1 -1
  119. package/dist/{progress-adapter-C644QK8l.mjs.map → progress-adapter-CjAeTxY_.mjs.map} +1 -1
  120. package/dist/{ref-advancement-DUZqsue6.mjs → ref-advancement-BkXlikCA.mjs} +1 -1
  121. package/dist/{ref-advancement-DUZqsue6.mjs.map → ref-advancement-BkXlikCA.mjs.map} +1 -1
  122. package/dist/schemas-CeGMYFYX.d.mts +191 -0
  123. package/dist/schemas-CeGMYFYX.d.mts.map +1 -0
  124. package/dist/schemas-KhXMzNA_.mjs +112 -0
  125. package/dist/schemas-KhXMzNA_.mjs.map +1 -0
  126. package/dist/telemetry-BIM4beEO.mjs +122 -0
  127. package/dist/telemetry-BIM4beEO.mjs.map +1 -0
  128. package/dist/{terminal-ui-5Y6mrg93.d.mts → terminal-ui-DGRNFWna.d.mts} +1 -1
  129. package/dist/terminal-ui-DGRNFWna.d.mts.map +1 -0
  130. package/dist/{types-Dt_SfqFm.d.mts → types-C_tYiJYx.d.mts} +53 -31
  131. package/dist/types-C_tYiJYx.d.mts.map +1 -0
  132. package/dist/{verify-DCA9Sldu.mjs → verify-DcOYZ1tH.mjs} +2 -2
  133. package/dist/{verify-DCA9Sldu.mjs.map → verify-DcOYZ1tH.mjs.map} +1 -1
  134. package/package.json +26 -22
  135. package/src/cli.ts +5 -0
  136. package/src/commands/contract-infer.ts +2 -2
  137. package/src/commands/db-update.ts +7 -1
  138. package/src/commands/init/index.ts +6 -35
  139. package/src/commands/init/init.ts +1 -14
  140. package/src/commands/init/inputs.ts +0 -75
  141. package/src/commands/inspect-live-schema.ts +10 -0
  142. package/src/commands/json/schemas.ts +195 -0
  143. package/src/commands/migrate.ts +527 -8
  144. package/src/commands/migration-check.ts +469 -134
  145. package/src/commands/migration-graph.ts +164 -91
  146. package/src/commands/migration-list.ts +72 -39
  147. package/src/commands/migration-log.ts +52 -102
  148. package/src/commands/migration-new.ts +2 -1
  149. package/src/commands/migration-plan.ts +2 -1
  150. package/src/commands/migration-show.ts +31 -66
  151. package/src/commands/migration-status-overlay.ts +61 -0
  152. package/src/commands/migration-status.ts +458 -1066
  153. package/src/commands/telemetry/index.ts +107 -0
  154. package/src/commands/telemetry/status.ts +67 -0
  155. package/src/control-api/client.ts +70 -9
  156. package/src/control-api/operations/contract-emit.ts +22 -2
  157. package/src/control-api/operations/db-init.ts +6 -3
  158. package/src/control-api/operations/{db-apply.ts → db-run.ts} +55 -14
  159. package/src/control-api/operations/db-update.ts +7 -4
  160. package/src/control-api/operations/db-verify.ts +15 -5
  161. package/src/control-api/operations/{migration-apply.ts → migrate.ts} +181 -80
  162. package/src/control-api/operations/{apply.ts → run-migration.ts} +33 -27
  163. package/src/control-api/types.ts +56 -29
  164. package/src/utils/cli-errors.ts +70 -2
  165. package/src/utils/formatters/errors.ts +11 -0
  166. package/src/utils/formatters/migration-graph-command-render.ts +239 -0
  167. package/src/utils/formatters/migration-graph-grid-layout.ts +1134 -0
  168. package/src/utils/formatters/migration-graph-labels.ts +408 -0
  169. package/src/utils/formatters/migration-graph-model.ts +103 -0
  170. package/src/utils/formatters/migration-graph-occlusion-render.ts +258 -0
  171. package/src/utils/formatters/migration-graph-rows.ts +128 -15
  172. package/src/utils/formatters/migration-graph-space-render.ts +188 -0
  173. package/src/utils/formatters/migration-list-data-column.ts +4 -91
  174. package/src/utils/formatters/migration-list-graph-topology.ts +72 -94
  175. package/src/utils/formatters/migration-list-render.ts +135 -71
  176. package/src/utils/formatters/migration-list-styler.ts +46 -5
  177. package/src/utils/formatters/migration-list-types.ts +5 -21
  178. package/src/utils/formatters/migration-log-table.ts +205 -0
  179. package/src/utils/formatters/migrations.ts +33 -11
  180. package/src/utils/global-flags.ts +35 -0
  181. package/src/utils/integrity-violation-to-check-failure.ts +28 -19
  182. package/src/utils/legend.ts +38 -0
  183. package/src/utils/migration-path-target.ts +60 -0
  184. package/src/utils/telemetry.ts +68 -32
  185. package/dist/client-KgJorIvG.mjs.map +0 -1
  186. package/dist/command-helpers-Bbw1GbwL.mjs.map +0 -1
  187. package/dist/commands/migration-list.mjs.map +0 -1
  188. package/dist/commands/migration-log.mjs.map +0 -1
  189. package/dist/commands/migration-status.mjs.map +0 -1
  190. package/dist/contract-emit-D-4jrNve.mjs.map +0 -1
  191. package/dist/contract-infer-D8uEbJuu.mjs.map +0 -1
  192. package/dist/graph-render-rFAqZujX.mjs +0 -1081
  193. package/dist/graph-render-rFAqZujX.mjs.map +0 -1
  194. package/dist/init-Cv9UzWL5.mjs.map +0 -1
  195. package/dist/inspect-live-schema-C6ohV_oQ.mjs.map +0 -1
  196. package/dist/migration-check-BiBJoYYW.mjs +0 -341
  197. package/dist/migration-check-BiBJoYYW.mjs.map +0 -1
  198. package/dist/migration-graph-D7DVUElV.mjs +0 -1232
  199. package/dist/migration-graph-D7DVUElV.mjs.map +0 -1
  200. package/dist/migration-list-styler-BRwF4-gy.mjs +0 -399
  201. package/dist/migration-list-styler-BRwF4-gy.mjs.map +0 -1
  202. package/dist/migration-plan-9DJ7q7_z.mjs.map +0 -1
  203. package/dist/migration-types-D2FW63pr.d.mts +0 -15
  204. package/dist/migration-types-D2FW63pr.d.mts.map +0 -1
  205. package/dist/migrations-Cv2jxNNK.mjs +0 -228
  206. package/dist/migrations-Cv2jxNNK.mjs.map +0 -1
  207. package/dist/terminal-ui-5Y6mrg93.d.mts.map +0 -1
  208. package/dist/types-Dt_SfqFm.d.mts.map +0 -1
  209. package/src/utils/formatters/graph-migration-mapper.ts +0 -235
  210. package/src/utils/formatters/graph-render.ts +0 -1323
  211. package/src/utils/formatters/graph-types.ts +0 -120
  212. package/src/utils/formatters/migration-graph-layout.ts +0 -1119
  213. package/src/utils/formatters/migration-graph-tree-render.ts +0 -459
@@ -1,15 +1,16 @@
1
- import { A as CliStructuredError } from "./command-helpers-Bbw1GbwL.mjs";
2
- import { t as assertFrameworkComponentsCompatible } from "./framework-components-fYXjz_in.mjs";
3
- import { t as enrichContract } from "./contract-enrichment-a0V5Y_mL.mjs";
4
- import { n as buildContractSpaceAggregate } from "./contract-space-aggregate-loader-DvZwdkrr.mjs";
1
+ import { F as CliStructuredError } from "./command-helpers-DGMvGBeX.mjs";
2
+ import { n as toExtensionInputs } from "./extension-pack-inputs-1ySHqxKG.mjs";
3
+ import { t as assertFrameworkComponentsCompatible } from "./framework-components-YVQHhPH7.mjs";
4
+ import { t as enrichContract } from "./contract-enrichment-gn9sWbPw.mjs";
5
+ import { t as buildContractSpaceAggregate } from "./contract-space-aggregate-loader-ClI1KN6d.mjs";
5
6
  import { emit } from "@prisma-next/emitter";
6
7
  import { ifDefined } from "@prisma-next/utils/defined";
7
8
  import { notOk, ok } from "@prisma-next/utils/result";
8
9
  import { APP_SPACE_ID, createControlStack, hasMigrations, hasOperationPreview, hasPslContractInfer, hasSchemaView } from "@prisma-next/framework-components/control";
9
- import { graphWalkStrategy, planMigration, requireHeadRef, verifyMigration } from "@prisma-next/migration-tools/aggregate";
10
+ import { blindCast, castAs } from "@prisma-next/utils/casts";
11
+ import { buildSynthMigrationEdge, collectAggregateNamespaces, graphWalkStrategy, planMigration, requireHeadRef, verifyMigration } from "@prisma-next/migration-tools/aggregate";
10
12
  import { EMPTY_CONTRACT_HASH } from "@prisma-next/migration-tools/constants";
11
13
  import { errorNoInvariantPath } from "@prisma-next/migration-tools/errors";
12
- import { castAs } from "@prisma-next/utils/casts";
13
14
  import { findPathWithDecision } from "@prisma-next/migration-tools/migration-graph";
14
15
  //#region src/control-api/errors.ts
15
16
  var ContractValidationError = class extends Error {
@@ -21,14 +22,27 @@ var ContractValidationError = class extends Error {
21
22
  }
22
23
  };
23
24
  //#endregion
24
- //#region src/control-api/operations/apply.ts
25
+ //#region src/control-api/operations/migration-helpers.ts
26
+ /**
27
+ * Strips operation objects to their public shape (id, label, operationClass).
28
+ * Used at the API boundary to avoid leaking internal fields (precheck, execute, postcheck, etc.).
29
+ */
30
+ function stripOperations(operations) {
31
+ return operations.map((op) => ({
32
+ id: op.id,
33
+ label: op.label,
34
+ operationClass: op.operationClass
35
+ }));
36
+ }
37
+ //#endregion
38
+ //#region src/control-api/operations/run-migration.ts
25
39
  /**
26
- * Span id emitted via `onProgress` for the apply phase. Stable
40
+ * Span id emitted via `onProgress` for the run phase. Stable
27
41
  * identifier consumed by the structured-output renderer and by tests.
28
42
  */
29
- const APPLY_SPAN_ID = "apply";
43
+ const RUN_SPAN_ID = "apply";
30
44
  /**
31
- * Runner-driving tail shared by every apply caller — `db init`,
45
+ * Runner-driving tail shared by every run caller — `db init`,
32
46
  * `db update`, and `migrate`. Consumes already-resolved per-space
33
47
  * plans (the planner-vs-replay distinction is owned by the caller) and
34
48
  * dispatches them to the runner in canonical order.
@@ -43,14 +57,14 @@ const APPLY_SPAN_ID = "apply";
43
57
  * so callers don't have to duplicate it; the `action` field on each
44
58
  * progress event is taken from the caller's `action` argument.
45
59
  */
46
- async function applyMigration(inputs) {
60
+ async function runMigration(inputs) {
47
61
  const { aggregate, perSpacePlans, applyOrder, driver, familyInstance, migrations, frameworkComponents, policy, action, onProgress } = inputs;
48
62
  const orderedResolutions = collectOrdered(applyOrder, perSpacePlans);
49
63
  const runner = migrations.createRunner(familyInstance);
50
64
  onProgress?.({
51
65
  action,
52
66
  kind: "spanStart",
53
- spanId: APPLY_SPAN_ID,
67
+ spanId: RUN_SPAN_ID,
54
68
  label: progressLabelForAction(action)
55
69
  });
56
70
  const perSpaceOptions = orderedResolutions.map((r) => ({
@@ -60,6 +74,7 @@ async function applyMigration(inputs) {
60
74
  destinationContract: r.entry.destinationContract,
61
75
  policy,
62
76
  frameworkComponents,
77
+ migrationEdges: r.entry.migrationEdges,
63
78
  strictVerification: false
64
79
  }));
65
80
  const runnerResult = await runner.execute({
@@ -70,7 +85,7 @@ async function applyMigration(inputs) {
70
85
  onProgress?.({
71
86
  action,
72
87
  kind: "spanEnd",
73
- spanId: APPLY_SPAN_ID,
88
+ spanId: RUN_SPAN_ID,
74
89
  outcome: "error"
75
90
  });
76
91
  return notOk({
@@ -86,7 +101,7 @@ async function applyMigration(inputs) {
86
101
  onProgress?.({
87
102
  action,
88
103
  kind: "spanEnd",
89
- spanId: APPLY_SPAN_ID,
104
+ spanId: RUN_SPAN_ID,
90
105
  outcome: "ok"
91
106
  });
92
107
  return ok({
@@ -105,7 +120,7 @@ async function applyMigration(inputs) {
105
120
  * advances as the last step of each space's transaction) and `false`
106
121
  * for plan-mode (no marker has been written yet).
107
122
  *
108
- * Exported alongside {@link applyMigration} so plan-mode callers can
123
+ * Exported alongside {@link runMigration} so plan-mode callers can
109
124
  * assemble the same per-space block without going through the runner.
110
125
  */
111
126
  function buildPerSpaceBreakdown(orderedResolutions, appSpaceId, options) {
@@ -146,8 +161,8 @@ function collectOrdered(applyOrder, perSpace) {
146
161
  });
147
162
  }
148
163
  /**
149
- * Action-appropriate label for the `spanStart` event the apply
150
- * primitive emits. `applyMigration` is shared by `db init`, `db update`,
164
+ * Action-appropriate label for the `spanStart` event the run
165
+ * primitive emits. `runMigration` is shared by `db init`, `db update`,
151
166
  * and `migrate`; the span label tracks the user-visible action
152
167
  * so structured-progress output reads naturally for each surface.
153
168
  */
@@ -155,29 +170,16 @@ function progressLabelForAction(action) {
155
170
  switch (action) {
156
171
  case "dbInit": return "Initialising database across spaces";
157
172
  case "dbUpdate": return "Updating database across spaces";
158
- case "migrationApply": return "Applying migration plan across spaces";
173
+ case "migrate": return "Running migration plan across spaces";
159
174
  }
160
175
  }
161
176
  //#endregion
162
- //#region src/control-api/operations/migration-helpers.ts
163
- /**
164
- * Strips operation objects to their public shape (id, label, operationClass).
165
- * Used at the API boundary to avoid leaking internal fields (precheck, execute, postcheck, etc.).
166
- */
167
- function stripOperations(operations) {
168
- return operations.map((op) => ({
169
- id: op.id,
170
- label: op.label,
171
- operationClass: op.operationClass
172
- }));
173
- }
174
- //#endregion
175
- //#region src/control-api/operations/db-apply.ts
177
+ //#region src/control-api/operations/db-run.ts
176
178
  /**
177
- * Span IDs emitted via `onProgress` during the apply flow.
179
+ * Span IDs emitted via `onProgress` during the run flow.
178
180
  * Stable identifiers consumed by the structured-output renderer and by
179
181
  * tests asserting on span ids. The `apply` span itself is owned by
180
- * the {@link applyMigration} primitive — only the introspect / plan
182
+ * the {@link runMigration} primitive — only the introspect / plan
181
183
  * spans are emitted directly here.
182
184
  */
183
185
  const SPAN_IDS$1 = {
@@ -203,8 +205,8 @@ const SPAN_IDS$1 = {
203
205
  * transaction across every space; failure on any space rolls back
204
206
  * every space's writes.
205
207
  */
206
- async function executeApply(options) {
207
- const { driver, familyInstance, contract, mode, migrations, frameworkComponents, migrationsDir, extensionPacks, targetId, policy, action, onProgress } = options;
208
+ async function executeRun(options) {
209
+ const { driver, adapter, familyInstance, contract, mode, migrations, frameworkComponents, migrationsDir, extensionPacks, targetId, policy, action, onProgress } = options;
208
210
  const loaded = await buildContractSpaceAggregate({
209
211
  targetId,
210
212
  migrationsDir,
@@ -225,7 +227,10 @@ async function executeApply(options) {
225
227
  spanId: SPAN_IDS$1.introspect,
226
228
  label: "Introspecting database schema"
227
229
  });
228
- const schemaIR = await familyInstance.introspect({ driver });
230
+ const schemaIR = await familyInstance.introspect({
231
+ driver,
232
+ contract: collectAggregateNamespaces(aggregate)
233
+ });
229
234
  onProgress?.({
230
235
  action,
231
236
  kind: "spanEnd",
@@ -244,7 +249,7 @@ async function executeApply(options) {
244
249
  markersBySpaceId: markerRows,
245
250
  schemaIntrospection: schemaIR
246
251
  },
247
- familyInstance,
252
+ adapter,
248
253
  migrations,
249
254
  frameworkComponents,
250
255
  callerPolicy: { ignoreGraphFor: new Set([aggregate.app.spaceId]) },
@@ -266,6 +271,7 @@ async function executeApply(options) {
266
271
  outcome: "ok"
267
272
  });
268
273
  const orderedResolutions = collectOrdered(planResult.value.applyOrder, planResult.value.perSpace);
274
+ const plannerWarnings = aggregatePlannerWarnings(orderedResolutions);
269
275
  const appResolution = orderedResolutions.find((r) => r.spaceId === aggregate.app.spaceId);
270
276
  if (!appResolution) throw new Error("Aggregate planner returned no plan for the app member — the planner is supposed to always emit one.");
271
277
  const appPlan = appResolution.entry.plan;
@@ -279,10 +285,11 @@ async function executeApply(options) {
279
285
  destination: appPlan.destination,
280
286
  preview,
281
287
  perSpace,
282
- summary
288
+ summary,
289
+ ...ifDefined("warnings", plannerWarnings)
283
290
  });
284
291
  }
285
- const applied = await applyMigration({
292
+ const applied = await runMigration({
286
293
  aggregate,
287
294
  perSpacePlans: planResult.value.perSpace,
288
295
  applyOrder: planResult.value.applyOrder,
@@ -297,7 +304,8 @@ async function executeApply(options) {
297
304
  if (!applied.ok) return buildRunnerFailure({
298
305
  summary: applied.failure.summary,
299
306
  ...ifDefined("why", applied.failure.why),
300
- meta: applied.failure.meta
307
+ meta: applied.failure.meta,
308
+ ...ifDefined("warnings", plannerWarnings)
301
309
  });
302
310
  const aggregateOps = applied.value.orderedResolutions.flatMap((r) => r.entry.displayOps);
303
311
  const summary = action === "dbInit" ? `Applied ${applied.value.totalOpsExecuted} operation(s) across ${applied.value.orderedResolutions.length} space(s), database signed` : applied.value.totalOpsExecuted === 0 ? `Database already matches contract across ${applied.value.orderedResolutions.length} space(s), signature updated` : `Applied ${applied.value.totalOpsExecuted} operation(s) across ${applied.value.orderedResolutions.length} space(s), signature updated`;
@@ -307,9 +315,14 @@ async function executeApply(options) {
307
315
  operationsPlanned: applied.value.totalOpsPlanned,
308
316
  operationsExecuted: applied.value.totalOpsExecuted,
309
317
  perSpace: applied.value.perSpace,
310
- summary
318
+ summary,
319
+ ...ifDefined("warnings", plannerWarnings)
311
320
  });
312
321
  }
322
+ function aggregatePlannerWarnings(orderedResolutions) {
323
+ const warnings = orderedResolutions.flatMap((r) => r.entry.warnings ?? []);
324
+ return warnings.length > 0 ? warnings : void 0;
325
+ }
313
326
  /**
314
327
  * Compare the live `_prisma_marker` rows against the aggregate's
315
328
  * declared members. Any marker row whose `space` is not a member of
@@ -342,13 +355,13 @@ function detectOrphanMarkers(aggregate, markerRows) {
342
355
  });
343
356
  }
344
357
  function mapPlannerError(error) {
345
- if (error.kind === "appSynthFailure") return notOk({
358
+ if (error.kind === "appSynthFailure") return blindCast(notOk({
346
359
  code: "PLANNING_FAILED",
347
360
  summary: "Migration planning failed due to conflicts",
348
361
  conflicts: error.conflicts,
349
362
  why: void 0,
350
363
  meta: void 0
351
- });
364
+ }));
352
365
  if (error.kind === "extensionPathUnreachable") return buildRunnerFailure({
353
366
  summary: `Cannot resolve apply path for extension space "${error.spaceId}"`,
354
367
  why: `No path in the on-disk migration graph for extension space "${error.spaceId}" reaches the on-disk head ref hash "${error.target}".`,
@@ -383,7 +396,8 @@ function wrapPlanResult(args) {
383
396
  ...ifDefined("profileHash", args.destination.profileHash)
384
397
  },
385
398
  perSpace: args.perSpace,
386
- summary: args.summary
399
+ summary: args.summary,
400
+ ...ifDefined("warnings", args.warnings)
387
401
  });
388
402
  }
389
403
  function wrapApplyResult(args) {
@@ -403,17 +417,19 @@ function wrapApplyResult(args) {
403
417
  profileHash: args.destination.profileHash
404
418
  } : { storageHash: args.destination.storageHash },
405
419
  perSpace: args.perSpace,
406
- summary: args.summary
420
+ summary: args.summary,
421
+ ...ifDefined("warnings", args.warnings)
407
422
  });
408
423
  }
409
424
  function buildRunnerFailure(args) {
410
- return notOk({
425
+ return blindCast(notOk({
411
426
  code: "RUNNER_FAILED",
412
427
  summary: args.summary,
413
428
  why: args.why,
414
429
  meta: args.meta,
415
- conflicts: void 0
416
- });
430
+ conflicts: void 0,
431
+ ...ifDefined("warnings", args.warnings)
432
+ }));
417
433
  }
418
434
  //#endregion
419
435
  //#region src/control-api/operations/db-init.ts
@@ -425,8 +441,9 @@ function buildRunnerFailure(args) {
425
441
  * changes belong to `db update`.
426
442
  */
427
443
  async function executeDbInit(options) {
428
- return await executeApply({
444
+ return await executeRun({
429
445
  driver: options.driver,
446
+ adapter: options.adapter,
430
447
  familyInstance: options.familyInstance,
431
448
  contract: options.contract,
432
449
  mode: options.mode,
@@ -459,6 +476,7 @@ const DB_UPDATE_POLICY = { allowedOperationClasses: [
459
476
  async function executeDbUpdate(options) {
460
477
  const sharedInputs = {
461
478
  driver: options.driver,
479
+ adapter: options.adapter,
462
480
  familyInstance: options.familyInstance,
463
481
  contract: options.contract,
464
482
  migrations: options.migrations,
@@ -474,7 +492,7 @@ async function executeDbUpdate(options) {
474
492
  const gate = await guardDestructiveChanges(sharedInputs);
475
493
  if (gate !== null) return gate;
476
494
  }
477
- return await executeApply({
495
+ return await executeRun({
478
496
  ...sharedInputs,
479
497
  mode: options.mode
480
498
  });
@@ -487,7 +505,7 @@ async function executeDbUpdate(options) {
487
505
  * run.
488
506
  */
489
507
  async function guardDestructiveChanges(sharedInputs) {
490
- const planResult = await executeApply({
508
+ const planResult = await executeRun({
491
509
  ...sharedInputs,
492
510
  mode: "plan"
493
511
  });
@@ -541,7 +559,8 @@ async function executeDbVerify(options) {
541
559
  const schemaIntrospection = skipSchema ? null : await runIntrospection({
542
560
  driver,
543
561
  familyInstance,
544
- onProgress
562
+ onProgress,
563
+ contract: collectAggregateNamespaces(aggregate)
545
564
  });
546
565
  emitVerifySpan(onProgress, "spanStart");
547
566
  return finaliseVerifyResult({
@@ -567,7 +586,7 @@ function buildLoadInputs(options) {
567
586
  };
568
587
  }
569
588
  async function runIntrospection(args) {
570
- const { driver, familyInstance, onProgress } = args;
589
+ const { driver, familyInstance, onProgress, contract } = args;
571
590
  onProgress?.({
572
591
  action: "dbVerify",
573
592
  kind: "spanStart",
@@ -575,7 +594,10 @@ async function runIntrospection(args) {
575
594
  label: "Introspecting database schema"
576
595
  });
577
596
  try {
578
- const result = await familyInstance.introspect({ driver });
597
+ const result = await familyInstance.introspect({
598
+ driver,
599
+ contract
600
+ });
579
601
  onProgress?.({
580
602
  action: "dbVerify",
581
603
  kind: "spanEnd",
@@ -605,7 +627,7 @@ function createPerMemberVerifier(options) {
605
627
  if (skipSchema) return buildSkippedSchemaResult(member);
606
628
  return familyInstance.verifySchema({
607
629
  contract: member.contract(),
608
- schema: projectedSchema,
630
+ schema: blindCast(projectedSchema),
609
631
  strict: verifyMode === "strict",
610
632
  frameworkComponents
611
633
  });
@@ -730,7 +752,7 @@ function mapMarkerCheckFailures(appSpaceId, section) {
730
752
  });
731
753
  }
732
754
  //#endregion
733
- //#region src/control-api/operations/migration-apply.ts
755
+ //#region src/control-api/operations/migrate.ts
734
756
  /**
735
757
  * Apply pending migrations across every contract space (app +
736
758
  * extensions). Replay-only: graph-walk against the on-disk graph for
@@ -745,14 +767,14 @@ function mapMarkerCheckFailures(appSpaceId, section) {
745
767
  * marker to `member.headRef.hash` (or `refHash` for the app
746
768
  * member when provided). Empty-graph members fail loudly — a
747
769
  * "never planned" space is a user-error condition for replay.
748
- * 4. Hand off to {@link applyMigration} (the runner-driving tail
770
+ * 4. Hand off to {@link runMigration} (the runner-driving tail
749
771
  * shared with `db init` / `db update`). Marker advancement is
750
772
  * inside the per-space transaction.
751
773
  *
752
774
  * Encodes the replay-only contract: every contract space must have an
753
775
  * authored migration graph on disk before this operation can advance it.
754
776
  */
755
- async function executeMigrationApply(options) {
777
+ async function executeMigrate(options) {
756
778
  const { driver, familyInstance, contract, migrations, frameworkComponents, migrationsDir, extensionPacks, targetId, refHash, refInvariants, refName, onProgress } = options;
757
779
  const loaded = await buildContractSpaceAggregate({
758
780
  targetId,
@@ -770,39 +792,23 @@ async function executeMigrationApply(options) {
770
792
  for (const member of allMembers) {
771
793
  const isAppMember = member.spaceId === aggregate.app.spaceId;
772
794
  const headRef = requireHeadRef(member);
773
- const targetHash = isAppMember && refHash !== void 0 ? refHash : headRef.hash;
774
- const liveMarker = markerRows.get(member.spaceId) ?? null;
775
- if (member.graph().nodes.size === 0) {
776
- const liveHash = liveMarker?.storageHash;
777
- if (targetHash === liveHash || liveHash === void 0 && targetHash === EMPTY_CONTRACT_HASH) {
778
- atHeadResolutions.set(member.spaceId, buildAtHeadResolution({
779
- aggregateTargetId: aggregate.targetId,
780
- member,
781
- targetHash,
782
- liveMarker
783
- }));
784
- continue;
785
- }
786
- return notOk(buildNeverPlannedFailure(member.spaceId, targetHash));
787
- }
788
- const targetInvariants = isAppMember && refHash !== void 0 && refInvariants !== void 0 ? refInvariants : headRef.invariants;
789
- const targetMember = targetHash === headRef.hash && targetInvariants === headRef.invariants ? member : {
790
- ...member,
791
- headRef: {
792
- hash: targetHash,
793
- invariants: targetInvariants
794
- }
795
- };
796
- const walked = graphWalkStrategy({
797
- aggregateTargetId: aggregate.targetId,
798
- member: targetMember,
799
- currentMarker: liveMarker,
800
- ...isAppMember && refName !== void 0 ? { refName } : {}
795
+ const memberTargetHash = isAppMember && refHash !== void 0 ? refHash : headRef.hash;
796
+ const outcome = planMemberPath({
797
+ member,
798
+ aggregate,
799
+ targetHash: memberTargetHash,
800
+ refInvariants: isAppMember && refHash !== void 0 ? refInvariants : void 0,
801
+ liveMarker: markerRows.get(member.spaceId) ?? null,
802
+ ...isAppMember ? { refName } : {}
801
803
  });
802
- if (walked.kind === "unreachable") return notOk(buildPathNotFoundFailure(member.spaceId, liveMarker, targetHash));
803
- if (walked.kind === "unsatisfiable") {
804
- const fromHash = liveMarker?.storageHash ?? EMPTY_CONTRACT_HASH;
805
- const structural = findPathWithDecision(targetMember.graph(), fromHash, targetHash, { required: /* @__PURE__ */ new Set() });
804
+ if (outcome.kind === "at-head") {
805
+ atHeadResolutions.set(member.spaceId, outcome.plan);
806
+ continue;
807
+ }
808
+ if (outcome.kind === "never-planned") return notOk(buildNeverPlannedFailure(outcome.spaceId, outcome.targetHash));
809
+ if (outcome.kind === "unreachable") return notOk(buildPathNotFoundFailure(outcome.spaceId, outcome.liveMarker, outcome.targetHash));
810
+ if (outcome.kind === "unsatisfiable") {
811
+ const structural = findPathWithDecision(outcome.targetMember.graph(), outcome.liveHash, memberTargetHash, { required: /* @__PURE__ */ new Set() });
806
812
  const structuralPath = structural.kind === "ok" ? structural.decision.selectedPath.map((edge) => ({
807
813
  dirName: edge.dirName,
808
814
  migrationHash: edge.migrationHash,
@@ -811,13 +817,13 @@ async function executeMigrationApply(options) {
811
817
  invariants: edge.invariants
812
818
  })) : [];
813
819
  throw errorNoInvariantPath({
814
- ...isAppMember && refName !== void 0 ? { refName } : {},
815
- required: targetInvariants,
816
- missing: walked.missing,
820
+ ...outcome.refName !== void 0 ? { refName: outcome.refName } : {},
821
+ required: outcome.targetInvariants,
822
+ missing: outcome.missing,
817
823
  structuralPath
818
824
  });
819
825
  }
820
- perSpacePlans.set(member.spaceId, walked.result);
826
+ perSpacePlans.set(member.spaceId, outcome.plan);
821
827
  }
822
828
  const canonicalOrder = [...aggregate.extensions.map((m) => m.spaceId), aggregate.app.spaceId];
823
829
  const applyOrder = canonicalOrder.filter((spaceId) => perSpacePlans.has(spaceId));
@@ -840,7 +846,7 @@ async function executeMigrationApply(options) {
840
846
  summary: totalSpaces === 0 ? "Already up to date — no contract spaces are loaded" : totalSpaces === 1 ? "Already up to date" : `Already up to date across ${totalSpaces} space(s)`
841
847
  }));
842
848
  }
843
- const applied = await applyMigration({
849
+ const applied = await runMigration({
844
850
  aggregate,
845
851
  perSpacePlans,
846
852
  applyOrder,
@@ -854,7 +860,7 @@ async function executeMigrationApply(options) {
854
860
  "destructive",
855
861
  "data"
856
862
  ] },
857
- action: "migrationApply",
863
+ action: "migrate",
858
864
  ...ifDefined("onProgress", onProgress)
859
865
  });
860
866
  if (!applied.ok) return notOk({
@@ -876,7 +882,7 @@ async function executeMigrationApply(options) {
876
882
  };
877
883
  });
878
884
  const perSpaceAll = buildPerSpaceBreakdown(orderedAll, aggregate.app.spaceId, { includeMarkers: true });
879
- const summary = `Applied ${applied.value.orderedResolutions.reduce((sum, r) => sum + (r.entry.migrationEdges?.length ?? 0), 0)} migration(s) (${applied.value.totalOpsExecuted} operation(s)) across ${orderedAll.length} contract space(s)`;
885
+ const summary = `Applied ${applied.value.orderedResolutions.reduce((sum, r) => sum + r.entry.migrationEdges.length, 0)} migration(s) (${applied.value.totalOpsExecuted} operation(s)) across ${orderedAll.length} contract space(s)`;
880
886
  return ok(buildSuccess({
881
887
  aggregate,
882
888
  orderedResolutions: orderedAll,
@@ -886,6 +892,79 @@ async function executeMigrationApply(options) {
886
892
  }));
887
893
  }
888
894
  /**
895
+ * Compute the graph-walk path for one contract-space member.
896
+ *
897
+ * Encapsulates the invariant-correct input assembly that both
898
+ * `executeMigrate` and `executeMigrateShowCommand` must use:
899
+ * - `currentMarker` carries the full live marker including `invariants`
900
+ * (not a stripped `{ storageHash, invariants: [] }` shell).
901
+ * - `targetInvariants` uses the caller-supplied `refInvariants` when a
902
+ * `--to` ref was resolved (not always the file head ref's invariants).
903
+ *
904
+ * Both callers map the returned `MemberPathOutcome` to their own error
905
+ * representation; the path-compute logic is shared and identical.
906
+ *
907
+ * @internal Exported for `executeMigrateShowCommand`.
908
+ */
909
+ function planMemberPath({ member, aggregate, targetHash, refInvariants, liveMarker, refName }) {
910
+ const isAppMember = member.spaceId === aggregate.app.spaceId;
911
+ const headRef = requireHeadRef(member);
912
+ if (member.graph().nodes.size === 0) {
913
+ const liveHash = liveMarker?.storageHash;
914
+ if (targetHash === liveHash || liveHash === void 0 && targetHash === EMPTY_CONTRACT_HASH) return {
915
+ kind: "at-head",
916
+ plan: buildAtHeadResolution({
917
+ aggregateTargetId: aggregate.targetId,
918
+ member,
919
+ targetHash,
920
+ liveMarker
921
+ })
922
+ };
923
+ return {
924
+ kind: "never-planned",
925
+ spaceId: member.spaceId,
926
+ targetHash
927
+ };
928
+ }
929
+ const targetInvariants = isAppMember && refInvariants !== void 0 ? refInvariants : headRef.invariants;
930
+ const targetMember = targetHash === headRef.hash && targetInvariants === headRef.invariants ? member : {
931
+ ...member,
932
+ headRef: {
933
+ hash: targetHash,
934
+ invariants: targetInvariants
935
+ }
936
+ };
937
+ const walked = graphWalkStrategy({
938
+ aggregateTargetId: aggregate.targetId,
939
+ member: targetMember,
940
+ currentMarker: liveMarker,
941
+ ...isAppMember && refName !== void 0 ? { refName } : {}
942
+ });
943
+ if (walked.kind === "unreachable") return {
944
+ kind: "unreachable",
945
+ spaceId: member.spaceId,
946
+ liveMarker,
947
+ targetHash
948
+ };
949
+ if (walked.kind === "unsatisfiable") {
950
+ const liveHash = liveMarker?.storageHash ?? EMPTY_CONTRACT_HASH;
951
+ return {
952
+ kind: "unsatisfiable",
953
+ spaceId: member.spaceId,
954
+ isAppMember,
955
+ missing: walked.missing,
956
+ targetInvariants,
957
+ targetMember,
958
+ liveHash,
959
+ refName
960
+ };
961
+ }
962
+ return {
963
+ kind: "ok",
964
+ plan: walked.result
965
+ };
966
+ }
967
+ /**
889
968
  * Build a zero-op {@link PerSpacePlan} for an empty-graph
890
969
  * member whose live marker already matches the target. Lets the apply
891
970
  * pipeline thread the member through `perSpacePlans` -> `applyOrder`
@@ -906,7 +985,11 @@ function buildAtHeadResolution(args) {
906
985
  displayOps: [],
907
986
  destinationContract: member.contract(),
908
987
  strategy: "graph-walk",
909
- migrationEdges: []
988
+ migrationEdges: [buildSynthMigrationEdge({
989
+ currentMarkerStorageHash: liveMarker?.storageHash,
990
+ destinationStorageHash: targetHash,
991
+ operationCount: 0
992
+ })]
910
993
  };
911
994
  }
912
995
  function sumPlannedOps(applyOrder, perSpacePlans) {
@@ -922,7 +1005,7 @@ function buildSuccess(args) {
922
1005
  const appResolution = args.orderedResolutions.find((r) => r.spaceId === args.aggregate.app.spaceId);
923
1006
  const appMarkerHash = appResolution?.entry.plan.destination.storageHash ?? requireHeadRef(args.aggregate.app).hash;
924
1007
  const applied = args.orderedResolutions.flatMap((r) => {
925
- return (r.entry.migrationEdges ?? []).map((edge) => ({
1008
+ return r.entry.migrationEdges.map((edge) => ({
926
1009
  spaceId: r.spaceId,
927
1010
  dirName: edge.dirName,
928
1011
  migrationHash: edge.migrationHash,
@@ -1064,6 +1147,18 @@ var ControlClientImpl = class {
1064
1147
  this.driver = null;
1065
1148
  }
1066
1149
  }
1150
+ /**
1151
+ * Construct the control adapter once for a migration operation and return
1152
+ * it, mirroring how the runtime plane builds the execution adapter once in
1153
+ * `createExecutionStack`. Only `dbInit` / `dbUpdate` need it (it lowers the
1154
+ * planner's DDL); read-only operations never build it. The descriptor is
1155
+ * optional on the stack — targets without migrations omit it.
1156
+ */
1157
+ buildControlAdapter() {
1158
+ this.init();
1159
+ if (!this.stack?.adapter) throw new Error(`Target "${this.options.target.targetId}" requires an adapter for migrations`);
1160
+ return this.stack.adapter.create(this.stack);
1161
+ }
1067
1162
  async ensureConnected() {
1068
1163
  this.init();
1069
1164
  if (!this.driver && this.defaultConnection !== void 0) await this.connect(this.defaultConnection);
@@ -1229,6 +1324,7 @@ var ControlClientImpl = class {
1229
1324
  await this.connectWithProgress(options.connection, "dbInit", onProgress);
1230
1325
  const { driver, familyInstance, frameworkComponents } = await this.ensureConnected();
1231
1326
  if (!hasMigrations(this.options.target)) throw new Error(`Target "${this.options.target.targetId}" does not support migrations`);
1327
+ const adapter = this.buildControlAdapter();
1232
1328
  let contract;
1233
1329
  try {
1234
1330
  contract = familyInstance.deserializeContract(options.contract);
@@ -1237,6 +1333,7 @@ var ControlClientImpl = class {
1237
1333
  }
1238
1334
  return executeDbInit({
1239
1335
  driver,
1336
+ adapter,
1240
1337
  familyInstance,
1241
1338
  contract,
1242
1339
  mode: options.mode,
@@ -1253,6 +1350,7 @@ var ControlClientImpl = class {
1253
1350
  await this.connectWithProgress(options.connection, "dbUpdate", onProgress);
1254
1351
  const { driver, familyInstance, frameworkComponents } = await this.ensureConnected();
1255
1352
  if (!hasMigrations(this.options.target)) throw new Error(`Target "${this.options.target.targetId}" does not support migrations`);
1353
+ const adapter = this.buildControlAdapter();
1256
1354
  let contract;
1257
1355
  try {
1258
1356
  contract = familyInstance.deserializeContract(options.contract);
@@ -1261,6 +1359,7 @@ var ControlClientImpl = class {
1261
1359
  }
1262
1360
  return executeDbUpdate({
1263
1361
  driver,
1362
+ adapter,
1264
1363
  familyInstance,
1265
1364
  contract,
1266
1365
  mode: options.mode,
@@ -1302,9 +1401,17 @@ var ControlClientImpl = class {
1302
1401
  const { driver, familyInstance } = await this.ensureConnected();
1303
1402
  return familyInstance.readAllMarkers({ driver });
1304
1403
  }
1305
- async migrationApply(options) {
1404
+ /** Reads the per-migration journal; omit `space` to return every space. */
1405
+ async readLedger(space) {
1406
+ const { driver, familyInstance } = await this.ensureConnected();
1407
+ return familyInstance.readLedger({
1408
+ driver,
1409
+ ...ifDefined("space", space)
1410
+ });
1411
+ }
1412
+ async migrate(options) {
1306
1413
  const { onProgress } = options;
1307
- await this.connectWithProgress(options.connection, "migrationApply", onProgress);
1414
+ await this.connectWithProgress(options.connection, "migrate", onProgress);
1308
1415
  const { driver, familyInstance, frameworkComponents } = await this.ensureConnected();
1309
1416
  if (!hasMigrations(this.options.target)) throw new Error(`Target "${this.options.target.targetId}" does not support migrations`);
1310
1417
  let contract;
@@ -1313,7 +1420,7 @@ var ControlClientImpl = class {
1313
1420
  } catch (error) {
1314
1421
  throw new ContractValidationError(error instanceof Error ? error.message : String(error), error);
1315
1422
  }
1316
- return executeMigrationApply({
1423
+ return executeMigrate({
1317
1424
  driver,
1318
1425
  familyInstance,
1319
1426
  contract,
@@ -1366,6 +1473,10 @@ var ControlClientImpl = class {
1366
1473
  this.init();
1367
1474
  if (this.familyInstance && hasPslContractInfer(this.familyInstance)) return this.familyInstance.inferPslContract(schemaIR);
1368
1475
  }
1476
+ getPslBlockDescriptors() {
1477
+ this.init();
1478
+ return this.stack.authoringContributions.pslBlockDescriptors;
1479
+ }
1369
1480
  toOperationPreview(operations) {
1370
1481
  this.init();
1371
1482
  if (this.familyInstance && hasOperationPreview(this.familyInstance)) return this.familyInstance.toOperationPreview(operations);
@@ -1383,8 +1494,11 @@ var ControlClientImpl = class {
1383
1494
  });
1384
1495
  try {
1385
1496
  const stack = this.stack;
1497
+ const extensionInputs = toExtensionInputs(blindCast(stack.extensionPacks));
1498
+ const composedExtensionContracts = new Map(extensionInputs.filter((p) => p.contractSpace !== void 0).map((p) => [p.id, blindCast(p.contractSpace.contractJson)]));
1386
1499
  const sourceContext = {
1387
1500
  composedExtensionPacks: stack.extensionPacks.map((p) => p.id),
1501
+ composedExtensionContracts,
1388
1502
  scalarTypeDescriptors: stack.scalarTypeDescriptors,
1389
1503
  authoringContributions: stack.authoringContributions,
1390
1504
  codecLookup: stack.codecLookup,
@@ -1444,8 +1558,9 @@ var ControlClientImpl = class {
1444
1558
  });
1445
1559
  try {
1446
1560
  const enrichedIR = enrichContract(contractRaw, this.frameworkComponents ?? []);
1561
+ let deserializedContract;
1447
1562
  try {
1448
- this.familyInstance.deserializeContract(enrichedIR);
1563
+ deserializedContract = this.familyInstance.deserializeContract(enrichedIR);
1449
1564
  } catch (error) {
1450
1565
  onProgress?.({
1451
1566
  action: "emit",
@@ -1460,7 +1575,7 @@ var ControlClientImpl = class {
1460
1575
  meta: void 0
1461
1576
  });
1462
1577
  }
1463
- const result = await emit(enrichedIR, this.stack, this.options.family.emission, { serializeContract: (contract) => this.options.target.contractSerializer.serializeContract(contract) });
1578
+ const result = await emit(deserializedContract, this.stack, this.options.family.emission, { serializeContract: (contract) => this.options.target.contractSerializer.serializeContract(contract) });
1464
1579
  onProgress?.({
1465
1580
  action: "emit",
1466
1581
  kind: "spanEnd",
@@ -1491,6 +1606,6 @@ var ControlClientImpl = class {
1491
1606
  }
1492
1607
  };
1493
1608
  //#endregion
1494
- export { ContractValidationError as a, executeDbInit as i, executeDbVerify as n, executeDbUpdate as r, createControlClient as t };
1609
+ export { executeDbInit as a, executeDbUpdate as i, planMemberPath as n, ContractValidationError as o, executeDbVerify as r, createControlClient as t };
1495
1610
 
1496
- //# sourceMappingURL=client-KgJorIvG.mjs.map
1611
+ //# sourceMappingURL=client-CJzuo5wX.mjs.map