@prisma-next/contract-authoring 0.3.0-pr.99.6 → 0.3.0

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.
@@ -1,159 +0,0 @@
1
- import type { TargetPackRef } from '@prisma-next/contract/framework-components';
2
- import type {
3
- ColumnBuilderState,
4
- ContractBuilderState,
5
- ModelBuilderState,
6
- RelationDefinition,
7
- TableBuilderState,
8
- } from './builder-state';
9
- import { ModelBuilder } from './model-builder';
10
- import { createTable, TableBuilder } from './table-builder';
11
-
12
- export class ContractBuilder<
13
- Target extends string | undefined = undefined,
14
- Tables extends Record<
15
- string,
16
- TableBuilderState<
17
- string,
18
- Record<string, ColumnBuilderState<string, boolean, string>>,
19
- readonly string[] | undefined
20
- >
21
- > = Record<never, never>,
22
- Models extends Record<
23
- string,
24
- ModelBuilderState<string, string, Record<string, string>, Record<string, RelationDefinition>>
25
- > = Record<never, never>,
26
- CoreHash extends string | undefined = undefined,
27
- ExtensionPacks extends Record<string, unknown> | undefined = undefined,
28
- Capabilities extends Record<string, Record<string, boolean>> | undefined = undefined,
29
- > {
30
- protected readonly state: ContractBuilderState<
31
- Target,
32
- Tables,
33
- Models,
34
- CoreHash,
35
- ExtensionPacks,
36
- Capabilities
37
- >;
38
-
39
- constructor(
40
- state?: ContractBuilderState<Target, Tables, Models, CoreHash, ExtensionPacks, Capabilities>,
41
- ) {
42
- this.state =
43
- state ??
44
- ({
45
- tables: {},
46
- models: {},
47
- } as ContractBuilderState<Target, Tables, Models, CoreHash, ExtensionPacks, Capabilities>);
48
- }
49
-
50
- target<T extends string>(
51
- packRef: TargetPackRef<string, T>,
52
- ): ContractBuilder<T, Tables, Models, CoreHash, ExtensionPacks, Capabilities> {
53
- return new ContractBuilder<T, Tables, Models, CoreHash, ExtensionPacks, Capabilities>({
54
- ...this.state,
55
- target: packRef.targetId,
56
- });
57
- }
58
-
59
- capabilities<C extends Record<string, Record<string, boolean>>>(
60
- capabilities: C,
61
- ): ContractBuilder<Target, Tables, Models, CoreHash, ExtensionPacks, C> {
62
- return new ContractBuilder<Target, Tables, Models, CoreHash, ExtensionPacks, C>({
63
- ...this.state,
64
- capabilities,
65
- });
66
- }
67
-
68
- table<
69
- TableName extends string,
70
- T extends TableBuilder<
71
- TableName,
72
- Record<string, ColumnBuilderState<string, boolean, string>>,
73
- readonly string[] | undefined
74
- >,
75
- >(
76
- name: TableName,
77
- callback: (t: TableBuilder<TableName>) => T | undefined,
78
- ): ContractBuilder<
79
- Target,
80
- Tables & Record<TableName, ReturnType<T['build']>>,
81
- Models,
82
- CoreHash,
83
- ExtensionPacks,
84
- Capabilities
85
- > {
86
- const tableBuilder = createTable(name);
87
- const result = callback(tableBuilder);
88
- const finalBuilder = result instanceof TableBuilder ? result : tableBuilder;
89
- const tableState = finalBuilder.build();
90
-
91
- return new ContractBuilder<
92
- Target,
93
- Tables & Record<TableName, ReturnType<T['build']>>,
94
- Models,
95
- CoreHash,
96
- ExtensionPacks,
97
- Capabilities
98
- >({
99
- ...this.state,
100
- tables: { ...this.state.tables, [name]: tableState } as Tables &
101
- Record<TableName, ReturnType<T['build']>>,
102
- });
103
- }
104
-
105
- model<
106
- ModelName extends string,
107
- TableName extends string,
108
- M extends ModelBuilder<
109
- ModelName,
110
- TableName,
111
- Record<string, string>,
112
- Record<string, RelationDefinition>
113
- >,
114
- >(
115
- name: ModelName,
116
- table: TableName,
117
- callback: (
118
- m: ModelBuilder<ModelName, TableName, Record<string, string>, Record<never, never>>,
119
- ) => M | undefined,
120
- ): ContractBuilder<
121
- Target,
122
- Tables,
123
- Models & Record<ModelName, ReturnType<M['build']>>,
124
- CoreHash,
125
- ExtensionPacks,
126
- Capabilities
127
- > {
128
- const modelBuilder = new ModelBuilder<ModelName, TableName>(name, table);
129
- const result = callback(modelBuilder);
130
- const finalBuilder = result instanceof ModelBuilder ? result : modelBuilder;
131
- const modelState = finalBuilder.build();
132
-
133
- return new ContractBuilder<
134
- Target,
135
- Tables,
136
- Models & Record<ModelName, ReturnType<M['build']>>,
137
- CoreHash,
138
- ExtensionPacks,
139
- Capabilities
140
- >({
141
- ...this.state,
142
- models: { ...this.state.models, [name]: modelState } as Models &
143
- Record<ModelName, ReturnType<M['build']>>,
144
- });
145
- }
146
-
147
- coreHash<H extends string>(
148
- hash: H,
149
- ): ContractBuilder<Target, Tables, Models, H, ExtensionPacks, Capabilities> {
150
- return new ContractBuilder<Target, Tables, Models, H, ExtensionPacks, Capabilities>({
151
- ...this.state,
152
- coreHash: hash,
153
- });
154
- }
155
- }
156
-
157
- export function defineContract(): ContractBuilder {
158
- return new ContractBuilder();
159
- }
@@ -1,160 +0,0 @@
1
- import type { ModelBuilderState, RelationDefinition } from './builder-state';
2
-
3
- export class ModelBuilder<
4
- Name extends string,
5
- Table extends string,
6
- Fields extends Record<string, string> = Record<never, never>,
7
- Relations extends Record<string, RelationDefinition> = Record<never, never>,
8
- > {
9
- private readonly _name: Name;
10
- private readonly _table: Table;
11
- private readonly _fields: Fields;
12
- private readonly _relations: Relations;
13
-
14
- constructor(
15
- name: Name,
16
- table: Table,
17
- fields: Fields = {} as Fields,
18
- relations: Relations = {} as Relations,
19
- ) {
20
- this._name = name;
21
- this._table = table;
22
- this._fields = fields;
23
- this._relations = relations;
24
- }
25
-
26
- field<FieldName extends string, ColumnName extends string>(
27
- fieldName: FieldName,
28
- columnName: ColumnName,
29
- ): ModelBuilder<Name, Table, Fields & Record<FieldName, ColumnName>, Relations> {
30
- return new ModelBuilder(
31
- this._name,
32
- this._table,
33
- {
34
- ...this._fields,
35
- [fieldName]: columnName,
36
- } as Fields & Record<FieldName, ColumnName>,
37
- this._relations,
38
- );
39
- }
40
-
41
- relation<RelationName extends string, ToModel extends string, ToTable extends string>(
42
- name: RelationName,
43
- options: {
44
- toModel: ToModel;
45
- toTable: ToTable;
46
- cardinality: '1:1' | '1:N' | 'N:1';
47
- on: {
48
- parentTable: Table;
49
- parentColumns: readonly string[];
50
- childTable: ToTable;
51
- childColumns: readonly string[];
52
- };
53
- },
54
- ): ModelBuilder<Name, Table, Fields, Relations & Record<RelationName, RelationDefinition>>;
55
- relation<
56
- RelationName extends string,
57
- ToModel extends string,
58
- ToTable extends string,
59
- JunctionTable extends string,
60
- >(
61
- name: RelationName,
62
- options: {
63
- toModel: ToModel;
64
- toTable: ToTable;
65
- cardinality: 'N:M';
66
- through: {
67
- table: JunctionTable;
68
- parentColumns: readonly string[];
69
- childColumns: readonly string[];
70
- };
71
- on: {
72
- parentTable: Table;
73
- parentColumns: readonly string[];
74
- childTable: JunctionTable;
75
- childColumns: readonly string[];
76
- };
77
- },
78
- ): ModelBuilder<Name, Table, Fields, Relations & Record<RelationName, RelationDefinition>>;
79
- relation<
80
- RelationName extends string,
81
- ToModel extends string,
82
- ToTable extends string,
83
- JunctionTable extends string = never,
84
- >(
85
- name: RelationName,
86
- options: {
87
- toModel: ToModel;
88
- toTable: ToTable;
89
- cardinality: '1:1' | '1:N' | 'N:1' | 'N:M';
90
- through?: {
91
- table: JunctionTable;
92
- parentColumns: readonly string[];
93
- childColumns: readonly string[];
94
- };
95
- on: {
96
- parentTable: Table;
97
- parentColumns: readonly string[];
98
- childTable: ToTable | JunctionTable;
99
- childColumns: readonly string[];
100
- };
101
- },
102
- ): ModelBuilder<Name, Table, Fields, Relations & Record<RelationName, RelationDefinition>> {
103
- // Validate parentTable matches model's table
104
- if (options.on.parentTable !== this._table) {
105
- throw new Error(
106
- `Relation "${name}" parentTable "${options.on.parentTable}" does not match model table "${this._table}"`,
107
- );
108
- }
109
-
110
- // Validate childTable matches toTable (for non-N:M) or through.table (for N:M)
111
- if (options.cardinality === 'N:M') {
112
- if (!options.through) {
113
- throw new Error(`Relation "${name}" with cardinality "N:M" requires through field`);
114
- }
115
- if (options.on.childTable !== options.through.table) {
116
- throw new Error(
117
- `Relation "${name}" childTable "${options.on.childTable}" does not match through.table "${options.through.table}"`,
118
- );
119
- }
120
- } else {
121
- if (options.on.childTable !== options.toTable) {
122
- throw new Error(
123
- `Relation "${name}" childTable "${options.on.childTable}" does not match toTable "${options.toTable}"`,
124
- );
125
- }
126
- }
127
-
128
- const relationDef: RelationDefinition = {
129
- to: options.toModel,
130
- cardinality: options.cardinality,
131
- on: {
132
- parentCols: options.on.parentColumns,
133
- childCols: options.on.childColumns,
134
- },
135
- ...(options.through
136
- ? {
137
- through: {
138
- table: options.through.table,
139
- parentCols: options.through.parentColumns,
140
- childCols: options.through.childColumns,
141
- },
142
- }
143
- : undefined),
144
- };
145
-
146
- return new ModelBuilder(this._name, this._table, this._fields, {
147
- ...this._relations,
148
- [name]: relationDef,
149
- } as Relations & Record<RelationName, RelationDefinition>);
150
- }
151
-
152
- build(): ModelBuilderState<Name, Table, Fields, Relations> {
153
- return {
154
- name: this._name,
155
- table: this._table,
156
- fields: this._fields,
157
- relations: this._relations,
158
- };
159
- }
160
- }
@@ -1,195 +0,0 @@
1
- import type {
2
- ColumnBuilderState,
3
- ColumnTypeDescriptor,
4
- ForeignKeyDef,
5
- IndexDef,
6
- TableBuilderState,
7
- UniqueConstraintDef,
8
- } from './builder-state';
9
-
10
- interface TableBuilderInternalState<
11
- Name extends string,
12
- Columns extends Record<string, ColumnBuilderState<string, boolean, string>>,
13
- PrimaryKey extends readonly string[] | undefined,
14
- > {
15
- readonly name: Name;
16
- readonly columns: Columns;
17
- readonly primaryKey: PrimaryKey;
18
- readonly primaryKeyName: string | undefined;
19
- readonly uniques: readonly UniqueConstraintDef[];
20
- readonly indexes: readonly IndexDef[];
21
- readonly foreignKeys: readonly ForeignKeyDef[];
22
- }
23
-
24
- /**
25
- * Creates a new table builder with the given name.
26
- * This is the preferred way to create a TableBuilder - it ensures
27
- * type parameters are inferred correctly without unsafe casts.
28
- */
29
- export function createTable<Name extends string>(name: Name): TableBuilder<Name> {
30
- return new TableBuilder(name, {}, undefined, undefined, [], [], []);
31
- }
32
-
33
- /**
34
- * Builder for defining table structure with type-safe chaining.
35
- * Use `createTable(name)` to create instances.
36
- */
37
- export class TableBuilder<
38
- Name extends string,
39
- Columns extends Record<string, ColumnBuilderState<string, boolean, string>> = Record<
40
- never,
41
- ColumnBuilderState<string, boolean, string>
42
- >,
43
- PrimaryKey extends readonly string[] | undefined = undefined,
44
- > {
45
- private readonly _state: TableBuilderInternalState<Name, Columns, PrimaryKey>;
46
-
47
- /** @internal Use createTable() instead */
48
- constructor(
49
- name: Name,
50
- columns: Columns,
51
- primaryKey: PrimaryKey,
52
- primaryKeyName: string | undefined,
53
- uniques: readonly UniqueConstraintDef[],
54
- indexes: readonly IndexDef[],
55
- foreignKeys: readonly ForeignKeyDef[],
56
- ) {
57
- this._state = {
58
- name,
59
- columns,
60
- primaryKey,
61
- primaryKeyName,
62
- uniques,
63
- indexes,
64
- foreignKeys,
65
- };
66
- }
67
-
68
- private get _name(): Name {
69
- return this._state.name;
70
- }
71
-
72
- private get _columns(): Columns {
73
- return this._state.columns;
74
- }
75
-
76
- private get _primaryKey(): PrimaryKey {
77
- return this._state.primaryKey;
78
- }
79
-
80
- column<
81
- ColName extends string,
82
- Descriptor extends ColumnTypeDescriptor,
83
- Nullable extends boolean | undefined = undefined,
84
- >(
85
- name: ColName,
86
- options: {
87
- type: Descriptor;
88
- nullable?: Nullable;
89
- },
90
- ): TableBuilder<
91
- Name,
92
- Columns &
93
- Record<
94
- ColName,
95
- ColumnBuilderState<ColName, Nullable extends true ? true : false, Descriptor['codecId']>
96
- >,
97
- PrimaryKey
98
- > {
99
- const nullable = (options.nullable ?? false) as Nullable extends true ? true : false;
100
- const { codecId, nativeType } = options.type;
101
-
102
- const columnState = {
103
- name,
104
- nullable,
105
- type: codecId,
106
- nativeType,
107
- } as ColumnBuilderState<ColName, Nullable extends true ? true : false, Descriptor['codecId']>;
108
- const newColumns = { ...this._columns, [name]: columnState } as Columns &
109
- Record<
110
- ColName,
111
- ColumnBuilderState<ColName, Nullable extends true ? true : false, Descriptor['codecId']>
112
- >;
113
- return new TableBuilder(
114
- this._state.name,
115
- newColumns,
116
- this._state.primaryKey,
117
- this._state.primaryKeyName,
118
- this._state.uniques,
119
- this._state.indexes,
120
- this._state.foreignKeys,
121
- );
122
- }
123
-
124
- primaryKey<PK extends readonly string[]>(
125
- columns: PK,
126
- name?: string,
127
- ): TableBuilder<Name, Columns, PK> {
128
- return new TableBuilder(
129
- this._state.name,
130
- this._state.columns,
131
- columns,
132
- name,
133
- this._state.uniques,
134
- this._state.indexes,
135
- this._state.foreignKeys,
136
- );
137
- }
138
-
139
- unique(columns: readonly string[], name?: string): TableBuilder<Name, Columns, PrimaryKey> {
140
- const constraint: UniqueConstraintDef = name ? { columns, name } : { columns };
141
- return new TableBuilder(
142
- this._state.name,
143
- this._state.columns,
144
- this._state.primaryKey,
145
- this._state.primaryKeyName,
146
- [...this._state.uniques, constraint],
147
- this._state.indexes,
148
- this._state.foreignKeys,
149
- );
150
- }
151
-
152
- index(columns: readonly string[], name?: string): TableBuilder<Name, Columns, PrimaryKey> {
153
- const indexDef: IndexDef = name ? { columns, name } : { columns };
154
- return new TableBuilder(
155
- this._state.name,
156
- this._state.columns,
157
- this._state.primaryKey,
158
- this._state.primaryKeyName,
159
- this._state.uniques,
160
- [...this._state.indexes, indexDef],
161
- this._state.foreignKeys,
162
- );
163
- }
164
-
165
- foreignKey(
166
- columns: readonly string[],
167
- references: { table: string; columns: readonly string[] },
168
- name?: string,
169
- ): TableBuilder<Name, Columns, PrimaryKey> {
170
- const fkDef: ForeignKeyDef = name ? { columns, references, name } : { columns, references };
171
- return new TableBuilder(
172
- this._state.name,
173
- this._state.columns,
174
- this._state.primaryKey,
175
- this._state.primaryKeyName,
176
- this._state.uniques,
177
- this._state.indexes,
178
- [...this._state.foreignKeys, fkDef],
179
- );
180
- }
181
-
182
- build(): TableBuilderState<Name, Columns, PrimaryKey> {
183
- return {
184
- name: this._name,
185
- columns: this._columns,
186
- ...(this._primaryKey !== undefined ? { primaryKey: this._primaryKey } : {}),
187
- ...(this._state.primaryKeyName !== undefined
188
- ? { primaryKeyName: this._state.primaryKeyName }
189
- : {}),
190
- uniques: this._state.uniques,
191
- indexes: this._state.indexes,
192
- foreignKeys: this._state.foreignKeys,
193
- } as TableBuilderState<Name, Columns, PrimaryKey>;
194
- }
195
- }
package/src/types.ts DELETED
@@ -1,129 +0,0 @@
1
- import type {
2
- ColumnBuilderState,
3
- ModelBuilderState,
4
- RelationDefinition,
5
- TableBuilderState,
6
- } from './builder-state';
7
-
8
- export type BuildStorageColumn<Nullable extends boolean, Type extends string> = {
9
- readonly nativeType: string;
10
- readonly codecId: Type;
11
- readonly nullable: Nullable;
12
- };
13
-
14
- export type ExtractColumns<
15
- T extends TableBuilderState<
16
- string,
17
- Record<string, ColumnBuilderState<string, boolean, string>>,
18
- readonly string[] | undefined
19
- >,
20
- > = T extends TableBuilderState<string, infer C, readonly string[] | undefined> ? C : never;
21
-
22
- export type ExtractPrimaryKey<
23
- T extends TableBuilderState<
24
- string,
25
- Record<string, ColumnBuilderState<string, boolean, string>>,
26
- readonly string[] | undefined
27
- >,
28
- > =
29
- T extends TableBuilderState<
30
- string,
31
- Record<string, ColumnBuilderState<string, boolean, string>>,
32
- infer PK
33
- >
34
- ? PK
35
- : never;
36
-
37
- export type BuildStorage<
38
- Tables extends Record<
39
- string,
40
- TableBuilderState<
41
- string,
42
- Record<string, ColumnBuilderState<string, boolean, string>>,
43
- readonly string[] | undefined
44
- >
45
- >,
46
- > = {
47
- readonly tables: {
48
- readonly [K in keyof Tables]: {
49
- readonly columns: {
50
- readonly [ColK in keyof ExtractColumns<Tables[K]>]: ExtractColumns<
51
- Tables[K]
52
- >[ColK] extends ColumnBuilderState<string, infer Null, infer TType>
53
- ? BuildStorageColumn<Null & boolean, TType>
54
- : never;
55
- };
56
- };
57
- };
58
- };
59
-
60
- export type BuildStorageTables<
61
- Tables extends Record<
62
- string,
63
- TableBuilderState<
64
- string,
65
- Record<string, ColumnBuilderState<string, boolean, string>>,
66
- readonly string[] | undefined
67
- >
68
- >,
69
- > = {
70
- readonly [K in keyof Tables]: {
71
- readonly columns: {
72
- readonly [ColK in keyof ExtractColumns<Tables[K]>]: ExtractColumns<
73
- Tables[K]
74
- >[ColK] extends ColumnBuilderState<string, infer Null, infer TType>
75
- ? BuildStorageColumn<Null & boolean, TType>
76
- : never;
77
- };
78
- };
79
- };
80
-
81
- export type Mutable<T> = {
82
- -readonly [K in keyof T]-?: T[K];
83
- };
84
-
85
- export type BuildModelFields<Fields extends Record<string, string>> = {
86
- readonly [K in keyof Fields]: { readonly column: Fields[K] };
87
- };
88
-
89
- export type ExtractModelFields<
90
- T extends ModelBuilderState<
91
- string,
92
- string,
93
- Record<string, string>,
94
- Record<string, RelationDefinition>
95
- >,
96
- > =
97
- T extends ModelBuilderState<string, string, infer F, Record<string, RelationDefinition>>
98
- ? F
99
- : never;
100
-
101
- export type ExtractModelRelations<
102
- T extends ModelBuilderState<
103
- string,
104
- string,
105
- Record<string, string>,
106
- Record<string, RelationDefinition>
107
- >,
108
- > = T extends ModelBuilderState<string, string, Record<string, string>, infer R> ? R : never;
109
-
110
- export type BuildModels<
111
- Models extends Record<
112
- string,
113
- ModelBuilderState<string, string, Record<string, string>, Record<string, RelationDefinition>>
114
- >,
115
- > = {
116
- readonly [K in keyof Models]: {
117
- readonly storage: { readonly table: Models[K]['table'] };
118
- readonly fields: BuildModelFields<ExtractModelFields<Models[K]>>;
119
- };
120
- };
121
-
122
- export type BuildRelations<
123
- Models extends Record<
124
- string,
125
- ModelBuilderState<string, string, Record<string, string>, Record<string, RelationDefinition>>
126
- >,
127
- > = {
128
- readonly [K in keyof Models as Models[K]['table']]: ExtractModelRelations<Models[K]>;
129
- };