@aurios/mizzle 1.0.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.
- package/CHANGELOG.md +20 -0
- package/package.json +62 -0
- package/src/builders/base.ts +71 -0
- package/src/builders/batch-get.ts +76 -0
- package/src/builders/batch-write.ts +98 -0
- package/src/builders/delete.ts +61 -0
- package/src/builders/insert.ts +156 -0
- package/src/builders/query-promise.ts +41 -0
- package/src/builders/relational-builder.ts +211 -0
- package/src/builders/select.ts +196 -0
- package/src/builders/transaction.ts +170 -0
- package/src/builders/update.ts +155 -0
- package/src/columns/binary-set.ts +49 -0
- package/src/columns/binary.ts +48 -0
- package/src/columns/boolean.ts +45 -0
- package/src/columns/date.ts +83 -0
- package/src/columns/index.ts +44 -0
- package/src/columns/json.ts +62 -0
- package/src/columns/list.ts +47 -0
- package/src/columns/map.ts +46 -0
- package/src/columns/number-set.ts +49 -0
- package/src/columns/number.ts +57 -0
- package/src/columns/string-set.ts +59 -0
- package/src/columns/string.ts +64 -0
- package/src/columns/uuid.ts +51 -0
- package/src/core/client.ts +18 -0
- package/src/core/column-builder.ts +272 -0
- package/src/core/column.ts +167 -0
- package/src/core/diff.ts +50 -0
- package/src/core/errors.ts +34 -0
- package/src/core/introspection.ts +73 -0
- package/src/core/operations.ts +34 -0
- package/src/core/parser.ts +109 -0
- package/src/core/relations.ts +149 -0
- package/src/core/retry.ts +70 -0
- package/src/core/snapshot.ts +192 -0
- package/src/core/strategies.ts +271 -0
- package/src/core/table.ts +260 -0
- package/src/core/validation.ts +75 -0
- package/src/db.ts +199 -0
- package/src/expressions/actions.ts +66 -0
- package/src/expressions/builder.ts +77 -0
- package/src/expressions/operators.ts +108 -0
- package/src/expressions/update-builder.ts +98 -0
- package/src/index.ts +20 -0
- package/src/indexes.ts +19 -0
- package/tsconfig.json +11 -0
- package/tsup.config.ts +20 -0
|
@@ -0,0 +1,155 @@
|
|
|
1
|
+
import { UpdateCommand } from "@aws-sdk/lib-dynamodb";
|
|
2
|
+
import { ENTITY_SYMBOLS } from "@mizzle/shared";
|
|
3
|
+
import { Entity, type InferInsertModel } from "../core/table";
|
|
4
|
+
import { type Expression } from "../expressions/operators";
|
|
5
|
+
import { BaseBuilder } from "./base";
|
|
6
|
+
import { type IMizzleClient } from "../core/client";
|
|
7
|
+
import { calculateItemSize } from "../core/validation";
|
|
8
|
+
import { ItemSizeExceededError } from "../core/errors";
|
|
9
|
+
import { buildExpression } from "../expressions/builder";
|
|
10
|
+
import { UpdateAction } from "../expressions/actions";
|
|
11
|
+
import {
|
|
12
|
+
createUpdateState,
|
|
13
|
+
partitionUpdateValues,
|
|
14
|
+
buildUpdateExpressionString
|
|
15
|
+
} from "../expressions/update-builder";
|
|
16
|
+
|
|
17
|
+
export class UpdateBuilder<
|
|
18
|
+
TEntity extends Entity,
|
|
19
|
+
TResult = unknown,
|
|
20
|
+
> extends BaseBuilder<TEntity, TResult> {
|
|
21
|
+
static readonly [ENTITY_SYMBOLS.ENTITY_KIND]: string = "UpdateBuilder";
|
|
22
|
+
|
|
23
|
+
private _state = createUpdateState();
|
|
24
|
+
private _whereClause?: Expression;
|
|
25
|
+
private _returnValues?: "NONE" | "ALL_OLD" | "UPDATED_OLD" | "ALL_NEW" | "UPDATED_NEW";
|
|
26
|
+
private _explicitKey?: Record<string, unknown>;
|
|
27
|
+
|
|
28
|
+
constructor(
|
|
29
|
+
entity: TEntity,
|
|
30
|
+
client: IMizzleClient,
|
|
31
|
+
) {
|
|
32
|
+
super(entity, client);
|
|
33
|
+
}
|
|
34
|
+
|
|
35
|
+
key(keyObject: Record<string, unknown>): this {
|
|
36
|
+
this._explicitKey = keyObject;
|
|
37
|
+
return this;
|
|
38
|
+
}
|
|
39
|
+
|
|
40
|
+
set(values: Partial<{ [K in keyof InferInsertModel<TEntity>]: InferInsertModel<TEntity>[K] | UpdateAction }>): this {
|
|
41
|
+
partitionUpdateValues(values as Record<string, any>, this._state, this.entity[ENTITY_SYMBOLS.COLUMNS] as Record<string, any>);
|
|
42
|
+
return this;
|
|
43
|
+
}
|
|
44
|
+
|
|
45
|
+
add(values: Partial<InferInsertModel<TEntity>>): this {
|
|
46
|
+
const columns = this.entity[ENTITY_SYMBOLS.COLUMNS] as Record<string, any>;
|
|
47
|
+
for (const [key, val] of Object.entries(values)) {
|
|
48
|
+
const col = columns[key];
|
|
49
|
+
this._state.add[key] = (col && typeof col.mapToDynamoValue === "function")
|
|
50
|
+
? col.mapToDynamoValue(val)
|
|
51
|
+
: val;
|
|
52
|
+
}
|
|
53
|
+
return this;
|
|
54
|
+
}
|
|
55
|
+
|
|
56
|
+
remove(...fields: (keyof InferInsertModel<TEntity> | (string & {}))[]): this {
|
|
57
|
+
this._state.remove.push(...(fields as string[]));
|
|
58
|
+
return this;
|
|
59
|
+
}
|
|
60
|
+
|
|
61
|
+
delete(values: Partial<InferInsertModel<TEntity>>): this {
|
|
62
|
+
const columns = this.entity[ENTITY_SYMBOLS.COLUMNS] as Record<string, any>;
|
|
63
|
+
for (const [key, val] of Object.entries(values)) {
|
|
64
|
+
const col = columns[key];
|
|
65
|
+
this._state.delete[key] = (col && typeof col.mapToDynamoValue === "function")
|
|
66
|
+
? col.mapToDynamoValue(val)
|
|
67
|
+
: val;
|
|
68
|
+
}
|
|
69
|
+
return this;
|
|
70
|
+
}
|
|
71
|
+
|
|
72
|
+
where(expression: Expression): this {
|
|
73
|
+
this._whereClause = expression;
|
|
74
|
+
return this;
|
|
75
|
+
}
|
|
76
|
+
|
|
77
|
+
returning(value: "NONE" | "ALL_OLD" | "UPDATED_OLD" | "ALL_NEW" | "UPDATED_NEW"): this {
|
|
78
|
+
this._returnValues = value;
|
|
79
|
+
return this;
|
|
80
|
+
}
|
|
81
|
+
|
|
82
|
+
/** @internal */
|
|
83
|
+
get state() {
|
|
84
|
+
return this._state;
|
|
85
|
+
}
|
|
86
|
+
|
|
87
|
+
/** @internal */
|
|
88
|
+
get whereClause() {
|
|
89
|
+
return this._whereClause;
|
|
90
|
+
}
|
|
91
|
+
|
|
92
|
+
/** @internal */
|
|
93
|
+
public override createExpressionContext(prefix = "") {
|
|
94
|
+
return super.createExpressionContext(prefix);
|
|
95
|
+
}
|
|
96
|
+
|
|
97
|
+
public override async execute(): Promise<TResult> {
|
|
98
|
+
const columns = this.entity[ENTITY_SYMBOLS.COLUMNS] as Record<string, any>;
|
|
99
|
+
for (const [key, col] of Object.entries(columns)) {
|
|
100
|
+
if (col.onUpdateFn && !this._state.set[key] && !this._state.remove.includes(key)) {
|
|
101
|
+
const val = col.onUpdateFn();
|
|
102
|
+
this._state.set[key] = {
|
|
103
|
+
value: typeof col.mapToDynamoValue === "function" ? col.mapToDynamoValue(val) : val
|
|
104
|
+
};
|
|
105
|
+
}
|
|
106
|
+
}
|
|
107
|
+
|
|
108
|
+
const keys = this.resolveUpdateKeys();
|
|
109
|
+
|
|
110
|
+
const { expressionAttributeNames, expressionAttributeValues, addName, addValue } = this.createExpressionContext("up_");
|
|
111
|
+
|
|
112
|
+
const updateExpression = buildUpdateExpressionString(this._state, addName, addValue);
|
|
113
|
+
|
|
114
|
+
let conditionExpression: string | undefined;
|
|
115
|
+
if (this._whereClause) {
|
|
116
|
+
conditionExpression = buildExpression(this._whereClause, addName, addValue);
|
|
117
|
+
}
|
|
118
|
+
|
|
119
|
+
// Estimate size for Update
|
|
120
|
+
// Update size is basically keys + attribute values.
|
|
121
|
+
const size = calculateItemSize({ ...keys, ...expressionAttributeValues });
|
|
122
|
+
if (size > 400 * 1024) {
|
|
123
|
+
throw new ItemSizeExceededError(`Estimated update size of ${Math.round(size / 1024)}KB exceeds the 400KB limit.`);
|
|
124
|
+
}
|
|
125
|
+
|
|
126
|
+
const command = new UpdateCommand({
|
|
127
|
+
TableName: this.tableName,
|
|
128
|
+
Key: keys,
|
|
129
|
+
UpdateExpression: updateExpression,
|
|
130
|
+
ConditionExpression: conditionExpression,
|
|
131
|
+
ExpressionAttributeNames:
|
|
132
|
+
Object.keys(expressionAttributeNames).length > 0
|
|
133
|
+
? expressionAttributeNames
|
|
134
|
+
: undefined,
|
|
135
|
+
ExpressionAttributeValues:
|
|
136
|
+
Object.keys(expressionAttributeValues).length > 0
|
|
137
|
+
? expressionAttributeValues
|
|
138
|
+
: undefined,
|
|
139
|
+
ReturnValues: this._returnValues,
|
|
140
|
+
});
|
|
141
|
+
|
|
142
|
+
const response = await this.client.send(command);
|
|
143
|
+
return response.Attributes as TResult;
|
|
144
|
+
}
|
|
145
|
+
|
|
146
|
+
/** @internal */
|
|
147
|
+
public resolveUpdateKeys(): Record<string, unknown> {
|
|
148
|
+
if (this._explicitKey) {
|
|
149
|
+
return this._explicitKey;
|
|
150
|
+
}
|
|
151
|
+
|
|
152
|
+
const resolved = this.resolveKeys(this._whereClause);
|
|
153
|
+
return resolved.keys;
|
|
154
|
+
}
|
|
155
|
+
}
|
|
@@ -0,0 +1,49 @@
|
|
|
1
|
+
import {
|
|
2
|
+
Column,
|
|
3
|
+
type ColumnBaseConfig,
|
|
4
|
+
type ColumnRuntimeConfig,
|
|
5
|
+
} from "../core/column";
|
|
6
|
+
import {
|
|
7
|
+
ColumnBuider,
|
|
8
|
+
type ColumnBuilderBaseConfig,
|
|
9
|
+
type MakeColumnConfig,
|
|
10
|
+
} from "../core/column-builder";
|
|
11
|
+
import type { AnyTable } from "../core/table";
|
|
12
|
+
|
|
13
|
+
export type BinarySetColumnInitial<TName extends string> =
|
|
14
|
+
BinarySetColumnBuilder<{
|
|
15
|
+
name: TName;
|
|
16
|
+
dataType: "binarySet";
|
|
17
|
+
columnType: "BS";
|
|
18
|
+
data: Set<Uint8Array>;
|
|
19
|
+
}>;
|
|
20
|
+
|
|
21
|
+
export class BinarySetColumnBuilder<
|
|
22
|
+
T extends ColumnBuilderBaseConfig<"binarySet", "BS">,
|
|
23
|
+
> extends ColumnBuider<T> {
|
|
24
|
+
constructor(name: T["name"]) {
|
|
25
|
+
super(name, "binarySet", "BS");
|
|
26
|
+
}
|
|
27
|
+
|
|
28
|
+
override build<TTableName extends string>(
|
|
29
|
+
table: AnyTable,
|
|
30
|
+
): BinarySetColumn<MakeColumnConfig<T, TTableName>> {
|
|
31
|
+
return new BinarySetColumn<MakeColumnConfig<T, TTableName>>(
|
|
32
|
+
table,
|
|
33
|
+
this.config as any,
|
|
34
|
+
);
|
|
35
|
+
}
|
|
36
|
+
}
|
|
37
|
+
|
|
38
|
+
export class BinarySetColumn<
|
|
39
|
+
T extends ColumnBaseConfig<"binarySet", "BS">,
|
|
40
|
+
> extends Column<T> {
|
|
41
|
+
}
|
|
42
|
+
|
|
43
|
+
export function binarySet(): BinarySetColumnInitial<"">;
|
|
44
|
+
export function binarySet<TName extends string>(
|
|
45
|
+
name: TName,
|
|
46
|
+
): BinarySetColumnInitial<TName>;
|
|
47
|
+
export function binarySet(name?: string) {
|
|
48
|
+
return new BinarySetColumnBuilder(name ?? "");
|
|
49
|
+
}
|
|
@@ -0,0 +1,48 @@
|
|
|
1
|
+
import {
|
|
2
|
+
Column,
|
|
3
|
+
type ColumnBaseConfig,
|
|
4
|
+
type ColumnRuntimeConfig,
|
|
5
|
+
} from "../core/column";
|
|
6
|
+
import {
|
|
7
|
+
ColumnBuider,
|
|
8
|
+
type ColumnBuilderBaseConfig,
|
|
9
|
+
type MakeColumnConfig,
|
|
10
|
+
} from "../core/column-builder";
|
|
11
|
+
import type { AnyTable } from "../core/table";
|
|
12
|
+
|
|
13
|
+
export type BinaryBuilderInitial<TName extends string> = BinaryColumnBuilder<{
|
|
14
|
+
name: TName;
|
|
15
|
+
dataType: "binary";
|
|
16
|
+
columnType: "B";
|
|
17
|
+
data: Buffer;
|
|
18
|
+
}>;
|
|
19
|
+
|
|
20
|
+
export class BinaryColumnBuilder<
|
|
21
|
+
T extends ColumnBuilderBaseConfig<"binary", "B">,
|
|
22
|
+
> extends ColumnBuider<T> {
|
|
23
|
+
constructor(name: T["name"]) {
|
|
24
|
+
super(name, "binary", "B");
|
|
25
|
+
}
|
|
26
|
+
|
|
27
|
+
build<TTableName extends string>(
|
|
28
|
+
table: AnyTable,
|
|
29
|
+
): BinaryColumn<MakeColumnConfig<T, TTableName>> {
|
|
30
|
+
return new BinaryColumn<MakeColumnConfig<T, TTableName>>(
|
|
31
|
+
table,
|
|
32
|
+
this.config as any,
|
|
33
|
+
);
|
|
34
|
+
}
|
|
35
|
+
}
|
|
36
|
+
|
|
37
|
+
export class BinaryColumn<
|
|
38
|
+
T extends ColumnBaseConfig<"binary", "B">,
|
|
39
|
+
> extends Column<T> {
|
|
40
|
+
}
|
|
41
|
+
|
|
42
|
+
export function binary(): BinaryBuilderInitial<"">;
|
|
43
|
+
export function binary<TName extends string>(
|
|
44
|
+
name: TName,
|
|
45
|
+
): BinaryBuilderInitial<TName>;
|
|
46
|
+
export function binary(name?: string) {
|
|
47
|
+
return new BinaryColumnBuilder(name ?? "");
|
|
48
|
+
}
|
|
@@ -0,0 +1,45 @@
|
|
|
1
|
+
import { Column, type ColumnBaseConfig } from "../core/column";
|
|
2
|
+
import {
|
|
3
|
+
ColumnBuider,
|
|
4
|
+
type ColumnBuilderBaseConfig,
|
|
5
|
+
type ColumnBuilderRuntimeConfig,
|
|
6
|
+
type MakeColumnConfig,
|
|
7
|
+
} from "../core/column-builder";
|
|
8
|
+
import type { AnyTable } from "../core/table";
|
|
9
|
+
|
|
10
|
+
export type BooleanColumnInitial<TName extends string> = BooleanColumnBuilder<{
|
|
11
|
+
name: TName;
|
|
12
|
+
dataType: "boolean";
|
|
13
|
+
columnType: "BOOL";
|
|
14
|
+
data: boolean;
|
|
15
|
+
}>;
|
|
16
|
+
|
|
17
|
+
export class BooleanColumnBuilder<
|
|
18
|
+
T extends ColumnBuilderBaseConfig<"boolean", "BOOL">,
|
|
19
|
+
> extends ColumnBuider<T> {
|
|
20
|
+
constructor(name: T["name"]) {
|
|
21
|
+
super(name, "boolean", "BOOL");
|
|
22
|
+
}
|
|
23
|
+
|
|
24
|
+
build<TTableName extends string>(
|
|
25
|
+
table: AnyTable,
|
|
26
|
+
): BooleanColumn<MakeColumnConfig<T, TTableName>> {
|
|
27
|
+
return new BooleanColumn<MakeColumnConfig<T, TTableName>>(
|
|
28
|
+
table,
|
|
29
|
+
this.config as any,
|
|
30
|
+
);
|
|
31
|
+
}
|
|
32
|
+
}
|
|
33
|
+
|
|
34
|
+
export class BooleanColumn<
|
|
35
|
+
T extends ColumnBaseConfig<"boolean", "BOOL">,
|
|
36
|
+
> extends Column<T> {
|
|
37
|
+
}
|
|
38
|
+
|
|
39
|
+
export function boolean(): BooleanColumnInitial<"">;
|
|
40
|
+
export function boolean<TName extends string>(
|
|
41
|
+
name: TName,
|
|
42
|
+
): BooleanColumnInitial<TName>;
|
|
43
|
+
export function boolean(name?: string) {
|
|
44
|
+
return new BooleanColumnBuilder(name ?? "");
|
|
45
|
+
}
|
|
@@ -0,0 +1,83 @@
|
|
|
1
|
+
import {
|
|
2
|
+
Column,
|
|
3
|
+
type ColumnBaseConfig,
|
|
4
|
+
type ColumnRuntimeConfig,
|
|
5
|
+
} from "../core/column";
|
|
6
|
+
import {
|
|
7
|
+
ColumnBuider,
|
|
8
|
+
type ColumnBuilderBaseConfig,
|
|
9
|
+
type MakeColumnConfig,
|
|
10
|
+
type HasDefault,
|
|
11
|
+
type HasRuntimeDefault,
|
|
12
|
+
} from "../core/column-builder";
|
|
13
|
+
import type { AnyTable } from "../core/table";
|
|
14
|
+
|
|
15
|
+
export type DateColumnInitial<TName extends string> = DateColumnBuilder<{
|
|
16
|
+
name: TName;
|
|
17
|
+
dataType: "date";
|
|
18
|
+
columnType: "S";
|
|
19
|
+
data: Date;
|
|
20
|
+
}>;
|
|
21
|
+
|
|
22
|
+
export class DateColumnBuilder<
|
|
23
|
+
T extends ColumnBuilderBaseConfig<"date", "S">,
|
|
24
|
+
> extends ColumnBuider<T> {
|
|
25
|
+
constructor(name: T["name"]) {
|
|
26
|
+
super(name, "date", "S");
|
|
27
|
+
}
|
|
28
|
+
|
|
29
|
+
defaultNow(): HasRuntimeDefault<HasDefault<this>> {
|
|
30
|
+
return this.$defaultFn(() => new Date() as any);
|
|
31
|
+
}
|
|
32
|
+
|
|
33
|
+
onUpdateNow(): HasDefault<this> {
|
|
34
|
+
return this.$onUpdateFn(() => new Date() as any);
|
|
35
|
+
}
|
|
36
|
+
|
|
37
|
+
build<TTableName extends string>(
|
|
38
|
+
table: AnyTable,
|
|
39
|
+
): DateColumn<MakeColumnConfig<T, TTableName>> {
|
|
40
|
+
return new DateColumn<MakeColumnConfig<T, TTableName>>(
|
|
41
|
+
table,
|
|
42
|
+
this.config as any,
|
|
43
|
+
);
|
|
44
|
+
}
|
|
45
|
+
}
|
|
46
|
+
|
|
47
|
+
export class DateColumn<
|
|
48
|
+
T extends ColumnBaseConfig<"date", "S">,
|
|
49
|
+
> extends Column<T> {
|
|
50
|
+
override mapToDynamoValue(value: unknown): unknown {
|
|
51
|
+
if (value === null || value === undefined) {
|
|
52
|
+
return value;
|
|
53
|
+
}
|
|
54
|
+
|
|
55
|
+
let date: Date;
|
|
56
|
+
if (value instanceof Date) {
|
|
57
|
+
date = value;
|
|
58
|
+
} else if (typeof value === "string" || typeof value === "number") {
|
|
59
|
+
date = new Date(value);
|
|
60
|
+
} else {
|
|
61
|
+
throw new Error(`Invalid date value: ${value}`);
|
|
62
|
+
}
|
|
63
|
+
|
|
64
|
+
if (Number.isNaN(date.getTime())) {
|
|
65
|
+
throw new Error(`Invalid date value: ${value}`);
|
|
66
|
+
}
|
|
67
|
+
|
|
68
|
+
return date.toISOString();
|
|
69
|
+
}
|
|
70
|
+
|
|
71
|
+
override mapFromDynamoValue(value: unknown): unknown {
|
|
72
|
+
if (typeof value === "string") {
|
|
73
|
+
return new Date(value);
|
|
74
|
+
}
|
|
75
|
+
return value;
|
|
76
|
+
}
|
|
77
|
+
}
|
|
78
|
+
|
|
79
|
+
export function date(): DateColumnInitial<"">;
|
|
80
|
+
export function date<TName extends string>(name: TName): DateColumnInitial<TName>;
|
|
81
|
+
export function date(name?: string) {
|
|
82
|
+
return new DateColumnBuilder(name ?? "");
|
|
83
|
+
}
|
|
@@ -0,0 +1,44 @@
|
|
|
1
|
+
export { binary } from "./binary";
|
|
2
|
+
export { binarySet } from "./binary-set";
|
|
3
|
+
export { boolean } from "./boolean";
|
|
4
|
+
export { date } from "./date";
|
|
5
|
+
export { list } from "./list";
|
|
6
|
+
export { map } from "./map";
|
|
7
|
+
export { number } from "./number";
|
|
8
|
+
export { numberSet } from "./number-set";
|
|
9
|
+
export { string } from "./string";
|
|
10
|
+
export { stringSet } from "./string-set";
|
|
11
|
+
export { uuid } from "./uuid";
|
|
12
|
+
export { json } from "./json";
|
|
13
|
+
|
|
14
|
+
import { binary } from "./binary";
|
|
15
|
+
import { binarySet } from "./binary-set";
|
|
16
|
+
import { boolean } from "./boolean";
|
|
17
|
+
import { date } from "./date";
|
|
18
|
+
import { json } from "./json";
|
|
19
|
+
import { list } from "./list";
|
|
20
|
+
import { map } from "./map";
|
|
21
|
+
import { number } from "./number";
|
|
22
|
+
import { numberSet } from "./number-set";
|
|
23
|
+
import { string } from "./string";
|
|
24
|
+
import { stringSet } from "./string-set";
|
|
25
|
+
import { uuid } from "./uuid";
|
|
26
|
+
|
|
27
|
+
export function getColumnBuilders() {
|
|
28
|
+
return {
|
|
29
|
+
binary,
|
|
30
|
+
binarySet,
|
|
31
|
+
boolean,
|
|
32
|
+
date,
|
|
33
|
+
json,
|
|
34
|
+
list,
|
|
35
|
+
map,
|
|
36
|
+
number,
|
|
37
|
+
numberSet,
|
|
38
|
+
string,
|
|
39
|
+
stringSet,
|
|
40
|
+
uuid,
|
|
41
|
+
};
|
|
42
|
+
}
|
|
43
|
+
|
|
44
|
+
export type ColumnsBuilder = ReturnType<typeof getColumnBuilders>;
|
|
@@ -0,0 +1,62 @@
|
|
|
1
|
+
import {
|
|
2
|
+
Column,
|
|
3
|
+
type ColumnBaseConfig,
|
|
4
|
+
type ColumnRuntimeConfig,
|
|
5
|
+
} from "../core/column";
|
|
6
|
+
import {
|
|
7
|
+
ColumnBuider,
|
|
8
|
+
type ColumnBuilderBaseConfig,
|
|
9
|
+
type MakeColumnConfig,
|
|
10
|
+
} from "../core/column-builder";
|
|
11
|
+
import type { AnyTable } from "../core/table";
|
|
12
|
+
|
|
13
|
+
export type JsonColumnInitial<TName extends string> = JsonColumnBuilder<{
|
|
14
|
+
name: TName;
|
|
15
|
+
dataType: "json";
|
|
16
|
+
columnType: "S";
|
|
17
|
+
data: unknown;
|
|
18
|
+
}>;
|
|
19
|
+
|
|
20
|
+
export class JsonColumnBuilder<
|
|
21
|
+
T extends ColumnBuilderBaseConfig<"json", "S">,
|
|
22
|
+
> extends ColumnBuider<T> {
|
|
23
|
+
constructor(name: T["name"]) {
|
|
24
|
+
super(name, "json", "S");
|
|
25
|
+
}
|
|
26
|
+
|
|
27
|
+
build<TTableName extends string>(
|
|
28
|
+
table: AnyTable,
|
|
29
|
+
): JsonColumn<MakeColumnConfig<T, TTableName>> {
|
|
30
|
+
return new JsonColumn<MakeColumnConfig<T, TTableName>>(
|
|
31
|
+
table,
|
|
32
|
+
this.config as any,
|
|
33
|
+
);
|
|
34
|
+
}
|
|
35
|
+
}
|
|
36
|
+
|
|
37
|
+
export class JsonColumn<
|
|
38
|
+
T extends ColumnBaseConfig<"json", "S">,
|
|
39
|
+
> extends Column<T> {
|
|
40
|
+
override mapToDynamoValue(value: T["data"]): string {
|
|
41
|
+
return JSON.stringify(value);
|
|
42
|
+
}
|
|
43
|
+
|
|
44
|
+
override mapFromDynamoValue(value: T["data"] | string): T["data"] {
|
|
45
|
+
if (typeof value === "string") {
|
|
46
|
+
try {
|
|
47
|
+
return JSON.parse(value);
|
|
48
|
+
} catch {
|
|
49
|
+
return value as T["data"];
|
|
50
|
+
}
|
|
51
|
+
}
|
|
52
|
+
return value;
|
|
53
|
+
}
|
|
54
|
+
}
|
|
55
|
+
|
|
56
|
+
export function json(): JsonColumnInitial<"">;
|
|
57
|
+
export function json<TName extends string>(
|
|
58
|
+
name: TName,
|
|
59
|
+
): JsonColumnInitial<TName>;
|
|
60
|
+
export function json(name?: string) {
|
|
61
|
+
return new JsonColumnBuilder(name ?? "");
|
|
62
|
+
}
|
|
@@ -0,0 +1,47 @@
|
|
|
1
|
+
import {
|
|
2
|
+
Column,
|
|
3
|
+
type ColumnBaseConfig,
|
|
4
|
+
type ColumnRuntimeConfig,
|
|
5
|
+
} from "../core/column";
|
|
6
|
+
import {
|
|
7
|
+
ColumnBuider,
|
|
8
|
+
type ColumnBuilderBaseConfig,
|
|
9
|
+
type MakeColumnConfig,
|
|
10
|
+
} from "../core/column-builder";
|
|
11
|
+
import type { AnyTable } from "../core/table";
|
|
12
|
+
|
|
13
|
+
export type ListColumnInitial<TName extends string> = ListColumnBuilder<{
|
|
14
|
+
name: TName;
|
|
15
|
+
data: unknown[];
|
|
16
|
+
dataType: "array";
|
|
17
|
+
columnType: "L";
|
|
18
|
+
}>;
|
|
19
|
+
|
|
20
|
+
export class ListColumnBuilder<
|
|
21
|
+
T extends ColumnBuilderBaseConfig<"array", "L">,
|
|
22
|
+
> extends ColumnBuider<T> {
|
|
23
|
+
constructor(name: T["name"]) {
|
|
24
|
+
super(name, "array", "L");
|
|
25
|
+
}
|
|
26
|
+
build<TTableName extends string>(
|
|
27
|
+
table: AnyTable,
|
|
28
|
+
): ListColumn<MakeColumnConfig<T, TTableName>> {
|
|
29
|
+
return new ListColumn<MakeColumnConfig<T, TTableName>>(
|
|
30
|
+
table,
|
|
31
|
+
this.config as any,
|
|
32
|
+
);
|
|
33
|
+
}
|
|
34
|
+
}
|
|
35
|
+
|
|
36
|
+
export class ListColumn<
|
|
37
|
+
T extends ColumnBaseConfig<"array", "L">,
|
|
38
|
+
> extends Column<T> {
|
|
39
|
+
}
|
|
40
|
+
|
|
41
|
+
export function list(): ListColumnInitial<"">;
|
|
42
|
+
export function list<TName extends string>(
|
|
43
|
+
name: TName,
|
|
44
|
+
): ListColumnInitial<TName>;
|
|
45
|
+
export function list(name?: string) {
|
|
46
|
+
return new ListColumnBuilder(name ?? "");
|
|
47
|
+
}
|
|
@@ -0,0 +1,46 @@
|
|
|
1
|
+
import {
|
|
2
|
+
Column,
|
|
3
|
+
type ColumnBaseConfig,
|
|
4
|
+
type ColumnRuntimeConfig,
|
|
5
|
+
} from "../core/column";
|
|
6
|
+
import {
|
|
7
|
+
ColumnBuider,
|
|
8
|
+
type ColumnBuilderBaseConfig,
|
|
9
|
+
type MakeColumnConfig,
|
|
10
|
+
} from "../core/column-builder";
|
|
11
|
+
import type { AnyTable } from "../core/table";
|
|
12
|
+
|
|
13
|
+
export type MapColumnInitial<TName extends string> = MapColumnBuilder<{
|
|
14
|
+
name: TName;
|
|
15
|
+
data: Record<string, unknown>;
|
|
16
|
+
dataType: "map";
|
|
17
|
+
columnType: "M";
|
|
18
|
+
}>;
|
|
19
|
+
|
|
20
|
+
export class MapColumnBuilder<
|
|
21
|
+
T extends ColumnBuilderBaseConfig<"map", "M">,
|
|
22
|
+
> extends ColumnBuider<T> {
|
|
23
|
+
constructor(name: T["name"]) {
|
|
24
|
+
super(name, "map", "M");
|
|
25
|
+
}
|
|
26
|
+
|
|
27
|
+
build<TTableName extends string>(
|
|
28
|
+
table: AnyTable,
|
|
29
|
+
): MapColumn<MakeColumnConfig<T, TTableName>> {
|
|
30
|
+
return new MapColumn<MakeColumnConfig<T, TTableName>>(
|
|
31
|
+
table,
|
|
32
|
+
this.config as any,
|
|
33
|
+
);
|
|
34
|
+
}
|
|
35
|
+
}
|
|
36
|
+
|
|
37
|
+
export class MapColumn<
|
|
38
|
+
T extends ColumnBaseConfig<"map", "M">,
|
|
39
|
+
> extends Column<T> {
|
|
40
|
+
}
|
|
41
|
+
|
|
42
|
+
export function map(): MapColumnInitial<"">;
|
|
43
|
+
export function map<TName extends string>(name: TName): MapColumnInitial<TName>;
|
|
44
|
+
export function map(name?: string) {
|
|
45
|
+
return new MapColumnBuilder(name ?? "");
|
|
46
|
+
}
|
|
@@ -0,0 +1,49 @@
|
|
|
1
|
+
import {
|
|
2
|
+
Column,
|
|
3
|
+
type ColumnBaseConfig,
|
|
4
|
+
type ColumnRuntimeConfig,
|
|
5
|
+
} from "../core/column";
|
|
6
|
+
import {
|
|
7
|
+
ColumnBuider,
|
|
8
|
+
type ColumnBuilderBaseConfig,
|
|
9
|
+
type MakeColumnConfig,
|
|
10
|
+
} from "../core/column-builder";
|
|
11
|
+
import type { AnyTable } from "../core/table";
|
|
12
|
+
|
|
13
|
+
export type NumberSetColumnInitial<TName extends string> =
|
|
14
|
+
NumberSetColumnBuilder<{
|
|
15
|
+
name: TName;
|
|
16
|
+
data: Set<number>;
|
|
17
|
+
columnType: "NS";
|
|
18
|
+
dataType: "numberSet";
|
|
19
|
+
}>;
|
|
20
|
+
|
|
21
|
+
export class NumberSetColumnBuilder<
|
|
22
|
+
T extends ColumnBuilderBaseConfig<"numberSet", "NS">,
|
|
23
|
+
> extends ColumnBuider<T> {
|
|
24
|
+
constructor(name: T["name"]) {
|
|
25
|
+
super(name, "numberSet", "NS");
|
|
26
|
+
}
|
|
27
|
+
|
|
28
|
+
build<TTableName extends string>(
|
|
29
|
+
table: AnyTable,
|
|
30
|
+
): NumberSetColumn<MakeColumnConfig<T, TTableName>> {
|
|
31
|
+
return new NumberSetColumn<MakeColumnConfig<T, TTableName>>(
|
|
32
|
+
table,
|
|
33
|
+
this.config as any,
|
|
34
|
+
);
|
|
35
|
+
}
|
|
36
|
+
}
|
|
37
|
+
|
|
38
|
+
export class NumberSetColumn<
|
|
39
|
+
T extends ColumnBaseConfig<"numberSet", "NS">,
|
|
40
|
+
> extends Column<T> {
|
|
41
|
+
}
|
|
42
|
+
|
|
43
|
+
export function numberSet(): NumberSetColumnInitial<"">;
|
|
44
|
+
export function numberSet<TName extends string>(
|
|
45
|
+
name: TName,
|
|
46
|
+
): NumberSetColumnInitial<TName>;
|
|
47
|
+
export function numberSet(name?: string) {
|
|
48
|
+
return new NumberSetColumnBuilder(name ?? "");
|
|
49
|
+
}
|
|
@@ -0,0 +1,57 @@
|
|
|
1
|
+
import { Column, type ColumnBaseConfig } from "../core/column";
|
|
2
|
+
import {
|
|
3
|
+
ColumnBuider,
|
|
4
|
+
type MakeColumnConfig,
|
|
5
|
+
type ColumnBuilderBaseConfig,
|
|
6
|
+
type ColumnBuilderRuntimeConfig,
|
|
7
|
+
} from "../core/column-builder";
|
|
8
|
+
import type { AnyTable } from "../core/table";
|
|
9
|
+
|
|
10
|
+
export type NumberColumnInitial<TName extends string> = NumberColumnBuilder<{
|
|
11
|
+
name: TName;
|
|
12
|
+
dataType: "number";
|
|
13
|
+
columnType: "N";
|
|
14
|
+
data: number;
|
|
15
|
+
}>;
|
|
16
|
+
|
|
17
|
+
export class NumberColumnBuilder<
|
|
18
|
+
T extends ColumnBuilderBaseConfig<"number", "N">,
|
|
19
|
+
> extends ColumnBuider<T, { validators?: { min?: number; max?: number } }> {
|
|
20
|
+
constructor(name: T["name"]) {
|
|
21
|
+
super(name, "number", "N");
|
|
22
|
+
}
|
|
23
|
+
|
|
24
|
+
min(value: number): this {
|
|
25
|
+
this.config.validators ??= {};
|
|
26
|
+
this.config.validators.min = value;
|
|
27
|
+
return this;
|
|
28
|
+
}
|
|
29
|
+
|
|
30
|
+
max(value: number): this {
|
|
31
|
+
this.config.validators ??= {};
|
|
32
|
+
this.config.validators.max = value;
|
|
33
|
+
return this;
|
|
34
|
+
}
|
|
35
|
+
|
|
36
|
+
build<TTableName extends string>(
|
|
37
|
+
table: AnyTable,
|
|
38
|
+
): NumberColumn<MakeColumnConfig<T, TTableName>> {
|
|
39
|
+
return new NumberColumn<MakeColumnConfig<T, TTableName>>(
|
|
40
|
+
table,
|
|
41
|
+
this.config as any,
|
|
42
|
+
);
|
|
43
|
+
}
|
|
44
|
+
}
|
|
45
|
+
|
|
46
|
+
export class NumberColumn<
|
|
47
|
+
T extends ColumnBaseConfig<"number", "N">,
|
|
48
|
+
> extends Column<T> {
|
|
49
|
+
}
|
|
50
|
+
|
|
51
|
+
export function number(): NumberColumnInitial<"">;
|
|
52
|
+
export function number<TName extends string>(
|
|
53
|
+
name: TName,
|
|
54
|
+
): NumberColumnInitial<TName>;
|
|
55
|
+
export function number(name?: string) {
|
|
56
|
+
return new NumberColumnBuilder(name ?? "");
|
|
57
|
+
}
|