@palmares/schemas 0.0.1 → 0.1.1
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/.turbo/turbo-build$colon$watch.log +12 -410
- package/.turbo/turbo-build.log +13 -4
- package/CHANGELOG.md +26 -0
- package/__tests__/.drizzle/migrations/0000_skinny_harrier.sql +22 -0
- package/__tests__/.drizzle/migrations/meta/0000_snapshot.json +156 -0
- package/__tests__/.drizzle/migrations/meta/_journal.json +13 -0
- package/__tests__/.drizzle/schema.ts +35 -0
- package/__tests__/drizzle.config.ts +11 -0
- package/__tests__/eslint.config.js +10 -0
- package/__tests__/manage.ts +5 -0
- package/__tests__/node_modules/.bin/drizzle-kit +17 -0
- package/__tests__/node_modules/.bin/esbuild +14 -0
- package/__tests__/node_modules/.bin/tsc +17 -0
- package/__tests__/node_modules/.bin/tsserver +17 -0
- package/__tests__/node_modules/.bin/tsx +17 -0
- package/__tests__/package.json +36 -0
- package/__tests__/sqlite.db +0 -0
- package/__tests__/src/core/array.test.ts +130 -0
- package/__tests__/src/core/boolean.test.ts +66 -0
- package/__tests__/src/core/datetime.test.ts +102 -0
- package/__tests__/src/core/index.ts +35 -0
- package/__tests__/src/core/model.test.ts +260 -0
- package/__tests__/src/core/models.ts +50 -0
- package/__tests__/src/core/numbers.test.ts +177 -0
- package/__tests__/src/core/object.test.ts +198 -0
- package/__tests__/src/core/string.test.ts +222 -0
- package/__tests__/src/core/test.test.ts +59 -0
- package/__tests__/src/core/types.test.ts +97 -0
- package/__tests__/src/core/union.test.ts +99 -0
- package/__tests__/src/settings.ts +71 -0
- package/__tests__/tsconfig.json +11 -0
- package/dist/cjs/src/adapter/fields/index.js +2 -2
- package/dist/cjs/src/adapter/fields/object.js +9 -0
- package/dist/cjs/src/adapter/index.js +1 -0
- package/dist/cjs/src/constants.js +1 -7
- package/dist/cjs/src/domain.js +146 -1
- package/dist/cjs/src/index.js +69 -74
- package/dist/cjs/src/model.js +206 -206
- package/dist/cjs/src/schema/array.js +185 -58
- package/dist/cjs/src/schema/boolean.js +105 -44
- package/dist/cjs/src/schema/datetime.js +104 -38
- package/dist/cjs/src/schema/number.js +134 -114
- package/dist/cjs/src/schema/object.js +106 -43
- package/dist/cjs/src/schema/schema.js +123 -75
- package/dist/cjs/src/schema/string.js +152 -58
- package/dist/cjs/src/schema/union.js +412 -290
- package/dist/cjs/src/utils.js +42 -15
- package/dist/cjs/src/validators/array.js +6 -1
- package/dist/cjs/src/validators/boolean.js +2 -0
- package/dist/cjs/src/validators/datetime.js +4 -0
- package/dist/cjs/src/validators/number.js +12 -40
- package/dist/cjs/src/validators/object.js +1 -0
- package/dist/cjs/src/validators/schema.js +5 -1
- package/dist/cjs/src/validators/string.js +30 -2
- package/dist/cjs/src/validators/union.js +5 -4
- package/dist/cjs/src/validators/utils.js +99 -27
- package/dist/cjs/tsconfig.types.tsbuildinfo +1 -1
- package/dist/cjs/types/adapter/fields/array.d.ts +2 -2
- package/dist/cjs/types/adapter/fields/array.d.ts.map +1 -1
- package/dist/cjs/types/adapter/fields/boolean.d.ts.map +1 -1
- package/dist/cjs/types/adapter/fields/datetime.d.ts.map +1 -1
- package/dist/cjs/types/adapter/fields/index.d.ts +2 -2
- package/dist/cjs/types/adapter/fields/index.d.ts.map +1 -1
- package/dist/cjs/types/adapter/fields/number.d.ts.map +1 -1
- package/dist/cjs/types/adapter/fields/object.d.ts +2 -1
- package/dist/cjs/types/adapter/fields/object.d.ts.map +1 -1
- package/dist/cjs/types/adapter/fields/string.d.ts.map +1 -1
- package/dist/cjs/types/adapter/fields/union.d.ts.map +1 -1
- package/dist/cjs/types/adapter/index.d.ts +1 -0
- package/dist/cjs/types/adapter/index.d.ts.map +1 -1
- package/dist/cjs/types/adapter/types.d.ts +28 -18
- package/dist/cjs/types/adapter/types.d.ts.map +1 -1
- package/dist/cjs/types/constants.d.ts +0 -1
- package/dist/cjs/types/constants.d.ts.map +1 -1
- package/dist/cjs/types/domain.d.ts +5 -4
- package/dist/cjs/types/domain.d.ts.map +1 -1
- package/dist/cjs/types/index.d.ts +78 -55
- package/dist/cjs/types/index.d.ts.map +1 -1
- package/dist/cjs/types/model.d.ts +17 -17
- package/dist/cjs/types/model.d.ts.map +1 -1
- package/dist/cjs/types/schema/array.d.ts +168 -47
- package/dist/cjs/types/schema/array.d.ts.map +1 -1
- package/dist/cjs/types/schema/boolean.d.ts +103 -44
- package/dist/cjs/types/schema/boolean.d.ts.map +1 -1
- package/dist/cjs/types/schema/datetime.d.ts +90 -30
- package/dist/cjs/types/schema/datetime.d.ts.map +1 -1
- package/dist/cjs/types/schema/number.d.ts +133 -125
- package/dist/cjs/types/schema/number.d.ts.map +1 -1
- package/dist/cjs/types/schema/object.d.ts +104 -35
- package/dist/cjs/types/schema/object.d.ts.map +1 -1
- package/dist/cjs/types/schema/schema.d.ts +62 -44
- package/dist/cjs/types/schema/schema.d.ts.map +1 -1
- package/dist/cjs/types/schema/string.d.ts +152 -65
- package/dist/cjs/types/schema/string.d.ts.map +1 -1
- package/dist/cjs/types/schema/types.d.ts +11 -2
- package/dist/cjs/types/schema/types.d.ts.map +1 -1
- package/dist/cjs/types/schema/union.d.ts +133 -40
- package/dist/cjs/types/schema/union.d.ts.map +1 -1
- package/dist/cjs/types/types.d.ts +35 -0
- package/dist/cjs/types/types.d.ts.map +1 -1
- package/dist/cjs/types/utils.d.ts +41 -27
- package/dist/cjs/types/utils.d.ts.map +1 -1
- package/dist/cjs/types/validators/array.d.ts.map +1 -1
- package/dist/cjs/types/validators/boolean.d.ts.map +1 -1
- package/dist/cjs/types/validators/datetime.d.ts.map +1 -1
- package/dist/cjs/types/validators/number.d.ts +5 -6
- package/dist/cjs/types/validators/number.d.ts.map +1 -1
- package/dist/cjs/types/validators/object.d.ts.map +1 -1
- package/dist/cjs/types/validators/schema.d.ts +2 -2
- package/dist/cjs/types/validators/schema.d.ts.map +1 -1
- package/dist/cjs/types/validators/string.d.ts +9 -9
- package/dist/cjs/types/validators/string.d.ts.map +1 -1
- package/dist/cjs/types/validators/utils.d.ts +44 -27
- package/dist/cjs/types/validators/utils.d.ts.map +1 -1
- package/dist/esm/src/adapter/fields/index.js +2 -2
- package/dist/esm/src/adapter/fields/object.js +6 -0
- package/dist/esm/src/adapter/index.js +1 -0
- package/dist/esm/src/constants.js +1 -2
- package/dist/esm/src/domain.js +11 -1
- package/dist/esm/src/index.js +38 -73
- package/dist/esm/src/model.js +83 -78
- package/dist/esm/src/schema/array.js +136 -54
- package/dist/esm/src/schema/boolean.js +98 -44
- package/dist/esm/src/schema/datetime.js +91 -38
- package/dist/esm/src/schema/number.js +127 -110
- package/dist/esm/src/schema/object.js +98 -43
- package/dist/esm/src/schema/schema.js +102 -67
- package/dist/esm/src/schema/string.js +147 -59
- package/dist/esm/src/schema/union.js +119 -40
- package/dist/esm/src/types.js +14 -1
- package/dist/esm/src/utils.js +56 -27
- package/dist/esm/src/validators/array.js +6 -1
- package/dist/esm/src/validators/boolean.js +2 -0
- package/dist/esm/src/validators/datetime.js +4 -0
- package/dist/esm/src/validators/number.js +9 -23
- package/dist/esm/src/validators/object.js +1 -0
- package/dist/esm/src/validators/schema.js +5 -1
- package/dist/esm/src/validators/string.js +30 -2
- package/dist/esm/src/validators/union.js +5 -4
- package/dist/esm/src/validators/utils.js +62 -36
- package/package.json +3 -3
- package/src/adapter/fields/array.ts +2 -2
- package/src/adapter/fields/boolean.ts +3 -8
- package/src/adapter/fields/datetime.ts +3 -9
- package/src/adapter/fields/index.ts +11 -11
- package/src/adapter/fields/number.ts +3 -9
- package/src/adapter/fields/object.ts +13 -10
- package/src/adapter/fields/string.ts +3 -9
- package/src/adapter/fields/union.ts +3 -9
- package/src/adapter/index.ts +1 -0
- package/src/adapter/types.ts +60 -45
- package/src/constants.ts +1 -3
- package/src/domain.ts +15 -1
- package/src/index.ts +189 -211
- package/src/model.ts +119 -115
- package/src/schema/array.ts +274 -90
- package/src/schema/boolean.ts +145 -60
- package/src/schema/datetime.ts +133 -49
- package/src/schema/number.ts +210 -173
- package/src/schema/object.ts +167 -74
- package/src/schema/schema.ts +205 -126
- package/src/schema/string.ts +221 -94
- package/src/schema/types.ts +44 -16
- package/src/schema/union.ts +193 -68
- package/src/types.ts +53 -0
- package/src/utils.ts +115 -57
- package/src/validators/array.ts +46 -27
- package/src/validators/boolean.ts +13 -7
- package/src/validators/datetime.ts +24 -16
- package/src/validators/number.ts +53 -63
- package/src/validators/object.ts +6 -5
- package/src/validators/schema.ts +33 -25
- package/src/validators/string.ts +122 -59
- package/src/validators/union.ts +8 -8
- package/src/validators/utils.ts +67 -42
@@ -0,0 +1,222 @@
|
|
1
|
+
import * as p from '@palmares/schemas';
|
2
|
+
import { describe } from '@palmares/tests';
|
3
|
+
|
4
|
+
import type JestTestAdapter from '@palmares/jest-tests';
|
5
|
+
|
6
|
+
describe<JestTestAdapter>('String Schema', ({ test }) => {
|
7
|
+
test('optional', async ({ expect }) => {
|
8
|
+
const stringSchema = p.string();
|
9
|
+
const stringSchemaWithCustomMessage = p.string().nonOptional({ message: 'hello' });
|
10
|
+
|
11
|
+
const [{ errors: errorsOnFail }, { errors: errorsOnFailWithCustomMessage }, { errors: errorsOnValid, parsed }] =
|
12
|
+
await Promise.all([
|
13
|
+
stringSchema.parse(undefined as any),
|
14
|
+
stringSchemaWithCustomMessage.parse(undefined as any),
|
15
|
+
stringSchema.parse('a')
|
16
|
+
]);
|
17
|
+
|
18
|
+
expect(errorsOnFailWithCustomMessage?.[0]?.message).toBe('hello');
|
19
|
+
expect(errorsOnFail?.[0]?.code).toBe('required');
|
20
|
+
expect(errorsOnFail?.[0]?.message).toBe('Required');
|
21
|
+
expect((errorsOnValid || []).length).toBe(0);
|
22
|
+
expect(parsed).toBe('a');
|
23
|
+
});
|
24
|
+
|
25
|
+
test('nullable', async ({ expect }) => {
|
26
|
+
const stringSchema = p.string();
|
27
|
+
const stringSchemaWithCustomMessage = p.string().nonNullable({ message: 'hello' });
|
28
|
+
|
29
|
+
const [{ errors: errorsOnFail }, { errors: errorsOnFailWithCustomMessage }, { errors: errorsOnValid, parsed }] =
|
30
|
+
await Promise.all([
|
31
|
+
stringSchema.parse(null as any),
|
32
|
+
stringSchemaWithCustomMessage.parse(null as any),
|
33
|
+
stringSchema.parse('a')
|
34
|
+
]);
|
35
|
+
|
36
|
+
expect(errorsOnFailWithCustomMessage?.[0]?.message).toBe('hello');
|
37
|
+
expect(errorsOnFail?.[0]?.code).toBe('null');
|
38
|
+
expect(errorsOnFail?.[0]?.message).toBe('Cannot be null');
|
39
|
+
expect((errorsOnValid || []).length).toBe(0);
|
40
|
+
expect(parsed).toBe('a');
|
41
|
+
});
|
42
|
+
|
43
|
+
test('is', async ({ expect }) => {
|
44
|
+
const stringSchema = p.string().is(['a', 'b']);
|
45
|
+
const stringSchemaWithCustomMessage = p.string().is(['a', 'b'], { message: 'hello' });
|
46
|
+
|
47
|
+
const [{ errors: errorsOnFail }, { errors: errorsOnFailWithCustomMessage }, { errors: errorsOnValid, parsed }] =
|
48
|
+
await Promise.all([
|
49
|
+
stringSchema.parse('c' as any),
|
50
|
+
stringSchemaWithCustomMessage.parse('c' as any),
|
51
|
+
stringSchema.parse('a')
|
52
|
+
]);
|
53
|
+
|
54
|
+
expect(errorsOnFailWithCustomMessage?.[0]?.message).toBe('hello');
|
55
|
+
expect(errorsOnFail?.[0]?.code).toBe('is');
|
56
|
+
expect(errorsOnFail?.[0]?.message).toBe('The value should be equal to a, b');
|
57
|
+
expect((errorsOnValid || []).length).toBe(0);
|
58
|
+
expect(parsed).toBe('a');
|
59
|
+
});
|
60
|
+
|
61
|
+
test('includes', async ({ expect }) => {
|
62
|
+
const stringSchema = p.string().includes('Hello');
|
63
|
+
const stringSchemaWithCustomMessage = p.string().includes('Hello', { message: 'hello' });
|
64
|
+
|
65
|
+
const [{ errors: errorsOnFail }, { errors: errorsOnFailWithCustomMessage }, { errors: errorsOnValid, parsed }] =
|
66
|
+
await Promise.all([
|
67
|
+
stringSchema.parse('World'),
|
68
|
+
stringSchemaWithCustomMessage.parse('World'),
|
69
|
+
stringSchema.parse('Hello World')
|
70
|
+
]);
|
71
|
+
|
72
|
+
expect(errorsOnFailWithCustomMessage?.[0]?.message).toBe('hello');
|
73
|
+
expect(errorsOnFail?.[0]?.code).toBe('includes');
|
74
|
+
expect(errorsOnFail?.[0]?.message).toBe(`The string value should include the following substring 'Hello'`);
|
75
|
+
expect((errorsOnValid || []).length).toBe(0);
|
76
|
+
expect(parsed).toBe('Hello World');
|
77
|
+
});
|
78
|
+
|
79
|
+
test('maxLength', async ({ expect }) => {
|
80
|
+
const stringSchema = p.string().maxLength(8);
|
81
|
+
const stringSchemaWithCustomMessage = p.string().maxLength(8, { message: 'hello' });
|
82
|
+
|
83
|
+
const [{ errors: errorsOnFail }, { errors: errorsOnFailWithCustomMessage }, { errors: errorsOnValid, parsed }] =
|
84
|
+
await Promise.all([
|
85
|
+
stringSchema.parse('Hello World'),
|
86
|
+
stringSchemaWithCustomMessage.parse('Hello World'),
|
87
|
+
stringSchema.parse('Hello')
|
88
|
+
]);
|
89
|
+
|
90
|
+
expect(errorsOnFailWithCustomMessage?.[0]?.message).toBe('hello');
|
91
|
+
expect(errorsOnFail?.[0]?.code).toBe('maxLength');
|
92
|
+
expect(errorsOnFail?.[0]?.message).toBe(`The value should have a maximum length of 8`);
|
93
|
+
expect((errorsOnValid || []).length).toBe(0);
|
94
|
+
expect(parsed).toBe('Hello');
|
95
|
+
});
|
96
|
+
|
97
|
+
test('minLength', async ({ expect }) => {
|
98
|
+
const stringSchema = p.string().minLength(8);
|
99
|
+
const stringSchemaWithCustomMessage = p.string().minLength(8, { message: 'hello' });
|
100
|
+
|
101
|
+
const [{ errors: errorsOnFail }, { errors: errorsOnFailWithCustomMessage }, { errors: errorsOnValid, parsed }] =
|
102
|
+
await Promise.all([
|
103
|
+
stringSchema.parse('Hello'),
|
104
|
+
stringSchemaWithCustomMessage.parse('Hello'),
|
105
|
+
stringSchema.parse('Hello World')
|
106
|
+
]);
|
107
|
+
|
108
|
+
expect(errorsOnFailWithCustomMessage?.[0]?.message).toBe('hello');
|
109
|
+
expect(errorsOnFail?.[0]?.code).toBe('minLength');
|
110
|
+
expect(errorsOnFail?.[0]?.message).toBe(`The value should have a minimum length of 8`);
|
111
|
+
expect((errorsOnValid || []).length).toBe(0);
|
112
|
+
expect(parsed).toBe('Hello World');
|
113
|
+
});
|
114
|
+
|
115
|
+
test('startsWith', async ({ expect }) => {
|
116
|
+
const stringSchema = p.string().startsWith('Hello');
|
117
|
+
const stringSchemaWithCustomMessage = p.string().startsWith('Hello', { message: 'hello' });
|
118
|
+
|
119
|
+
const [{ errors: errorsOnFail }, { errors: errorsOnFailWithCustomMessage }, { errors: errorsOnValid, parsed }] =
|
120
|
+
await Promise.all([
|
121
|
+
stringSchema.parse('Palmares, the best FW in the world!!!!!'),
|
122
|
+
stringSchemaWithCustomMessage.parse(`I actually think it's bad`),
|
123
|
+
stringSchema.parse('Hello, World')
|
124
|
+
]);
|
125
|
+
|
126
|
+
expect(errorsOnFailWithCustomMessage?.[0]?.message).toBe('hello');
|
127
|
+
expect(errorsOnFail?.[0]?.code).toBe('startsWith');
|
128
|
+
expect(errorsOnFail?.[0]?.message).toBe(`The value should start with Hello`);
|
129
|
+
expect((errorsOnValid || []).length).toBe(0);
|
130
|
+
expect(parsed).toBe('Hello, World');
|
131
|
+
});
|
132
|
+
|
133
|
+
test('endsWith', async ({ expect }) => {
|
134
|
+
const stringSchema = p.string().endsWith('World');
|
135
|
+
const stringSchemaWithCustomMessage = p.string().endsWith('World', { message: 'hello' });
|
136
|
+
|
137
|
+
const [{ errors: errorsOnFail }, { errors: errorsOnFailWithCustomMessage }, { errors: errorsOnValid, parsed }] =
|
138
|
+
await Promise.all([
|
139
|
+
stringSchema.parse('Palmares, the best FW in the world!!!!!'),
|
140
|
+
stringSchemaWithCustomMessage.parse(`I actually think it's bad`),
|
141
|
+
stringSchema.parse('Hello, World')
|
142
|
+
]);
|
143
|
+
|
144
|
+
expect(errorsOnFailWithCustomMessage?.[0]?.message).toBe('hello');
|
145
|
+
expect(errorsOnFail?.[0]?.code).toBe('endsWith');
|
146
|
+
expect(errorsOnFail?.[0]?.message).toBe(`The value should end with World`);
|
147
|
+
expect((errorsOnValid || []).length).toBe(0);
|
148
|
+
expect(parsed).toBe('Hello, World');
|
149
|
+
});
|
150
|
+
|
151
|
+
test('endsWith', async ({ expect }) => {
|
152
|
+
const stringSchema = p.string().endsWith('World');
|
153
|
+
const stringSchemaWithCustomMessage = p.string().endsWith('World', { message: 'hello' });
|
154
|
+
|
155
|
+
const [{ errors: errorsOnFail }, { errors: errorsOnFailWithCustomMessage }, { errors: errorsOnValid, parsed }] =
|
156
|
+
await Promise.all([
|
157
|
+
stringSchema.parse('Palmares, the best FW in the world!!!!!'),
|
158
|
+
stringSchemaWithCustomMessage.parse(`I actually think it's bad`),
|
159
|
+
stringSchema.parse('Hello, World')
|
160
|
+
]);
|
161
|
+
|
162
|
+
expect(errorsOnFailWithCustomMessage?.[0]?.message).toBe('hello');
|
163
|
+
expect(errorsOnFail?.[0]?.code).toBe('endsWith');
|
164
|
+
expect(errorsOnFail?.[0]?.message).toBe(`The value should end with World`);
|
165
|
+
expect((errorsOnValid || []).length).toBe(0);
|
166
|
+
expect(parsed).toBe('Hello, World');
|
167
|
+
});
|
168
|
+
|
169
|
+
test('regex', async ({ expect }) => {
|
170
|
+
const regex = new RegExp('Hello', 'g');
|
171
|
+
const stringSchema = p.string().regex(regex);
|
172
|
+
const stringSchemaWithCustomMessage = p.string().regex(regex, { message: 'hello' });
|
173
|
+
|
174
|
+
const [{ errors: errorsOnFail }, { errors: errorsOnFailWithCustomMessage }, { errors: errorsOnValid, parsed }] =
|
175
|
+
await Promise.all([
|
176
|
+
stringSchema.parse('Palmares, the best FW in the world!!!!!'),
|
177
|
+
stringSchemaWithCustomMessage.parse(`I actually think it's bad`),
|
178
|
+
stringSchema.parse('Hello, World')
|
179
|
+
]);
|
180
|
+
|
181
|
+
expect(errorsOnFailWithCustomMessage?.[0]?.message).toBe('hello');
|
182
|
+
expect(errorsOnFail?.[0]?.code).toBe('regex');
|
183
|
+
expect(errorsOnFail?.[0]?.message).toBe(`The value should match the following regex '/Hello/g'`);
|
184
|
+
expect((errorsOnValid || []).length).toBe(0);
|
185
|
+
expect(parsed).toBe('Hello, World');
|
186
|
+
});
|
187
|
+
|
188
|
+
test('uuid', async ({ expect }) => {
|
189
|
+
const stringSchema = p.string().uuid();
|
190
|
+
const stringSchemaWithCustomMessage = p.string().uuid({ message: 'hello' });
|
191
|
+
|
192
|
+
const [{ errors: errorsOnFail }, { errors: errorsOnFailWithCustomMessage }, { errors: errorsOnValid, parsed }] =
|
193
|
+
await Promise.all([
|
194
|
+
stringSchema.parse('Palmares, the best FW in the world!!!!!'),
|
195
|
+
stringSchemaWithCustomMessage.parse(`I actually think it's bad`),
|
196
|
+
stringSchema.parse('f54bb64b-0aed-47f9-976e-a8900d86f6c9')
|
197
|
+
]);
|
198
|
+
|
199
|
+
expect(errorsOnFailWithCustomMessage?.[0]?.message).toBe('hello');
|
200
|
+
expect(errorsOnFail?.[0]?.code).toBe('uuid');
|
201
|
+
expect(errorsOnFail?.[0]?.message).toBe(`The value should be a valid UUID`);
|
202
|
+
expect((errorsOnValid || []).length).toBe(0);
|
203
|
+
expect(parsed).toBe('f54bb64b-0aed-47f9-976e-a8900d86f6c9');
|
204
|
+
});
|
205
|
+
|
206
|
+
test('email', async ({ expect }) => {
|
207
|
+
const stringSchema = p.string().email();
|
208
|
+
const stringSchemaWithCustomMessage = p.string().email({ message: 'hello' });
|
209
|
+
|
210
|
+
const [{ errors: errorsOnFail }, { errors: errorsOnFailWithCustomMessage }, { errors: errorsOnValid, parsed }] =
|
211
|
+
await Promise.all([
|
212
|
+
stringSchema.parse('Palmares, the best FW in the world!!!!!'),
|
213
|
+
stringSchemaWithCustomMessage.parse(`I actually think it's bad`),
|
214
|
+
stringSchema.parse('test@test.com')
|
215
|
+
]);
|
216
|
+
expect(errorsOnFailWithCustomMessage?.[0]?.message).toBe('hello');
|
217
|
+
expect(errorsOnFail?.[0]?.code).toBe('email');
|
218
|
+
expect(errorsOnFail?.[0]?.message).toBe(`The value should be a valid email`);
|
219
|
+
expect((errorsOnValid || []).length).toBe(0);
|
220
|
+
expect(parsed).toBe('test@test.com');
|
221
|
+
});
|
222
|
+
});
|
@@ -0,0 +1,59 @@
|
|
1
|
+
import * as p from '@palmares/schemas';
|
2
|
+
import { describe } from '@palmares/tests';
|
3
|
+
|
4
|
+
import type JestTestAdapter from '@palmares/jest-tests';
|
5
|
+
|
6
|
+
describe<JestTestAdapter>('Basic Schemas', ({ test }) => {
|
7
|
+
test('basic representation', async ({ expect }) => {
|
8
|
+
const basicSchema = p.number();
|
9
|
+
|
10
|
+
const data = await basicSchema.data(2);
|
11
|
+
|
12
|
+
expect(data).toBe(2);
|
13
|
+
});
|
14
|
+
|
15
|
+
test('basic to representation', async ({ expect }) => {
|
16
|
+
const defaultMessage = 'This used to be a number';
|
17
|
+
// eslint-disable-next-line ts/require-await
|
18
|
+
const numberSchema = p.number().toRepresentation(async () => {
|
19
|
+
return defaultMessage;
|
20
|
+
});
|
21
|
+
|
22
|
+
// eslint-disable-next-line ts/require-await
|
23
|
+
const schemaTransformingData = p.number().toRepresentation(async (data) => {
|
24
|
+
return {
|
25
|
+
number: data,
|
26
|
+
message: defaultMessage
|
27
|
+
};
|
28
|
+
});
|
29
|
+
|
30
|
+
const stringMessage = await numberSchema.data(2);
|
31
|
+
const objectMessage = await schemaTransformingData.data(2);
|
32
|
+
|
33
|
+
expect(stringMessage).toBe(defaultMessage);
|
34
|
+
expect(objectMessage.message).toBe(defaultMessage);
|
35
|
+
expect(objectMessage.number).toBe(2);
|
36
|
+
});
|
37
|
+
|
38
|
+
test('basic internal', async ({ expect }) => {
|
39
|
+
// eslint-disable-next-line ts/require-await
|
40
|
+
const internalSchema = p.number().toInternal(async (data) => {
|
41
|
+
return data * 2;
|
42
|
+
});
|
43
|
+
|
44
|
+
const { parsed } = await internalSchema.parse(2);
|
45
|
+
|
46
|
+
expect(parsed).toBe(4);
|
47
|
+
});
|
48
|
+
|
49
|
+
test('basic validation', async ({ expect }) => {
|
50
|
+
// eslint-disable-next-line ts/require-await
|
51
|
+
const internalSchema = p.number().toValidate(async () => {
|
52
|
+
return 'Should fail';
|
53
|
+
});
|
54
|
+
|
55
|
+
const { errors } = await internalSchema.parse(2);
|
56
|
+
|
57
|
+
expect((errors?.length || 0) > 0).toBe(true);
|
58
|
+
});
|
59
|
+
});
|
@@ -0,0 +1,97 @@
|
|
1
|
+
import * as p from '@palmares/schemas';
|
2
|
+
import { describe } from '@palmares/tests';
|
3
|
+
|
4
|
+
import type JestTestAdapter from '@palmares/jest-tests';
|
5
|
+
|
6
|
+
describe<JestTestAdapter>('Schema Types', ({ test }) => {
|
7
|
+
test('number schema', async ({ expect }) => {
|
8
|
+
const numberSchema = p.number();
|
9
|
+
|
10
|
+
const { errors } = await numberSchema.parse('value' as any);
|
11
|
+
|
12
|
+
expect((errors?.length || 0) > 0).toBe(true);
|
13
|
+
});
|
14
|
+
|
15
|
+
test('boolean schema', async ({ expect }) => {
|
16
|
+
const booleanSchema = p.boolean();
|
17
|
+
|
18
|
+
const { errors } = await booleanSchema.parse('value' as any);
|
19
|
+
|
20
|
+
expect((errors?.length || 0) > 0).toBe(true);
|
21
|
+
});
|
22
|
+
|
23
|
+
test('date schema', async ({ expect }) => {
|
24
|
+
const dateSchema = p.datetime();
|
25
|
+
|
26
|
+
const { errors } = await dateSchema.parse('value' as any);
|
27
|
+
|
28
|
+
expect((errors?.length || 0) > 0).toBe(true);
|
29
|
+
});
|
30
|
+
|
31
|
+
test('string schema', async ({ expect }) => {
|
32
|
+
const stringSchema = p.string();
|
33
|
+
|
34
|
+
const { errors } = await stringSchema.parse(2 as any);
|
35
|
+
|
36
|
+
expect((errors?.length || 0) > 0).toBe(true);
|
37
|
+
});
|
38
|
+
|
39
|
+
test('array schema', async ({ expect }) => {
|
40
|
+
const tupleSchema = p.array(p.number(), p.string());
|
41
|
+
const arraySchema = p.array([p.number()]);
|
42
|
+
|
43
|
+
const [
|
44
|
+
{ errors: errorsOfInvalidArray },
|
45
|
+
{ errors: errorsOfInvalidTuple },
|
46
|
+
{ errors: errorsOfValidArray, parsed: parsedArray },
|
47
|
+
{ errors: errorsOfValidTuple, parsed: parsedTuple }
|
48
|
+
] = await Promise.all([
|
49
|
+
arraySchema.parse('value' as any),
|
50
|
+
tupleSchema.parse([1, 2, 3] as any),
|
51
|
+
arraySchema.parse([1, 2, 3]),
|
52
|
+
tupleSchema.parse([1, 'string'])
|
53
|
+
]);
|
54
|
+
|
55
|
+
expect((errorsOfInvalidArray?.length || 0) > 0).toBe(true);
|
56
|
+
expect((errorsOfInvalidTuple?.length || 0) > 0).toBe(true);
|
57
|
+
expect(errorsOfValidArray?.length || 0).toBe(0);
|
58
|
+
expect(errorsOfValidTuple?.length || 0).toBe(0);
|
59
|
+
expect(parsedArray[0]).toBe(1);
|
60
|
+
expect(parsedArray[1]).toBe(2);
|
61
|
+
expect(parsedArray[2]).toBe(3);
|
62
|
+
expect(parsedTuple[0]).toBe(1);
|
63
|
+
expect(parsedTuple[1]).toBe('string');
|
64
|
+
});
|
65
|
+
|
66
|
+
test('object schema', async ({ expect }) => {
|
67
|
+
const objectSchema = p.object({
|
68
|
+
number: p.number(),
|
69
|
+
string: p.string()
|
70
|
+
});
|
71
|
+
|
72
|
+
const [{ errors: errorsOfInvalid }, { errors: errorsOfValid, parsed }] = await Promise.all([
|
73
|
+
objectSchema.parse('value' as any),
|
74
|
+
objectSchema.parse({
|
75
|
+
number: 1,
|
76
|
+
string: 'string'
|
77
|
+
})
|
78
|
+
]);
|
79
|
+
|
80
|
+
expect((errorsOfInvalid?.length || 0) > 0).toBe(true);
|
81
|
+
expect((errorsOfValid?.length || 0) === 0).toBe(true);
|
82
|
+
expect(parsed.number).toBe(1);
|
83
|
+
expect(parsed.string).toBe('string');
|
84
|
+
});
|
85
|
+
|
86
|
+
test('union schema', async ({ expect }) => {
|
87
|
+
const unionSchema = p.union([p.string(), p.number()]);
|
88
|
+
|
89
|
+
const [{ errors: errorsOfInvalid }, { errors: errorsOfValid, parsed }] = await Promise.all([
|
90
|
+
unionSchema.parse(true as any),
|
91
|
+
unionSchema.parse(2)
|
92
|
+
]);
|
93
|
+
expect((errorsOfInvalid?.length || 0) > 0).toBe(true);
|
94
|
+
expect((errorsOfValid?.length || 0) === 0).toBe(true);
|
95
|
+
expect(parsed).toBe(2);
|
96
|
+
});
|
97
|
+
});
|
@@ -0,0 +1,99 @@
|
|
1
|
+
import * as p from '@palmares/schemas';
|
2
|
+
import { getDefaultAdapter } from '@palmares/schemas';
|
3
|
+
import { describe } from '@palmares/tests';
|
4
|
+
|
5
|
+
import type JestTestAdapter from '@palmares/jest-tests';
|
6
|
+
|
7
|
+
describe<JestTestAdapter>('Union Tests', ({ test }) => {
|
8
|
+
test('optional', async ({ expect }) => {
|
9
|
+
const unionSchema = p.union([p.number(), p.string()]);
|
10
|
+
const unionSchemaWithCustomMessage = p.union([p.number(), p.string()]).nonOptional({ message: 'hello' });
|
11
|
+
|
12
|
+
const [{ errors: errorsOnFail }, { errors: errorsOnFailWithCustomMessage }, { errors: errorsOnValid, parsed }] =
|
13
|
+
await Promise.all([
|
14
|
+
unionSchema.parse(undefined as any),
|
15
|
+
unionSchemaWithCustomMessage.parse(undefined as any),
|
16
|
+
unionSchema.parse(1)
|
17
|
+
]);
|
18
|
+
|
19
|
+
expect(errorsOnFailWithCustomMessage?.[0]?.message).toBe('hello');
|
20
|
+
expect(errorsOnFail?.[0]?.code).toBe('required');
|
21
|
+
expect(errorsOnFail?.[0]?.message).toBe('Required');
|
22
|
+
expect((errorsOnValid || []).length).toBe(0);
|
23
|
+
expect(parsed).toBe(1);
|
24
|
+
});
|
25
|
+
|
26
|
+
test('nullable', async ({ expect }) => {
|
27
|
+
const unionSchema = p.union([p.number(), p.string()]);
|
28
|
+
const unionSchemaWithCustomMessage = p.union([p.number(), p.string()]).nonNullable({ message: 'hello' });
|
29
|
+
|
30
|
+
const [{ errors: errorsOnFail }, { errors: errorsOnFailWithCustomMessage }, { errors: errorsOnValid, parsed }] =
|
31
|
+
await Promise.all([
|
32
|
+
unionSchema.parse(null as any),
|
33
|
+
unionSchemaWithCustomMessage.parse(null as any),
|
34
|
+
unionSchema.parse('teste')
|
35
|
+
]);
|
36
|
+
|
37
|
+
expect(errorsOnFailWithCustomMessage?.[0]?.message).toBe('hello');
|
38
|
+
expect(errorsOnFail?.[0]?.code).toBe('null');
|
39
|
+
expect(errorsOnFail?.[0]?.message).toBe('Cannot be null');
|
40
|
+
expect((errorsOnValid || []).length).toBe(0);
|
41
|
+
expect(parsed).toBe('teste');
|
42
|
+
});
|
43
|
+
|
44
|
+
test('in case of failure use the other', async ({ expect }) => {
|
45
|
+
const unionSchema = p.union([p.number().max(20), p.number().min(12)]);
|
46
|
+
|
47
|
+
const { errors, parsed } = await unionSchema.parse(25);
|
48
|
+
expect((errors || []).length).toBe(0);
|
49
|
+
expect(parsed).toBe(25);
|
50
|
+
});
|
51
|
+
|
52
|
+
test('in case of failure, show first', async ({ expect }) => {
|
53
|
+
const unionSchema = p.union([p.number().min(25), p.number().max(20)]);
|
54
|
+
|
55
|
+
const { errors } = await unionSchema.parse(23);
|
56
|
+
expect((errors || []).length > 0).toBe(true);
|
57
|
+
});
|
58
|
+
|
59
|
+
test('works when not defined on adapter', async ({ expect }) => {
|
60
|
+
const adapter = getDefaultAdapter();
|
61
|
+
const existingUnion = adapter.union;
|
62
|
+
adapter.union = undefined;
|
63
|
+
const unionSchema = p.union([p.number().min(25), p.number().max(20)]);
|
64
|
+
const { errors } = await unionSchema.parse(23);
|
65
|
+
expect((errors || []).length > 0).toBe(true);
|
66
|
+
|
67
|
+
adapter.union = existingUnion;
|
68
|
+
});
|
69
|
+
|
70
|
+
test('nested in case of failure use the other', async ({ expect }) => {
|
71
|
+
const unionSchema = p.object({
|
72
|
+
test: p.union([p.number().max(20), p.number().min(12)] as const)
|
73
|
+
});
|
74
|
+
|
75
|
+
const { errors, parsed } = await unionSchema.parse({
|
76
|
+
test: 23
|
77
|
+
});
|
78
|
+
expect((errors || []).length).toBe(0);
|
79
|
+
expect(parsed.test).toBe(23);
|
80
|
+
});
|
81
|
+
|
82
|
+
test('nested in case of failure, show first', async ({ expect }) => {
|
83
|
+
const unionSchema = p.object({ test: p.union([p.number().min(25), p.number().max(20)]) });
|
84
|
+
|
85
|
+
const { errors } = await unionSchema.parse({ test: 23 });
|
86
|
+
expect((errors || []).length > 0).toBe(true);
|
87
|
+
});
|
88
|
+
|
89
|
+
test('nested works when not defined on adapter', async ({ expect }) => {
|
90
|
+
const adapter = getDefaultAdapter();
|
91
|
+
const existingUnion = adapter.union;
|
92
|
+
adapter.union = undefined;
|
93
|
+
const unionSchema = p.object({ test: p.union([p.number().min(25), p.number().max(20)]) });
|
94
|
+
const { errors } = await unionSchema.parse({ test: 23 });
|
95
|
+
expect((errors || []).length > 0).toBe(true);
|
96
|
+
|
97
|
+
adapter.union = existingUnion;
|
98
|
+
});
|
99
|
+
});
|
@@ -0,0 +1,71 @@
|
|
1
|
+
import ConsoleLogging from '@palmares/console-logging';
|
2
|
+
import CoreDomain, { defineSettings } from '@palmares/core';
|
3
|
+
import DatabasesDomain from '@palmares/databases';
|
4
|
+
import DrizzleEngine from '@palmares/drizzle-engine';
|
5
|
+
import { drizzle as drizzleBetterSqlite3 } from '@palmares/drizzle-engine/better-sqlite3';
|
6
|
+
import JestTestAdapter from '@palmares/jest-tests';
|
7
|
+
import LoggingDomain from '@palmares/logging';
|
8
|
+
import NodeStd from '@palmares/node-std';
|
9
|
+
import SchemasDomain from '@palmares/schemas';
|
10
|
+
import TestsDomain from '@palmares/tests';
|
11
|
+
import { ZodSchemaAdapter } from '@palmares/zod-schema';
|
12
|
+
import Database from 'better-sqlite3';
|
13
|
+
import { dirname, resolve } from 'path';
|
14
|
+
|
15
|
+
import CustomCoreDomain from './core';
|
16
|
+
import { User } from '../.drizzle/schema';
|
17
|
+
import { eq } from 'drizzle-orm';
|
18
|
+
//import * as schema from '../.drizzle/schema';
|
19
|
+
|
20
|
+
const database = new Database('sqlite.db');
|
21
|
+
|
22
|
+
const args = DrizzleEngine.new({
|
23
|
+
output: './.drizzle/schema.ts',
|
24
|
+
type: 'better-sqlite3',
|
25
|
+
drizzle: drizzleBetterSqlite3(database)
|
26
|
+
});
|
27
|
+
export const db = args[1].instance.instance;
|
28
|
+
export default defineSettings({
|
29
|
+
basePath: dirname(resolve(__dirname)),
|
30
|
+
settingsLocation: __filename,
|
31
|
+
std: NodeStd,
|
32
|
+
installedDomains: [
|
33
|
+
[
|
34
|
+
LoggingDomain,
|
35
|
+
{
|
36
|
+
logger: ConsoleLogging
|
37
|
+
}
|
38
|
+
],
|
39
|
+
// Domain Core, required for palmares to work
|
40
|
+
[
|
41
|
+
CoreDomain,
|
42
|
+
{
|
43
|
+
appName: 'example'
|
44
|
+
}
|
45
|
+
],
|
46
|
+
[
|
47
|
+
TestsDomain,
|
48
|
+
{
|
49
|
+
testAdapter: JestTestAdapter
|
50
|
+
}
|
51
|
+
],
|
52
|
+
[
|
53
|
+
SchemasDomain,
|
54
|
+
{
|
55
|
+
schemaAdapter: ZodSchemaAdapter
|
56
|
+
}
|
57
|
+
],
|
58
|
+
[
|
59
|
+
DatabasesDomain,
|
60
|
+
{
|
61
|
+
databases: {
|
62
|
+
default: {
|
63
|
+
engine: args
|
64
|
+
}
|
65
|
+
}
|
66
|
+
}
|
67
|
+
],
|
68
|
+
// We have just created this custom domain, and it defines our routes.
|
69
|
+
CustomCoreDomain
|
70
|
+
]
|
71
|
+
});
|
@@ -0,0 +1,11 @@
|
|
1
|
+
{
|
2
|
+
"extends": "../../../tsconfig.json",
|
3
|
+
"compilerOptions": {
|
4
|
+
"declaration": true,
|
5
|
+
"module": "ESNext",
|
6
|
+
"moduleResolution": "Bundler",
|
7
|
+
"outDir": "./dist",
|
8
|
+
"types": ["node"]
|
9
|
+
},
|
10
|
+
"include": ["./src/**/*", "manage.drizzle.ts", "manage.sequelize.ts", "./src/core/types.test.ts"]
|
11
|
+
}
|
@@ -275,7 +275,7 @@ var FieldAdapter = /*#__PURE__*/ function() {
|
|
275
275
|
},
|
276
276
|
{
|
277
277
|
key: "parse",
|
278
|
-
value: function parse(_adapter, _fieldAdapter,
|
278
|
+
value: function parse(_adapter, _fieldAdapter, _schema, _value, _args) {
|
279
279
|
throw new _exceptions.SchemaAdapterNotImplementedError({
|
280
280
|
className: this.constructor.name,
|
281
281
|
functionName: 'parse'
|
@@ -294,7 +294,7 @@ var FieldAdapter = /*#__PURE__*/ function() {
|
|
294
294
|
{
|
295
295
|
key: "formatError",
|
296
296
|
value: // eslint-disable-next-line ts/require-await
|
297
|
-
function formatError(_adapter, _fieldAdapter, _error, _metadata) {
|
297
|
+
function formatError(_adapter, _fieldAdapter, _schema, _error, _metadata) {
|
298
298
|
var _this = this;
|
299
299
|
return _async_to_generator(function() {
|
300
300
|
return _ts_generator(this, function(_state) {
|
@@ -161,6 +161,15 @@ var ObjectFieldAdapter = /*#__PURE__*/ function(FieldAdapter) {
|
|
161
161
|
functionName: 'parse'
|
162
162
|
});
|
163
163
|
}
|
164
|
+
},
|
165
|
+
{
|
166
|
+
key: "toString",
|
167
|
+
value: function toString(_adapter, _fieldAdapter, _args, _base) {
|
168
|
+
throw new _exceptions.SchemaAdapterNotImplementedError({
|
169
|
+
className: this.constructor.name,
|
170
|
+
functionName: 'toString'
|
171
|
+
});
|
172
|
+
}
|
164
173
|
}
|
165
174
|
]);
|
166
175
|
return ObjectFieldAdapter;
|
@@ -177,6 +177,7 @@ var SchemaAdapter = /*#__PURE__*/ function() {
|
|
177
177
|
_define_property(this, "array", void 0);
|
178
178
|
_define_property(this, "boolean", void 0);
|
179
179
|
_define_property(this, "datetime", void 0);
|
180
|
+
_define_property(this, "adapterInstance", void 0);
|
180
181
|
}
|
181
182
|
_create_class(SchemaAdapter, [
|
182
183
|
{
|
@@ -18,9 +18,6 @@ _export(exports, {
|
|
18
18
|
DEFAULT_NUMBER_MIN_EXCEPTION: function() {
|
19
19
|
return DEFAULT_NUMBER_MIN_EXCEPTION;
|
20
20
|
},
|
21
|
-
DEFAULT_NUMBER_NEGATIVE_EXCEPTION: function() {
|
22
|
-
return DEFAULT_NUMBER_NEGATIVE_EXCEPTION;
|
23
|
-
},
|
24
21
|
DEFAULT_NUMBER_POSITIVE_EXCEPTION: function() {
|
25
22
|
return DEFAULT_NUMBER_POSITIVE_EXCEPTION;
|
26
23
|
}
|
@@ -31,12 +28,9 @@ var DEFAULT_NUMBER_MAX_EXCEPTION = function(max, inclusive) {
|
|
31
28
|
var DEFAULT_NUMBER_MIN_EXCEPTION = function(min, inclusive) {
|
32
29
|
return "The number is less than the allowed ".concat(min, ".").concat(inclusive ? " The value ".concat(min, " is accepted as well.") : '');
|
33
30
|
};
|
34
|
-
var DEFAULT_NUMBER_NEGATIVE_EXCEPTION = function(allowZero) {
|
35
|
-
return "The number should be negative.".concat(allowZero ? " The value 0 is accepted as well." : '');
|
36
|
-
};
|
37
31
|
var DEFAULT_NUMBER_POSITIVE_EXCEPTION = function(allowZero) {
|
38
32
|
return "The number should be positive.".concat(allowZero ? " The value 0 is accepted as well." : '');
|
39
33
|
};
|
40
34
|
var DEFAULT_NUMBER_INTEGER_EXCEPTION = function() {
|
41
|
-
return "
|
35
|
+
return "The number should be an integer.";
|
42
36
|
};
|