@prisma-next/target-postgres 0.14.0-dev.39 → 0.14.0-dev.40

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 (106) hide show
  1. package/dist/{authoring-CZmSQriw.mjs → authoring-BX1WHIdN.mjs} +2 -2
  2. package/dist/authoring-BX1WHIdN.mjs.map +1 -0
  3. package/dist/contract-free.mjs +2 -2
  4. package/dist/control.d.mts.map +1 -1
  5. package/dist/control.mjs +633 -16
  6. package/dist/control.mjs.map +1 -1
  7. package/dist/{ddl-CGf6UABz.mjs → ddl-BmLIe1z_.mjs} +2 -2
  8. package/dist/{ddl-CGf6UABz.mjs.map → ddl-BmLIe1z_.mjs.map} +1 -1
  9. package/dist/{descriptor-meta-Du6olWQI.mjs → descriptor-meta-tjatyhtZ.mjs} +3 -3
  10. package/dist/{descriptor-meta-Du6olWQI.mjs.map → descriptor-meta-tjatyhtZ.mjs.map} +1 -1
  11. package/dist/{issue-planner-C-CwZd8D.mjs → issue-planner-DbFvaAgu.mjs} +5 -5
  12. package/dist/issue-planner-DbFvaAgu.mjs.map +1 -0
  13. package/dist/issue-planner.d.mts +1 -1
  14. package/dist/issue-planner.mjs +1 -1
  15. package/dist/migration.d.mts +2 -2
  16. package/dist/migration.mjs +2 -2
  17. package/dist/{op-factory-call-DPJR7tJc.d.mts → op-factory-call-CJWUxyUW.d.mts} +2 -2
  18. package/dist/{op-factory-call-DPJR7tJc.d.mts.map → op-factory-call-CJWUxyUW.d.mts.map} +1 -1
  19. package/dist/{op-factory-call-DArx_1HM.mjs → op-factory-call-t65c4jyY.mjs} +3 -3
  20. package/dist/op-factory-call-t65c4jyY.mjs.map +1 -0
  21. package/dist/op-factory-call.d.mts +1 -1
  22. package/dist/op-factory-call.mjs +1 -1
  23. package/dist/pack.d.mts +2 -2
  24. package/dist/pack.mjs +1 -1
  25. package/dist/{planner-BQ7lSqbm.mjs → planner-CG2pLHk-.mjs} +310 -126
  26. package/dist/planner-CG2pLHk-.mjs.map +1 -0
  27. package/dist/{planner-produced-postgres-migration-3ppG0t3i.mjs → planner-produced-postgres-migration-BolD0Mvc.mjs} +2 -2
  28. package/dist/{planner-produced-postgres-migration-3ppG0t3i.mjs.map → planner-produced-postgres-migration-BolD0Mvc.mjs.map} +1 -1
  29. package/dist/{planner-produced-postgres-migration-BauTSigX.d.mts → planner-produced-postgres-migration-Cz9--XOT.d.mts} +2 -2
  30. package/dist/{planner-produced-postgres-migration-BauTSigX.d.mts.map → planner-produced-postgres-migration-Cz9--XOT.d.mts.map} +1 -1
  31. package/dist/planner-produced-postgres-migration.d.mts +1 -1
  32. package/dist/planner-produced-postgres-migration.mjs +1 -1
  33. package/dist/{planner-sql-checks-CyjaoKhm.mjs → planner-sql-checks-DE9c4519.mjs} +2 -2
  34. package/dist/{planner-sql-checks-CyjaoKhm.mjs.map → planner-sql-checks-DE9c4519.mjs.map} +1 -1
  35. package/dist/planner-sql-checks.mjs +1 -1
  36. package/dist/planner.d.mts +73 -22
  37. package/dist/planner.d.mts.map +1 -1
  38. package/dist/planner.mjs +2 -2
  39. package/dist/{postgres-contract-view-CoRZewAp.mjs → postgres-contract-view-BegduLr6.mjs} +3 -3
  40. package/dist/{postgres-contract-view-CoRZewAp.mjs.map → postgres-contract-view-BegduLr6.mjs.map} +1 -1
  41. package/dist/postgres-database-schema-node-os8ogEap.d.mts +183 -0
  42. package/dist/postgres-database-schema-node-os8ogEap.d.mts.map +1 -0
  43. package/dist/{postgres-migration-BVjq0iFW.mjs → postgres-migration-BfMmK6tv.mjs} +3 -3
  44. package/dist/{postgres-migration-BVjq0iFW.mjs.map → postgres-migration-BfMmK6tv.mjs.map} +1 -1
  45. package/dist/{postgres-migration-UtGCjw5j.d.mts → postgres-migration-D7kNVWVG.d.mts} +2 -2
  46. package/dist/{postgres-migration-UtGCjw5j.d.mts.map → postgres-migration-D7kNVWVG.d.mts.map} +1 -1
  47. package/dist/{postgres-rls-policy-12wAEQhs.d.mts → postgres-rls-policy--CSddvMR.d.mts} +8 -16
  48. package/dist/postgres-rls-policy--CSddvMR.d.mts.map +1 -0
  49. package/dist/{postgres-schema-DLcc3W2-.mjs → postgres-schema-BLIHBEfX.mjs} +34 -64
  50. package/dist/postgres-schema-BLIHBEfX.mjs.map +1 -0
  51. package/dist/{postgres-schema-DJUEkWg-.d.mts → postgres-schema-BywoeKlt.d.mts} +9 -10
  52. package/dist/postgres-schema-BywoeKlt.d.mts.map +1 -0
  53. package/dist/postgres-table-schema-node-1nNc8XDT.mjs +248 -0
  54. package/dist/postgres-table-schema-node-1nNc8XDT.mjs.map +1 -0
  55. package/dist/resolve-ddl-schema-CL1RR1mx.mjs +20 -0
  56. package/dist/resolve-ddl-schema-CL1RR1mx.mjs.map +1 -0
  57. package/dist/runtime.mjs +1 -1
  58. package/dist/schema-ir-annotations.d.mts +9 -3
  59. package/dist/schema-ir-annotations.d.mts.map +1 -1
  60. package/dist/schema-ir-annotations.mjs +1 -1
  61. package/dist/types.d.mts +4 -4
  62. package/dist/types.mjs +3 -3
  63. package/package.json +20 -19
  64. package/src/core/authoring.ts +2 -2
  65. package/src/core/entity-kinds.ts +2 -2
  66. package/src/core/migrations/contract-to-postgres-database-schema-node.ts +125 -0
  67. package/src/core/migrations/diff-database-schema.ts +191 -0
  68. package/src/core/migrations/issue-planner.ts +1 -1
  69. package/src/core/migrations/op-factory-call.ts +1 -1
  70. package/src/core/migrations/operations/rls.ts +1 -1
  71. package/src/core/migrations/planner.ts +117 -68
  72. package/src/core/{schema-ir/postgres-schema-ir-annotations.ts → migrations/resolve-ddl-schema.ts} +8 -6
  73. package/src/core/migrations/runner.ts +13 -16
  74. package/src/core/migrations/verify-postgres-namespaces.ts +22 -14
  75. package/src/core/{schema-ir/postgres-rls-policy.ts → postgres-rls-policy.ts} +6 -43
  76. package/src/core/{schema-ir/postgres-role.ts → postgres-role.ts} +6 -21
  77. package/src/core/postgres-schema.ts +2 -2
  78. package/src/core/psl-infer/infer-psl-contract.ts +834 -0
  79. package/src/core/psl-infer/postgres-default-mapping.ts +16 -0
  80. package/src/core/psl-infer/postgres-type-map.ts +157 -0
  81. package/src/core/schema-ir/postgres-database-schema-node.ts +63 -0
  82. package/src/core/schema-ir/postgres-namespace-schema-node.ts +61 -0
  83. package/src/core/schema-ir/postgres-policy-schema-node.ts +93 -0
  84. package/src/core/schema-ir/postgres-role-schema-node.ts +66 -0
  85. package/src/core/schema-ir/{postgres-table-ir.ts → postgres-table-schema-node.ts} +29 -18
  86. package/src/core/schema-ir/schema-node-kinds.ts +28 -0
  87. package/src/exports/control.ts +30 -2
  88. package/src/exports/planner.ts +2 -5
  89. package/src/exports/schema-ir-annotations.ts +1 -1
  90. package/src/exports/types.ts +23 -15
  91. package/dist/authoring-CZmSQriw.mjs.map +0 -1
  92. package/dist/issue-planner-C-CwZd8D.mjs.map +0 -1
  93. package/dist/op-factory-call-DArx_1HM.mjs.map +0 -1
  94. package/dist/planner-BQ7lSqbm.mjs.map +0 -1
  95. package/dist/postgres-rls-policy-12wAEQhs.d.mts.map +0 -1
  96. package/dist/postgres-schema-DJUEkWg-.d.mts.map +0 -1
  97. package/dist/postgres-schema-DLcc3W2-.mjs.map +0 -1
  98. package/dist/postgres-schema-ir-BJl_a3J7.d.mts +0 -102
  99. package/dist/postgres-schema-ir-BJl_a3J7.d.mts.map +0 -1
  100. package/dist/postgres-schema-ir-I_FiUndw.mjs +0 -133
  101. package/dist/postgres-schema-ir-I_FiUndw.mjs.map +0 -1
  102. package/dist/postgres-schema-ir-annotations-BbDSiwx2.mjs +0 -14
  103. package/dist/postgres-schema-ir-annotations-BbDSiwx2.mjs.map +0 -1
  104. package/src/core/migrations/contract-to-postgres-schema-ir.ts +0 -91
  105. package/src/core/migrations/diff-postgres-schema.ts +0 -55
  106. package/src/core/schema-ir/postgres-schema-ir.ts +0 -138
@@ -2,9 +2,9 @@ import type { Contract } from '@prisma-next/contract/types';
2
2
  import type { SchemaIssue } from '@prisma-next/framework-components/control';
3
3
  import { UNBOUND_NAMESPACE_ID } from '@prisma-next/framework-components/ir';
4
4
  import type { SqlStorage } from '@prisma-next/sql-contract/types';
5
- import type { SqlSchemaIR } from '@prisma-next/sql-schema-ir/types';
5
+ import type { SqlSchemaIRNode } from '@prisma-next/sql-schema-ir/types';
6
6
  import { isPostgresSchema } from '../postgres-schema';
7
- import { isPostgresSchemaIR } from '../schema-ir/postgres-schema-ir';
7
+ import { PostgresDatabaseSchemaNode } from '../schema-ir/postgres-database-schema-node';
8
8
 
9
9
  /**
10
10
  * Resolves the live-database schema name for a given namespace
@@ -24,20 +24,23 @@ function resolveDdlSchemaName(storage: SqlStorage, namespaceId: string): string
24
24
  }
25
25
 
26
26
  /**
27
- * Reads the introspected list of schema names from a `PostgresSchemaIR`.
28
- * Defaults to the always-present `public` schema when the schema IR is not a
29
- * `PostgresSchemaIR` — a fresh Postgres database always carries `public`
30
- * (unless an operator dropped it manually), so any verifier path that runs
31
- * without an enriched introspection still suppresses the redundant
32
- * `CREATE SCHEMA "public"`.
27
+ * Reads the introspected list of schema names from the database-root schema
28
+ * node. `existingSchemas` is database-level, so it lives on the
29
+ * `PostgresDatabaseSchemaNode` root not on the per-schema namespace nodes.
30
+ *
31
+ * Defaults to the always-present `public` schema when the node is not the
32
+ * database root — a fresh Postgres database always carries `public` (unless an
33
+ * operator dropped it manually), so any verifier path that runs without an
34
+ * enriched introspection still suppresses the redundant `CREATE SCHEMA
35
+ * "public"`.
33
36
  *
34
37
  * Production introspection (`PostgresControlAdapter.introspect`) is the
35
38
  * authoritative source: it queries `pg_namespace` and sets `existingSchemas`
36
- * on the returned `PostgresSchemaIR`. Tests that want to assert against a
37
- * richer initial state construct a `PostgresSchemaIR` explicitly.
39
+ * on the returned root. Tests that want to assert against a richer initial
40
+ * state construct a `PostgresDatabaseSchemaNode` explicitly.
38
41
  */
39
- function existingSchemasFromSchema(schema: SqlSchemaIR): readonly string[] {
40
- if (isPostgresSchemaIR(schema)) {
42
+ function existingSchemasFromSchema(schema: SqlSchemaIRNode): readonly string[] {
43
+ if (PostgresDatabaseSchemaNode.is(schema)) {
41
44
  return schema.existingSchemas;
42
45
  }
43
46
  return ['public'];
@@ -45,7 +48,11 @@ function existingSchemasFromSchema(schema: SqlSchemaIR): readonly string[] {
45
48
 
46
49
  /**
47
50
  * Emits a `missing_schema` issue for every contract-declared Postgres
48
- * namespace whose live container does not yet exist.
51
+ * namespace whose live container does not yet exist. The planner's
52
+ * `collectSchemaIssues` prepends these to the relational findings so a
53
+ * multi-schema plan emits `CREATE SCHEMA` before the tables that need it —
54
+ * a planner-only concern (verify already rejects via the `missing_table` a
55
+ * missing schema produces), so this is not part of the shared diff.
49
56
  *
50
57
  * A namespace's live container is the schema returned by its
51
58
  * polymorphic `ddlSchemaName(storage)` method — named schemas resolve
@@ -63,7 +70,7 @@ function existingSchemasFromSchema(schema: SqlSchemaIR): readonly string[] {
63
70
  */
64
71
  export function verifyPostgresNamespacePresence(input: {
65
72
  readonly contract: Contract<SqlStorage>;
66
- readonly schema: SqlSchemaIR;
73
+ readonly schema: SqlSchemaIRNode;
67
74
  }): readonly SchemaIssue[] {
68
75
  const { contract, schema } = input;
69
76
  const existing = new Set(existingSchemasFromSchema(schema));
@@ -76,6 +83,7 @@ export function verifyPostgresNamespacePresence(input: {
76
83
  if (existing.has(ddlName)) continue;
77
84
  issues.push({
78
85
  kind: 'missing_schema',
86
+ reason: 'not-found',
79
87
  namespaceId,
80
88
  message: `Schema "${ddlName}" is missing from database`,
81
89
  });
@@ -1,4 +1,3 @@
1
- import type { DiffableNode } from '@prisma-next/framework-components/control';
2
1
  import { freezeNode } from '@prisma-next/framework-components/ir';
3
2
  import { SqlNode } from '@prisma-next/sql-contract/types';
4
3
 
@@ -25,7 +24,11 @@ export interface PostgresRlsPolicyInput {
25
24
  }
26
25
 
27
26
  /**
28
- * Postgres IR class for a row-level security policy (`CREATE POLICY … ON …`).
27
+ * Postgres contract-IR class for a row-level security policy (`CREATE POLICY … ON …`).
28
+ *
29
+ * This is an authored, serialized Contract-IR entity — it is registered as an entity
30
+ * kind, extends `SqlNode`, and is stored in `contract.json`. It is NOT a DiffableNode;
31
+ * the schema-diff tree uses `PostgresPolicySchemaNode` for that role.
29
32
  *
30
33
  * Target-only concept — no SQL-family abstract. Extends `SqlNode` directly.
31
34
  * Frozen at construction via `freezeNode(this)`. The `kind: 'policy'`
@@ -33,7 +36,7 @@ export interface PostgresRlsPolicyInput {
33
36
  * survives JSON serialization and enables dispatch. The literal matches the
34
37
  * entries key (one-string rule: node.kind === entries key === entity kind).
35
38
  */
36
- export class PostgresRlsPolicy extends SqlNode implements DiffableNode {
39
+ export class PostgresRlsPolicy extends SqlNode {
37
40
  override readonly kind = 'policy' as const;
38
41
  readonly name: string;
39
42
  readonly prefix: string;
@@ -58,44 +61,4 @@ export class PostgresRlsPolicy extends SqlNode implements DiffableNode {
58
61
  this.permissive = input.permissive;
59
62
  freezeNode(this);
60
63
  }
61
-
62
- get id(): string {
63
- return this.name;
64
- }
65
-
66
- children(): readonly DiffableNode[] {
67
- return [];
68
- }
69
-
70
- /**
71
- * Equality by wire name only. The wire name is `<prefix>_<sha256(body)[0..8]>`,
72
- * so name-equality IS body-equality — two policies with different bodies
73
- * have different hashes and therefore different names. We deliberately
74
- * skip comparing bodies directly because Postgres reprints predicate
75
- * expressions (e.g. strips outer parentheses), so a byte-compare against
76
- * the authored body would produce false mismatches on a clean re-verify.
77
- */
78
- isEqualTo(other: DiffableNode): boolean {
79
- if (!isPostgresRlsPolicy(other)) {
80
- throw new Error(
81
- `PostgresRlsPolicy.isEqualTo: expected a PostgresRlsPolicy, got ${other.constructor?.name ?? typeof other}`,
82
- );
83
- }
84
- return this.name === other.name;
85
- }
86
- }
87
-
88
- export function isPostgresRlsPolicy(node: DiffableNode | undefined): node is PostgresRlsPolicy {
89
- return node !== undefined && 'kind' in node && node.kind === 'policy';
90
- }
91
-
92
- export function assertPostgresRlsPolicy(
93
- node: DiffableNode | undefined,
94
- ): asserts node is PostgresRlsPolicy {
95
- if (!isPostgresRlsPolicy(node)) {
96
- const kind = node !== undefined && 'kind' in node ? String(node.kind) : typeof node;
97
- throw new Error(
98
- `planPostgresSchemaDiff: expected a PostgresRlsPolicy on the policy-diff path but got ${kind}`,
99
- );
100
- }
101
64
  }
@@ -1,4 +1,3 @@
1
- import type { DiffableNode } from '@prisma-next/framework-components/control';
2
1
  import { freezeNode } from '@prisma-next/framework-components/ir';
3
2
  import { SqlNode } from '@prisma-next/sql-contract/types';
4
3
 
@@ -12,7 +11,11 @@ export interface PostgresRoleInput {
12
11
  }
13
12
 
14
13
  /**
15
- * Postgres IR class for a database role (`CREATE ROLE …`).
14
+ * Postgres contract-IR class for a database role (`CREATE ROLE …`).
15
+ *
16
+ * This is an authored, serialized Contract-IR entity — it is registered as an entity
17
+ * kind, extends `SqlNode`, and is stored in `contract.json`. It is NOT a DiffableNode;
18
+ * the schema-diff tree uses `PostgresRoleSchemaNode` for that role.
16
19
  *
17
20
  * Roles are cluster-scoped, so their namespace coordinate is always
18
21
  * `UNBOUND_NAMESPACE_ID`. Target-only concept — no SQL-family abstract.
@@ -20,7 +23,7 @@ export interface PostgresRoleInput {
20
23
  * The `kind: 'role'` discriminant is enumerable so it survives JSON.
21
24
  * Matches the entries key (one-string rule).
22
25
  */
23
- export class PostgresRole extends SqlNode implements DiffableNode {
26
+ export class PostgresRole extends SqlNode {
24
27
  override readonly kind = 'role' as const;
25
28
  readonly name: string;
26
29
  readonly namespaceId: string;
@@ -31,22 +34,4 @@ export class PostgresRole extends SqlNode implements DiffableNode {
31
34
  this.namespaceId = input.namespaceId;
32
35
  freezeNode(this);
33
36
  }
34
-
35
- /** Roles are cluster-unique; the name alone is sufficient as the id. */
36
- get id(): string {
37
- return this.name;
38
- }
39
-
40
- children(): readonly DiffableNode[] {
41
- return [];
42
- }
43
-
44
- isEqualTo(other: DiffableNode): boolean {
45
- if (!(other instanceof PostgresRole)) {
46
- throw new Error(
47
- `PostgresRole.isEqualTo: expected a PostgresRole, got ${other.constructor?.name ?? typeof other}`,
48
- );
49
- }
50
- return this.name === other.name;
51
- }
52
37
  }
@@ -20,8 +20,8 @@ import { ifDefined } from '@prisma-next/utils/defined';
20
20
  import { PostgresTableSource } from './ast/table-source';
21
21
  import { PG_TEXT_CODEC_ID } from './codec-ids';
22
22
  import { policyEntityKind, roleEntityKind } from './entity-kinds';
23
- import type { PostgresRlsPolicy } from './schema-ir/postgres-rls-policy';
24
- import type { PostgresRole } from './schema-ir/postgres-role';
23
+ import type { PostgresRlsPolicy } from './postgres-rls-policy';
24
+ import type { PostgresRole } from './postgres-role';
25
25
  import { escapeLiteral } from './sql-utils';
26
26
 
27
27
  export type PostgresContract = Contract<SqlStorage> & { readonly target: 'postgres' };