@prisma-next/family-sql 0.4.2 → 0.4.3
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.
- package/README.md +2 -2
- package/dist/control-adapter.d.mts +12 -1
- package/dist/control-adapter.d.mts.map +1 -1
- package/dist/control.d.mts +3 -2
- package/dist/control.d.mts.map +1 -1
- package/dist/control.mjs +1025 -11
- package/dist/control.mjs.map +1 -1
- package/dist/migration.d.mts +14 -2
- package/dist/migration.d.mts.map +1 -1
- package/dist/migration.mjs +16 -1
- package/dist/migration.mjs.map +1 -1
- package/dist/schema-verify.d.mts +2 -2
- package/dist/{types-C6K4mxDM.d.mts → types-gLyIyd2X.d.mts} +36 -11
- package/dist/types-gLyIyd2X.d.mts.map +1 -0
- package/dist/verify-BdES8wgQ.mjs +82 -0
- package/dist/verify-BdES8wgQ.mjs.map +1 -0
- package/dist/verify-sql-schema-Ovz7RXR5.mjs.map +1 -1
- package/dist/{verify-sql-schema-BBhkqEDo.d.mts → verify-sql-schema-_EoNcGIq.d.mts} +2 -2
- package/dist/{verify-sql-schema-BBhkqEDo.d.mts.map → verify-sql-schema-_EoNcGIq.d.mts.map} +1 -1
- package/dist/verify.d.mts +16 -20
- package/dist/verify.d.mts.map +1 -1
- package/dist/verify.mjs +2 -2
- package/package.json +20 -20
- package/src/core/control-adapter.ts +12 -0
- package/src/core/control-instance.ts +43 -15
- package/src/core/migrations/plan-helpers.ts +1 -0
- package/src/core/migrations/types.ts +29 -6
- package/src/core/operation-preview.ts +62 -0
- package/src/core/psl-contract-infer/default-mapping.ts +56 -0
- package/src/core/psl-contract-infer/name-transforms.ts +178 -0
- package/src/core/psl-contract-infer/postgres-default-mapping.ts +16 -0
- package/src/core/psl-contract-infer/postgres-type-map.ts +165 -0
- package/src/core/psl-contract-infer/printer-config.ts +55 -0
- package/src/core/psl-contract-infer/raw-default-parser.ts +91 -0
- package/src/core/psl-contract-infer/relation-inference.ts +196 -0
- package/src/core/psl-contract-infer/sql-schema-ir-to-psl-ast.ts +832 -0
- package/src/core/sql-migration.ts +16 -1
- package/src/core/verify.ts +46 -108
- package/src/exports/verify.ts +1 -1
- package/dist/types-C6K4mxDM.d.mts.map +0 -1
- package/dist/verify-4GshvY4p.mjs +0 -122
- package/dist/verify-4GshvY4p.mjs.map +0 -1
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
import { deriveProvidedInvariants } from '@prisma-next/migration-tools/invariants';
|
|
1
2
|
import { Migration } from '@prisma-next/migration-tools/migration';
|
|
2
3
|
import type { AnySqlMigrationOperation, SqlPlanTargetDetails } from './migrations/types';
|
|
3
4
|
|
|
@@ -31,4 +32,18 @@ import type { AnySqlMigrationOperation, SqlPlanTargetDetails } from './migration
|
|
|
31
32
|
export abstract class SqlMigration<
|
|
32
33
|
TDetails extends SqlPlanTargetDetails,
|
|
33
34
|
TTargetId extends string = string,
|
|
34
|
-
> extends Migration<AnySqlMigrationOperation<TDetails>, 'sql', TTargetId> {
|
|
35
|
+
> extends Migration<AnySqlMigrationOperation<TDetails>, 'sql', TTargetId> {
|
|
36
|
+
/**
|
|
37
|
+
* Sorted, deduplicated invariant ids declared by this migration's
|
|
38
|
+
* data-transform ops. Derived from `this.operations` so the field remains
|
|
39
|
+
* consistent with the operation list — planner-built plans (`db init`,
|
|
40
|
+
* `db update`) yield `[]` because they emit no data-transform ops.
|
|
41
|
+
*
|
|
42
|
+
* Required by `SqlMigrationPlan.providedInvariants` (tightened from
|
|
43
|
+
* optional at the SQL-family layer); the framework-level
|
|
44
|
+
* `MigrationPlan.providedInvariants?` stays optional.
|
|
45
|
+
*/
|
|
46
|
+
get providedInvariants(): readonly string[] {
|
|
47
|
+
return deriveProvidedInvariants(this.operations);
|
|
48
|
+
}
|
|
49
|
+
}
|
package/src/core/verify.ts
CHANGED
|
@@ -1,5 +1,4 @@
|
|
|
1
1
|
import type { ContractMarkerRecord } from '@prisma-next/contract/types';
|
|
2
|
-
import type { ControlDriverInstance } from '@prisma-next/framework-components/control';
|
|
3
2
|
import { type } from 'arktype';
|
|
4
3
|
|
|
5
4
|
const MetaSchema = type({ '[string]': 'unknown' });
|
|
@@ -28,6 +27,40 @@ function parseMeta(meta: unknown): Record<string, unknown> {
|
|
|
28
27
|
return result as Record<string, unknown>;
|
|
29
28
|
}
|
|
30
29
|
|
|
30
|
+
/**
|
|
31
|
+
* SQLite stores `contract_json` as TEXT, so the wire shape is a JSON string;
|
|
32
|
+
* Postgres uses `jsonb` and returns an already-parsed value. Normalize both
|
|
33
|
+
* here so `ContractMarkerRecord.contractJson` is always the structured form.
|
|
34
|
+
*/
|
|
35
|
+
function parseContractJson(value: unknown): unknown {
|
|
36
|
+
if (value === null || value === undefined) return null;
|
|
37
|
+
if (typeof value !== 'string') return value;
|
|
38
|
+
try {
|
|
39
|
+
return JSON.parse(value);
|
|
40
|
+
} catch {
|
|
41
|
+
return null;
|
|
42
|
+
}
|
|
43
|
+
}
|
|
44
|
+
|
|
45
|
+
/**
|
|
46
|
+
* Wire shape of a `prisma_contract.marker` row as it comes out of a SQL
|
|
47
|
+
* driver. Snake-cased to match the on-disk column names. Shared by every
|
|
48
|
+
* SQL target's `readMarker` so each runner doesn't redeclare it inline.
|
|
49
|
+
*/
|
|
50
|
+
export type ContractMarkerRow = {
|
|
51
|
+
core_hash: string;
|
|
52
|
+
profile_hash: string;
|
|
53
|
+
contract_json: unknown | null;
|
|
54
|
+
canonical_version: number | null;
|
|
55
|
+
updated_at: Date | string;
|
|
56
|
+
app_tag: string | null;
|
|
57
|
+
meta: unknown | null;
|
|
58
|
+
// SQLite stores arrays as JSON-TEXT, so this is `string` on the wire from
|
|
59
|
+
// a SQLite driver and `string[]` from a Postgres driver. Targets normalize
|
|
60
|
+
// before passing to `parseContractMarkerRow`.
|
|
61
|
+
invariants: unknown;
|
|
62
|
+
};
|
|
63
|
+
|
|
31
64
|
const ContractMarkerRowSchema = type({
|
|
32
65
|
core_hash: 'string',
|
|
33
66
|
profile_hash: 'string',
|
|
@@ -36,6 +69,7 @@ const ContractMarkerRowSchema = type({
|
|
|
36
69
|
'updated_at?': 'Date | string',
|
|
37
70
|
'app_tag?': 'string | null',
|
|
38
71
|
'meta?': 'unknown | null',
|
|
72
|
+
invariants: type('string').array(),
|
|
39
73
|
});
|
|
40
74
|
|
|
41
75
|
/**
|
|
@@ -49,120 +83,24 @@ export function parseContractMarkerRow(row: unknown): ContractMarkerRecord {
|
|
|
49
83
|
throw new Error(`Invalid contract marker row: ${messages}`);
|
|
50
84
|
}
|
|
51
85
|
|
|
52
|
-
const
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
canonical_version?: number | null;
|
|
57
|
-
updated_at?: Date | string;
|
|
58
|
-
app_tag?: string | null;
|
|
59
|
-
meta?: unknown | null;
|
|
60
|
-
};
|
|
61
|
-
|
|
62
|
-
const updatedAt = validatedRow.updated_at
|
|
63
|
-
? validatedRow.updated_at instanceof Date
|
|
64
|
-
? validatedRow.updated_at
|
|
65
|
-
: new Date(validatedRow.updated_at)
|
|
86
|
+
const updatedAt = result.updated_at
|
|
87
|
+
? result.updated_at instanceof Date
|
|
88
|
+
? result.updated_at
|
|
89
|
+
: new Date(result.updated_at)
|
|
66
90
|
: new Date();
|
|
67
91
|
|
|
68
92
|
return {
|
|
69
|
-
storageHash:
|
|
70
|
-
profileHash:
|
|
71
|
-
contractJson:
|
|
72
|
-
canonicalVersion:
|
|
93
|
+
storageHash: result.core_hash,
|
|
94
|
+
profileHash: result.profile_hash,
|
|
95
|
+
contractJson: parseContractJson(result.contract_json),
|
|
96
|
+
canonicalVersion: result.canonical_version ?? null,
|
|
73
97
|
updatedAt,
|
|
74
|
-
appTag:
|
|
75
|
-
meta: parseMeta(
|
|
98
|
+
appTag: result.app_tag ?? null,
|
|
99
|
+
meta: parseMeta(result.meta),
|
|
100
|
+
invariants: result.invariants,
|
|
76
101
|
};
|
|
77
102
|
}
|
|
78
103
|
|
|
79
|
-
/**
|
|
80
|
-
* Returns the SQL statement to read the contract marker.
|
|
81
|
-
* This is a migration-plane helper (no runtime imports).
|
|
82
|
-
* @internal - Used internally by readMarker(). Prefer readMarker() for Control Plane usage.
|
|
83
|
-
*/
|
|
84
|
-
export function readMarkerSql(): { readonly sql: string; readonly params: readonly unknown[] } {
|
|
85
|
-
return {
|
|
86
|
-
sql: `select
|
|
87
|
-
core_hash,
|
|
88
|
-
profile_hash,
|
|
89
|
-
contract_json,
|
|
90
|
-
canonical_version,
|
|
91
|
-
updated_at,
|
|
92
|
-
app_tag,
|
|
93
|
-
meta
|
|
94
|
-
from prisma_contract.marker
|
|
95
|
-
where id = $1`,
|
|
96
|
-
params: [1],
|
|
97
|
-
};
|
|
98
|
-
}
|
|
99
|
-
|
|
100
|
-
/**
|
|
101
|
-
* Returns the SQL statement that probes for the existence of the marker table.
|
|
102
|
-
* Uses the SQL-standard `information_schema.tables` view so the query succeeds
|
|
103
|
-
* (returning zero rows) when the table has not been created yet — avoiding a
|
|
104
|
-
* `relation does not exist` error. Some Postgres wire-protocol implementations
|
|
105
|
-
* (e.g. PGlite's TCP proxy) do not fully recover from an extended-protocol
|
|
106
|
-
* parse error, so we probe first instead of relying on an error signal.
|
|
107
|
-
* @internal - Used internally by readMarker().
|
|
108
|
-
*/
|
|
109
|
-
export function markerTableExistsSql(): {
|
|
110
|
-
readonly sql: string;
|
|
111
|
-
readonly params: readonly unknown[];
|
|
112
|
-
} {
|
|
113
|
-
return {
|
|
114
|
-
sql: `select 1
|
|
115
|
-
from information_schema.tables
|
|
116
|
-
where table_schema = $1 and table_name = $2`,
|
|
117
|
-
params: ['prisma_contract', 'marker'],
|
|
118
|
-
};
|
|
119
|
-
}
|
|
120
|
-
|
|
121
|
-
/**
|
|
122
|
-
* Reads the contract marker from the database using the provided driver.
|
|
123
|
-
* Returns the parsed marker record or null if no marker is found.
|
|
124
|
-
* This abstracts SQL-specific details from the Control Plane.
|
|
125
|
-
*
|
|
126
|
-
* @param driver - ControlDriverInstance instance for executing queries
|
|
127
|
-
* @returns Promise resolving to ContractMarkerRecord or null if marker not found
|
|
128
|
-
*/
|
|
129
|
-
export async function readMarker(
|
|
130
|
-
driver: ControlDriverInstance<'sql', string>,
|
|
131
|
-
): Promise<ContractMarkerRecord | null> {
|
|
132
|
-
// Probe for the marker table first so that a fresh database (no
|
|
133
|
-
// `prisma_contract` schema) returns null cleanly instead of surfacing a
|
|
134
|
-
// `relation does not exist` error. This keeps the control connection in a
|
|
135
|
-
// predictable state for driver implementations that are sensitive to
|
|
136
|
-
// extended-protocol parse errors.
|
|
137
|
-
const existsStatement = markerTableExistsSql();
|
|
138
|
-
const existsResult = await driver.query(existsStatement.sql, existsStatement.params);
|
|
139
|
-
if (existsResult.rows.length === 0) {
|
|
140
|
-
return null;
|
|
141
|
-
}
|
|
142
|
-
|
|
143
|
-
const markerStatement = readMarkerSql();
|
|
144
|
-
const queryResult = await driver.query<{
|
|
145
|
-
core_hash: string;
|
|
146
|
-
profile_hash: string;
|
|
147
|
-
contract_json: unknown | null;
|
|
148
|
-
canonical_version: number | null;
|
|
149
|
-
updated_at: Date | string;
|
|
150
|
-
app_tag: string | null;
|
|
151
|
-
meta: unknown | null;
|
|
152
|
-
}>(markerStatement.sql, markerStatement.params);
|
|
153
|
-
|
|
154
|
-
if (queryResult.rows.length === 0) {
|
|
155
|
-
return null;
|
|
156
|
-
}
|
|
157
|
-
|
|
158
|
-
const markerRow = queryResult.rows[0];
|
|
159
|
-
if (!markerRow) {
|
|
160
|
-
throw new Error('Database query returned unexpected result structure');
|
|
161
|
-
}
|
|
162
|
-
|
|
163
|
-
return parseContractMarkerRow(markerRow);
|
|
164
|
-
}
|
|
165
|
-
|
|
166
104
|
/**
|
|
167
105
|
* Collects supported codec type IDs from adapter and extension manifests.
|
|
168
106
|
* Returns a sorted, unique array of type IDs that are declared in the manifests.
|
package/src/exports/verify.ts
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
export {
|
|
1
|
+
export { type ContractMarkerRow, parseContractMarkerRow } from '../core/verify';
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"types-C6K4mxDM.d.mts","names":[],"sources":["../src/core/control-instance.ts","../src/core/migrations/types.ts"],"sourcesContent":[],"mappings":"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"}
|
package/dist/verify-4GshvY4p.mjs
DELETED
|
@@ -1,122 +0,0 @@
|
|
|
1
|
-
import { type } from "arktype";
|
|
2
|
-
|
|
3
|
-
//#region src/core/verify.ts
|
|
4
|
-
const MetaSchema = type({ "[string]": "unknown" });
|
|
5
|
-
function parseMeta(meta) {
|
|
6
|
-
if (meta === null || meta === void 0) return {};
|
|
7
|
-
let parsed;
|
|
8
|
-
if (typeof meta === "string") try {
|
|
9
|
-
parsed = JSON.parse(meta);
|
|
10
|
-
} catch {
|
|
11
|
-
return {};
|
|
12
|
-
}
|
|
13
|
-
else parsed = meta;
|
|
14
|
-
const result = MetaSchema(parsed);
|
|
15
|
-
if (result instanceof type.errors) return {};
|
|
16
|
-
return result;
|
|
17
|
-
}
|
|
18
|
-
const ContractMarkerRowSchema = type({
|
|
19
|
-
core_hash: "string",
|
|
20
|
-
profile_hash: "string",
|
|
21
|
-
"contract_json?": "unknown | null",
|
|
22
|
-
"canonical_version?": "number | null",
|
|
23
|
-
"updated_at?": "Date | string",
|
|
24
|
-
"app_tag?": "string | null",
|
|
25
|
-
"meta?": "unknown | null"
|
|
26
|
-
});
|
|
27
|
-
/**
|
|
28
|
-
* Parses a contract marker row from database query result.
|
|
29
|
-
* This is SQL-specific parsing logic (handles SQL row structure with snake_case columns).
|
|
30
|
-
*/
|
|
31
|
-
function parseContractMarkerRow(row) {
|
|
32
|
-
const result = ContractMarkerRowSchema(row);
|
|
33
|
-
if (result instanceof type.errors) {
|
|
34
|
-
const messages = result.map((p) => p.message).join("; ");
|
|
35
|
-
throw new Error(`Invalid contract marker row: ${messages}`);
|
|
36
|
-
}
|
|
37
|
-
const validatedRow = result;
|
|
38
|
-
const updatedAt = validatedRow.updated_at ? validatedRow.updated_at instanceof Date ? validatedRow.updated_at : new Date(validatedRow.updated_at) : /* @__PURE__ */ new Date();
|
|
39
|
-
return {
|
|
40
|
-
storageHash: validatedRow.core_hash,
|
|
41
|
-
profileHash: validatedRow.profile_hash,
|
|
42
|
-
contractJson: validatedRow.contract_json ?? null,
|
|
43
|
-
canonicalVersion: validatedRow.canonical_version ?? null,
|
|
44
|
-
updatedAt,
|
|
45
|
-
appTag: validatedRow.app_tag ?? null,
|
|
46
|
-
meta: parseMeta(validatedRow.meta)
|
|
47
|
-
};
|
|
48
|
-
}
|
|
49
|
-
/**
|
|
50
|
-
* Returns the SQL statement to read the contract marker.
|
|
51
|
-
* This is a migration-plane helper (no runtime imports).
|
|
52
|
-
* @internal - Used internally by readMarker(). Prefer readMarker() for Control Plane usage.
|
|
53
|
-
*/
|
|
54
|
-
function readMarkerSql() {
|
|
55
|
-
return {
|
|
56
|
-
sql: `select
|
|
57
|
-
core_hash,
|
|
58
|
-
profile_hash,
|
|
59
|
-
contract_json,
|
|
60
|
-
canonical_version,
|
|
61
|
-
updated_at,
|
|
62
|
-
app_tag,
|
|
63
|
-
meta
|
|
64
|
-
from prisma_contract.marker
|
|
65
|
-
where id = $1`,
|
|
66
|
-
params: [1]
|
|
67
|
-
};
|
|
68
|
-
}
|
|
69
|
-
/**
|
|
70
|
-
* Returns the SQL statement that probes for the existence of the marker table.
|
|
71
|
-
* Uses the SQL-standard `information_schema.tables` view so the query succeeds
|
|
72
|
-
* (returning zero rows) when the table has not been created yet — avoiding a
|
|
73
|
-
* `relation does not exist` error. Some Postgres wire-protocol implementations
|
|
74
|
-
* (e.g. PGlite's TCP proxy) do not fully recover from an extended-protocol
|
|
75
|
-
* parse error, so we probe first instead of relying on an error signal.
|
|
76
|
-
* @internal - Used internally by readMarker().
|
|
77
|
-
*/
|
|
78
|
-
function markerTableExistsSql() {
|
|
79
|
-
return {
|
|
80
|
-
sql: `select 1
|
|
81
|
-
from information_schema.tables
|
|
82
|
-
where table_schema = $1 and table_name = $2`,
|
|
83
|
-
params: ["prisma_contract", "marker"]
|
|
84
|
-
};
|
|
85
|
-
}
|
|
86
|
-
/**
|
|
87
|
-
* Reads the contract marker from the database using the provided driver.
|
|
88
|
-
* Returns the parsed marker record or null if no marker is found.
|
|
89
|
-
* This abstracts SQL-specific details from the Control Plane.
|
|
90
|
-
*
|
|
91
|
-
* @param driver - ControlDriverInstance instance for executing queries
|
|
92
|
-
* @returns Promise resolving to ContractMarkerRecord or null if marker not found
|
|
93
|
-
*/
|
|
94
|
-
async function readMarker(driver) {
|
|
95
|
-
const existsStatement = markerTableExistsSql();
|
|
96
|
-
if ((await driver.query(existsStatement.sql, existsStatement.params)).rows.length === 0) return null;
|
|
97
|
-
const markerStatement = readMarkerSql();
|
|
98
|
-
const queryResult = await driver.query(markerStatement.sql, markerStatement.params);
|
|
99
|
-
if (queryResult.rows.length === 0) return null;
|
|
100
|
-
const markerRow = queryResult.rows[0];
|
|
101
|
-
if (!markerRow) throw new Error("Database query returned unexpected result structure");
|
|
102
|
-
return parseContractMarkerRow(markerRow);
|
|
103
|
-
}
|
|
104
|
-
/**
|
|
105
|
-
* Collects supported codec type IDs from adapter and extension manifests.
|
|
106
|
-
* Returns a sorted, unique array of type IDs that are declared in the manifests.
|
|
107
|
-
* This enables coverage checks by comparing contract column types against supported types.
|
|
108
|
-
*
|
|
109
|
-
* Note: This extracts type IDs from manifest type imports, not from runtime codec registries.
|
|
110
|
-
* The manifests declare which codec types are available, but the actual type IDs
|
|
111
|
-
* are defined in the codec-types TypeScript modules that are imported.
|
|
112
|
-
*
|
|
113
|
-
* For MVP, we return an empty array since extracting type IDs from TypeScript modules
|
|
114
|
-
* would require runtime evaluation or static analysis. This can be enhanced later.
|
|
115
|
-
*/
|
|
116
|
-
function collectSupportedCodecTypeIds(descriptors) {
|
|
117
|
-
return [];
|
|
118
|
-
}
|
|
119
|
-
|
|
120
|
-
//#endregion
|
|
121
|
-
export { readMarkerSql as i, parseContractMarkerRow as n, readMarker as r, collectSupportedCodecTypeIds as t };
|
|
122
|
-
//# sourceMappingURL=verify-4GshvY4p.mjs.map
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"verify-4GshvY4p.mjs","names":["parsed: unknown"],"sources":["../src/core/verify.ts"],"sourcesContent":["import type { ContractMarkerRecord } from '@prisma-next/contract/types';\nimport type { ControlDriverInstance } from '@prisma-next/framework-components/control';\nimport { type } from 'arktype';\n\nconst MetaSchema = type({ '[string]': 'unknown' });\n\nfunction parseMeta(meta: unknown): Record<string, unknown> {\n if (meta === null || meta === undefined) {\n return {};\n }\n\n let parsed: unknown;\n if (typeof meta === 'string') {\n try {\n parsed = JSON.parse(meta);\n } catch {\n return {};\n }\n } else {\n parsed = meta;\n }\n\n const result = MetaSchema(parsed);\n if (result instanceof type.errors) {\n return {};\n }\n\n return result as Record<string, unknown>;\n}\n\nconst ContractMarkerRowSchema = type({\n core_hash: 'string',\n profile_hash: 'string',\n 'contract_json?': 'unknown | null',\n 'canonical_version?': 'number | null',\n 'updated_at?': 'Date | string',\n 'app_tag?': 'string | null',\n 'meta?': 'unknown | null',\n});\n\n/**\n * Parses a contract marker row from database query result.\n * This is SQL-specific parsing logic (handles SQL row structure with snake_case columns).\n */\nexport function parseContractMarkerRow(row: unknown): ContractMarkerRecord {\n const result = ContractMarkerRowSchema(row);\n if (result instanceof type.errors) {\n const messages = result.map((p: { message: string }) => p.message).join('; ');\n throw new Error(`Invalid contract marker row: ${messages}`);\n }\n\n const validatedRow = result as {\n core_hash: string;\n profile_hash: string;\n contract_json?: unknown | null;\n canonical_version?: number | null;\n updated_at?: Date | string;\n app_tag?: string | null;\n meta?: unknown | null;\n };\n\n const updatedAt = validatedRow.updated_at\n ? validatedRow.updated_at instanceof Date\n ? validatedRow.updated_at\n : new Date(validatedRow.updated_at)\n : new Date();\n\n return {\n storageHash: validatedRow.core_hash,\n profileHash: validatedRow.profile_hash,\n contractJson: validatedRow.contract_json ?? null,\n canonicalVersion: validatedRow.canonical_version ?? null,\n updatedAt,\n appTag: validatedRow.app_tag ?? null,\n meta: parseMeta(validatedRow.meta),\n };\n}\n\n/**\n * Returns the SQL statement to read the contract marker.\n * This is a migration-plane helper (no runtime imports).\n * @internal - Used internally by readMarker(). Prefer readMarker() for Control Plane usage.\n */\nexport function readMarkerSql(): { readonly sql: string; readonly params: readonly unknown[] } {\n return {\n sql: `select\n core_hash,\n profile_hash,\n contract_json,\n canonical_version,\n updated_at,\n app_tag,\n meta\n from prisma_contract.marker\n where id = $1`,\n params: [1],\n };\n}\n\n/**\n * Returns the SQL statement that probes for the existence of the marker table.\n * Uses the SQL-standard `information_schema.tables` view so the query succeeds\n * (returning zero rows) when the table has not been created yet — avoiding a\n * `relation does not exist` error. Some Postgres wire-protocol implementations\n * (e.g. PGlite's TCP proxy) do not fully recover from an extended-protocol\n * parse error, so we probe first instead of relying on an error signal.\n * @internal - Used internally by readMarker().\n */\nexport function markerTableExistsSql(): {\n readonly sql: string;\n readonly params: readonly unknown[];\n} {\n return {\n sql: `select 1\n from information_schema.tables\n where table_schema = $1 and table_name = $2`,\n params: ['prisma_contract', 'marker'],\n };\n}\n\n/**\n * Reads the contract marker from the database using the provided driver.\n * Returns the parsed marker record or null if no marker is found.\n * This abstracts SQL-specific details from the Control Plane.\n *\n * @param driver - ControlDriverInstance instance for executing queries\n * @returns Promise resolving to ContractMarkerRecord or null if marker not found\n */\nexport async function readMarker(\n driver: ControlDriverInstance<'sql', string>,\n): Promise<ContractMarkerRecord | null> {\n // Probe for the marker table first so that a fresh database (no\n // `prisma_contract` schema) returns null cleanly instead of surfacing a\n // `relation does not exist` error. This keeps the control connection in a\n // predictable state for driver implementations that are sensitive to\n // extended-protocol parse errors.\n const existsStatement = markerTableExistsSql();\n const existsResult = await driver.query(existsStatement.sql, existsStatement.params);\n if (existsResult.rows.length === 0) {\n return null;\n }\n\n const markerStatement = readMarkerSql();\n const queryResult = await driver.query<{\n core_hash: string;\n profile_hash: string;\n contract_json: unknown | null;\n canonical_version: number | null;\n updated_at: Date | string;\n app_tag: string | null;\n meta: unknown | null;\n }>(markerStatement.sql, markerStatement.params);\n\n if (queryResult.rows.length === 0) {\n return null;\n }\n\n const markerRow = queryResult.rows[0];\n if (!markerRow) {\n throw new Error('Database query returned unexpected result structure');\n }\n\n return parseContractMarkerRow(markerRow);\n}\n\n/**\n * Collects supported codec type IDs from adapter and extension manifests.\n * Returns a sorted, unique array of type IDs that are declared in the manifests.\n * This enables coverage checks by comparing contract column types against supported types.\n *\n * Note: This extracts type IDs from manifest type imports, not from runtime codec registries.\n * The manifests declare which codec types are available, but the actual type IDs\n * are defined in the codec-types TypeScript modules that are imported.\n *\n * For MVP, we return an empty array since extracting type IDs from TypeScript modules\n * would require runtime evaluation or static analysis. This can be enhanced later.\n */\nexport function collectSupportedCodecTypeIds(\n descriptors: ReadonlyArray<{ readonly id: string }>,\n): readonly string[] {\n // For MVP, return empty array\n // Future enhancement: Extract type IDs from codec-types modules via static analysis\n // or require manifests to explicitly list supported type IDs\n void descriptors;\n return [];\n}\n"],"mappings":";;;AAIA,MAAM,aAAa,KAAK,EAAE,YAAY,WAAW,CAAC;AAElD,SAAS,UAAU,MAAwC;AACzD,KAAI,SAAS,QAAQ,SAAS,OAC5B,QAAO,EAAE;CAGX,IAAIA;AACJ,KAAI,OAAO,SAAS,SAClB,KAAI;AACF,WAAS,KAAK,MAAM,KAAK;SACnB;AACN,SAAO,EAAE;;KAGX,UAAS;CAGX,MAAM,SAAS,WAAW,OAAO;AACjC,KAAI,kBAAkB,KAAK,OACzB,QAAO,EAAE;AAGX,QAAO;;AAGT,MAAM,0BAA0B,KAAK;CACnC,WAAW;CACX,cAAc;CACd,kBAAkB;CAClB,sBAAsB;CACtB,eAAe;CACf,YAAY;CACZ,SAAS;CACV,CAAC;;;;;AAMF,SAAgB,uBAAuB,KAAoC;CACzE,MAAM,SAAS,wBAAwB,IAAI;AAC3C,KAAI,kBAAkB,KAAK,QAAQ;EACjC,MAAM,WAAW,OAAO,KAAK,MAA2B,EAAE,QAAQ,CAAC,KAAK,KAAK;AAC7E,QAAM,IAAI,MAAM,gCAAgC,WAAW;;CAG7D,MAAM,eAAe;CAUrB,MAAM,YAAY,aAAa,aAC3B,aAAa,sBAAsB,OACjC,aAAa,aACb,IAAI,KAAK,aAAa,WAAW,mBACnC,IAAI,MAAM;AAEd,QAAO;EACL,aAAa,aAAa;EAC1B,aAAa,aAAa;EAC1B,cAAc,aAAa,iBAAiB;EAC5C,kBAAkB,aAAa,qBAAqB;EACpD;EACA,QAAQ,aAAa,WAAW;EAChC,MAAM,UAAU,aAAa,KAAK;EACnC;;;;;;;AAQH,SAAgB,gBAA+E;AAC7F,QAAO;EACL,KAAK;;;;;;;;;;EAUL,QAAQ,CAAC,EAAE;EACZ;;;;;;;;;;;AAYH,SAAgB,uBAGd;AACA,QAAO;EACL,KAAK;;;EAGL,QAAQ,CAAC,mBAAmB,SAAS;EACtC;;;;;;;;;;AAWH,eAAsB,WACpB,QACsC;CAMtC,MAAM,kBAAkB,sBAAsB;AAE9C,MADqB,MAAM,OAAO,MAAM,gBAAgB,KAAK,gBAAgB,OAAO,EACnE,KAAK,WAAW,EAC/B,QAAO;CAGT,MAAM,kBAAkB,eAAe;CACvC,MAAM,cAAc,MAAM,OAAO,MAQ9B,gBAAgB,KAAK,gBAAgB,OAAO;AAE/C,KAAI,YAAY,KAAK,WAAW,EAC9B,QAAO;CAGT,MAAM,YAAY,YAAY,KAAK;AACnC,KAAI,CAAC,UACH,OAAM,IAAI,MAAM,sDAAsD;AAGxE,QAAO,uBAAuB,UAAU;;;;;;;;;;;;;;AAe1C,SAAgB,6BACd,aACmB;AAKnB,QAAO,EAAE"}
|