orchid-orm 1.5.28 → 1.5.30
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/dist/index.js +10 -10
- package/dist/index.js.map +1 -1
- package/dist/index.mjs +10 -10
- package/dist/index.mjs.map +1 -1
- package/package.json +13 -22
- package/.env.example +0 -1
- package/.turbo/turbo-test.log +0 -26
- package/.turbo/turbo-test:ci.log +0 -26
- package/CHANGELOG.md +0 -375
- package/coverage/coverage-summary.json +0 -28
- package/jest-setup.ts +0 -11
- package/rollup.config.js +0 -18
- package/src/bin/bin.ts +0 -3
- package/src/bin/init.test.ts +0 -810
- package/src/bin/init.ts +0 -529
- package/src/codegen/appCodeUpdater.test.ts +0 -75
- package/src/codegen/appCodeUpdater.ts +0 -53
- package/src/codegen/createBaseTableFile.test.ts +0 -53
- package/src/codegen/createBaseTableFile.ts +0 -31
- package/src/codegen/fileChanges.ts +0 -41
- package/src/codegen/testUtils.ts +0 -56
- package/src/codegen/tsUtils.ts +0 -180
- package/src/codegen/updateMainFile.test.ts +0 -253
- package/src/codegen/updateMainFile.ts +0 -210
- package/src/codegen/updateTableFile/changeTable.test.ts +0 -804
- package/src/codegen/updateTableFile/changeTable.ts +0 -536
- package/src/codegen/updateTableFile/createTable.test.ts +0 -139
- package/src/codegen/updateTableFile/createTable.ts +0 -51
- package/src/codegen/updateTableFile/renameTable.test.ts +0 -124
- package/src/codegen/updateTableFile/renameTable.ts +0 -67
- package/src/codegen/updateTableFile/updateTableFile.ts +0 -22
- package/src/codegen/utils.ts +0 -13
- package/src/index.ts +0 -5
- package/src/orm.test.ts +0 -92
- package/src/orm.ts +0 -98
- package/src/relations/belongsTo.test.ts +0 -1122
- package/src/relations/belongsTo.ts +0 -352
- package/src/relations/hasAndBelongsToMany.test.ts +0 -1335
- package/src/relations/hasAndBelongsToMany.ts +0 -472
- package/src/relations/hasMany.test.ts +0 -2616
- package/src/relations/hasMany.ts +0 -401
- package/src/relations/hasOne.test.ts +0 -1701
- package/src/relations/hasOne.ts +0 -351
- package/src/relations/relations.test.ts +0 -37
- package/src/relations/relations.ts +0 -363
- package/src/relations/utils.ts +0 -162
- package/src/repo.test.ts +0 -200
- package/src/repo.ts +0 -119
- package/src/table.test.ts +0 -121
- package/src/table.ts +0 -184
- package/src/test-utils/test-db.ts +0 -32
- package/src/test-utils/test-tables.ts +0 -194
- package/src/test-utils/test-utils.ts +0 -119
- package/src/transaction.test.ts +0 -47
- package/src/transaction.ts +0 -27
- package/src/utils.ts +0 -9
- package/tsconfig.json +0 -14
package/src/repo.test.ts
DELETED
|
@@ -1,200 +0,0 @@
|
|
|
1
|
-
import { orchidORM } from './orm';
|
|
2
|
-
import { pgConfig } from './test-utils/test-db';
|
|
3
|
-
import { createBaseTable } from './table';
|
|
4
|
-
import { assertType, expectSql } from './test-utils/test-utils';
|
|
5
|
-
import { QueryReturnType } from 'pqb';
|
|
6
|
-
import { createRepo } from './repo';
|
|
7
|
-
|
|
8
|
-
const BaseTable = createBaseTable();
|
|
9
|
-
|
|
10
|
-
class SomeTable extends BaseTable {
|
|
11
|
-
table = 'someTable';
|
|
12
|
-
columns = this.setColumns((t) => ({
|
|
13
|
-
id: t.serial().primaryKey(),
|
|
14
|
-
name: t.text(0, 100),
|
|
15
|
-
}));
|
|
16
|
-
|
|
17
|
-
relations = {
|
|
18
|
-
other: this.hasMany(() => OtherTable, {
|
|
19
|
-
primaryKey: 'id',
|
|
20
|
-
foreignKey: 'someId',
|
|
21
|
-
}),
|
|
22
|
-
};
|
|
23
|
-
}
|
|
24
|
-
|
|
25
|
-
class OtherTable extends BaseTable {
|
|
26
|
-
table = 'otherTable';
|
|
27
|
-
columns = this.setColumns((t) => ({
|
|
28
|
-
id: t.serial().primaryKey(),
|
|
29
|
-
someId: t.integer().foreignKey(() => SomeTable, 'id'),
|
|
30
|
-
anotherId: t.integer().foreignKey(() => AnotherTable, 'id'),
|
|
31
|
-
}));
|
|
32
|
-
|
|
33
|
-
relations = {
|
|
34
|
-
some: this.belongsTo(() => SomeTable, {
|
|
35
|
-
primaryKey: 'id',
|
|
36
|
-
foreignKey: 'someId',
|
|
37
|
-
}),
|
|
38
|
-
another: this.belongsTo(() => AnotherTable, {
|
|
39
|
-
primaryKey: 'id',
|
|
40
|
-
foreignKey: 'anotherId',
|
|
41
|
-
}),
|
|
42
|
-
};
|
|
43
|
-
}
|
|
44
|
-
|
|
45
|
-
class AnotherTable extends BaseTable {
|
|
46
|
-
table = 'another';
|
|
47
|
-
columns = this.setColumns((t) => ({
|
|
48
|
-
id: t.serial().primaryKey(),
|
|
49
|
-
}));
|
|
50
|
-
}
|
|
51
|
-
|
|
52
|
-
const db = orchidORM(pgConfig, {
|
|
53
|
-
some: SomeTable,
|
|
54
|
-
other: OtherTable,
|
|
55
|
-
another: AnotherTable,
|
|
56
|
-
});
|
|
57
|
-
|
|
58
|
-
describe('createRepo', () => {
|
|
59
|
-
describe('queryMethods', () => {
|
|
60
|
-
const repo = createRepo(db.some, {
|
|
61
|
-
queryMethods: {
|
|
62
|
-
one(q) {
|
|
63
|
-
return q.select('id');
|
|
64
|
-
},
|
|
65
|
-
two(q) {
|
|
66
|
-
return q.select('name');
|
|
67
|
-
},
|
|
68
|
-
three(q, id: number) {
|
|
69
|
-
return q.where({ id });
|
|
70
|
-
},
|
|
71
|
-
},
|
|
72
|
-
});
|
|
73
|
-
|
|
74
|
-
it('should accept user defined methods and allow to use them on the table with chaining', async () => {
|
|
75
|
-
const q = repo.one().two().three(123).take();
|
|
76
|
-
|
|
77
|
-
assertType<Awaited<typeof q>, { id: number; name: string }>();
|
|
78
|
-
|
|
79
|
-
expectSql(
|
|
80
|
-
q.toSql(),
|
|
81
|
-
`
|
|
82
|
-
SELECT "someTable"."id", "someTable"."name"
|
|
83
|
-
FROM "someTable"
|
|
84
|
-
WHERE "someTable"."id" = $1
|
|
85
|
-
LIMIT $2
|
|
86
|
-
`,
|
|
87
|
-
[123, 1],
|
|
88
|
-
);
|
|
89
|
-
});
|
|
90
|
-
|
|
91
|
-
it('should have custom methods on relation queries inside of select', async () => {
|
|
92
|
-
const q = db.other.select('id', {
|
|
93
|
-
some: (q) => repo(q.some).one().two().three(123),
|
|
94
|
-
});
|
|
95
|
-
|
|
96
|
-
assertType<
|
|
97
|
-
Awaited<typeof q>,
|
|
98
|
-
{ id: number; some: { id: number; name: string } | null }[]
|
|
99
|
-
>();
|
|
100
|
-
|
|
101
|
-
expectSql(
|
|
102
|
-
q.toSql(),
|
|
103
|
-
`
|
|
104
|
-
SELECT
|
|
105
|
-
"otherTable"."id",
|
|
106
|
-
(
|
|
107
|
-
SELECT row_to_json("t".*)
|
|
108
|
-
FROM (
|
|
109
|
-
SELECT "some"."id", "some"."name"
|
|
110
|
-
FROM "someTable" AS "some"
|
|
111
|
-
WHERE "some"."id" = $1
|
|
112
|
-
AND "some"."id" = "otherTable"."someId"
|
|
113
|
-
LIMIT $2
|
|
114
|
-
) AS "t"
|
|
115
|
-
) AS "some"
|
|
116
|
-
FROM "otherTable"
|
|
117
|
-
`,
|
|
118
|
-
[123, 1],
|
|
119
|
-
);
|
|
120
|
-
});
|
|
121
|
-
});
|
|
122
|
-
|
|
123
|
-
describe('queryOneMethods', () => {
|
|
124
|
-
const repo = createRepo(db.some, {
|
|
125
|
-
queryOneMethods: {
|
|
126
|
-
one(q) {
|
|
127
|
-
const type: Exclude<QueryReturnType, 'all'> = q.returnType;
|
|
128
|
-
return type;
|
|
129
|
-
},
|
|
130
|
-
},
|
|
131
|
-
});
|
|
132
|
-
|
|
133
|
-
it('should define methods which are available only after .take, .find, or similar', () => {
|
|
134
|
-
// @ts-expect-error should prevent using method on query which returns multiple
|
|
135
|
-
repo.one();
|
|
136
|
-
|
|
137
|
-
repo.take().one();
|
|
138
|
-
repo.find(1).one();
|
|
139
|
-
});
|
|
140
|
-
});
|
|
141
|
-
|
|
142
|
-
describe('queryWithWhereMethods', () => {
|
|
143
|
-
const repo = createRepo(db.some, {
|
|
144
|
-
queryWithWhereMethods: {
|
|
145
|
-
one(q) {
|
|
146
|
-
const hasWhere: true = q.hasWhere;
|
|
147
|
-
return hasWhere;
|
|
148
|
-
},
|
|
149
|
-
},
|
|
150
|
-
});
|
|
151
|
-
|
|
152
|
-
it('should define methods which are available only after .where, .find, or similar', () => {
|
|
153
|
-
// @ts-expect-error should prevent using method on query without where conditions
|
|
154
|
-
repo.one();
|
|
155
|
-
// @ts-expect-error should prevent using method on query without where conditions
|
|
156
|
-
repo.take().one();
|
|
157
|
-
|
|
158
|
-
repo.where().one();
|
|
159
|
-
repo.find(1).one();
|
|
160
|
-
});
|
|
161
|
-
});
|
|
162
|
-
|
|
163
|
-
describe('queryOneWithWhere', () => {
|
|
164
|
-
const repo = createRepo(db.some, {
|
|
165
|
-
queryOneWithWhereMethods: {
|
|
166
|
-
one(q) {
|
|
167
|
-
const type: Exclude<QueryReturnType, 'all'> = q.returnType;
|
|
168
|
-
const hasWhere: true = q.hasWhere;
|
|
169
|
-
return [type, hasWhere];
|
|
170
|
-
},
|
|
171
|
-
},
|
|
172
|
-
});
|
|
173
|
-
|
|
174
|
-
it('should define methods which are available only after .where, .find, or similar', () => {
|
|
175
|
-
// @ts-expect-error should prevent using method on query without where conditions
|
|
176
|
-
repo.one();
|
|
177
|
-
// @ts-expect-error should prevent using method on query without where conditions
|
|
178
|
-
repo.take().one();
|
|
179
|
-
|
|
180
|
-
// @ts-expect-error should prevent using method on query which returns multiple
|
|
181
|
-
repo.where().one();
|
|
182
|
-
|
|
183
|
-
repo.find(1).one();
|
|
184
|
-
});
|
|
185
|
-
});
|
|
186
|
-
|
|
187
|
-
describe('methods', () => {
|
|
188
|
-
const repo = createRepo(db.some, {
|
|
189
|
-
methods: {
|
|
190
|
-
one(a: number, b: string) {
|
|
191
|
-
return a + b;
|
|
192
|
-
},
|
|
193
|
-
},
|
|
194
|
-
});
|
|
195
|
-
|
|
196
|
-
it('should assign methods as is to the repo', () => {
|
|
197
|
-
expect(repo.take().one(1, '2')).toBe('12');
|
|
198
|
-
});
|
|
199
|
-
});
|
|
200
|
-
});
|
package/src/repo.ts
DELETED
|
@@ -1,119 +0,0 @@
|
|
|
1
|
-
import {
|
|
2
|
-
EmptyObject,
|
|
3
|
-
getClonedQueryData,
|
|
4
|
-
MergeQuery,
|
|
5
|
-
Query,
|
|
6
|
-
QueryReturnType,
|
|
7
|
-
SetQueryReturns,
|
|
8
|
-
WhereResult,
|
|
9
|
-
} from 'pqb';
|
|
10
|
-
|
|
11
|
-
export type QueryMethods<T extends Query> = Record<
|
|
12
|
-
string,
|
|
13
|
-
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
14
|
-
(q: T, ...args: any[]) => any
|
|
15
|
-
>;
|
|
16
|
-
|
|
17
|
-
type QueryOne<T extends Query> = SetQueryReturns<
|
|
18
|
-
T,
|
|
19
|
-
Exclude<QueryReturnType, 'all'>
|
|
20
|
-
>;
|
|
21
|
-
|
|
22
|
-
export type MethodsBase<T extends Query> = {
|
|
23
|
-
queryMethods?: QueryMethods<T>;
|
|
24
|
-
queryOneMethods?: QueryMethods<QueryOne<T>>;
|
|
25
|
-
queryWithWhereMethods?: QueryMethods<WhereResult<T>>;
|
|
26
|
-
queryOneWithWhereMethods?: QueryMethods<QueryOne<WhereResult<T>>>;
|
|
27
|
-
methods?: Record<string, unknown>;
|
|
28
|
-
};
|
|
29
|
-
|
|
30
|
-
export type MapQueryMethods<
|
|
31
|
-
T extends Query,
|
|
32
|
-
BaseQuery extends Query,
|
|
33
|
-
Methods,
|
|
34
|
-
> = Methods extends QueryMethods<T>
|
|
35
|
-
? {
|
|
36
|
-
[K in keyof Methods]: Methods[K] extends (
|
|
37
|
-
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
38
|
-
q: any,
|
|
39
|
-
...args: infer Args
|
|
40
|
-
) => // eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
41
|
-
infer Result
|
|
42
|
-
? <T extends BaseQuery>(
|
|
43
|
-
this: T,
|
|
44
|
-
...args: Args
|
|
45
|
-
) => Result extends Query ? MergeQuery<T, Result> : Result
|
|
46
|
-
: never;
|
|
47
|
-
}
|
|
48
|
-
: EmptyObject;
|
|
49
|
-
|
|
50
|
-
export type MapMethods<
|
|
51
|
-
T extends Query,
|
|
52
|
-
Methods extends MethodsBase<T>,
|
|
53
|
-
> = MapQueryMethods<T, Query, Methods['queryMethods']> &
|
|
54
|
-
MapQueryMethods<QueryOne<T>, QueryOne<Query>, Methods['queryOneMethods']> &
|
|
55
|
-
MapQueryMethods<
|
|
56
|
-
WhereResult<T>,
|
|
57
|
-
WhereResult<Query>,
|
|
58
|
-
Methods['queryWithWhereMethods']
|
|
59
|
-
> &
|
|
60
|
-
MapQueryMethods<
|
|
61
|
-
QueryOne<WhereResult<T>>,
|
|
62
|
-
QueryOne<WhereResult<Query>>,
|
|
63
|
-
Methods['queryOneWithWhereMethods']
|
|
64
|
-
> &
|
|
65
|
-
(Methods['methods'] extends Record<string, unknown>
|
|
66
|
-
? Methods['methods']
|
|
67
|
-
: EmptyObject);
|
|
68
|
-
|
|
69
|
-
export type Repo<
|
|
70
|
-
T extends Query,
|
|
71
|
-
Methods extends MethodsBase<T>,
|
|
72
|
-
Mapped = MapMethods<T, Methods>,
|
|
73
|
-
> = (<Q extends { table: T['table']; shape: T['shape'] }>(q: Q) => Q & Mapped) &
|
|
74
|
-
T &
|
|
75
|
-
Mapped;
|
|
76
|
-
|
|
77
|
-
export const createRepo = <T extends Query, Methods extends MethodsBase<T>>(
|
|
78
|
-
table: T,
|
|
79
|
-
methods: Methods,
|
|
80
|
-
): Repo<T, Methods> => {
|
|
81
|
-
const queryMethods = {
|
|
82
|
-
...methods.queryMethods,
|
|
83
|
-
...methods.queryOneMethods,
|
|
84
|
-
...methods.queryWithWhereMethods,
|
|
85
|
-
...methods.queryOneWithWhereMethods,
|
|
86
|
-
};
|
|
87
|
-
|
|
88
|
-
const plainMethods = methods.methods;
|
|
89
|
-
|
|
90
|
-
const repo = (q: Query) => {
|
|
91
|
-
const proto = Object.create(q.__table);
|
|
92
|
-
proto.__table = proto;
|
|
93
|
-
const result = Object.create(proto);
|
|
94
|
-
result.query = getClonedQueryData(q.query);
|
|
95
|
-
|
|
96
|
-
if (plainMethods) {
|
|
97
|
-
Object.assign(proto.__table, plainMethods);
|
|
98
|
-
}
|
|
99
|
-
|
|
100
|
-
for (const key in queryMethods) {
|
|
101
|
-
const method = queryMethods[key] as (...args: unknown[]) => unknown;
|
|
102
|
-
(proto.__table as unknown as Record<string, unknown>)[key] = function (
|
|
103
|
-
...args: unknown[]
|
|
104
|
-
) {
|
|
105
|
-
return method(this, ...args);
|
|
106
|
-
};
|
|
107
|
-
}
|
|
108
|
-
|
|
109
|
-
return result;
|
|
110
|
-
};
|
|
111
|
-
|
|
112
|
-
const q = repo(table);
|
|
113
|
-
|
|
114
|
-
return new Proxy(repo, {
|
|
115
|
-
get(_, key) {
|
|
116
|
-
return q[key];
|
|
117
|
-
},
|
|
118
|
-
}) as unknown as Repo<T, Methods>;
|
|
119
|
-
};
|
package/src/table.test.ts
DELETED
|
@@ -1,121 +0,0 @@
|
|
|
1
|
-
import { createBaseTable } from './table';
|
|
2
|
-
import { orchidORM } from './orm';
|
|
3
|
-
import { adapter, db } from './test-utils/test-db';
|
|
4
|
-
import { assertType, userData, useTestDatabase } from './test-utils/test-utils';
|
|
5
|
-
import { ColumnType, Operators } from 'pqb';
|
|
6
|
-
import { BaseTable } from './test-utils/test-tables';
|
|
7
|
-
|
|
8
|
-
describe('table', () => {
|
|
9
|
-
useTestDatabase();
|
|
10
|
-
|
|
11
|
-
describe('overriding column types', () => {
|
|
12
|
-
it('should have .raw with overridden types', () => {
|
|
13
|
-
class Type extends ColumnType {
|
|
14
|
-
dataType = 'type';
|
|
15
|
-
operators = Operators.any;
|
|
16
|
-
toCode() {
|
|
17
|
-
return '';
|
|
18
|
-
}
|
|
19
|
-
}
|
|
20
|
-
const type = new Type();
|
|
21
|
-
const BaseTable = createBaseTable({ columnTypes: { type: () => type } });
|
|
22
|
-
class UserTable extends BaseTable {
|
|
23
|
-
table = 'user';
|
|
24
|
-
columns = this.setColumns((t) => ({
|
|
25
|
-
id: t.type().primaryKey(),
|
|
26
|
-
createdAt: t.type(),
|
|
27
|
-
}));
|
|
28
|
-
}
|
|
29
|
-
|
|
30
|
-
const { user } = orchidORM(
|
|
31
|
-
{ adapter },
|
|
32
|
-
{
|
|
33
|
-
user: UserTable,
|
|
34
|
-
},
|
|
35
|
-
);
|
|
36
|
-
|
|
37
|
-
const value = user.raw((t) => t.type(), '');
|
|
38
|
-
|
|
39
|
-
expect(value.__column).toBe(type);
|
|
40
|
-
});
|
|
41
|
-
|
|
42
|
-
it('should return date as string by default', async () => {
|
|
43
|
-
await db.user.create(userData);
|
|
44
|
-
|
|
45
|
-
const BaseTable = createBaseTable();
|
|
46
|
-
class UserTable extends BaseTable {
|
|
47
|
-
table = 'user';
|
|
48
|
-
columns = this.setColumns((t) => ({
|
|
49
|
-
id: t.serial().primaryKey(),
|
|
50
|
-
createdAt: t.timestamp(),
|
|
51
|
-
}));
|
|
52
|
-
}
|
|
53
|
-
|
|
54
|
-
const { user } = orchidORM(
|
|
55
|
-
{ adapter },
|
|
56
|
-
{
|
|
57
|
-
user: UserTable,
|
|
58
|
-
},
|
|
59
|
-
);
|
|
60
|
-
|
|
61
|
-
const result = await user.get('createdAt');
|
|
62
|
-
expect(typeof result).toBe('string');
|
|
63
|
-
|
|
64
|
-
assertType<typeof result, string>();
|
|
65
|
-
});
|
|
66
|
-
|
|
67
|
-
it('should return date as Date when overridden', async () => {
|
|
68
|
-
await db.user.create(userData);
|
|
69
|
-
|
|
70
|
-
const BaseTable = createBaseTable({
|
|
71
|
-
columnTypes: (t) => ({
|
|
72
|
-
serial: t.serial,
|
|
73
|
-
timestamp() {
|
|
74
|
-
return t.timestamp().parse((input) => new Date(input));
|
|
75
|
-
},
|
|
76
|
-
}),
|
|
77
|
-
});
|
|
78
|
-
|
|
79
|
-
class UserTable extends BaseTable {
|
|
80
|
-
table = 'user';
|
|
81
|
-
columns = this.setColumns((t) => ({
|
|
82
|
-
id: t.serial().primaryKey(),
|
|
83
|
-
createdAt: t.timestamp(),
|
|
84
|
-
}));
|
|
85
|
-
}
|
|
86
|
-
|
|
87
|
-
const { user } = orchidORM(
|
|
88
|
-
{ adapter },
|
|
89
|
-
{
|
|
90
|
-
user: UserTable,
|
|
91
|
-
},
|
|
92
|
-
);
|
|
93
|
-
|
|
94
|
-
const result = await user.get('createdAt');
|
|
95
|
-
expect(result instanceof Date).toBe(true);
|
|
96
|
-
|
|
97
|
-
assertType<typeof result, Date>();
|
|
98
|
-
});
|
|
99
|
-
});
|
|
100
|
-
|
|
101
|
-
describe('noPrimaryKey', () => {
|
|
102
|
-
it('should allow to the table to not have a primary key', () => {
|
|
103
|
-
class UserTable extends BaseTable {
|
|
104
|
-
table = 'user';
|
|
105
|
-
noPrimaryKey = true;
|
|
106
|
-
columns = this.setColumns((t) => ({
|
|
107
|
-
name: t.text(),
|
|
108
|
-
}));
|
|
109
|
-
}
|
|
110
|
-
|
|
111
|
-
orchidORM(
|
|
112
|
-
{
|
|
113
|
-
adapter,
|
|
114
|
-
},
|
|
115
|
-
{
|
|
116
|
-
user: UserTable,
|
|
117
|
-
},
|
|
118
|
-
);
|
|
119
|
-
});
|
|
120
|
-
});
|
|
121
|
-
});
|
package/src/table.ts
DELETED
|
@@ -1,184 +0,0 @@
|
|
|
1
|
-
import {
|
|
2
|
-
ColumnShapeOutput,
|
|
3
|
-
ColumnsShape,
|
|
4
|
-
columnTypes,
|
|
5
|
-
ColumnTypesBase,
|
|
6
|
-
Db,
|
|
7
|
-
DefaultColumnTypes,
|
|
8
|
-
getColumnTypes,
|
|
9
|
-
Query,
|
|
10
|
-
} from 'pqb';
|
|
11
|
-
import { MapRelations, Relation, RelationThunks } from './relations/relations';
|
|
12
|
-
import { OrchidORM } from './orm';
|
|
13
|
-
|
|
14
|
-
export type TableClass<T extends Table = Table> = new () => T;
|
|
15
|
-
|
|
16
|
-
export type TableClasses = Record<string, TableClass>;
|
|
17
|
-
|
|
18
|
-
export type TableToDb<T extends Table> = Db<
|
|
19
|
-
T['table'],
|
|
20
|
-
T['columns']['shape'],
|
|
21
|
-
'relations' extends keyof T
|
|
22
|
-
? T['relations'] extends RelationThunks
|
|
23
|
-
? {
|
|
24
|
-
[K in keyof T['relations']]: Relation<T, T['relations'], K>;
|
|
25
|
-
}
|
|
26
|
-
: Query['relations']
|
|
27
|
-
: Query['relations'],
|
|
28
|
-
T['columnTypes']
|
|
29
|
-
> & { definedAs: string; db: OrchidORM<TableClasses> };
|
|
30
|
-
|
|
31
|
-
export type DbTable<T extends TableClass> = TableToDb<InstanceType<T>> &
|
|
32
|
-
Omit<MapRelations<InstanceType<T>>, keyof Query>;
|
|
33
|
-
|
|
34
|
-
type TableConfig = {
|
|
35
|
-
shape: ColumnsShape;
|
|
36
|
-
type: unknown;
|
|
37
|
-
};
|
|
38
|
-
|
|
39
|
-
type ScopeFn<Related extends TableClass, Scope extends Query> = (
|
|
40
|
-
q: DbTable<Related>,
|
|
41
|
-
) => Scope;
|
|
42
|
-
|
|
43
|
-
export type Table = {
|
|
44
|
-
table: string;
|
|
45
|
-
columns: TableConfig;
|
|
46
|
-
schema?: string;
|
|
47
|
-
columnTypes: ColumnTypesBase;
|
|
48
|
-
noPrimaryKey?: boolean;
|
|
49
|
-
};
|
|
50
|
-
|
|
51
|
-
export const createBaseTable = <CT extends ColumnTypesBase>(
|
|
52
|
-
options: {
|
|
53
|
-
columnTypes?: CT | ((t: DefaultColumnTypes) => CT);
|
|
54
|
-
} = { columnTypes: columnTypes as unknown as CT },
|
|
55
|
-
) => {
|
|
56
|
-
const ct =
|
|
57
|
-
typeof options.columnTypes === 'function'
|
|
58
|
-
? options.columnTypes(columnTypes)
|
|
59
|
-
: options.columnTypes;
|
|
60
|
-
|
|
61
|
-
return create(ct as ColumnTypesBase extends CT ? DefaultColumnTypes : CT);
|
|
62
|
-
};
|
|
63
|
-
|
|
64
|
-
const create = <CT extends ColumnTypesBase>(columnTypes: CT) => {
|
|
65
|
-
return class BaseTable {
|
|
66
|
-
table!: string;
|
|
67
|
-
columns!: TableConfig;
|
|
68
|
-
schema?: string;
|
|
69
|
-
columnTypes: CT;
|
|
70
|
-
noPrimaryKey?: boolean;
|
|
71
|
-
|
|
72
|
-
constructor() {
|
|
73
|
-
this.columnTypes = columnTypes;
|
|
74
|
-
}
|
|
75
|
-
|
|
76
|
-
setColumns = <T extends ColumnsShape>(
|
|
77
|
-
fn: (t: CT) => T,
|
|
78
|
-
): { shape: T; type: ColumnShapeOutput<T> } => {
|
|
79
|
-
const shape = getColumnTypes(columnTypes, fn);
|
|
80
|
-
|
|
81
|
-
return {
|
|
82
|
-
shape,
|
|
83
|
-
type: undefined as unknown as ColumnShapeOutput<T>,
|
|
84
|
-
};
|
|
85
|
-
};
|
|
86
|
-
|
|
87
|
-
belongsTo<
|
|
88
|
-
Self extends this,
|
|
89
|
-
Related extends TableClass,
|
|
90
|
-
Scope extends Query,
|
|
91
|
-
Options extends {
|
|
92
|
-
primaryKey: keyof InstanceType<Related>['columns']['shape'];
|
|
93
|
-
foreignKey: keyof Self['columns']['shape'];
|
|
94
|
-
scope?: ScopeFn<Related, Scope>;
|
|
95
|
-
required?: boolean;
|
|
96
|
-
},
|
|
97
|
-
>(this: Self, fn: () => Related, options: Options) {
|
|
98
|
-
return {
|
|
99
|
-
type: 'belongsTo' as const,
|
|
100
|
-
returns: 'one' as const,
|
|
101
|
-
fn,
|
|
102
|
-
options,
|
|
103
|
-
};
|
|
104
|
-
}
|
|
105
|
-
|
|
106
|
-
hasOne<
|
|
107
|
-
Self extends this,
|
|
108
|
-
Related extends TableClass,
|
|
109
|
-
Scope extends Query,
|
|
110
|
-
Through extends string,
|
|
111
|
-
Source extends string,
|
|
112
|
-
Options extends (
|
|
113
|
-
| {
|
|
114
|
-
primaryKey: keyof Self['columns']['shape'];
|
|
115
|
-
foreignKey: keyof InstanceType<Related>['columns']['shape'];
|
|
116
|
-
}
|
|
117
|
-
| {
|
|
118
|
-
through: Through;
|
|
119
|
-
source: Source;
|
|
120
|
-
}
|
|
121
|
-
) & {
|
|
122
|
-
scope?: ScopeFn<Related, Scope>;
|
|
123
|
-
required?: boolean;
|
|
124
|
-
},
|
|
125
|
-
>(this: Self, fn: () => Related, options: Options) {
|
|
126
|
-
return {
|
|
127
|
-
type: 'hasOne' as const,
|
|
128
|
-
returns: 'one' as const,
|
|
129
|
-
fn,
|
|
130
|
-
options,
|
|
131
|
-
};
|
|
132
|
-
}
|
|
133
|
-
|
|
134
|
-
hasMany<
|
|
135
|
-
Self extends this,
|
|
136
|
-
Related extends TableClass,
|
|
137
|
-
Scope extends Query,
|
|
138
|
-
Through extends string,
|
|
139
|
-
Source extends string,
|
|
140
|
-
Options extends (
|
|
141
|
-
| {
|
|
142
|
-
primaryKey: keyof Self['columns']['shape'];
|
|
143
|
-
foreignKey: keyof InstanceType<Related>['columns']['shape'];
|
|
144
|
-
}
|
|
145
|
-
| {
|
|
146
|
-
through: Through;
|
|
147
|
-
source: Source;
|
|
148
|
-
}
|
|
149
|
-
) & {
|
|
150
|
-
scope?: ScopeFn<Related, Scope>;
|
|
151
|
-
required?: boolean;
|
|
152
|
-
},
|
|
153
|
-
>(this: Self, fn: () => Related, options: Options) {
|
|
154
|
-
return {
|
|
155
|
-
type: 'hasMany' as const,
|
|
156
|
-
returns: 'many' as const,
|
|
157
|
-
fn,
|
|
158
|
-
options,
|
|
159
|
-
};
|
|
160
|
-
}
|
|
161
|
-
|
|
162
|
-
hasAndBelongsToMany<
|
|
163
|
-
Self extends this,
|
|
164
|
-
Related extends TableClass,
|
|
165
|
-
Scope extends Query,
|
|
166
|
-
Options extends {
|
|
167
|
-
primaryKey: keyof Self['columns']['shape'];
|
|
168
|
-
associationPrimaryKey: keyof InstanceType<Related>['columns']['shape'];
|
|
169
|
-
foreignKey: string;
|
|
170
|
-
associationForeignKey: string;
|
|
171
|
-
joinTable: string;
|
|
172
|
-
scope?: ScopeFn<Related, Scope>;
|
|
173
|
-
required?: boolean;
|
|
174
|
-
},
|
|
175
|
-
>(this: Self, fn: () => Related, options: Options) {
|
|
176
|
-
return {
|
|
177
|
-
type: 'hasAndBelongsToMany' as const,
|
|
178
|
-
returns: 'many' as const,
|
|
179
|
-
fn,
|
|
180
|
-
options,
|
|
181
|
-
};
|
|
182
|
-
}
|
|
183
|
-
};
|
|
184
|
-
};
|
|
@@ -1,32 +0,0 @@
|
|
|
1
|
-
import { orchidORM } from '../orm';
|
|
2
|
-
import {
|
|
3
|
-
ChatTable,
|
|
4
|
-
MessageTable,
|
|
5
|
-
PostTable,
|
|
6
|
-
PostTagTable,
|
|
7
|
-
ProfileTable,
|
|
8
|
-
TagTable,
|
|
9
|
-
UserTable,
|
|
10
|
-
} from './test-tables';
|
|
11
|
-
|
|
12
|
-
export const pgConfig = {
|
|
13
|
-
databaseURL: process.env.DATABASE_URL,
|
|
14
|
-
};
|
|
15
|
-
|
|
16
|
-
export const db = orchidORM(
|
|
17
|
-
{
|
|
18
|
-
...pgConfig,
|
|
19
|
-
log: false,
|
|
20
|
-
},
|
|
21
|
-
{
|
|
22
|
-
user: UserTable,
|
|
23
|
-
profile: ProfileTable,
|
|
24
|
-
chat: ChatTable,
|
|
25
|
-
message: MessageTable,
|
|
26
|
-
post: PostTable,
|
|
27
|
-
postTag: PostTagTable,
|
|
28
|
-
tag: TagTable,
|
|
29
|
-
},
|
|
30
|
-
);
|
|
31
|
-
|
|
32
|
-
export const adapter = db.$adapter;
|