@supabase/pg-delta 1.0.0-alpha.10 → 1.0.0-alpha.11

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 (123) hide show
  1. package/dist/cli/commands/declarative-export.js +12 -17
  2. package/dist/cli/commands/plan.js +10 -13
  3. package/dist/cli/commands/sync.js +8 -12
  4. package/dist/cli/utils/integrations.d.ts +30 -6
  5. package/dist/cli/utils/integrations.js +98 -6
  6. package/dist/core/change-utils.d.ts +9 -0
  7. package/dist/core/change-utils.js +71 -0
  8. package/dist/core/change.types.d.ts +22 -0
  9. package/dist/core/change.types.js +37 -1
  10. package/dist/core/depend.js +25 -0
  11. package/dist/core/export/file-mapper.d.ts +2 -2
  12. package/dist/core/integrations/filter/dsl.d.ts +78 -74
  13. package/dist/core/integrations/filter/dsl.js +127 -79
  14. package/dist/core/integrations/filter/flatten.d.ts +51 -0
  15. package/dist/core/integrations/filter/flatten.js +116 -0
  16. package/dist/core/integrations/integration-dsl.d.ts +17 -1
  17. package/dist/core/integrations/merge.d.ts +20 -0
  18. package/dist/core/integrations/merge.js +60 -0
  19. package/dist/core/integrations/serialize/dsl.d.ts +7 -4
  20. package/dist/core/integrations/serialize/dsl.js +2 -2
  21. package/dist/core/integrations/supabase.js +23 -8
  22. package/dist/core/objects/aggregate/changes/aggregate.types.d.ts +1 -0
  23. package/dist/core/objects/base.change.d.ts +10 -0
  24. package/dist/core/objects/base.change.js +10 -0
  25. package/dist/core/objects/base.model.d.ts +4 -1
  26. package/dist/core/objects/base.model.js +5 -2
  27. package/dist/core/objects/collation/changes/collation.types.d.ts +1 -0
  28. package/dist/core/objects/domain/changes/domain.create.d.ts +1 -1
  29. package/dist/core/objects/domain/changes/domain.create.js +7 -1
  30. package/dist/core/objects/domain/changes/domain.types.d.ts +1 -0
  31. package/dist/core/objects/event-trigger/changes/event-trigger.types.d.ts +1 -0
  32. package/dist/core/objects/extension/changes/extension.types.d.ts +1 -0
  33. package/dist/core/objects/foreign-data-wrapper/foreign-data-wrapper/changes/foreign-data-wrapper.types.d.ts +1 -0
  34. package/dist/core/objects/foreign-data-wrapper/foreign-data-wrapper.types.d.ts +1 -0
  35. package/dist/core/objects/foreign-data-wrapper/foreign-table/changes/foreign-table.types.d.ts +1 -0
  36. package/dist/core/objects/foreign-data-wrapper/server/changes/server.types.d.ts +1 -0
  37. package/dist/core/objects/foreign-data-wrapper/user-mapping/changes/user-mapping.types.d.ts +1 -0
  38. package/dist/core/objects/index/changes/index.types.d.ts +1 -0
  39. package/dist/core/objects/language/changes/language.types.d.ts +1 -0
  40. package/dist/core/objects/materialized-view/changes/materialized-view.types.d.ts +1 -0
  41. package/dist/core/objects/procedure/changes/procedure.types.d.ts +1 -0
  42. package/dist/core/objects/publication/changes/publication.types.d.ts +1 -0
  43. package/dist/core/objects/rls-policy/changes/rls-policy.types.d.ts +1 -0
  44. package/dist/core/objects/role/changes/role.types.d.ts +1 -0
  45. package/dist/core/objects/rule/changes/rule.types.d.ts +1 -0
  46. package/dist/core/objects/schema/changes/schema.types.d.ts +1 -0
  47. package/dist/core/objects/sequence/changes/sequence.types.d.ts +1 -0
  48. package/dist/core/objects/subscription/changes/subscription.types.d.ts +1 -0
  49. package/dist/core/objects/table/changes/table.types.d.ts +1 -0
  50. package/dist/core/objects/trigger/changes/trigger.types.d.ts +1 -0
  51. package/dist/core/objects/type/composite-type/changes/composite-type.types.d.ts +1 -0
  52. package/dist/core/objects/type/enum/changes/enum.types.d.ts +1 -0
  53. package/dist/core/objects/type/range/changes/range.types.d.ts +1 -0
  54. package/dist/core/objects/type/type.types.d.ts +1 -0
  55. package/dist/core/objects/view/changes/view.types.d.ts +1 -0
  56. package/dist/core/objects/view/view.diff.js +24 -13
  57. package/dist/core/postgres-config.d.ts +2 -2
  58. package/dist/core/sort/custom-constraints.js +1 -1
  59. package/dist/core/sort/logical-sort.js +3 -24
  60. package/package.json +5 -1
  61. package/src/cli/commands/declarative-export.ts +19 -27
  62. package/src/cli/commands/plan.ts +14 -20
  63. package/src/cli/commands/sync.ts +8 -15
  64. package/src/cli/utils/integrations.test.ts +210 -3
  65. package/src/cli/utils/integrations.ts +134 -6
  66. package/src/core/catalog.snapshot.test.ts +11 -2
  67. package/src/core/change-utils.test.ts +61 -0
  68. package/src/core/change-utils.ts +73 -0
  69. package/src/core/change.types.ts +50 -0
  70. package/src/core/depend.ts +25 -0
  71. package/src/core/export/file-mapper.ts +7 -2
  72. package/src/core/integrations/filter/dsl.test.ts +299 -60
  73. package/src/core/integrations/filter/dsl.ts +208 -169
  74. package/src/core/integrations/filter/flatten.test.ts +282 -0
  75. package/src/core/integrations/filter/flatten.ts +150 -0
  76. package/src/core/integrations/integration-dsl.ts +17 -1
  77. package/src/core/integrations/merge.test.ts +128 -0
  78. package/src/core/integrations/merge.ts +72 -0
  79. package/src/core/integrations/serialize/dsl.test.ts +6 -6
  80. package/src/core/integrations/serialize/dsl.ts +7 -4
  81. package/src/core/integrations/supabase.ts +23 -8
  82. package/src/core/objects/aggregate/changes/aggregate.types.ts +1 -0
  83. package/src/core/objects/base.change.ts +10 -0
  84. package/src/core/objects/base.model.test.ts +43 -0
  85. package/src/core/objects/base.model.ts +5 -2
  86. package/src/core/objects/collation/changes/collation.types.ts +1 -0
  87. package/src/core/objects/domain/changes/domain.create.ts +17 -1
  88. package/src/core/objects/domain/changes/domain.types.ts +1 -0
  89. package/src/core/objects/event-trigger/changes/event-trigger.types.ts +1 -0
  90. package/src/core/objects/extension/changes/extension.types.ts +1 -0
  91. package/src/core/objects/foreign-data-wrapper/foreign-data-wrapper/changes/foreign-data-wrapper.types.ts +1 -0
  92. package/src/core/objects/foreign-data-wrapper/foreign-data-wrapper.types.ts +1 -0
  93. package/src/core/objects/foreign-data-wrapper/foreign-table/changes/foreign-table.types.ts +1 -0
  94. package/src/core/objects/foreign-data-wrapper/server/changes/server.types.ts +1 -0
  95. package/src/core/objects/foreign-data-wrapper/user-mapping/changes/user-mapping.types.ts +1 -0
  96. package/src/core/objects/index/changes/index.types.ts +1 -0
  97. package/src/core/objects/language/changes/language.types.ts +1 -0
  98. package/src/core/objects/materialized-view/changes/materialized-view.types.ts +1 -0
  99. package/src/core/objects/procedure/changes/procedure.types.ts +1 -0
  100. package/src/core/objects/publication/changes/publication.types.ts +1 -0
  101. package/src/core/objects/rls-policy/changes/rls-policy.types.ts +1 -0
  102. package/src/core/objects/role/changes/role.types.ts +1 -0
  103. package/src/core/objects/rule/changes/rule.types.ts +1 -0
  104. package/src/core/objects/schema/changes/schema.types.ts +1 -0
  105. package/src/core/objects/sequence/changes/sequence.types.ts +1 -0
  106. package/src/core/objects/subscription/changes/subscription.types.ts +1 -0
  107. package/src/core/objects/table/changes/table.types.ts +1 -0
  108. package/src/core/objects/trigger/changes/trigger.types.ts +1 -0
  109. package/src/core/objects/type/composite-type/changes/composite-type.types.ts +1 -0
  110. package/src/core/objects/type/enum/changes/enum.types.ts +1 -0
  111. package/src/core/objects/type/range/changes/range.types.ts +1 -0
  112. package/src/core/objects/type/type.types.ts +1 -0
  113. package/src/core/objects/view/changes/view.types.ts +1 -0
  114. package/src/core/objects/view/view.diff.test.ts +96 -0
  115. package/src/core/objects/view/view.diff.ts +30 -15
  116. package/src/core/postgres-config.ts +2 -2
  117. package/src/core/sort/custom-constraints.ts +1 -1
  118. package/src/core/sort/logical-sort.ts +3 -27
  119. package/src/typedoc.ts +248 -0
  120. package/dist/core/integrations/filter/extractors.d.ts +0 -12
  121. package/dist/core/integrations/filter/extractors.js +0 -178
  122. package/src/core/integrations/filter/extractors.test.ts +0 -244
  123. package/src/core/integrations/filter/extractors.ts +0 -187
@@ -0,0 +1,61 @@
1
+ import { describe, expect, test } from "bun:test";
2
+ import type { Change } from "./change.types.ts";
3
+ import { getSchema } from "./change-utils.ts";
4
+
5
+ describe("getSchema", () => {
6
+ test("returns schema for table", () => {
7
+ const change = {
8
+ objectType: "table",
9
+ table: { schema: "public" },
10
+ } as unknown as Change;
11
+ expect(getSchema(change)).toBe("public");
12
+ });
13
+
14
+ test("returns schema for view", () => {
15
+ const change = {
16
+ objectType: "view",
17
+ view: { schema: "app" },
18
+ } as unknown as Change;
19
+ expect(getSchema(change)).toBe("app");
20
+ });
21
+
22
+ test("returns schema for enum", () => {
23
+ const change = {
24
+ objectType: "enum",
25
+ enum: { schema: "types" },
26
+ } as unknown as Change;
27
+ expect(getSchema(change)).toBe("types");
28
+ });
29
+
30
+ test("returns schema.name for schema type", () => {
31
+ const change = {
32
+ objectType: "schema",
33
+ schema: { name: "auth" },
34
+ } as unknown as Change;
35
+ expect(getSchema(change)).toBe("auth");
36
+ });
37
+
38
+ test("returns null for role", () => {
39
+ const change = {
40
+ objectType: "role",
41
+ role: { name: "admin" },
42
+ } as unknown as Change;
43
+ expect(getSchema(change)).toBeNull();
44
+ });
45
+
46
+ test("returns null for publication", () => {
47
+ const change = {
48
+ objectType: "publication",
49
+ publication: { name: "pub1" },
50
+ } as unknown as Change;
51
+ expect(getSchema(change)).toBeNull();
52
+ });
53
+
54
+ test("returns null for language", () => {
55
+ const change = {
56
+ objectType: "language",
57
+ language: { name: "plpgsql" },
58
+ } as unknown as Change;
59
+ expect(getSchema(change)).toBeNull();
60
+ });
61
+ });
@@ -0,0 +1,73 @@
1
+ import type { Change } from "./change.types.ts";
2
+
3
+ /**
4
+ * Extract the schema name from a Change using the model sub-object.
5
+ *
6
+ * This is a convenience function used by the filter DSL (for schema
7
+ * normalization) and the sort module. It reads the `schema` (or `name`
8
+ * for schema objectType) from the model sub-object.
9
+ */
10
+ export function getSchema(change: Change): string | null {
11
+ if (change.scope === "default_privilege") {
12
+ return change.inSchema;
13
+ }
14
+ switch (change.objectType) {
15
+ case "aggregate":
16
+ return change.aggregate.schema;
17
+ case "collation":
18
+ return change.collation.schema;
19
+ case "composite_type":
20
+ return change.compositeType.schema;
21
+ case "domain":
22
+ return change.domain.schema;
23
+ case "enum":
24
+ return change.enum.schema;
25
+ case "event_trigger":
26
+ return change.eventTrigger.function_schema;
27
+ case "extension":
28
+ return change.extension.schema;
29
+ case "index":
30
+ return change.index.schema;
31
+ case "language":
32
+ return null;
33
+ case "materialized_view":
34
+ return change.materializedView.schema;
35
+ case "procedure":
36
+ return change.procedure.schema;
37
+ case "publication":
38
+ return null;
39
+ case "range":
40
+ return change.range.schema;
41
+ case "rls_policy":
42
+ return change.policy.schema;
43
+ case "role":
44
+ return null;
45
+ case "rule":
46
+ return change.rule.schema;
47
+ case "schema":
48
+ return change.schema.name;
49
+ case "sequence":
50
+ return change.sequence.schema;
51
+ case "subscription":
52
+ return null;
53
+ case "table":
54
+ return change.table.schema;
55
+ case "trigger":
56
+ return change.trigger.schema;
57
+ case "view":
58
+ return change.view.schema;
59
+ case "foreign_data_wrapper":
60
+ return null;
61
+ case "server":
62
+ return null;
63
+ case "user_mapping":
64
+ return null;
65
+ case "foreign_table":
66
+ return change.foreignTable.schema;
67
+ default: {
68
+ // exhaustiveness check
69
+ const _exhaustive: never = change;
70
+ return _exhaustive;
71
+ }
72
+ }
73
+ }
@@ -20,6 +20,16 @@ import type { TriggerChange } from "./objects/trigger/changes/trigger.types.ts";
20
20
  import type { TypeChange } from "./objects/type/type.types.ts";
21
21
  import type { ViewChange } from "./objects/view/changes/view.types.ts";
22
22
 
23
+ /**
24
+ * Discriminated union of all PostgreSQL object change types.
25
+ *
26
+ * Every member shares a common `objectType` discriminant (e.g. `"table"`,
27
+ * `"view"`, `"role"`) that the filter DSL pattern-matches against. Use
28
+ * {@link OBJECT_TYPE_TO_PROPERTY_KEY} to map an `objectType` value to the
29
+ * corresponding JS property key on the Change instance.
30
+ *
31
+ * @category Change Types
32
+ */
23
33
  export type Change =
24
34
  | AggregateChange
25
35
  | CollationChange
@@ -42,3 +52,43 @@ export type Change =
42
52
  | TypeChange
43
53
  | ViewChange
44
54
  | ForeignDataWrapperChange;
55
+
56
+ /**
57
+ * Exhaustive map from every `objectType` discriminant value to the JS property
58
+ * key that holds the model sub-object on the corresponding {@link Change}.
59
+ *
60
+ * Used internally by the filter DSL flattening logic to locate nested
61
+ * properties and expose them as `<objectType>/<field>` paths.
62
+ *
63
+ * @category Change Types
64
+ */
65
+ export const OBJECT_TYPE_TO_PROPERTY_KEY: {
66
+ [K in Change["objectType"]]: string;
67
+ } = {
68
+ aggregate: "aggregate",
69
+ collation: "collation",
70
+ composite_type: "compositeType",
71
+ domain: "domain",
72
+ enum: "enum",
73
+ event_trigger: "eventTrigger",
74
+ extension: "extension",
75
+ foreign_data_wrapper: "foreignDataWrapper",
76
+ foreign_table: "foreignTable",
77
+ index: "index",
78
+ language: "language",
79
+ materialized_view: "materializedView",
80
+ procedure: "procedure",
81
+ publication: "publication",
82
+ range: "range",
83
+ rls_policy: "policy",
84
+ role: "role",
85
+ rule: "rule",
86
+ schema: "schema",
87
+ sequence: "sequence",
88
+ server: "server",
89
+ subscription: "subscription",
90
+ table: "table",
91
+ trigger: "trigger",
92
+ user_mapping: "userMapping",
93
+ view: "view",
94
+ };
@@ -1420,6 +1420,29 @@ export async function extractDepends(pool: Pool): Promise<PgDepend[]> {
1420
1420
  JOIN pg_namespace ns ON ns.oid = idx_rel.relnamespace
1421
1421
  WHERE idx_rel.relkind = 'i'
1422
1422
  ),
1423
+ index_extension_deps AS (
1424
+ -- Indexes depend on extensions that provide their operator classes
1425
+ -- (e.g. gin_trgm_ops from pg_trgm). Without this, CREATE INDEX can be
1426
+ -- ordered before CREATE EXTENSION when schemas sort alphabetically.
1427
+ SELECT DISTINCT
1428
+ format('index:%I.%I.%I', ns.nspname, tbl.relname, idx_rel.relname) AS dependent_stable_id,
1429
+ format('extension:%I', ext.extname) AS referenced_stable_id,
1430
+ 'n'::"char" AS deptype,
1431
+ ns.nspname AS dep_schema,
1432
+ NULL::text AS ref_schema
1433
+ FROM pg_class idx_rel
1434
+ JOIN pg_index idx ON idx.indexrelid = idx_rel.oid
1435
+ JOIN pg_class tbl ON tbl.oid = idx.indrelid
1436
+ JOIN pg_namespace ns ON ns.oid = idx_rel.relnamespace
1437
+ JOIN LATERAL unnest(idx.indclass) WITH ORDINALITY AS oc(oid, ord) ON true
1438
+ JOIN pg_opclass opcl ON opcl.oid = oc.oid
1439
+ JOIN pg_depend d ON d.classid = 'pg_opclass'::regclass
1440
+ AND d.objid = opcl.oid
1441
+ AND d.refclassid = 'pg_extension'::regclass
1442
+ AND d.deptype = 'e'
1443
+ JOIN pg_extension ext ON ext.oid = d.refobjid
1444
+ WHERE idx_rel.relkind IN ('i', 'I')
1445
+ ),
1423
1446
  ownership_deps AS (
1424
1447
  -- Schema ownership dependencies
1425
1448
  SELECT DISTINCT
@@ -1833,6 +1856,8 @@ export async function extractDepends(pool: Pool): Promise<PgDepend[]> {
1833
1856
  UNION ALL
1834
1857
  SELECT dependent_stable_id, referenced_stable_id, deptype, dep_schema, ref_schema FROM index_table_deps
1835
1858
  UNION ALL
1859
+ SELECT dependent_stable_id, referenced_stable_id, deptype, dep_schema, ref_schema FROM index_extension_deps
1860
+ UNION ALL
1836
1861
  SELECT dependent_stable_id, referenced_stable_id, deptype, dep_schema, ref_schema FROM ownership_deps
1837
1862
  UNION ALL
1838
1863
  SELECT dependent_stable_id, referenced_stable_id, deptype, dep_schema, ref_schema FROM publication_deps
@@ -9,7 +9,12 @@ import {
9
9
  getObjectSchema,
10
10
  getParentInfo,
11
11
  } from "../plan/serialize.ts";
12
- import type { FileCategory, FilePath, Grouping } from "./types.ts";
12
+ import type {
13
+ FileCategory,
14
+ FilePath,
15
+ Grouping,
16
+ GroupingPattern,
17
+ } from "./types.ts";
13
18
 
14
19
  const debugExport = createDebug("pg-delta:export");
15
20
 
@@ -380,7 +385,7 @@ interface CompilePatternsResult {
380
385
  * Any skipped patterns are reported in `warnings`.
381
386
  */
382
387
  export function compilePatterns(
383
- patterns: import("./types.ts").GroupingPattern[],
388
+ patterns: GroupingPattern[],
384
389
  ): CompilePatternsResult {
385
390
  const compiled: CompiledPattern[] = [];
386
391
  const warnings: string[] = [];