graphile-meta-schema 0.2.4 → 0.2.6
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/LICENSE +3 -1
- package/README.md +101 -4
- package/belongs-to.d.ts +3 -0
- package/belongs-to.js +37 -0
- package/esm/belongs-to.js +35 -0
- package/esm/has.js +36 -0
- package/esm/index.js +503 -0
- package/esm/many-to-many.js +81 -0
- package/esm/types.js +1 -0
- package/has.d.ts +3 -0
- package/has.js +38 -0
- package/index.d.ts +4 -0
- package/index.js +509 -0
- package/many-to-many.d.ts +3 -0
- package/many-to-many.js +83 -0
- package/package.json +28 -43
- package/types.d.ts +105 -0
- package/types.js +2 -0
- package/main/index.js +0 -496
- package/main/many-to-many.js +0 -124
- package/module/index.js +0 -629
- package/module/many-to-many.js +0 -79
package/module/index.js
DELETED
|
@@ -1,629 +0,0 @@
|
|
|
1
|
-
import _defineProperty from "@babel/runtime/helpers/esm/defineProperty";
|
|
2
|
-
|
|
3
|
-
function ownKeys(object, enumerableOnly) { var keys = Object.keys(object); if (Object.getOwnPropertySymbols) { var symbols = Object.getOwnPropertySymbols(object); if (enumerableOnly) symbols = symbols.filter(function (sym) { return Object.getOwnPropertyDescriptor(object, sym).enumerable; }); keys.push.apply(keys, symbols); } return keys; }
|
|
4
|
-
|
|
5
|
-
function _objectSpread(target) { for (var i = 1; i < arguments.length; i++) { var source = arguments[i] != null ? arguments[i] : {}; if (i % 2) { ownKeys(Object(source), true).forEach(function (key) { _defineProperty(target, key, source[key]); }); } else if (Object.getOwnPropertyDescriptors) { Object.defineProperties(target, Object.getOwnPropertyDescriptors(source)); } else { ownKeys(Object(source)).forEach(function (key) { Object.defineProperty(target, key, Object.getOwnPropertyDescriptor(source, key)); }); } } return target; }
|
|
6
|
-
|
|
7
|
-
import { makeExtendSchemaPlugin, gql } from 'graphile-utils';
|
|
8
|
-
import m2m from './many-to-many';
|
|
9
|
-
const GIS_TYPES = ['Geometry', 'Point', 'LineString', 'Polygon', 'MultiPoint', 'MultiLineString', 'MultiPolygon', 'GeometryCollection'];
|
|
10
|
-
|
|
11
|
-
const aliasTypes = type => {
|
|
12
|
-
switch (type) {
|
|
13
|
-
case 'int8':
|
|
14
|
-
return 'bigint';
|
|
15
|
-
|
|
16
|
-
case 'bool':
|
|
17
|
-
return 'boolean';
|
|
18
|
-
|
|
19
|
-
case 'bpchar':
|
|
20
|
-
return 'char';
|
|
21
|
-
|
|
22
|
-
case 'float8':
|
|
23
|
-
return 'float';
|
|
24
|
-
|
|
25
|
-
case 'float4':
|
|
26
|
-
return 'real';
|
|
27
|
-
|
|
28
|
-
case 'int4':
|
|
29
|
-
return 'int';
|
|
30
|
-
|
|
31
|
-
case 'int2':
|
|
32
|
-
return 'smallint';
|
|
33
|
-
|
|
34
|
-
default:
|
|
35
|
-
return type;
|
|
36
|
-
}
|
|
37
|
-
};
|
|
38
|
-
|
|
39
|
-
export const PgMetaschemaPlugin = makeExtendSchemaPlugin((build, schemaOptions) => {
|
|
40
|
-
/** @type {import('graphile-build-pg').PgIntrospectionResultsByKind} */
|
|
41
|
-
const introspection = build.pgIntrospectionResultsByKind;
|
|
42
|
-
const inflection = build.inflection;
|
|
43
|
-
/** @type {string[]} */
|
|
44
|
-
|
|
45
|
-
const schemas = schemaOptions.pgSchemas;
|
|
46
|
-
const pgGetGqlTypeByTypeIdAndModifier = build.pgGetGqlTypeByTypeIdAndModifier;
|
|
47
|
-
return {
|
|
48
|
-
typeDefs: gql`
|
|
49
|
-
type MetaschemaType {
|
|
50
|
-
pgAlias: String!
|
|
51
|
-
pgType: String!
|
|
52
|
-
gqlType: String!
|
|
53
|
-
subtype: String
|
|
54
|
-
modifier: Int
|
|
55
|
-
typmod: JSON
|
|
56
|
-
isArray: Boolean!
|
|
57
|
-
}
|
|
58
|
-
type MetaschemaField {
|
|
59
|
-
name: String!
|
|
60
|
-
type: MetaschemaType!
|
|
61
|
-
}
|
|
62
|
-
type MetaschemaTableInflection {
|
|
63
|
-
# https://github.com/graphile/graphile-engine/blob/v4/packages/graphile-build-pg/src/plugins/PgBasicsPlugin.js
|
|
64
|
-
allRows: String!
|
|
65
|
-
allRowsSimple: String!
|
|
66
|
-
tableFieldName: String!
|
|
67
|
-
tableType: String!
|
|
68
|
-
createPayloadType: String!
|
|
69
|
-
orderByType: String!
|
|
70
|
-
filterType: String
|
|
71
|
-
inputType: String!
|
|
72
|
-
patchType: String
|
|
73
|
-
conditionType: String!
|
|
74
|
-
patchField: String!
|
|
75
|
-
edge: String!
|
|
76
|
-
edgeField: String!
|
|
77
|
-
connection: String!
|
|
78
|
-
typeName: String!
|
|
79
|
-
enumType: String!
|
|
80
|
-
|
|
81
|
-
updatePayloadType: String
|
|
82
|
-
deletePayloadType: String!
|
|
83
|
-
deleteByPrimaryKey: String
|
|
84
|
-
updateByPrimaryKey: String
|
|
85
|
-
|
|
86
|
-
createField: String!
|
|
87
|
-
createInputType: String!
|
|
88
|
-
}
|
|
89
|
-
type MetaschemaTableQuery {
|
|
90
|
-
all: String!
|
|
91
|
-
one: String!
|
|
92
|
-
create: String!
|
|
93
|
-
update: String
|
|
94
|
-
delete: String
|
|
95
|
-
}
|
|
96
|
-
type MetaschemaTableManyToManyRelation {
|
|
97
|
-
query: String
|
|
98
|
-
leftKeyAttributes: [MetaschemaField]
|
|
99
|
-
rightKeyAttributes: [MetaschemaField]
|
|
100
|
-
junctionLeftKeyAttributes: [MetaschemaField]
|
|
101
|
-
junctionRightKeyAttributes: [MetaschemaField]
|
|
102
|
-
junctionTable: MetaschemaTable
|
|
103
|
-
rightTable: MetaschemaTable
|
|
104
|
-
junctionLeftConstraint: MetaschemaForeignKeyConstraint
|
|
105
|
-
junctionRightConstraint: MetaschemaForeignKeyConstraint
|
|
106
|
-
}
|
|
107
|
-
type MetaschemaTableOneToOneRelation {
|
|
108
|
-
query: JSON
|
|
109
|
-
}
|
|
110
|
-
|
|
111
|
-
type MetaschemaTableRelation {
|
|
112
|
-
oneToOne: [MetaschemaTableOneToOneRelation]
|
|
113
|
-
hasOne: JSON
|
|
114
|
-
belongsTo: JSON
|
|
115
|
-
hasMany: JSON
|
|
116
|
-
manyToMany: [MetaschemaTableManyToManyRelation]
|
|
117
|
-
}
|
|
118
|
-
type MetaschemaTable {
|
|
119
|
-
name: String!
|
|
120
|
-
query: MetaschemaTableQuery!
|
|
121
|
-
inflection: MetaschemaTableInflection!
|
|
122
|
-
relations: MetaschemaTableRelation
|
|
123
|
-
fields: [MetaschemaField]
|
|
124
|
-
constraints: [MetaschemaConstraint]
|
|
125
|
-
foreignKeyConstraints: [MetaschemaForeignKeyConstraint]
|
|
126
|
-
primaryKeyConstraints: [MetaschemaPrimaryKeyConstraint]
|
|
127
|
-
uniqueConstraints: [MetaschemaUniqueConstraint]
|
|
128
|
-
checkConstraints: [MetaschemaCheckConstraint]
|
|
129
|
-
exclusionConstraints: [MetaschemaExclusionConstraint]
|
|
130
|
-
}
|
|
131
|
-
union MetaschemaConstraint =
|
|
132
|
-
MetaschemaForeignKeyConstraint
|
|
133
|
-
| MetaschemaUniqueConstraint
|
|
134
|
-
| MetaschemaPrimaryKeyConstraint
|
|
135
|
-
| MetaschemaCheckConstraint
|
|
136
|
-
| MetaschemaExclusionConstraint
|
|
137
|
-
type MetaschemaForeignKeyConstraint {
|
|
138
|
-
name: String!
|
|
139
|
-
fields: [MetaschemaField]
|
|
140
|
-
refTable: MetaschemaTable
|
|
141
|
-
refFields: [MetaschemaField]
|
|
142
|
-
}
|
|
143
|
-
type MetaschemaUniqueConstraint {
|
|
144
|
-
name: String!
|
|
145
|
-
fields: [MetaschemaField]
|
|
146
|
-
}
|
|
147
|
-
type MetaschemaPrimaryKeyConstraint {
|
|
148
|
-
name: String!
|
|
149
|
-
fields: [MetaschemaField]
|
|
150
|
-
}
|
|
151
|
-
type MetaschemaCheckConstraint {
|
|
152
|
-
name: String!
|
|
153
|
-
fields: [MetaschemaField]
|
|
154
|
-
}
|
|
155
|
-
type MetaschemaExclusionConstraint {
|
|
156
|
-
name: String!
|
|
157
|
-
fields: [MetaschemaField]
|
|
158
|
-
}
|
|
159
|
-
type Metaschema {
|
|
160
|
-
tables: [MetaschemaTable]
|
|
161
|
-
}
|
|
162
|
-
extend type Query {
|
|
163
|
-
_meta: Metaschema
|
|
164
|
-
}
|
|
165
|
-
`,
|
|
166
|
-
resolvers: {
|
|
167
|
-
// TODO determine why check constraints aren't coming through
|
|
168
|
-
MetaschemaCheckConstraint: {
|
|
169
|
-
/** @param constraint {import('graphile-build-pg').PgConstraint} */
|
|
170
|
-
fields(constraint) {
|
|
171
|
-
return constraint.keyAttributes;
|
|
172
|
-
}
|
|
173
|
-
|
|
174
|
-
},
|
|
175
|
-
MetaschemaExclusionConstraint: {
|
|
176
|
-
/** @param constraint {import('graphile-build-pg').PgConstraint} */
|
|
177
|
-
fields(constraint) {
|
|
178
|
-
return constraint.keyAttributes;
|
|
179
|
-
}
|
|
180
|
-
|
|
181
|
-
},
|
|
182
|
-
MetaschemaUniqueConstraint: {
|
|
183
|
-
/** @param constraint {import('graphile-build-pg').PgConstraint} */
|
|
184
|
-
fields(constraint) {
|
|
185
|
-
return constraint.keyAttributes;
|
|
186
|
-
}
|
|
187
|
-
|
|
188
|
-
},
|
|
189
|
-
MetaschemaPrimaryKeyConstraint: {
|
|
190
|
-
/** @param constraint {import('graphile-build-pg').PgConstraint} */
|
|
191
|
-
fields(constraint) {
|
|
192
|
-
return constraint.keyAttributes;
|
|
193
|
-
}
|
|
194
|
-
|
|
195
|
-
},
|
|
196
|
-
MetaschemaForeignKeyConstraint: {
|
|
197
|
-
/** @param constraint {import('graphile-build-pg').PgConstraint} */
|
|
198
|
-
fields(constraint) {
|
|
199
|
-
return constraint.keyAttributes;
|
|
200
|
-
},
|
|
201
|
-
|
|
202
|
-
/** @param constraint {import('graphile-build-pg').PgConstraint} */
|
|
203
|
-
refTable(constraint) {
|
|
204
|
-
return constraint.foreignClass;
|
|
205
|
-
},
|
|
206
|
-
|
|
207
|
-
/** @param constraint {import('graphile-build-pg').PgConstraint} */
|
|
208
|
-
refFields(constraint) {
|
|
209
|
-
return constraint.foreignKeyAttributes;
|
|
210
|
-
}
|
|
211
|
-
|
|
212
|
-
},
|
|
213
|
-
MetaschemaType: {
|
|
214
|
-
/** @param attr {import('graphile-build-pg').PgType} */
|
|
215
|
-
pgType(type) {
|
|
216
|
-
// TODO what is the best API here?
|
|
217
|
-
// 1. we could return original _name, e.g. _citext (= citext[])
|
|
218
|
-
// 2. we could return original type name and include isArray
|
|
219
|
-
if (type.isPgArray && type.arrayItemType?.name) {
|
|
220
|
-
return type.arrayItemType.name;
|
|
221
|
-
}
|
|
222
|
-
|
|
223
|
-
return type.name;
|
|
224
|
-
},
|
|
225
|
-
|
|
226
|
-
pgAlias(type) {
|
|
227
|
-
if (type.isPgArray && type.arrayItemType?.name) {
|
|
228
|
-
return aliasTypes(type.arrayItemType.name);
|
|
229
|
-
}
|
|
230
|
-
|
|
231
|
-
return aliasTypes(type.name);
|
|
232
|
-
},
|
|
233
|
-
|
|
234
|
-
gqlType(type) {
|
|
235
|
-
const gqlType = pgGetGqlTypeByTypeIdAndModifier(type.id, type.attrTypeModifier);
|
|
236
|
-
|
|
237
|
-
switch (gqlType.name) {
|
|
238
|
-
case 'GeometryInterface':
|
|
239
|
-
case 'GeometryPoint':
|
|
240
|
-
case 'GeometryPolygon':
|
|
241
|
-
return 'GeoJSON';
|
|
242
|
-
|
|
243
|
-
default:
|
|
244
|
-
return gqlType;
|
|
245
|
-
}
|
|
246
|
-
},
|
|
247
|
-
|
|
248
|
-
subtype(type) {
|
|
249
|
-
const gqlType = pgGetGqlTypeByTypeIdAndModifier(type.id, type.attrTypeModifier);
|
|
250
|
-
|
|
251
|
-
switch (gqlType.name) {
|
|
252
|
-
case 'GeometryInterface':
|
|
253
|
-
case 'GeometryPoint':
|
|
254
|
-
case 'GeometryPolygon':
|
|
255
|
-
return gqlType.name;
|
|
256
|
-
|
|
257
|
-
default:
|
|
258
|
-
return null;
|
|
259
|
-
}
|
|
260
|
-
},
|
|
261
|
-
|
|
262
|
-
typmod(type) {
|
|
263
|
-
const modifier = type.attrTypeModifier;
|
|
264
|
-
if (!modifier) return null;
|
|
265
|
-
|
|
266
|
-
if (type.name === 'geography' || type.name === 'geometry') {
|
|
267
|
-
// Ref: https://github.com/postgis/postgis/blob/2.5.2/liblwgeom/liblwgeom.h.in#L156-L173
|
|
268
|
-
// #define TYPMOD_GET_SRID(typmod) ((((typmod) & 0x0FFFFF00) - ((typmod) & 0x10000000)) >> 8)
|
|
269
|
-
// #define TYPMOD_GET_TYPE(typmod) ((typmod & 0x000000FC)>>2)
|
|
270
|
-
// #define TYPMOD_GET_Z(typmod) ((typmod & 0x00000002)>>1)
|
|
271
|
-
// #define TYPMOD_GET_M(typmod) (typmod & 0x00000001)
|
|
272
|
-
const srid = (modifier & 0x0fffff00) - (modifier & 0x10000000) >> 8;
|
|
273
|
-
const subtype = (modifier & 0x000000fc) >> 2;
|
|
274
|
-
const hasZ = (modifier & 0x00000002) >> 1 === 1;
|
|
275
|
-
const hasM = (modifier & 0x00000001) === 1;
|
|
276
|
-
|
|
277
|
-
if (subtype < GIS_TYPES.length) {
|
|
278
|
-
return {
|
|
279
|
-
srid,
|
|
280
|
-
subtype,
|
|
281
|
-
hasZ,
|
|
282
|
-
hasM,
|
|
283
|
-
gisType: GIS_TYPES[subtype]
|
|
284
|
-
};
|
|
285
|
-
}
|
|
286
|
-
}
|
|
287
|
-
|
|
288
|
-
return {
|
|
289
|
-
modifier
|
|
290
|
-
};
|
|
291
|
-
},
|
|
292
|
-
|
|
293
|
-
modifier(type) {
|
|
294
|
-
return type.attrTypeModifier;
|
|
295
|
-
},
|
|
296
|
-
|
|
297
|
-
isArray(type) {
|
|
298
|
-
return type.isPgArray;
|
|
299
|
-
}
|
|
300
|
-
|
|
301
|
-
},
|
|
302
|
-
MetaschemaField: {
|
|
303
|
-
/** @param attr {import('graphile-build-pg').PgAttribute} */
|
|
304
|
-
name(attr) {
|
|
305
|
-
return inflection.column(attr);
|
|
306
|
-
},
|
|
307
|
-
|
|
308
|
-
/** @param attr {import('graphile-build-pg').PgAttribute} */
|
|
309
|
-
type(attr) {
|
|
310
|
-
if (attr.typeModifier > 0) {
|
|
311
|
-
return _objectSpread(_objectSpread({}, attr.type), {}, {
|
|
312
|
-
attrTypeModifier: attr.typeModifier
|
|
313
|
-
});
|
|
314
|
-
}
|
|
315
|
-
|
|
316
|
-
return attr.type;
|
|
317
|
-
}
|
|
318
|
-
|
|
319
|
-
},
|
|
320
|
-
MetaschemaTableInflection: {
|
|
321
|
-
deleteByPrimaryKey(table) {
|
|
322
|
-
if (!table.primaryKeyConstraint?.keyAttributes?.length) return null;
|
|
323
|
-
return inflection.deleteByKeys(table.primaryKeyConstraint.keyAttributes, table, table.primaryKeyConstraint);
|
|
324
|
-
},
|
|
325
|
-
|
|
326
|
-
updateByPrimaryKey(table) {
|
|
327
|
-
if (!table.primaryKeyConstraint?.keyAttributes?.length) return null;
|
|
328
|
-
return inflection.updateByKeys(table.primaryKeyConstraint.keyAttributes, table, table.primaryKeyConstraint);
|
|
329
|
-
},
|
|
330
|
-
|
|
331
|
-
createField(table) {
|
|
332
|
-
return inflection.createField(table);
|
|
333
|
-
},
|
|
334
|
-
|
|
335
|
-
createInputType(table) {
|
|
336
|
-
return inflection.createInputType(table);
|
|
337
|
-
},
|
|
338
|
-
|
|
339
|
-
allRows(table) {
|
|
340
|
-
return inflection.allRows(table);
|
|
341
|
-
},
|
|
342
|
-
|
|
343
|
-
allRowsSimple(table) {
|
|
344
|
-
return inflection.allRowsSimple(table);
|
|
345
|
-
},
|
|
346
|
-
|
|
347
|
-
tableFieldName(table) {
|
|
348
|
-
return inflection.tableFieldName(table);
|
|
349
|
-
},
|
|
350
|
-
|
|
351
|
-
tableType(table) {
|
|
352
|
-
return inflection.tableType(table);
|
|
353
|
-
},
|
|
354
|
-
|
|
355
|
-
orderByType(table) {
|
|
356
|
-
return inflection.orderByType(inflection.tableType(table));
|
|
357
|
-
},
|
|
358
|
-
|
|
359
|
-
filterType(table) {
|
|
360
|
-
if (typeof inflection.filterType === 'function') return inflection.filterType(inflection.tableType(table));
|
|
361
|
-
return null;
|
|
362
|
-
},
|
|
363
|
-
|
|
364
|
-
inputType(table) {
|
|
365
|
-
return inflection.inputType(inflection.tableType(table));
|
|
366
|
-
},
|
|
367
|
-
|
|
368
|
-
patchType(table) {
|
|
369
|
-
return inflection.patchType(inflection.tableType(table));
|
|
370
|
-
},
|
|
371
|
-
|
|
372
|
-
conditionType(table) {
|
|
373
|
-
return inflection.conditionType(inflection.tableType(table));
|
|
374
|
-
},
|
|
375
|
-
|
|
376
|
-
patchField(table) {
|
|
377
|
-
return inflection.patchField(inflection.tableType(table));
|
|
378
|
-
},
|
|
379
|
-
|
|
380
|
-
edge(table) {
|
|
381
|
-
return inflection.edge(inflection.tableType(table));
|
|
382
|
-
},
|
|
383
|
-
|
|
384
|
-
edgeField(table) {
|
|
385
|
-
return inflection.edgeField(table);
|
|
386
|
-
},
|
|
387
|
-
|
|
388
|
-
connection(table) {
|
|
389
|
-
return inflection.connection(inflection.tableType(table));
|
|
390
|
-
},
|
|
391
|
-
|
|
392
|
-
typeName(table) {
|
|
393
|
-
return inflection._typeName(table);
|
|
394
|
-
},
|
|
395
|
-
|
|
396
|
-
enumType(table) {
|
|
397
|
-
return inflection.enumType(table);
|
|
398
|
-
},
|
|
399
|
-
|
|
400
|
-
createPayloadType(table) {
|
|
401
|
-
return inflection.createPayloadType(table);
|
|
402
|
-
},
|
|
403
|
-
|
|
404
|
-
updatePayloadType(table) {
|
|
405
|
-
return inflection.updatePayloadType(table);
|
|
406
|
-
},
|
|
407
|
-
|
|
408
|
-
deletePayloadType(table) {
|
|
409
|
-
return inflection.deletePayloadType(table);
|
|
410
|
-
}
|
|
411
|
-
|
|
412
|
-
},
|
|
413
|
-
MetaschemaTableQuery: {
|
|
414
|
-
delete(table) {
|
|
415
|
-
if (!table.primaryKeyConstraint?.keyAttributes?.length) return null;
|
|
416
|
-
return inflection.deleteByKeys(table.primaryKeyConstraint.keyAttributes, table, table.primaryKeyConstraint);
|
|
417
|
-
},
|
|
418
|
-
|
|
419
|
-
update(table) {
|
|
420
|
-
if (!table.primaryKeyConstraint?.keyAttributes?.length) return null;
|
|
421
|
-
return inflection.updateByKeys(table.primaryKeyConstraint.keyAttributes, table, table.primaryKeyConstraint);
|
|
422
|
-
},
|
|
423
|
-
|
|
424
|
-
create(table) {
|
|
425
|
-
return inflection.createField(table);
|
|
426
|
-
},
|
|
427
|
-
|
|
428
|
-
all(table) {
|
|
429
|
-
return inflection.allRows(table);
|
|
430
|
-
},
|
|
431
|
-
|
|
432
|
-
one(table) {
|
|
433
|
-
return inflection.tableFieldName(table);
|
|
434
|
-
}
|
|
435
|
-
|
|
436
|
-
},
|
|
437
|
-
MetaschemaTableRelation: {
|
|
438
|
-
oneToOne(table) {
|
|
439
|
-
return null;
|
|
440
|
-
},
|
|
441
|
-
|
|
442
|
-
oneToMany(table) {
|
|
443
|
-
return null;
|
|
444
|
-
},
|
|
445
|
-
|
|
446
|
-
manyToOne(table) {
|
|
447
|
-
return null;
|
|
448
|
-
},
|
|
449
|
-
|
|
450
|
-
hasOne(table) {
|
|
451
|
-
return null;
|
|
452
|
-
},
|
|
453
|
-
|
|
454
|
-
belongsTo(table) {
|
|
455
|
-
return null;
|
|
456
|
-
},
|
|
457
|
-
|
|
458
|
-
hasMany(table) {
|
|
459
|
-
return null;
|
|
460
|
-
},
|
|
461
|
-
|
|
462
|
-
manyToMany(table) {
|
|
463
|
-
if (!inflection.manyToManyRelationByKeys) {
|
|
464
|
-
return null;
|
|
465
|
-
}
|
|
466
|
-
|
|
467
|
-
return m2m(table, build);
|
|
468
|
-
}
|
|
469
|
-
|
|
470
|
-
},
|
|
471
|
-
MetaschemaTableOneToOneRelation: {
|
|
472
|
-
query(relation) {
|
|
473
|
-
return null;
|
|
474
|
-
}
|
|
475
|
-
|
|
476
|
-
},
|
|
477
|
-
MetaschemaTableManyToManyRelation: {
|
|
478
|
-
leftKeyAttributes(relation) {
|
|
479
|
-
return relation.leftKeyAttributes;
|
|
480
|
-
},
|
|
481
|
-
|
|
482
|
-
junctionLeftKeyAttributes(relation) {
|
|
483
|
-
return relation.junctionLeftKeyAttributes;
|
|
484
|
-
},
|
|
485
|
-
|
|
486
|
-
junctionRightKeyAttributes(relation) {
|
|
487
|
-
return relation.junctionRightKeyAttributes;
|
|
488
|
-
},
|
|
489
|
-
|
|
490
|
-
rightKeyAttributes(relation) {
|
|
491
|
-
return relation.rightKeyAttributes;
|
|
492
|
-
},
|
|
493
|
-
|
|
494
|
-
junctionTable(relation) {
|
|
495
|
-
return relation.junctionTable;
|
|
496
|
-
},
|
|
497
|
-
|
|
498
|
-
rightTable(relation) {
|
|
499
|
-
return relation.rightTable;
|
|
500
|
-
},
|
|
501
|
-
|
|
502
|
-
junctionLeftConstraint(relation) {
|
|
503
|
-
return relation.junctionLeftConstraint;
|
|
504
|
-
},
|
|
505
|
-
|
|
506
|
-
junctionRightConstraint(relation) {
|
|
507
|
-
return relation.junctionRightConstraint;
|
|
508
|
-
},
|
|
509
|
-
|
|
510
|
-
query(relation) {
|
|
511
|
-
const {
|
|
512
|
-
leftKeyAttributes,
|
|
513
|
-
junctionLeftKeyAttributes,
|
|
514
|
-
junctionRightKeyAttributes,
|
|
515
|
-
rightKeyAttributes,
|
|
516
|
-
junctionTable,
|
|
517
|
-
rightTable,
|
|
518
|
-
junctionLeftConstraint,
|
|
519
|
-
junctionRightConstraint
|
|
520
|
-
} = relation;
|
|
521
|
-
return inflection.manyToManyRelationByKeys(leftKeyAttributes, junctionLeftKeyAttributes, junctionRightKeyAttributes, rightKeyAttributes, junctionTable, rightTable, junctionLeftConstraint, junctionRightConstraint);
|
|
522
|
-
}
|
|
523
|
-
|
|
524
|
-
},
|
|
525
|
-
MetaschemaTable: {
|
|
526
|
-
relations(table) {
|
|
527
|
-
return table;
|
|
528
|
-
},
|
|
529
|
-
|
|
530
|
-
/** @param table {import('graphile-build-pg').PgClass} */
|
|
531
|
-
name(table) {
|
|
532
|
-
return inflection.tableType(table); // return inflection._tableName(table);
|
|
533
|
-
},
|
|
534
|
-
|
|
535
|
-
/** @param table {import('graphile-build-pg').PgClass} */
|
|
536
|
-
fields(table) {
|
|
537
|
-
return table.attributes.filter(attr => {
|
|
538
|
-
if (attr.num < 1) return false; // low-level props
|
|
539
|
-
|
|
540
|
-
return true;
|
|
541
|
-
});
|
|
542
|
-
},
|
|
543
|
-
|
|
544
|
-
/** @param table {import('graphile-build-pg').PgClass} */
|
|
545
|
-
inflection(table) {
|
|
546
|
-
// return table so the MetaschemaTableInflection resolver uses that as input
|
|
547
|
-
return table;
|
|
548
|
-
},
|
|
549
|
-
|
|
550
|
-
/** @param table {import('graphile-build-pg').PgClass} */
|
|
551
|
-
query(table) {
|
|
552
|
-
return table;
|
|
553
|
-
},
|
|
554
|
-
|
|
555
|
-
/** @param table {import('graphile-build-pg').PgClass} */
|
|
556
|
-
constraints(table) {
|
|
557
|
-
return table.constraints;
|
|
558
|
-
},
|
|
559
|
-
|
|
560
|
-
/** @param table {import('graphile-build-pg').PgClass} */
|
|
561
|
-
foreignKeyConstraints(table) {
|
|
562
|
-
return table.constraints.filter(c => c.type === 'f');
|
|
563
|
-
},
|
|
564
|
-
|
|
565
|
-
/** @param table {import('graphile-build-pg').PgClass} */
|
|
566
|
-
primaryKeyConstraints(table) {
|
|
567
|
-
return table.constraints.filter(c => c.type === 'p');
|
|
568
|
-
},
|
|
569
|
-
|
|
570
|
-
/** @param table {import('graphile-build-pg').PgClass} */
|
|
571
|
-
uniqueConstraints(table) {
|
|
572
|
-
return table.constraints.filter(c => c.type === 'u');
|
|
573
|
-
},
|
|
574
|
-
|
|
575
|
-
/** @param table {import('graphile-build-pg').PgClass} */
|
|
576
|
-
checkConstraints(table) {
|
|
577
|
-
return table.constraints.filter(c => c.type === 'c');
|
|
578
|
-
},
|
|
579
|
-
|
|
580
|
-
/** @param table {import('graphile-build-pg').PgClass} */
|
|
581
|
-
exclusionConstraints(table) {
|
|
582
|
-
return table.constraints.filter(c => c.type === 'x');
|
|
583
|
-
}
|
|
584
|
-
|
|
585
|
-
},
|
|
586
|
-
MetaschemaConstraint: {
|
|
587
|
-
/** @param obj {import('graphile-build-pg').PgConstraint} */
|
|
588
|
-
__resolveType(obj) {
|
|
589
|
-
switch (obj.type) {
|
|
590
|
-
case 'p':
|
|
591
|
-
return 'MetaschemaPrimaryKeyConstraint';
|
|
592
|
-
|
|
593
|
-
case 'f':
|
|
594
|
-
return 'MetaschemaForeignKeyConstraint';
|
|
595
|
-
|
|
596
|
-
case 'c':
|
|
597
|
-
return 'MetaschemaCheckConstraint';
|
|
598
|
-
|
|
599
|
-
case 'u':
|
|
600
|
-
return 'MetaschemaUniqueConstraint';
|
|
601
|
-
|
|
602
|
-
case 'x':
|
|
603
|
-
return 'MetaschemaExclusionConstraint';
|
|
604
|
-
}
|
|
605
|
-
}
|
|
606
|
-
|
|
607
|
-
},
|
|
608
|
-
Metaschema: {
|
|
609
|
-
tables() {
|
|
610
|
-
return introspection.class.filter(kls => {
|
|
611
|
-
if (!schemas.includes(kls.namespaceName)) return false; // r = ordinary table, i = index, S = sequence, t = TOAST table, v = view, m = materialized view, c = composite type, f = foreign table, p = partitioned table, I = partitioned index
|
|
612
|
-
|
|
613
|
-
if (kls.classKind !== 'r') return false;
|
|
614
|
-
return true;
|
|
615
|
-
});
|
|
616
|
-
}
|
|
617
|
-
|
|
618
|
-
},
|
|
619
|
-
Query: {
|
|
620
|
-
_meta() {
|
|
621
|
-
// just placeholder
|
|
622
|
-
return {};
|
|
623
|
-
}
|
|
624
|
-
|
|
625
|
-
}
|
|
626
|
-
}
|
|
627
|
-
};
|
|
628
|
-
});
|
|
629
|
-
export default PgMetaschemaPlugin;
|
package/module/many-to-many.js
DELETED
|
@@ -1,79 +0,0 @@
|
|
|
1
|
-
function arraysAreEqual(array1, array2) {
|
|
2
|
-
return array1.length === array2.length && array1.every((el, i) => array2[i] === el);
|
|
3
|
-
} // Given a `leftTable`, trace through the foreign key relations
|
|
4
|
-
// and identify a `junctionTable` and `rightTable`.
|
|
5
|
-
// Returns a list of data objects for these many-to-many relationships.
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
export default function manyToManyRelationships(leftTable, build) {
|
|
9
|
-
const {
|
|
10
|
-
pgIntrospectionResultsByKind: introspectionResultsByKind,
|
|
11
|
-
pgOmit: omit
|
|
12
|
-
} = build;
|
|
13
|
-
return leftTable.foreignConstraints.filter(con => con.type === 'f').reduce((memoLeft, junctionLeftConstraint) => {
|
|
14
|
-
if (omit(junctionLeftConstraint, 'read') || omit(junctionLeftConstraint, 'manyToMany')) {
|
|
15
|
-
return memoLeft;
|
|
16
|
-
}
|
|
17
|
-
|
|
18
|
-
const junctionTable = introspectionResultsByKind.classById[junctionLeftConstraint.classId];
|
|
19
|
-
|
|
20
|
-
if (!junctionTable) {
|
|
21
|
-
throw new Error(`Could not find the table that referenced us (constraint: ${junctionLeftConstraint.name})`);
|
|
22
|
-
}
|
|
23
|
-
|
|
24
|
-
if (omit(junctionTable, 'read') || omit(junctionTable, 'manyToMany')) {
|
|
25
|
-
return memoLeft;
|
|
26
|
-
}
|
|
27
|
-
|
|
28
|
-
const memoRight = junctionTable.constraints.filter(con => con.id !== junctionLeftConstraint.id && // Don't follow the same constraint back to the left table
|
|
29
|
-
con.type === 'f' && !omit(con, 'read') && !omit(con, 'manyToMany')).reduce((memoRight, junctionRightConstraint) => {
|
|
30
|
-
const rightTable = junctionRightConstraint.foreignClass;
|
|
31
|
-
|
|
32
|
-
if (omit(rightTable, 'read') || omit(rightTable, 'manyToMany')) {
|
|
33
|
-
return memoRight;
|
|
34
|
-
}
|
|
35
|
-
|
|
36
|
-
const leftKeyAttributes = junctionLeftConstraint.foreignKeyAttributes;
|
|
37
|
-
const junctionLeftKeyAttributes = junctionLeftConstraint.keyAttributes;
|
|
38
|
-
const junctionRightKeyAttributes = junctionRightConstraint.keyAttributes;
|
|
39
|
-
const rightKeyAttributes = junctionRightConstraint.foreignKeyAttributes; // Ensure keys were found
|
|
40
|
-
|
|
41
|
-
if (!leftKeyAttributes.every(_ => _) || !junctionLeftKeyAttributes.every(_ => _) || !junctionRightKeyAttributes.every(_ => _) || !rightKeyAttributes.every(_ => _)) {
|
|
42
|
-
throw new Error('Could not find key columns!');
|
|
43
|
-
} // Ensure keys can be read
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
if (leftKeyAttributes.some(attr => omit(attr, 'read')) || junctionLeftKeyAttributes.some(attr => omit(attr, 'read')) || junctionRightKeyAttributes.some(attr => omit(attr, 'read')) || rightKeyAttributes.some(attr => omit(attr, 'read'))) {
|
|
47
|
-
return memoRight;
|
|
48
|
-
} // Ensure both constraints are single-column
|
|
49
|
-
// TODO: handle multi-column
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
if (leftKeyAttributes.length > 1 || rightKeyAttributes.length > 1) {
|
|
53
|
-
return memoRight;
|
|
54
|
-
} // Ensure junction constraint keys are not unique (which would result in a one-to-one relation)
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
const junctionLeftConstraintIsUnique = !!junctionTable.constraints.find(c => ['p', 'u'].includes(c.type) && arraysAreEqual(c.keyAttributeNums, junctionLeftKeyAttributes.map(attr => attr.num)));
|
|
58
|
-
const junctionRightConstraintIsUnique = !!junctionTable.constraints.find(c => ['p', 'u'].includes(c.type) && arraysAreEqual(c.keyAttributeNums, junctionRightKeyAttributes.map(attr => attr.num)));
|
|
59
|
-
|
|
60
|
-
if (junctionLeftConstraintIsUnique || junctionRightConstraintIsUnique) {
|
|
61
|
-
return memoRight;
|
|
62
|
-
}
|
|
63
|
-
|
|
64
|
-
const allowsMultipleEdgesToNode = !junctionTable.constraints.find(c => ['p', 'u'].includes(c.type) && arraysAreEqual(c.keyAttributeNums.concat().sort(), [...junctionLeftKeyAttributes.map(obj => obj.num), ...junctionRightKeyAttributes.map(obj => obj.num)].sort()));
|
|
65
|
-
return [...memoRight, {
|
|
66
|
-
leftKeyAttributes,
|
|
67
|
-
junctionLeftKeyAttributes,
|
|
68
|
-
junctionRightKeyAttributes,
|
|
69
|
-
rightKeyAttributes,
|
|
70
|
-
junctionTable,
|
|
71
|
-
rightTable,
|
|
72
|
-
junctionLeftConstraint,
|
|
73
|
-
junctionRightConstraint,
|
|
74
|
-
allowsMultipleEdgesToNode
|
|
75
|
-
}];
|
|
76
|
-
}, []);
|
|
77
|
-
return [...memoLeft, ...memoRight];
|
|
78
|
-
}, []);
|
|
79
|
-
}
|