@snowtop/ent 0.1.12 → 0.1.13
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/action/experimental_action.js +2 -2
- package/action/operations.js +4 -2
- package/core/base.d.ts +12 -10
- package/core/clause.d.ts +4 -3
- package/core/clause.js +98 -43
- package/core/config.d.ts +6 -0
- package/core/context.d.ts +6 -14
- package/core/context.js +9 -4
- package/core/db.js +1 -1
- package/core/ent.d.ts +1 -0
- package/core/ent.js +30 -11
- package/core/loaders/assoc_count_loader.js +1 -1
- package/core/loaders/assoc_edge_loader.d.ts +3 -0
- package/core/loaders/assoc_edge_loader.js +18 -0
- package/core/loaders/object_loader.js +2 -2
- package/core/loaders/query_loader.d.ts +3 -3
- package/core/loaders/query_loader.js +2 -1
- package/core/loaders/raw_count_loader.js +1 -1
- package/core/query/assoc_query.d.ts +22 -0
- package/core/query/assoc_query.js +101 -2
- package/core/query/custom_query.js +2 -9
- package/core/query/query.d.ts +1 -0
- package/core/query/query.js +72 -11
- package/core/query/shared_assoc_test.js +404 -7
- package/core/query/shared_test.js +9 -37
- package/core/query_impl.d.ts +2 -1
- package/core/query_impl.js +25 -7
- package/graphql/query/edge_connection.js +2 -2
- package/package.json +2 -2
- package/parse_schema/parse.d.ts +2 -2
- package/parse_schema/parse.js +3 -3
- package/schema/struct_field.d.ts +4 -2
- package/schema/struct_field.js +33 -4
- package/scripts/custom_graphql.js +1 -1
- package/testutils/builder.d.ts +1 -1
- package/testutils/builder.js +4 -4
- package/testutils/ent-graphql-tests/index.js +2 -2
- package/testutils/fake_data/fake_contact.js +1 -1
- package/testutils/fake_data/fake_event.js +1 -1
- package/testutils/fake_data/test_helpers.js +2 -2
- package/testutils/fake_data/user_query.js +1 -1
- package/testutils/query.d.ts +9 -0
- package/testutils/query.js +45 -0
- package/testutils/write.js +3 -3
package/parse_schema/parse.d.ts
CHANGED
|
@@ -69,14 +69,14 @@ interface Result {
|
|
|
69
69
|
patterns: patternsDict;
|
|
70
70
|
globalSchema?: ProcessedGlobalSchema;
|
|
71
71
|
config?: {
|
|
72
|
-
rome?:
|
|
72
|
+
rome?: BiomeConfig;
|
|
73
73
|
};
|
|
74
74
|
}
|
|
75
75
|
declare type PotentialSchemas = {
|
|
76
76
|
[key: string]: any;
|
|
77
77
|
};
|
|
78
78
|
export declare function parseSchema(potentialSchemas: PotentialSchemas, globalSchema?: GlobalSchema): Promise<Result>;
|
|
79
|
-
interface
|
|
79
|
+
interface BiomeConfig {
|
|
80
80
|
indentStyle?: string;
|
|
81
81
|
lineWidth?: number;
|
|
82
82
|
indentSize?: number;
|
package/parse_schema/parse.js
CHANGED
|
@@ -317,13 +317,13 @@ async function parseSchema(potentialSchemas, globalSchema) {
|
|
|
317
317
|
}
|
|
318
318
|
schemas[key] = processedSchema;
|
|
319
319
|
}
|
|
320
|
-
const
|
|
320
|
+
const biome = translatePrettier();
|
|
321
321
|
return {
|
|
322
322
|
schemas,
|
|
323
323
|
patterns,
|
|
324
324
|
globalSchema: parsedGlobalSchema,
|
|
325
325
|
config: {
|
|
326
|
-
rome,
|
|
326
|
+
rome: biome,
|
|
327
327
|
},
|
|
328
328
|
};
|
|
329
329
|
}
|
|
@@ -354,7 +354,7 @@ function translatePrettier() {
|
|
|
354
354
|
}
|
|
355
355
|
if (r.config.quoteProps !== undefined) {
|
|
356
356
|
if (r.config.quoteProps === "consistent") {
|
|
357
|
-
//
|
|
357
|
+
// biome doesn't support this
|
|
358
358
|
ret.quoteProperties = "as-needed";
|
|
359
359
|
}
|
|
360
360
|
else {
|
package/schema/struct_field.d.ts
CHANGED
|
@@ -17,16 +17,18 @@ export declare class StructField extends BaseField implements Field {
|
|
|
17
17
|
private options;
|
|
18
18
|
private jsonAsList?;
|
|
19
19
|
type: Type;
|
|
20
|
+
private validateUniqueKey?;
|
|
21
|
+
private checkUniqueKey;
|
|
20
22
|
constructor(options: StructOptions, jsonAsList?: boolean | undefined);
|
|
21
23
|
formatImpl(obj: any, nested?: boolean): string | Object;
|
|
22
24
|
format(obj: any, nested?: boolean): any;
|
|
23
25
|
private validImpl;
|
|
24
26
|
valid(obj: any): Promise<boolean>;
|
|
25
27
|
}
|
|
26
|
-
export declare function StructType(options: StructOptions): StructField &
|
|
28
|
+
export declare function StructType(options: StructOptions): (StructField & structFieldOptions) | (StructField & GlobalStructOptions);
|
|
27
29
|
/**
|
|
28
30
|
* @deprecated use StructTypeAsList
|
|
29
31
|
*/
|
|
30
32
|
export declare function StructListType(options: StructOptions): ListField;
|
|
31
|
-
export declare function StructTypeAsList(options: StructOptions): StructField &
|
|
33
|
+
export declare function StructTypeAsList(options: StructOptions): (StructField & structFieldOptions) | (StructField & GlobalStructOptions);
|
|
32
34
|
export {};
|
package/schema/struct_field.js
CHANGED
|
@@ -26,6 +26,10 @@ class StructField extends field_1.BaseField {
|
|
|
26
26
|
dbType: schema_1.DBType.JSONB,
|
|
27
27
|
};
|
|
28
28
|
}
|
|
29
|
+
if (options.validateUniqueKey) {
|
|
30
|
+
this.validateUniqueKey = options.validateUniqueKey;
|
|
31
|
+
this.checkUniqueKey = true;
|
|
32
|
+
}
|
|
29
33
|
}
|
|
30
34
|
formatImpl(obj, nested) {
|
|
31
35
|
if (!(obj instanceof Object)) {
|
|
@@ -113,9 +117,27 @@ class StructField extends field_1.BaseField {
|
|
|
113
117
|
let dbKey = (0, schema_1.getStorageKey)(field, k);
|
|
114
118
|
let camelKey = (0, camel_case_1.camelCase)(k);
|
|
115
119
|
let val = obj[camelKey];
|
|
120
|
+
let uniqueKeyField = false;
|
|
121
|
+
if (this.validateUniqueKey !== undefined &&
|
|
122
|
+
(camelKey === this.validateUniqueKey ||
|
|
123
|
+
k === this.validateUniqueKey ||
|
|
124
|
+
dbKey === this.validateUniqueKey)) {
|
|
125
|
+
// this.validateUniqueKey = camelKey;
|
|
126
|
+
uniqueKeyField = true;
|
|
127
|
+
}
|
|
128
|
+
if (uniqueKeyField && this.checkUniqueKey) {
|
|
129
|
+
this.validateUniqueKey = camelKey;
|
|
130
|
+
}
|
|
116
131
|
if (val === undefined && obj[dbKey] !== undefined) {
|
|
132
|
+
if (uniqueKeyField && this.checkUniqueKey) {
|
|
133
|
+
this.validateUniqueKey = dbKey;
|
|
134
|
+
}
|
|
117
135
|
val = obj[dbKey];
|
|
118
136
|
}
|
|
137
|
+
// we've processed this once and no need to process this again
|
|
138
|
+
if (uniqueKeyField && this.checkUniqueKey) {
|
|
139
|
+
this.checkUniqueKey = false;
|
|
140
|
+
}
|
|
119
141
|
if (val === undefined || val === null) {
|
|
120
142
|
// nullable, nothing to do here
|
|
121
143
|
if (field.nullable) {
|
|
@@ -168,16 +190,23 @@ class StructField extends field_1.BaseField {
|
|
|
168
190
|
if (!Array.isArray(obj)) {
|
|
169
191
|
return false;
|
|
170
192
|
}
|
|
193
|
+
// hmm shared instance across tests means this is needed.
|
|
194
|
+
// are there other places that have an issue like this???
|
|
195
|
+
this.checkUniqueKey = true;
|
|
171
196
|
const unique = new Set();
|
|
172
|
-
const valid = await Promise.all(obj.map((v) => {
|
|
173
|
-
|
|
174
|
-
|
|
197
|
+
const valid = await Promise.all(obj.map(async (v) => {
|
|
198
|
+
const valid = await this.validImpl(v);
|
|
199
|
+
if (!valid) {
|
|
200
|
+
return false;
|
|
201
|
+
}
|
|
202
|
+
if (this.validateUniqueKey) {
|
|
203
|
+
let value = v[this.validateUniqueKey];
|
|
175
204
|
if (unique.has(value)) {
|
|
176
205
|
return false;
|
|
177
206
|
}
|
|
178
207
|
unique.add(value);
|
|
179
208
|
}
|
|
180
|
-
return
|
|
209
|
+
return true;
|
|
181
210
|
}));
|
|
182
211
|
return valid.every((b) => b);
|
|
183
212
|
}
|
|
@@ -43,7 +43,7 @@ const const_1 = require("../core/const");
|
|
|
43
43
|
// life is hard
|
|
44
44
|
const MODULE_PATH = const_1.GRAPHQL_PATH;
|
|
45
45
|
async function readInputs() {
|
|
46
|
-
return
|
|
46
|
+
return new Promise((resolve) => {
|
|
47
47
|
const rl = readline.createInterface({
|
|
48
48
|
input: process.stdin,
|
|
49
49
|
// output: process.stdout,
|
package/testutils/builder.d.ts
CHANGED
|
@@ -4,7 +4,7 @@ import { Action, Builder, Changeset, WriteOperation, Validator, Trigger, Observe
|
|
|
4
4
|
import { FieldMap, Schema } from "../schema";
|
|
5
5
|
import { SchemaConfig, EntSchema } from "../schema/base_schema";
|
|
6
6
|
import { FieldInfoMap } from "../schema/schema";
|
|
7
|
-
import { Clause } from "
|
|
7
|
+
import { Clause } from "../core/clause";
|
|
8
8
|
import { ChangesetOptions } from "../action/action";
|
|
9
9
|
export declare class BaseEnt {
|
|
10
10
|
viewer: Viewer;
|
package/testutils/builder.js
CHANGED
|
@@ -248,10 +248,10 @@ class SimpleBuilder {
|
|
|
248
248
|
return this.orchestrator.buildWithOptions_BETA(options);
|
|
249
249
|
}
|
|
250
250
|
async editedEnt() {
|
|
251
|
-
return
|
|
251
|
+
return this.orchestrator.editedEnt();
|
|
252
252
|
}
|
|
253
253
|
async editedEntX() {
|
|
254
|
-
return
|
|
254
|
+
return this.orchestrator.editedEntX();
|
|
255
255
|
}
|
|
256
256
|
async save() {
|
|
257
257
|
await (0, action_1.saveBuilder)(this);
|
|
@@ -260,10 +260,10 @@ class SimpleBuilder {
|
|
|
260
260
|
await (0, action_1.saveBuilderX)(this);
|
|
261
261
|
}
|
|
262
262
|
async valid() {
|
|
263
|
-
return
|
|
263
|
+
return this.orchestrator.valid();
|
|
264
264
|
}
|
|
265
265
|
async validX() {
|
|
266
|
-
return
|
|
266
|
+
return this.orchestrator.validX();
|
|
267
267
|
}
|
|
268
268
|
}
|
|
269
269
|
exports.SimpleBuilder = SimpleBuilder;
|
|
@@ -275,7 +275,7 @@ function expectQueryResult(schema, fieldType, ...options) {
|
|
|
275
275
|
}
|
|
276
276
|
async function expectQueryFromRoot(config, ...options // TODO queries? expected values
|
|
277
277
|
) {
|
|
278
|
-
return
|
|
278
|
+
return expectFromRoot({
|
|
279
279
|
...config,
|
|
280
280
|
queryPrefix: "query",
|
|
281
281
|
querySuffix: "Query",
|
|
@@ -292,7 +292,7 @@ async function expectMutation(config, ...options) {
|
|
|
292
292
|
input: args,
|
|
293
293
|
};
|
|
294
294
|
}
|
|
295
|
-
return
|
|
295
|
+
return expectFromRoot({
|
|
296
296
|
...config,
|
|
297
297
|
args: args,
|
|
298
298
|
root: config.mutation,
|
|
@@ -89,7 +89,7 @@ function getContactBuilder(viewer, input) {
|
|
|
89
89
|
exports.getContactBuilder = getContactBuilder;
|
|
90
90
|
async function createContact(viewer, input) {
|
|
91
91
|
const builder = getContactBuilder(viewer, input);
|
|
92
|
-
return
|
|
92
|
+
return builder.saveX();
|
|
93
93
|
}
|
|
94
94
|
exports.createContact = createContact;
|
|
95
95
|
exports.contactLoader = new loaders_1.ObjectLoaderFactory({
|
|
@@ -93,6 +93,6 @@ function getEventBuilder(viewer, input) {
|
|
|
93
93
|
exports.getEventBuilder = getEventBuilder;
|
|
94
94
|
async function createEvent(viewer, input) {
|
|
95
95
|
const builder = getEventBuilder(viewer, input);
|
|
96
|
-
return
|
|
96
|
+
return builder.saveX();
|
|
97
97
|
}
|
|
98
98
|
exports.createEvent = createEvent;
|
|
@@ -110,7 +110,7 @@ async function createAllContacts(opts) {
|
|
|
110
110
|
time: new Date(), // set time to advanceBy time
|
|
111
111
|
});
|
|
112
112
|
await builder.saveX();
|
|
113
|
-
return
|
|
113
|
+
return builder.editedEntX();
|
|
114
114
|
}));
|
|
115
115
|
expect(contacts.length).toBe(userInputs.length);
|
|
116
116
|
return [userr, contacts];
|
|
@@ -221,7 +221,7 @@ async function createTestEvent(user, input) {
|
|
|
221
221
|
});
|
|
222
222
|
builder.orchestrator.addOutboundEdge(user.id, _1.EdgeType.EventToHosts, "User");
|
|
223
223
|
await builder.saveX();
|
|
224
|
-
return
|
|
224
|
+
return builder.editedEntX();
|
|
225
225
|
}
|
|
226
226
|
exports.createTestEvent = createTestEvent;
|
|
227
227
|
async function setupTempDB(global = false) {
|
|
@@ -158,7 +158,7 @@ class CustomEdge extends ent_1.AssocEdge {
|
|
|
158
158
|
this.deleted_at = data.deleted_at;
|
|
159
159
|
}
|
|
160
160
|
async loadUser(viewer) {
|
|
161
|
-
return
|
|
161
|
+
return internal_1.FakeUser.load(viewer, this.id2);
|
|
162
162
|
}
|
|
163
163
|
}
|
|
164
164
|
exports.CustomEdge = CustomEdge;
|
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
import { Data, Ent, Viewer } from "../core/base";
|
|
2
|
+
import { FakeUser } from "./fake_data";
|
|
3
|
+
import { EdgeQuery } from "../core/query";
|
|
4
|
+
import { MockLogs } from "./mock_log";
|
|
5
|
+
export declare function getVerifyAfterEachCursorGeneric<TSource extends Ent<Viewer>, TDest extends Ent<Viewer>, TData extends Data>(edges: TData[], pageLength: number, user: FakeUser, getQuery: () => EdgeQuery<TSource, TDest, TData>, ml: MockLogs, verifyQuery?: (query: EdgeQuery<TSource, TDest, TData>, cursor: string | undefined) => void): {
|
|
6
|
+
verify: (i: number, hasEdge: boolean, hasNextPage: boolean | undefined, cursor?: string) => Promise<void>;
|
|
7
|
+
getCursor: (edge: TData) => string;
|
|
8
|
+
};
|
|
9
|
+
export declare function getWhereClause(query: any): any;
|
|
@@ -0,0 +1,45 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.getWhereClause = exports.getVerifyAfterEachCursorGeneric = void 0;
|
|
4
|
+
function getVerifyAfterEachCursorGeneric(edges, pageLength, user, getQuery, ml, verifyQuery) {
|
|
5
|
+
let query;
|
|
6
|
+
async function verify(i, hasEdge, hasNextPage, cursor) {
|
|
7
|
+
ml.clear();
|
|
8
|
+
query = getQuery();
|
|
9
|
+
const newEdges = await query.first(pageLength, cursor).queryEdges();
|
|
10
|
+
const pagination = query.paginationInfo().get(user.id);
|
|
11
|
+
if (hasEdge) {
|
|
12
|
+
expect(newEdges[0], `${i}`).toEqual(edges[i]);
|
|
13
|
+
expect(newEdges.length, `${i}`).toBe(edges.length - i >= pageLength ? pageLength : edges.length - i);
|
|
14
|
+
// verify items are the same in order
|
|
15
|
+
expect(newEdges, `${i}`).toEqual(edges.slice(i, i + newEdges.length));
|
|
16
|
+
}
|
|
17
|
+
else {
|
|
18
|
+
expect(newEdges.length, `${i}`).toBe(0);
|
|
19
|
+
}
|
|
20
|
+
if (hasNextPage) {
|
|
21
|
+
expect(pagination?.hasNextPage, `${i}`).toBe(true);
|
|
22
|
+
expect(pagination?.hasPreviousPage, `${i}`).toBe(false);
|
|
23
|
+
}
|
|
24
|
+
else {
|
|
25
|
+
expect(pagination?.hasPreviousPage, `${i}`).toBeFalsy();
|
|
26
|
+
expect(pagination?.hasNextPage, `${i}`).toBeFalsy();
|
|
27
|
+
}
|
|
28
|
+
if (verifyQuery) {
|
|
29
|
+
verifyQuery(query, cursor);
|
|
30
|
+
}
|
|
31
|
+
}
|
|
32
|
+
function getCursor(edge) {
|
|
33
|
+
return query.getCursor(edge);
|
|
34
|
+
}
|
|
35
|
+
return { verify, getCursor };
|
|
36
|
+
}
|
|
37
|
+
exports.getVerifyAfterEachCursorGeneric = getVerifyAfterEachCursorGeneric;
|
|
38
|
+
function getWhereClause(query) {
|
|
39
|
+
const idx = query.query.indexOf("WHERE");
|
|
40
|
+
if (idx !== -1) {
|
|
41
|
+
return query.query.substr(idx + 6);
|
|
42
|
+
}
|
|
43
|
+
return null;
|
|
44
|
+
}
|
|
45
|
+
exports.getWhereClause = getWhereClause;
|
package/testutils/write.js
CHANGED
|
@@ -41,7 +41,7 @@ async function createRowForTest(options, suffix) {
|
|
|
41
41
|
if (isSyncClient(client)) {
|
|
42
42
|
return (0, ent_1.createRowSync)(client, options, suffix || "");
|
|
43
43
|
}
|
|
44
|
-
return
|
|
44
|
+
return (0, ent_1.createRow)(client, options, suffix || "");
|
|
45
45
|
}
|
|
46
46
|
finally {
|
|
47
47
|
client.release();
|
|
@@ -54,7 +54,7 @@ async function editRowForTest(options, suffix) {
|
|
|
54
54
|
if (isSyncClient(client)) {
|
|
55
55
|
return (0, ent_1.editRowSync)(client, options, suffix || "");
|
|
56
56
|
}
|
|
57
|
-
return
|
|
57
|
+
return (0, ent_1.editRow)(client, options, suffix);
|
|
58
58
|
}
|
|
59
59
|
finally {
|
|
60
60
|
client.release();
|
|
@@ -67,7 +67,7 @@ async function deleteRowsForTest(options, cls) {
|
|
|
67
67
|
if (isSyncClient(client)) {
|
|
68
68
|
return (0, ent_1.deleteRowsSync)(client, options, cls);
|
|
69
69
|
}
|
|
70
|
-
return
|
|
70
|
+
return (0, ent_1.deleteRows)(client, options, cls);
|
|
71
71
|
}
|
|
72
72
|
finally {
|
|
73
73
|
client.release();
|