@powerhousedao/reactor-api 6.0.0-dev.253 → 6.0.0-dev.255
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/index.d.mts +28 -11
- package/dist/index.d.mts.map +1 -1
- package/dist/index.mjs +197 -137
- package/dist/index.mjs.map +1 -1
- package/package.json +15 -13
package/dist/index.mjs
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
|
|
2
|
-
!function(){try{var e="undefined"!=typeof window?window:"undefined"!=typeof global?global:"undefined"!=typeof globalThis?globalThis:"undefined"!=typeof self?self:{},n=(new e.Error).stack;n&&(e._sentryDebugIds=e._sentryDebugIds||{},e._sentryDebugIds[n]="
|
|
2
|
+
!function(){try{var e="undefined"!=typeof window?window:"undefined"!=typeof global?global:"undefined"!=typeof globalThis?globalThis:"undefined"!=typeof self?self:{},n=(new e.Error).stack;n&&(e._sentryDebugIds=e._sentryDebugIds||{},e._sentryDebugIds[n]="7376325d-a64e-53ca-8757-5f06b3be132b")}catch(e){}}();
|
|
3
3
|
import { a as isSubgraphClass, c as loadDocumentModels, d as BaseSubgraph, i as buildGraphqlOperations, l as loadProcessors, n as buildGraphQlDriveDocument, o as debounce, r as buildGraphqlOperation, t as buildGraphQlDocument, u as loadSubgraphs } from "./utils-CHCRSWig.mjs";
|
|
4
4
|
import { AnalyticsQueryEngine } from "@powerhousedao/analytics-engine-core";
|
|
5
5
|
import { AnalyticsModel, AnalyticsResolvers, typedefs } from "@powerhousedao/analytics-engine-graphql";
|
|
@@ -33,7 +33,7 @@ import { typeDefs } from "@powerhousedao/document-engineering/graphql";
|
|
|
33
33
|
import { camelCase, kebabCase, pascalCase } from "change-case";
|
|
34
34
|
import { GraphQLJSONObject } from "graphql-type-json";
|
|
35
35
|
import { setName } from "@powerhousedao/shared/document-model";
|
|
36
|
-
import { PropagationMode as PropagationMode$1, consolidateSyncOperations, driveIdFromUrl, envelopesToSyncOperations, parseDriveUrl } from "@powerhousedao/reactor";
|
|
36
|
+
import { DEFAULT_DRIVE_CONTAINER_TYPES, PropagationMode as PropagationMode$1, consolidateSyncOperations, driveIdFromUrl, envelopesToSyncOperations, parseDriveUrl } from "@powerhousedao/reactor";
|
|
37
37
|
import * as z$1 from "zod";
|
|
38
38
|
import { z } from "zod";
|
|
39
39
|
import { createHandler } from "graphql-sse/lib/use/fetch";
|
|
@@ -41,6 +41,7 @@ import { PubSub, withFilter } from "graphql-subscriptions";
|
|
|
41
41
|
import dotenv from "dotenv";
|
|
42
42
|
import { buildTreeUrl } from "@powerhousedao/shared";
|
|
43
43
|
import { getConfig } from "@powerhousedao/config/node";
|
|
44
|
+
import { reactorDriveDocumentModelModule } from "@powerhousedao/reactor-drive";
|
|
44
45
|
import { driveDocumentModelModule } from "@powerhousedao/shared/document-drive";
|
|
45
46
|
import EventEmitter from "node:events";
|
|
46
47
|
import { PostgresAnalyticsStore } from "@powerhousedao/analytics-engine-pg";
|
|
@@ -251,12 +252,12 @@ var AuthSubgraph = class extends BaseSubgraph {
|
|
|
251
252
|
resolvers = {
|
|
252
253
|
Query: {
|
|
253
254
|
documentAccess: async (_parent, args) => {
|
|
254
|
-
this.logger.debug("documentAccess", args);
|
|
255
|
+
this.logger.debug("documentAccess(@args)", args);
|
|
255
256
|
if (!this.documentPermissionService) throw new GraphQLError("DocumentPermissionService not available");
|
|
256
257
|
try {
|
|
257
258
|
return await documentAccess(this.documentPermissionService, args);
|
|
258
259
|
} catch (error) {
|
|
259
|
-
this.logger.error("Error in documentAccess:", error);
|
|
260
|
+
this.logger.error("Error in documentAccess: @error", error);
|
|
260
261
|
throw error;
|
|
261
262
|
}
|
|
262
263
|
},
|
|
@@ -267,7 +268,7 @@ var AuthSubgraph = class extends BaseSubgraph {
|
|
|
267
268
|
try {
|
|
268
269
|
return await userDocumentPermissions(this.documentPermissionService, ctx.user.address);
|
|
269
270
|
} catch (error) {
|
|
270
|
-
this.logger.error("Error in userDocumentPermissions:", error);
|
|
271
|
+
this.logger.error("Error in userDocumentPermissions: @error", error);
|
|
271
272
|
throw error;
|
|
272
273
|
}
|
|
273
274
|
},
|
|
@@ -277,210 +278,210 @@ var AuthSubgraph = class extends BaseSubgraph {
|
|
|
277
278
|
try {
|
|
278
279
|
return await groups(this.documentPermissionService);
|
|
279
280
|
} catch (error) {
|
|
280
|
-
this.logger.error("Error in groups:", error);
|
|
281
|
+
this.logger.error("Error in groups: @error", error);
|
|
281
282
|
throw error;
|
|
282
283
|
}
|
|
283
284
|
},
|
|
284
285
|
group: async (_parent, args) => {
|
|
285
|
-
this.logger.debug("group", args);
|
|
286
|
+
this.logger.debug("group(@args)", args);
|
|
286
287
|
if (!this.documentPermissionService) throw new GraphQLError("DocumentPermissionService not available");
|
|
287
288
|
try {
|
|
288
289
|
return await group(this.documentPermissionService, args);
|
|
289
290
|
} catch (error) {
|
|
290
|
-
this.logger.error("Error in group:", error);
|
|
291
|
+
this.logger.error("Error in group: @error", error);
|
|
291
292
|
throw error;
|
|
292
293
|
}
|
|
293
294
|
},
|
|
294
295
|
userGroups: async (_parent, args) => {
|
|
295
|
-
this.logger.debug("userGroups", args);
|
|
296
|
+
this.logger.debug("userGroups(@args)", args);
|
|
296
297
|
if (!this.documentPermissionService) throw new GraphQLError("DocumentPermissionService not available");
|
|
297
298
|
try {
|
|
298
299
|
return await userGroups(this.documentPermissionService, args);
|
|
299
300
|
} catch (error) {
|
|
300
|
-
this.logger.error("Error in userGroups:", error);
|
|
301
|
+
this.logger.error("Error in userGroups: @error", error);
|
|
301
302
|
throw error;
|
|
302
303
|
}
|
|
303
304
|
},
|
|
304
305
|
operationPermissions: async (_parent, args) => {
|
|
305
|
-
this.logger.debug("operationPermissions", args);
|
|
306
|
+
this.logger.debug("operationPermissions(@args)", args);
|
|
306
307
|
if (!this.documentPermissionService) throw new GraphQLError("DocumentPermissionService not available");
|
|
307
308
|
try {
|
|
308
309
|
return await operationPermissions(this.documentPermissionService, args);
|
|
309
310
|
} catch (error) {
|
|
310
|
-
this.logger.error("Error in operationPermissions:", error);
|
|
311
|
+
this.logger.error("Error in operationPermissions: @error", error);
|
|
311
312
|
throw error;
|
|
312
313
|
}
|
|
313
314
|
},
|
|
314
315
|
canExecuteOperation: async (_parent, args, ctx) => {
|
|
315
|
-
this.logger.debug("canExecuteOperation", args);
|
|
316
|
+
this.logger.debug("canExecuteOperation(@args)", args);
|
|
316
317
|
if (!this.documentPermissionService) throw new GraphQLError("DocumentPermissionService not available");
|
|
317
318
|
try {
|
|
318
319
|
return await canExecuteOperation(this.documentPermissionService, args, ctx.user?.address);
|
|
319
320
|
} catch (error) {
|
|
320
|
-
this.logger.error("Error in canExecuteOperation:", error);
|
|
321
|
+
this.logger.error("Error in canExecuteOperation: @error", error);
|
|
321
322
|
throw error;
|
|
322
323
|
}
|
|
323
324
|
},
|
|
324
325
|
documentProtection: async (_parent, args, ctx) => {
|
|
325
|
-
this.logger.debug("documentProtection", args);
|
|
326
|
+
this.logger.debug("documentProtection(@args)", args);
|
|
326
327
|
if (!this.documentPermissionService) throw new GraphQLError("DocumentPermissionService not available");
|
|
327
328
|
if (!ctx.user?.address) throw new GraphQLError("Authentication required to view document protection info");
|
|
328
329
|
try {
|
|
329
330
|
return await documentProtection(this.documentPermissionService, args);
|
|
330
331
|
} catch (error) {
|
|
331
|
-
this.logger.error("Error in documentProtection:", error);
|
|
332
|
+
this.logger.error("Error in documentProtection: @error", error);
|
|
332
333
|
throw error;
|
|
333
334
|
}
|
|
334
335
|
}
|
|
335
336
|
},
|
|
336
337
|
Mutation: {
|
|
337
338
|
setDocumentProtection: async (_parent, args, ctx) => {
|
|
338
|
-
this.logger.debug("setDocumentProtection", args);
|
|
339
|
+
this.logger.debug("setDocumentProtection(@args)", args);
|
|
339
340
|
if (!this.documentPermissionService) throw new GraphQLError("DocumentPermissionService not available");
|
|
340
341
|
try {
|
|
341
342
|
const isGlobalAdmin = ctx.isAdmin?.(ctx.user?.address ?? "") ?? false;
|
|
342
343
|
return await setDocumentProtection(this.documentPermissionService, this.authorizationService, args, ctx.user?.address, isGlobalAdmin);
|
|
343
344
|
} catch (error) {
|
|
344
|
-
this.logger.error("Error in setDocumentProtection:", error);
|
|
345
|
+
this.logger.error("Error in setDocumentProtection: @error", error);
|
|
345
346
|
throw error;
|
|
346
347
|
}
|
|
347
348
|
},
|
|
348
349
|
transferDocumentOwnership: async (_parent, args, ctx) => {
|
|
349
|
-
this.logger.debug("transferDocumentOwnership", args);
|
|
350
|
+
this.logger.debug("transferDocumentOwnership(@args)", args);
|
|
350
351
|
if (!this.documentPermissionService) throw new GraphQLError("DocumentPermissionService not available");
|
|
351
352
|
try {
|
|
352
353
|
const isGlobalAdmin = ctx.isAdmin?.(ctx.user?.address ?? "") ?? false;
|
|
353
354
|
return await transferDocumentOwnership(this.documentPermissionService, this.authorizationService, args, ctx.user?.address, isGlobalAdmin);
|
|
354
355
|
} catch (error) {
|
|
355
|
-
this.logger.error("Error in transferDocumentOwnership:", error);
|
|
356
|
+
this.logger.error("Error in transferDocumentOwnership: @error", error);
|
|
356
357
|
throw error;
|
|
357
358
|
}
|
|
358
359
|
},
|
|
359
360
|
grantDocumentPermission: async (_parent, args, ctx) => {
|
|
360
|
-
this.logger.debug("grantDocumentPermission", args);
|
|
361
|
+
this.logger.debug("grantDocumentPermission(@args)", args);
|
|
361
362
|
if (!this.documentPermissionService) throw new GraphQLError("DocumentPermissionService not available");
|
|
362
363
|
try {
|
|
363
364
|
const isGlobalAdmin = ctx.isAdmin?.(ctx.user?.address ?? "") ?? false;
|
|
364
365
|
return await grantDocumentPermission(this.documentPermissionService, args, ctx.user?.address, isGlobalAdmin);
|
|
365
366
|
} catch (error) {
|
|
366
|
-
this.logger.error("Error in grantDocumentPermission:", error);
|
|
367
|
+
this.logger.error("Error in grantDocumentPermission: @error", error);
|
|
367
368
|
throw error;
|
|
368
369
|
}
|
|
369
370
|
},
|
|
370
371
|
revokeDocumentPermission: async (_parent, args, ctx) => {
|
|
371
|
-
this.logger.debug("revokeDocumentPermission", args);
|
|
372
|
+
this.logger.debug("revokeDocumentPermission(@args)", args);
|
|
372
373
|
if (!this.documentPermissionService) throw new GraphQLError("DocumentPermissionService not available");
|
|
373
374
|
try {
|
|
374
375
|
const isGlobalAdmin = ctx.isAdmin?.(ctx.user?.address ?? "") ?? false;
|
|
375
376
|
return await revokeDocumentPermission(this.documentPermissionService, args, ctx.user?.address, isGlobalAdmin);
|
|
376
377
|
} catch (error) {
|
|
377
|
-
this.logger.error("Error in revokeDocumentPermission:", error);
|
|
378
|
+
this.logger.error("Error in revokeDocumentPermission: @error", error);
|
|
378
379
|
throw error;
|
|
379
380
|
}
|
|
380
381
|
},
|
|
381
382
|
createGroup: async (_parent, args) => {
|
|
382
|
-
this.logger.debug("createGroup", args);
|
|
383
|
+
this.logger.debug("createGroup(@args)", args);
|
|
383
384
|
if (!this.documentPermissionService) throw new GraphQLError("DocumentPermissionService not available");
|
|
384
385
|
try {
|
|
385
386
|
return await createGroup(this.documentPermissionService, args);
|
|
386
387
|
} catch (error) {
|
|
387
|
-
this.logger.error("Error in createGroup:", error);
|
|
388
|
+
this.logger.error("Error in createGroup: @error", error);
|
|
388
389
|
throw error;
|
|
389
390
|
}
|
|
390
391
|
},
|
|
391
392
|
deleteGroup: async (_parent, args) => {
|
|
392
|
-
this.logger.debug("deleteGroup", args);
|
|
393
|
+
this.logger.debug("deleteGroup(@args)", args);
|
|
393
394
|
if (!this.documentPermissionService) throw new GraphQLError("DocumentPermissionService not available");
|
|
394
395
|
try {
|
|
395
396
|
return await deleteGroup(this.documentPermissionService, args);
|
|
396
397
|
} catch (error) {
|
|
397
|
-
this.logger.error("Error in deleteGroup:", error);
|
|
398
|
+
this.logger.error("Error in deleteGroup: @error", error);
|
|
398
399
|
throw error;
|
|
399
400
|
}
|
|
400
401
|
},
|
|
401
402
|
addUserToGroup: async (_parent, args) => {
|
|
402
|
-
this.logger.debug("addUserToGroup", args);
|
|
403
|
+
this.logger.debug("addUserToGroup(@args)", args);
|
|
403
404
|
if (!this.documentPermissionService) throw new GraphQLError("DocumentPermissionService not available");
|
|
404
405
|
try {
|
|
405
406
|
return await addUserToGroup(this.documentPermissionService, args);
|
|
406
407
|
} catch (error) {
|
|
407
|
-
this.logger.error("Error in addUserToGroup:", error);
|
|
408
|
+
this.logger.error("Error in addUserToGroup: @error", error);
|
|
408
409
|
throw error;
|
|
409
410
|
}
|
|
410
411
|
},
|
|
411
412
|
removeUserFromGroup: async (_parent, args) => {
|
|
412
|
-
this.logger.debug("removeUserFromGroup", args);
|
|
413
|
+
this.logger.debug("removeUserFromGroup(@args)", args);
|
|
413
414
|
if (!this.documentPermissionService) throw new GraphQLError("DocumentPermissionService not available");
|
|
414
415
|
try {
|
|
415
416
|
return await removeUserFromGroup(this.documentPermissionService, args);
|
|
416
417
|
} catch (error) {
|
|
417
|
-
this.logger.error("Error in removeUserFromGroup:", error);
|
|
418
|
+
this.logger.error("Error in removeUserFromGroup: @error", error);
|
|
418
419
|
throw error;
|
|
419
420
|
}
|
|
420
421
|
},
|
|
421
422
|
grantGroupPermission: async (_parent, args, ctx) => {
|
|
422
|
-
this.logger.debug("grantGroupPermission", args);
|
|
423
|
+
this.logger.debug("grantGroupPermission(@args)", args);
|
|
423
424
|
if (!this.documentPermissionService) throw new GraphQLError("DocumentPermissionService not available");
|
|
424
425
|
try {
|
|
425
426
|
const isGlobalAdmin = ctx.isAdmin?.(ctx.user?.address ?? "") ?? false;
|
|
426
427
|
return await grantGroupPermission(this.documentPermissionService, args, ctx.user?.address, isGlobalAdmin);
|
|
427
428
|
} catch (error) {
|
|
428
|
-
this.logger.error("Error in grantGroupPermission:", error);
|
|
429
|
+
this.logger.error("Error in grantGroupPermission: @error", error);
|
|
429
430
|
throw error;
|
|
430
431
|
}
|
|
431
432
|
},
|
|
432
433
|
revokeGroupPermission: async (_parent, args, ctx) => {
|
|
433
|
-
this.logger.debug("revokeGroupPermission", args);
|
|
434
|
+
this.logger.debug("revokeGroupPermission(@args)", args);
|
|
434
435
|
if (!this.documentPermissionService) throw new GraphQLError("DocumentPermissionService not available");
|
|
435
436
|
try {
|
|
436
437
|
const isGlobalAdmin = ctx.isAdmin?.(ctx.user?.address ?? "") ?? false;
|
|
437
438
|
return await revokeGroupPermission(this.documentPermissionService, args, ctx.user?.address, isGlobalAdmin);
|
|
438
439
|
} catch (error) {
|
|
439
|
-
this.logger.error("Error in revokeGroupPermission:", error);
|
|
440
|
+
this.logger.error("Error in revokeGroupPermission: @error", error);
|
|
440
441
|
throw error;
|
|
441
442
|
}
|
|
442
443
|
},
|
|
443
444
|
grantOperationPermission: async (_parent, args, ctx) => {
|
|
444
|
-
this.logger.debug("grantOperationPermission", args);
|
|
445
|
+
this.logger.debug("grantOperationPermission(@args)", args);
|
|
445
446
|
if (!this.documentPermissionService) throw new GraphQLError("DocumentPermissionService not available");
|
|
446
447
|
try {
|
|
447
448
|
const isGlobalAdmin = ctx.isAdmin?.(ctx.user?.address ?? "") ?? false;
|
|
448
449
|
return await grantOperationPermission(this.documentPermissionService, args, ctx.user?.address, isGlobalAdmin);
|
|
449
450
|
} catch (error) {
|
|
450
|
-
this.logger.error("Error in grantOperationPermission:", error);
|
|
451
|
+
this.logger.error("Error in grantOperationPermission: @error", error);
|
|
451
452
|
throw error;
|
|
452
453
|
}
|
|
453
454
|
},
|
|
454
455
|
revokeOperationPermission: async (_parent, args, ctx) => {
|
|
455
|
-
this.logger.debug("revokeOperationPermission", args);
|
|
456
|
+
this.logger.debug("revokeOperationPermission(@args)", args);
|
|
456
457
|
if (!this.documentPermissionService) throw new GraphQLError("DocumentPermissionService not available");
|
|
457
458
|
try {
|
|
458
459
|
const isGlobalAdmin = ctx.isAdmin?.(ctx.user?.address ?? "") ?? false;
|
|
459
460
|
return await revokeOperationPermission(this.documentPermissionService, args, ctx.user?.address, isGlobalAdmin);
|
|
460
461
|
} catch (error) {
|
|
461
|
-
this.logger.error("Error in revokeOperationPermission:", error);
|
|
462
|
+
this.logger.error("Error in revokeOperationPermission: @error", error);
|
|
462
463
|
throw error;
|
|
463
464
|
}
|
|
464
465
|
},
|
|
465
466
|
grantGroupOperationPermission: async (_parent, args, ctx) => {
|
|
466
|
-
this.logger.debug("grantGroupOperationPermission", args);
|
|
467
|
+
this.logger.debug("grantGroupOperationPermission(@args)", args);
|
|
467
468
|
if (!this.documentPermissionService) throw new GraphQLError("DocumentPermissionService not available");
|
|
468
469
|
try {
|
|
469
470
|
const isGlobalAdmin = ctx.isAdmin?.(ctx.user?.address ?? "") ?? false;
|
|
470
471
|
return await grantGroupOperationPermission(this.documentPermissionService, args, ctx.user?.address, isGlobalAdmin);
|
|
471
472
|
} catch (error) {
|
|
472
|
-
this.logger.error("Error in grantGroupOperationPermission:", error);
|
|
473
|
+
this.logger.error("Error in grantGroupOperationPermission: @error", error);
|
|
473
474
|
throw error;
|
|
474
475
|
}
|
|
475
476
|
},
|
|
476
477
|
revokeGroupOperationPermission: async (_parent, args, ctx) => {
|
|
477
|
-
this.logger.debug("revokeGroupOperationPermission", args);
|
|
478
|
+
this.logger.debug("revokeGroupOperationPermission(@args)", args);
|
|
478
479
|
if (!this.documentPermissionService) throw new GraphQLError("DocumentPermissionService not available");
|
|
479
480
|
try {
|
|
480
481
|
const isGlobalAdmin = ctx.isAdmin?.(ctx.user?.address ?? "") ?? false;
|
|
481
482
|
return await revokeGroupOperationPermission(this.documentPermissionService, args, ctx.user?.address, isGlobalAdmin);
|
|
482
483
|
} catch (error) {
|
|
483
|
-
this.logger.error("Error in revokeGroupOperationPermission:", error);
|
|
484
|
+
this.logger.error("Error in revokeGroupOperationPermission: @error", error);
|
|
484
485
|
throw error;
|
|
485
486
|
}
|
|
486
487
|
}
|
|
@@ -2739,11 +2740,29 @@ function matchesJobFilter(payload, args) {
|
|
|
2739
2740
|
//#endregion
|
|
2740
2741
|
//#region src/graphql/reactor/constants.ts
|
|
2741
2742
|
/**
|
|
2742
|
-
*
|
|
2743
|
-
*
|
|
2744
|
-
*
|
|
2743
|
+
* Returns true when the given document type represents a drive container.
|
|
2744
|
+
* Delegates to the reactor's `DEFAULT_DRIVE_CONTAINER_TYPES`, so both the
|
|
2745
|
+
* legacy `powerhouse/document-drive` and the newer `powerhouse/reactor-drive`
|
|
2746
|
+
* count.
|
|
2745
2747
|
*/
|
|
2746
|
-
|
|
2748
|
+
function isDriveContainerType(documentType) {
|
|
2749
|
+
return DEFAULT_DRIVE_CONTAINER_TYPES.has(documentType);
|
|
2750
|
+
}
|
|
2751
|
+
//#endregion
|
|
2752
|
+
//#region src/graphql/reactor/resolvers.ts
|
|
2753
|
+
const REACTOR_DRIVE_DOCUMENT_TYPE = "powerhouse/reactor-drive";
|
|
2754
|
+
/**
|
|
2755
|
+
* Returns the drive client to use for the given drive-container parent type.
|
|
2756
|
+
* Throws when the parent is a reactor-drive container but no
|
|
2757
|
+
* `reactorDriveClient` was provided.
|
|
2758
|
+
*/
|
|
2759
|
+
function pickDriveClient(reactorClient, driveContainerType, reactorDriveClient) {
|
|
2760
|
+
if (driveContainerType === REACTOR_DRIVE_DOCUMENT_TYPE) {
|
|
2761
|
+
if (!reactorDriveClient) throw new GraphQLError("Reactor-drive parent encountered but no reactorDriveClient is configured on this switchboard");
|
|
2762
|
+
return reactorDriveClient;
|
|
2763
|
+
}
|
|
2764
|
+
return reactorClient.drives;
|
|
2765
|
+
}
|
|
2747
2766
|
async function documentModels(reactorClient, args) {
|
|
2748
2767
|
const namespace = fromInputMaybe(args.namespace);
|
|
2749
2768
|
let paging;
|
|
@@ -2932,16 +2951,18 @@ async function documentOperations(reactorClient, args) {
|
|
|
2932
2951
|
throw new GraphQLError(`Failed to convert operations to GraphQL: ${error instanceof Error ? error.message : "Unknown error"}`);
|
|
2933
2952
|
}
|
|
2934
2953
|
}
|
|
2935
|
-
async function createDocument(reactorClient, args) {
|
|
2954
|
+
async function createDocument(reactorClient, args, reactorDriveClient) {
|
|
2936
2955
|
if (!args.document || typeof args.document !== "object") throw new GraphQLError("Invalid document: must be an object");
|
|
2937
2956
|
const document = args.document;
|
|
2938
2957
|
if (!document.header || typeof document.header !== "object") throw new GraphQLError("Invalid document: missing or invalid header");
|
|
2939
2958
|
const parentIdentifier = fromInputMaybe(args.parentIdentifier);
|
|
2940
2959
|
let result;
|
|
2941
2960
|
try {
|
|
2942
|
-
if (parentIdentifier)
|
|
2943
|
-
|
|
2944
|
-
|
|
2961
|
+
if (parentIdentifier) {
|
|
2962
|
+
const parent = await reactorClient.get(parentIdentifier);
|
|
2963
|
+
if (isDriveContainerType(parent.header.documentType)) result = await pickDriveClient(reactorClient, parent.header.documentType, reactorDriveClient).addFile(parentIdentifier, document);
|
|
2964
|
+
else result = await reactorClient.create(document, parentIdentifier);
|
|
2965
|
+
} else result = await reactorClient.create(document);
|
|
2945
2966
|
} catch (error) {
|
|
2946
2967
|
throw new GraphQLError(`Failed to create document: ${error instanceof Error ? error.message : "Unknown error"}`);
|
|
2947
2968
|
}
|
|
@@ -2951,17 +2972,19 @@ async function createDocument(reactorClient, args) {
|
|
|
2951
2972
|
throw new GraphQLError(`Failed to convert created document to GraphQL: ${error instanceof Error ? error.message : "Unknown error"}`);
|
|
2952
2973
|
}
|
|
2953
2974
|
}
|
|
2954
|
-
async function createEmptyDocument(reactorClient, args) {
|
|
2975
|
+
async function createEmptyDocument(reactorClient, args, reactorDriveClient) {
|
|
2955
2976
|
const parentIdentifier = fromInputMaybe(args.parentIdentifier);
|
|
2956
2977
|
const name = fromInputMaybe(args.name);
|
|
2957
2978
|
let result;
|
|
2958
2979
|
try {
|
|
2959
|
-
if (parentIdentifier)
|
|
2960
|
-
const
|
|
2961
|
-
if (
|
|
2962
|
-
|
|
2963
|
-
|
|
2964
|
-
|
|
2980
|
+
if (parentIdentifier) {
|
|
2981
|
+
const parent = await reactorClient.get(parentIdentifier);
|
|
2982
|
+
if (isDriveContainerType(parent.header.documentType)) {
|
|
2983
|
+
const document = (await reactorClient.getDocumentModelModule(args.documentType)).utils.createDocument();
|
|
2984
|
+
if (name) document.header.name = name;
|
|
2985
|
+
result = await pickDriveClient(reactorClient, parent.header.documentType, reactorDriveClient).addFile(parentIdentifier, document);
|
|
2986
|
+
} else result = await reactorClient.createEmpty(args.documentType, { parentIdentifier });
|
|
2987
|
+
} else result = await reactorClient.createEmpty(args.documentType, {});
|
|
2965
2988
|
} catch (error) {
|
|
2966
2989
|
throw new GraphQLError(`Failed to create empty document: ${error instanceof Error ? error.message : "Unknown error"}`);
|
|
2967
2990
|
}
|
|
@@ -2971,7 +2994,7 @@ async function createEmptyDocument(reactorClient, args) {
|
|
|
2971
2994
|
throw new GraphQLError(`Failed to convert created document to GraphQL: ${error instanceof Error ? error.message : "Unknown error"}`);
|
|
2972
2995
|
}
|
|
2973
2996
|
}
|
|
2974
|
-
async function createDocumentWithInitialState(reactorClient, args) {
|
|
2997
|
+
async function createDocumentWithInitialState(reactorClient, args, reactorDriveClient) {
|
|
2975
2998
|
const parentIdentifier = fromInputMaybe(args.parentIdentifier);
|
|
2976
2999
|
const name = fromInputMaybe(args.name);
|
|
2977
3000
|
const slug = fromInputMaybe(args.slug);
|
|
@@ -3003,12 +3026,14 @@ async function createDocumentWithInitialState(reactorClient, args) {
|
|
|
3003
3026
|
} catch (error) {
|
|
3004
3027
|
throw new GraphQLError(`Parent document not found: ${error instanceof Error ? error.message : "Unknown error"}`);
|
|
3005
3028
|
}
|
|
3006
|
-
if (parent.header.documentType
|
|
3007
|
-
|
|
3008
|
-
|
|
3009
|
-
|
|
3010
|
-
|
|
3011
|
-
|
|
3029
|
+
if (isDriveContainerType(parent.header.documentType)) {
|
|
3030
|
+
const driveClient = pickDriveClient(reactorClient, parent.header.documentType, reactorDriveClient);
|
|
3031
|
+
try {
|
|
3032
|
+
result = await driveClient.addFile(parentIdentifier, document);
|
|
3033
|
+
} catch (error) {
|
|
3034
|
+
throw new GraphQLError(`Failed to create document in drive: ${error instanceof Error ? error.message : "Unknown error"}`);
|
|
3035
|
+
}
|
|
3036
|
+
} else try {
|
|
3012
3037
|
result = await reactorClient.create(document, parentIdentifier);
|
|
3013
3038
|
} catch (error) {
|
|
3014
3039
|
throw new GraphQLError(`Failed to create document with parent: ${error instanceof Error ? error.message : "Unknown error"}`);
|
|
@@ -3136,11 +3161,11 @@ async function moveRelationship(reactorClient, args) {
|
|
|
3136
3161
|
throw new GraphQLError(`Failed to convert documents to GraphQL: ${error instanceof Error ? error.message : "Unknown error"}`);
|
|
3137
3162
|
}
|
|
3138
3163
|
}
|
|
3139
|
-
async function deleteDocument(reactorClient, args) {
|
|
3164
|
+
async function deleteDocument(reactorClient, args, reactorDriveClient) {
|
|
3140
3165
|
const propagate = toReactorPropagationMode(args.propagate);
|
|
3141
3166
|
try {
|
|
3142
|
-
const driveParent = (await reactorClient.getIncomingRelationships(args.identifier, "child")).results.find((p) => p.header.documentType
|
|
3143
|
-
if (driveParent) await reactorClient.
|
|
3167
|
+
const driveParent = (await reactorClient.getIncomingRelationships(args.identifier, "child")).results.find((p) => isDriveContainerType(p.header.documentType));
|
|
3168
|
+
if (driveParent) await pickDriveClient(reactorClient, driveParent.header.documentType, reactorDriveClient).removeNode(driveParent.header.id, args.identifier);
|
|
3144
3169
|
else await reactorClient.deleteDocument(args.identifier, propagate);
|
|
3145
3170
|
return true;
|
|
3146
3171
|
} catch (error) {
|
|
@@ -3500,12 +3525,12 @@ var DocumentModelSubgraph = class extends BaseSubgraph {
|
|
|
3500
3525
|
slug,
|
|
3501
3526
|
preferredEditor,
|
|
3502
3527
|
initialState: initialState ?? {}
|
|
3503
|
-
});
|
|
3528
|
+
}, this.graphqlManager.reactorDriveClient);
|
|
3504
3529
|
else createdDoc = await createEmptyDocument(this.reactorClient, {
|
|
3505
3530
|
documentType,
|
|
3506
3531
|
parentIdentifier,
|
|
3507
3532
|
name
|
|
3508
|
-
});
|
|
3533
|
+
}, this.graphqlManager.reactorDriveClient);
|
|
3509
3534
|
if (this.authorizationService && ctx.user?.address && createdDoc?.id) await this.documentPermissionService?.initializeDocumentProtection(createdDoc.id, ctx.user.address, this.authorizationService.config.defaultProtection);
|
|
3510
3535
|
if (!initialState && !preferredEditor && name && createdDoc.name !== name) return toGqlPhDocument(await this.reactorClient.execute(createdDoc.id, "main", [setName(name)]));
|
|
3511
3536
|
return createdDoc;
|
|
@@ -3519,7 +3544,7 @@ var DocumentModelSubgraph = class extends BaseSubgraph {
|
|
|
3519
3544
|
const result = await createEmptyDocument(this.reactorClient, {
|
|
3520
3545
|
documentType,
|
|
3521
3546
|
parentIdentifier
|
|
3522
|
-
});
|
|
3547
|
+
}, this.graphqlManager.reactorDriveClient);
|
|
3523
3548
|
if (this.authorizationService && ctx.user?.address && result?.id) await this.documentPermissionService?.initializeDocumentProtection(result.id, ctx.user.address, this.authorizationService.config.defaultProtection);
|
|
3524
3549
|
return result;
|
|
3525
3550
|
},
|
|
@@ -3627,11 +3652,12 @@ function wrongShardResponse(driveId) {
|
|
|
3627
3652
|
/**
|
|
3628
3653
|
* In-memory record of which drives this switchboard instance owns.
|
|
3629
3654
|
*
|
|
3630
|
-
* Populated at startup by walking the reactor for documents
|
|
3631
|
-
*
|
|
3632
|
-
*
|
|
3633
|
-
* drive
|
|
3634
|
-
* requests with a structured
|
|
3655
|
+
* Populated at startup by walking the reactor for documents whose type is
|
|
3656
|
+
* listed in `DEFAULT_DRIVE_CONTAINER_TYPES` (both legacy `document-drive`
|
|
3657
|
+
* and `reactor-drive`). Mutated explicitly by resolver hooks after
|
|
3658
|
+
* successful drive create / delete operations. Read by the drive-validation
|
|
3659
|
+
* fetch middleware to short-circuit wrong-shard requests with a structured
|
|
3660
|
+
* 421 response.
|
|
3635
3661
|
*/
|
|
3636
3662
|
var DriveOwnershipCache = class {
|
|
3637
3663
|
drives = /* @__PURE__ */ new Set();
|
|
@@ -3640,11 +3666,13 @@ var DriveOwnershipCache = class {
|
|
|
3640
3666
|
}
|
|
3641
3667
|
async init() {
|
|
3642
3668
|
this.drives.clear();
|
|
3643
|
-
|
|
3644
|
-
|
|
3645
|
-
|
|
3646
|
-
|
|
3647
|
-
|
|
3669
|
+
for (const driveType of DEFAULT_DRIVE_CONTAINER_TYPES) {
|
|
3670
|
+
let page = await this.reactorClient.find({ type: driveType });
|
|
3671
|
+
while (true) {
|
|
3672
|
+
for (const drive of page.results) this.drives.add(drive.header.id);
|
|
3673
|
+
if (!page.next) break;
|
|
3674
|
+
page = await page.next();
|
|
3675
|
+
}
|
|
3648
3676
|
}
|
|
3649
3677
|
}
|
|
3650
3678
|
has(driveId) {
|
|
@@ -3729,7 +3757,13 @@ var GraphQLManager = class {
|
|
|
3729
3757
|
/** Cached document models for schema generation - updated on init and regenerate */
|
|
3730
3758
|
cachedDocumentModels = [];
|
|
3731
3759
|
subgraphHandlerCache = /* @__PURE__ */ new Map();
|
|
3732
|
-
|
|
3760
|
+
/**
|
|
3761
|
+
* Optional reactor-drive client. When the switchboard is configured with a
|
|
3762
|
+
* reactor-drive container, this is provided and the resolvers dispatch to
|
|
3763
|
+
* it for reactor-drive parents.
|
|
3764
|
+
*/
|
|
3765
|
+
reactorDriveClient;
|
|
3766
|
+
constructor(path, httpServer, wsServer, reactorClient, relationalDb, analyticsStore, syncManager, logger, httpAdapter, gatewayAdapter, authConfig, documentPermissionService, featureFlags = DefaultFeatureFlags, port = 4001, authorizationService, reactorDriveClient) {
|
|
3733
3767
|
this.path = path;
|
|
3734
3768
|
this.httpServer = httpServer;
|
|
3735
3769
|
this.wsServer = wsServer;
|
|
@@ -3745,6 +3779,7 @@ var GraphQLManager = class {
|
|
|
3745
3779
|
this.featureFlags = featureFlags;
|
|
3746
3780
|
this.port = port;
|
|
3747
3781
|
this.authorizationService = authorizationService;
|
|
3782
|
+
this.reactorDriveClient = reactorDriveClient;
|
|
3748
3783
|
if (this.authConfig) this.authService = new AuthService(this.authConfig);
|
|
3749
3784
|
this.driveOwnershipCache = new DriveOwnershipCache(this.reactorClient);
|
|
3750
3785
|
this.wsServer.setMaxListeners(0);
|
|
@@ -3802,7 +3837,7 @@ var GraphQLManager = class {
|
|
|
3802
3837
|
await this.updateRouter();
|
|
3803
3838
|
this.logger.info("Regenerated document model subgraphs with @count models", models.length);
|
|
3804
3839
|
} catch (error) {
|
|
3805
|
-
this.logger.error("Failed to regenerate document model subgraphs", error);
|
|
3840
|
+
this.logger.error("Failed to regenerate document model subgraphs: @error", error);
|
|
3806
3841
|
throw error;
|
|
3807
3842
|
}
|
|
3808
3843
|
}
|
|
@@ -3886,7 +3921,7 @@ var GraphQLManager = class {
|
|
|
3886
3921
|
await this.gatewayAdapter.updateSupergraph();
|
|
3887
3922
|
this.logger.debug("Updated Apollo Gateway supergraph");
|
|
3888
3923
|
} catch (error) {
|
|
3889
|
-
this.logger.error("Failed to update Apollo Gateway supergraph", error);
|
|
3924
|
+
this.logger.error("Failed to update Apollo Gateway supergraph: @error", error);
|
|
3890
3925
|
}
|
|
3891
3926
|
const superGraphPath = path.join(this.path, "graphql");
|
|
3892
3927
|
this.#setupSupergraphSSE(superGraphPath);
|
|
@@ -4124,16 +4159,16 @@ var PackagesSubgraph = class extends BaseSubgraph {
|
|
|
4124
4159
|
try {
|
|
4125
4160
|
return await installedPackages(this.packageManagementService);
|
|
4126
4161
|
} catch (error) {
|
|
4127
|
-
this.logger.error("Error in installedPackages:", error);
|
|
4162
|
+
this.logger.error("Error in installedPackages: @error", error);
|
|
4128
4163
|
throw error;
|
|
4129
4164
|
}
|
|
4130
4165
|
},
|
|
4131
4166
|
installedPackage: async (_parent, args) => {
|
|
4132
|
-
this.logger.debug("installedPackage", args);
|
|
4167
|
+
this.logger.debug("installedPackage(@args)", args);
|
|
4133
4168
|
try {
|
|
4134
4169
|
return await installedPackage(this.packageManagementService, args);
|
|
4135
4170
|
} catch (error) {
|
|
4136
|
-
this.logger.error("Error in installedPackage:", error);
|
|
4171
|
+
this.logger.error("Error in installedPackage: @error", error);
|
|
4137
4172
|
throw error;
|
|
4138
4173
|
}
|
|
4139
4174
|
}
|
|
@@ -4141,20 +4176,20 @@ var PackagesSubgraph = class extends BaseSubgraph {
|
|
|
4141
4176
|
Mutation: { Packages: () => ({}) },
|
|
4142
4177
|
PackagesMutations: {
|
|
4143
4178
|
installPackage: async (_parent, args, ctx) => {
|
|
4144
|
-
this.logger.debug("installPackage", args);
|
|
4179
|
+
this.logger.debug("installPackage(@args)", args);
|
|
4145
4180
|
try {
|
|
4146
4181
|
return await installPackage(this.packageManagementService, args, ctx);
|
|
4147
4182
|
} catch (error) {
|
|
4148
|
-
this.logger.error("Error in installPackage:", error);
|
|
4183
|
+
this.logger.error("Error in installPackage: @error", error);
|
|
4149
4184
|
throw error;
|
|
4150
4185
|
}
|
|
4151
4186
|
},
|
|
4152
4187
|
uninstallPackage: async (_parent, args, ctx) => {
|
|
4153
|
-
this.logger.debug("uninstallPackage", args);
|
|
4188
|
+
this.logger.debug("uninstallPackage(@args)", args);
|
|
4154
4189
|
try {
|
|
4155
4190
|
return await uninstallPackage(this.packageManagementService, args, ctx);
|
|
4156
4191
|
} catch (error) {
|
|
4157
|
-
this.logger.error("Error in uninstallPackage:", error);
|
|
4192
|
+
this.logger.error("Error in uninstallPackage: @error", error);
|
|
4158
4193
|
throw error;
|
|
4159
4194
|
}
|
|
4160
4195
|
}
|
|
@@ -4593,7 +4628,7 @@ var ReactorSubgraph = class extends BaseSubgraph {
|
|
|
4593
4628
|
async #resolveDriveId(identifier) {
|
|
4594
4629
|
try {
|
|
4595
4630
|
const doc = await this.reactorClient.get(identifier);
|
|
4596
|
-
if (doc.header.documentType
|
|
4631
|
+
if (isDriveContainerType(doc.header.documentType)) return doc.header.id;
|
|
4597
4632
|
return;
|
|
4598
4633
|
} catch {
|
|
4599
4634
|
return;
|
|
@@ -4723,7 +4758,7 @@ var ReactorSubgraph = class extends BaseSubgraph {
|
|
|
4723
4758
|
hasMore
|
|
4724
4759
|
};
|
|
4725
4760
|
} catch (error) {
|
|
4726
|
-
this.logger.error("Error in pollSyncEnvelopes(@args): @Error", error);
|
|
4761
|
+
this.logger.error("Error in pollSyncEnvelopes(@args): @Error", args, error);
|
|
4727
4762
|
throw error;
|
|
4728
4763
|
}
|
|
4729
4764
|
}
|
|
@@ -4738,12 +4773,12 @@ var ReactorSubgraph = class extends BaseSubgraph {
|
|
|
4738
4773
|
} else if (this.authorizationService) {
|
|
4739
4774
|
if (!ctx.user?.address) throw new GraphQLError("Forbidden: authentication required to create documents");
|
|
4740
4775
|
} else if (!this.hasGlobalAdminAccess(ctx)) throw new GraphQLError("Forbidden: insufficient permissions to create documents");
|
|
4741
|
-
const result = await createDocument(this.reactorClient, args);
|
|
4742
|
-
if (result?.id && result.documentType
|
|
4776
|
+
const result = await createDocument(this.reactorClient, args, this.graphqlManager.reactorDriveClient);
|
|
4777
|
+
if (result?.id && isDriveContainerType(result.documentType)) this.graphqlManager.driveOwnershipCache.add(result.id);
|
|
4743
4778
|
if (this.authorizationService && ctx.user?.address && result?.id) await this.documentPermissionService?.initializeDocumentProtection(result.id, ctx.user.address, this.authorizationService.config.defaultProtection);
|
|
4744
4779
|
return result;
|
|
4745
4780
|
} catch (error) {
|
|
4746
|
-
this.logger.error("Error in createDocument(@args): @Error", error);
|
|
4781
|
+
this.logger.error("Error in createDocument(@args): @Error", args, error);
|
|
4747
4782
|
throw error;
|
|
4748
4783
|
}
|
|
4749
4784
|
},
|
|
@@ -4756,12 +4791,12 @@ var ReactorSubgraph = class extends BaseSubgraph {
|
|
|
4756
4791
|
} else if (this.authorizationService) {
|
|
4757
4792
|
if (!ctx.user?.address) throw new GraphQLError("Forbidden: authentication required to create documents");
|
|
4758
4793
|
} else if (!this.hasGlobalAdminAccess(ctx)) throw new GraphQLError("Forbidden: insufficient permissions to create documents");
|
|
4759
|
-
const result = await createEmptyDocument(this.reactorClient, args);
|
|
4760
|
-
if (result?.id && result.documentType
|
|
4794
|
+
const result = await createEmptyDocument(this.reactorClient, args, this.graphqlManager.reactorDriveClient);
|
|
4795
|
+
if (result?.id && isDriveContainerType(result.documentType)) this.graphqlManager.driveOwnershipCache.add(result.id);
|
|
4761
4796
|
if (this.authorizationService && ctx.user?.address && result?.id) await this.documentPermissionService?.initializeDocumentProtection(result.id, ctx.user.address, this.authorizationService.config.defaultProtection);
|
|
4762
4797
|
return result;
|
|
4763
4798
|
} catch (error) {
|
|
4764
|
-
this.logger.error("Error in createEmptyDocument(@args): @Error", error);
|
|
4799
|
+
this.logger.error("Error in createEmptyDocument(@args): @Error", args, error);
|
|
4765
4800
|
throw error;
|
|
4766
4801
|
}
|
|
4767
4802
|
},
|
|
@@ -4772,7 +4807,7 @@ var ReactorSubgraph = class extends BaseSubgraph {
|
|
|
4772
4807
|
await this.assertCanExecuteOperations(args.documentIdentifier, args.actions, ctx);
|
|
4773
4808
|
return await mutateDocument(this.reactorClient, args);
|
|
4774
4809
|
} catch (error) {
|
|
4775
|
-
this.logger.error("Error in mutateDocument(@args): @Error", error);
|
|
4810
|
+
this.logger.error("Error in mutateDocument(@args): @Error", args, error);
|
|
4776
4811
|
throw error;
|
|
4777
4812
|
}
|
|
4778
4813
|
},
|
|
@@ -4783,7 +4818,7 @@ var ReactorSubgraph = class extends BaseSubgraph {
|
|
|
4783
4818
|
await this.assertCanExecuteOperations(args.documentIdentifier, args.actions, ctx);
|
|
4784
4819
|
return await mutateDocumentAsync(this.reactorClient, args);
|
|
4785
4820
|
} catch (error) {
|
|
4786
|
-
this.logger.error("Error in mutateDocumentAsync(@args): @Error", error);
|
|
4821
|
+
this.logger.error("Error in mutateDocumentAsync(@args): @Error", args, error);
|
|
4787
4822
|
throw error;
|
|
4788
4823
|
}
|
|
4789
4824
|
},
|
|
@@ -4793,7 +4828,7 @@ var ReactorSubgraph = class extends BaseSubgraph {
|
|
|
4793
4828
|
await this.assertCanWrite(args.documentIdentifier, ctx);
|
|
4794
4829
|
return await renameDocument(this.reactorClient, args);
|
|
4795
4830
|
} catch (error) {
|
|
4796
|
-
this.logger.error("Error in renameDocument(@args): @Error", error);
|
|
4831
|
+
this.logger.error("Error in renameDocument(@args): @Error", args, error);
|
|
4797
4832
|
throw error;
|
|
4798
4833
|
}
|
|
4799
4834
|
},
|
|
@@ -4803,7 +4838,7 @@ var ReactorSubgraph = class extends BaseSubgraph {
|
|
|
4803
4838
|
await this.assertCanWrite(args.documentIdentifier, ctx);
|
|
4804
4839
|
return await setPreferredEditor(this.reactorClient, args);
|
|
4805
4840
|
} catch (error) {
|
|
4806
|
-
this.logger.error("Error in setPreferredEditor(@args): @Error", error);
|
|
4841
|
+
this.logger.error("Error in setPreferredEditor(@args): @Error", args, error);
|
|
4807
4842
|
throw error;
|
|
4808
4843
|
}
|
|
4809
4844
|
},
|
|
@@ -4813,7 +4848,7 @@ var ReactorSubgraph = class extends BaseSubgraph {
|
|
|
4813
4848
|
await this.assertCanWrite(args.sourceIdentifier, ctx);
|
|
4814
4849
|
return await addRelationship(this.reactorClient, args);
|
|
4815
4850
|
} catch (error) {
|
|
4816
|
-
this.logger.error("Error in addRelationship(@args): @Error", error);
|
|
4851
|
+
this.logger.error("Error in addRelationship(@args): @Error", args, error);
|
|
4817
4852
|
throw error;
|
|
4818
4853
|
}
|
|
4819
4854
|
},
|
|
@@ -4823,7 +4858,7 @@ var ReactorSubgraph = class extends BaseSubgraph {
|
|
|
4823
4858
|
await this.assertCanWrite(args.sourceIdentifier, ctx);
|
|
4824
4859
|
return await removeRelationship(this.reactorClient, args);
|
|
4825
4860
|
} catch (error) {
|
|
4826
|
-
this.logger.error("Error in removeRelationship(@args): @Error", error);
|
|
4861
|
+
this.logger.error("Error in removeRelationship(@args): @Error", args, error);
|
|
4827
4862
|
throw error;
|
|
4828
4863
|
}
|
|
4829
4864
|
},
|
|
@@ -4843,11 +4878,11 @@ var ReactorSubgraph = class extends BaseSubgraph {
|
|
|
4843
4878
|
try {
|
|
4844
4879
|
await this.assertCanWrite(args.identifier, ctx);
|
|
4845
4880
|
const driveIdToInvalidate = await this.#resolveDriveId(args.identifier);
|
|
4846
|
-
const result = await deleteDocument(this.reactorClient, args);
|
|
4881
|
+
const result = await deleteDocument(this.reactorClient, args, this.graphqlManager.reactorDriveClient);
|
|
4847
4882
|
if (result && driveIdToInvalidate) this.graphqlManager.driveOwnershipCache.remove(driveIdToInvalidate);
|
|
4848
4883
|
return result;
|
|
4849
4884
|
} catch (error) {
|
|
4850
|
-
this.logger.error("Error in deleteDocument(@args): @Error", error);
|
|
4885
|
+
this.logger.error("Error in deleteDocument(@args): @Error", args, error);
|
|
4851
4886
|
throw error;
|
|
4852
4887
|
}
|
|
4853
4888
|
},
|
|
@@ -4857,7 +4892,7 @@ var ReactorSubgraph = class extends BaseSubgraph {
|
|
|
4857
4892
|
for (const identifier of args.identifiers) await this.assertCanWrite(identifier, ctx);
|
|
4858
4893
|
return await deleteDocuments(this.reactorClient, args);
|
|
4859
4894
|
} catch (error) {
|
|
4860
|
-
this.logger.error("Error in deleteDocuments(@args): @Error", error);
|
|
4895
|
+
this.logger.error("Error in deleteDocuments(@args): @Error", args, error);
|
|
4861
4896
|
throw error;
|
|
4862
4897
|
}
|
|
4863
4898
|
},
|
|
@@ -4866,7 +4901,7 @@ var ReactorSubgraph = class extends BaseSubgraph {
|
|
|
4866
4901
|
try {
|
|
4867
4902
|
return await touchChannel(this.syncManager, args);
|
|
4868
4903
|
} catch (error) {
|
|
4869
|
-
this.logger.error("Error in touchChannel(@args): @Error", error);
|
|
4904
|
+
this.logger.error("Error in touchChannel(@args): @Error", args, error);
|
|
4870
4905
|
throw error;
|
|
4871
4906
|
}
|
|
4872
4907
|
},
|
|
@@ -4896,7 +4931,7 @@ var ReactorSubgraph = class extends BaseSubgraph {
|
|
|
4896
4931
|
})) };
|
|
4897
4932
|
return await pushSyncEnvelopes(this.syncManager, mutableArgs);
|
|
4898
4933
|
} catch (error) {
|
|
4899
|
-
this.logger.error("Error in pushSyncEnvelopes(@args): @Error", error);
|
|
4934
|
+
this.logger.error("Error in pushSyncEnvelopes(@args): @Error", args, error);
|
|
4900
4935
|
throw error;
|
|
4901
4936
|
}
|
|
4902
4937
|
}
|
|
@@ -4904,7 +4939,7 @@ var ReactorSubgraph = class extends BaseSubgraph {
|
|
|
4904
4939
|
Subscription: {
|
|
4905
4940
|
documentChanges: {
|
|
4906
4941
|
subscribe: withFilter((() => {
|
|
4907
|
-
this.logger.debug("documentChanges
|
|
4942
|
+
this.logger.debug("documentChanges subscription started");
|
|
4908
4943
|
ensureGlobalDocumentSubscription(this.reactorClient);
|
|
4909
4944
|
return getPubSub().asyncIterableIterator(SUBSCRIPTION_TRIGGERS.DOCUMENT_CHANGES);
|
|
4910
4945
|
}), ((payload, args) => {
|
|
@@ -4951,10 +4986,10 @@ const ADMIN_USERS = getAdminUsers();
|
|
|
4951
4986
|
//#endregion
|
|
4952
4987
|
//#region src/graphql/system/version.ts
|
|
4953
4988
|
function getVersion() {
|
|
4954
|
-
return "6.0.0-dev.
|
|
4989
|
+
return "6.0.0-dev.255";
|
|
4955
4990
|
}
|
|
4956
4991
|
function getGitHash() {
|
|
4957
|
-
return "
|
|
4992
|
+
return "9fec21bf56b8b4aeed4a623a750982706e5b2b82";
|
|
4958
4993
|
}
|
|
4959
4994
|
function getGitUrl() {
|
|
4960
4995
|
return buildTreeUrl(getGitHash());
|
|
@@ -5231,7 +5266,7 @@ var PackageManager = class {
|
|
|
5231
5266
|
try {
|
|
5232
5267
|
this.subscribePackages(packages);
|
|
5233
5268
|
} catch (error) {
|
|
5234
|
-
this.logger.error("Failed to subscribe to packages", error);
|
|
5269
|
+
this.logger.error("Failed to subscribe to packages: @error", error);
|
|
5235
5270
|
}
|
|
5236
5271
|
return {
|
|
5237
5272
|
documentModels: getUniqueDocumentModels(...Array.from(documentModelsMap.values())),
|
|
@@ -5244,6 +5279,7 @@ var PackageManager = class {
|
|
|
5244
5279
|
const documentModelModuleMap = /* @__PURE__ */ new Map();
|
|
5245
5280
|
documentModelModuleMap.set("document-drive", [driveDocumentModelModule]);
|
|
5246
5281
|
documentModelModuleMap.set("document-model", [documentModelDocumentModelModule]);
|
|
5282
|
+
documentModelModuleMap.set("reactor-drive", [reactorDriveDocumentModelModule]);
|
|
5247
5283
|
for (const pkg of packages) {
|
|
5248
5284
|
const allDocumentModels = [];
|
|
5249
5285
|
for (const loader of this.loaders) try {
|
|
@@ -6124,7 +6160,30 @@ function isPG(connectionString) {
|
|
|
6124
6160
|
if (connectionString.startsWith("postgresql://") || connectionString.startsWith("postgres://")) return true;
|
|
6125
6161
|
return false;
|
|
6126
6162
|
}
|
|
6163
|
+
/**
|
|
6164
|
+
* Cache of DB clients keyed by connection string. Reactor-api's read-model
|
|
6165
|
+
* layer wires analytics, attachments, and document-permissions as separate
|
|
6166
|
+
* consumers but they all target the same logical database (one postgres
|
|
6167
|
+
* instance, many schemas). Without caching:
|
|
6168
|
+
* - PGlite: two `new PGlite(samePath)` calls mean two embedded postgres
|
|
6169
|
+
* processes contending for the same data dir, racing shutdown syncs
|
|
6170
|
+
* and silently losing writes — a correctness bug.
|
|
6171
|
+
* - Postgres: each consumer opens an independent pool against the same
|
|
6172
|
+
* backend — wasteful but correct.
|
|
6173
|
+
* Caching by connection string returns the same knex/PGlite pair to every
|
|
6174
|
+
* consumer so writes coexist in one MemoryFS and one atomic snapshot, and
|
|
6175
|
+
* postgres callers get connection-pool dedup for free.
|
|
6176
|
+
*
|
|
6177
|
+
* Entries are evicted from inside the wrapped `knex.destroy()` below, so a
|
|
6178
|
+
* teardown + re-init in the same process (tests, hot-reloads) constructs
|
|
6179
|
+
* a fresh client instead of returning a closed pool.
|
|
6180
|
+
*/
|
|
6181
|
+
const IN_MEMORY_CACHE_KEY = Symbol("getDbClient:in-memory");
|
|
6182
|
+
const dbClientCache = /* @__PURE__ */ new Map();
|
|
6127
6183
|
function getDbClient(connectionString = void 0, pgliteFactory) {
|
|
6184
|
+
const cacheKey = connectionString ?? IN_MEMORY_CACHE_KEY;
|
|
6185
|
+
const cached = dbClientCache.get(cacheKey);
|
|
6186
|
+
if (cached) return cached;
|
|
6128
6187
|
const isPg = connectionString && isPG(connectionString);
|
|
6129
6188
|
const client = isPg ? "pg" : ClientPgLite;
|
|
6130
6189
|
const pgliteInstance = isPg ? void 0 : pgliteFactory ? pgliteFactory(connectionString) : connectionString ? new PGlite({ fs: new AtomicNodeFs(connectionString) }) : new PGlite();
|
|
@@ -6137,7 +6196,7 @@ function getDbClient(connectionString = void 0, pgliteFactory) {
|
|
|
6137
6196
|
client,
|
|
6138
6197
|
connection
|
|
6139
6198
|
});
|
|
6140
|
-
|
|
6199
|
+
const dbClient = {
|
|
6141
6200
|
db: new Kysely({ dialect: new KyselyKnexDialect({
|
|
6142
6201
|
knex: knexInstance,
|
|
6143
6202
|
kyselySubDialect: new PGColdDialect()
|
|
@@ -6145,6 +6204,17 @@ function getDbClient(connectionString = void 0, pgliteFactory) {
|
|
|
6145
6204
|
knex: knexInstance,
|
|
6146
6205
|
pglite: pgliteInstance
|
|
6147
6206
|
};
|
|
6207
|
+
const originalDestroy = knexInstance.destroy.bind(knexInstance);
|
|
6208
|
+
Object.defineProperty(knexInstance, "destroy", {
|
|
6209
|
+
configurable: true,
|
|
6210
|
+
writable: true,
|
|
6211
|
+
value: async (...args) => {
|
|
6212
|
+
if (dbClientCache.get(cacheKey) === dbClient) dbClientCache.delete(cacheKey);
|
|
6213
|
+
return originalDestroy(...args);
|
|
6214
|
+
}
|
|
6215
|
+
});
|
|
6216
|
+
dbClientCache.set(cacheKey, dbClient);
|
|
6217
|
+
return dbClient;
|
|
6148
6218
|
}
|
|
6149
6219
|
const initAnalyticsStoreSql = [
|
|
6150
6220
|
`create table if not exists "AnalyticsSeries"
|
|
@@ -6248,11 +6318,11 @@ function makeDbClosers(knexInstance, pglite) {
|
|
|
6248
6318
|
/**
|
|
6249
6319
|
* Sets up the subgraph manager and registers subgraphs
|
|
6250
6320
|
*/
|
|
6251
|
-
async function setupGraphQLManager(httpAdapter, authFetchMiddleware, httpServer, wsServer, client, relationalDb, analyticsStore, syncManager, subgraphs, logger, auth, documentPermissionService, enableDocumentModelSubgraphs, port, authorizationService) {
|
|
6321
|
+
async function setupGraphQLManager(httpAdapter, authFetchMiddleware, httpServer, wsServer, client, relationalDb, analyticsStore, syncManager, subgraphs, logger, auth, documentPermissionService, enableDocumentModelSubgraphs, port, authorizationService, reactorDriveClient) {
|
|
6252
6322
|
const graphqlManager = new GraphQLManager(config.basePath, httpServer, wsServer, client, relationalDb, analyticsStore, syncManager, logger, httpAdapter, createGatewayAdapter("apollo", logger), {
|
|
6253
6323
|
enabled: auth?.enabled ?? false,
|
|
6254
6324
|
admins: auth?.admins ?? []
|
|
6255
|
-
}, documentPermissionService, { enableDocumentModelSubgraphs }, port, authorizationService);
|
|
6325
|
+
}, documentPermissionService, { enableDocumentModelSubgraphs }, port, authorizationService, reactorDriveClient);
|
|
6256
6326
|
await graphqlManager.init(subgraphs.core, authFetchMiddleware);
|
|
6257
6327
|
for (const [, collection] of subgraphs.extended.entries()) for (const subgraph of collection) await graphqlManager.registerSubgraph(subgraph, "graphql");
|
|
6258
6328
|
await graphqlManager.updateRouter();
|
|
@@ -6413,7 +6483,7 @@ async function _setupCommonInfrastructure(options) {
|
|
|
6413
6483
|
/**
|
|
6414
6484
|
* Private helper function containing common setup logic for API initialization
|
|
6415
6485
|
*/
|
|
6416
|
-
async function _setupAPI(reactorClient, syncManager, reactorProcessorManager, httpAdapter, authFetchMiddleware, authService, port, packages, relationalDb, analyticsStore, documentPermissionService, processors, subgraphs, options, auth, processorApp, readModels, attachments, authorizationService, documentModelRegistry, dbClosers = []) {
|
|
6486
|
+
async function _setupAPI(reactorClient, syncManager, reactorProcessorManager, httpAdapter, authFetchMiddleware, authService, port, packages, relationalDb, analyticsStore, documentPermissionService, processors, subgraphs, options, auth, processorApp, readModels, attachments, authorizationService, documentModelRegistry, dbClosers = [], reactorDriveClient) {
|
|
6417
6487
|
const hostModule = {
|
|
6418
6488
|
relationalDb,
|
|
6419
6489
|
analyticsStore,
|
|
@@ -6465,7 +6535,7 @@ async function _setupAPI(reactorClient, syncManager, reactorProcessorManager, ht
|
|
|
6465
6535
|
const graphqlManager = await setupGraphQLManager(httpAdapter, authFetchMiddleware, httpServer, wsServer, reactorClient, relationalDb, analyticsStore, syncManager, {
|
|
6466
6536
|
extended: subgraphs,
|
|
6467
6537
|
core: coreSubgraphs
|
|
6468
|
-
}, logger.child(["graphql-manager"]), auth, documentPermissionService, options.enableDocumentModelSubgraphs, port, authorizationService);
|
|
6538
|
+
}, logger.child(["graphql-manager"]), auth, documentPermissionService, options.enableDocumentModelSubgraphs, port, authorizationService, reactorDriveClient);
|
|
6469
6539
|
setupEventListeners(packages, graphqlManager, reactorProcessorManager, hostModule, documentModelRegistry);
|
|
6470
6540
|
if (mcpServerEnabled) {
|
|
6471
6541
|
await setupMcpServer({
|
|
@@ -6505,41 +6575,31 @@ function buildApiDispose(args) {
|
|
|
6505
6575
|
try {
|
|
6506
6576
|
await graphqlManager.shutdown();
|
|
6507
6577
|
} catch (error) {
|
|
6508
|
-
logger.error("API dispose: graphqlManager.shutdown failed:", error);
|
|
6578
|
+
logger.error("API dispose: graphqlManager.shutdown failed: @error", error);
|
|
6509
6579
|
}
|
|
6510
6580
|
try {
|
|
6511
6581
|
for (const client of wsServer.clients) client.terminate();
|
|
6512
6582
|
await new Promise((resolve) => wsServer.close(() => resolve()));
|
|
6513
6583
|
} catch (error) {
|
|
6514
|
-
logger.error("API dispose: wsServer.close failed:", error);
|
|
6584
|
+
logger.error("API dispose: wsServer.close failed: @error", error);
|
|
6515
6585
|
}
|
|
6516
6586
|
if (httpServer.listening) try {
|
|
6517
6587
|
httpServer.closeAllConnections();
|
|
6518
6588
|
await new Promise((resolve, reject) => httpServer.close((err) => err ? reject(err) : resolve()));
|
|
6519
6589
|
} catch (error) {
|
|
6520
|
-
logger.error("API dispose: httpServer.close failed:", error);
|
|
6590
|
+
logger.error("API dispose: httpServer.close failed: @error", error);
|
|
6521
6591
|
}
|
|
6522
6592
|
for (const close of dbClosers) try {
|
|
6523
6593
|
await close();
|
|
6524
6594
|
} catch (error) {
|
|
6525
|
-
logger.error("API dispose: db closer failed:", error);
|
|
6595
|
+
logger.error("API dispose: db closer failed: @error", error);
|
|
6526
6596
|
}
|
|
6527
6597
|
};
|
|
6528
6598
|
}
|
|
6529
|
-
/**
|
|
6530
|
-
* Initializes and starts the API server using an initializer function.
|
|
6531
|
-
* This function first loads packages to get document models, then calls the initializer function
|
|
6532
|
-
* to create the reactor client module with the appropriate dependencies.
|
|
6533
|
-
*
|
|
6534
|
-
* @param clientInitializer - Initializer function that creates the reactor client module with document models.
|
|
6535
|
-
* @param options - Additional options for server configuration.
|
|
6536
|
-
*
|
|
6537
|
-
* @returns The API server components along with the created client instances.
|
|
6538
|
-
*/
|
|
6539
6599
|
async function initializeAndStartAPI(clientInitializer, options, processorApp) {
|
|
6540
6600
|
const { port, httpAdapter, authFetchMiddleware, authService, auth, relationalDb, analyticsStore, documentPermissionService, authorizationService, attachments, packages, dbClosers } = await _setupCommonInfrastructure(options);
|
|
6541
6601
|
const { documentModels, processors, subgraphs } = await packages.init();
|
|
6542
|
-
const reactorClientModule = await clientInitializer(documentModels);
|
|
6602
|
+
const { module: reactorClientModule, reactorDriveClient } = await clientInitializer(documentModels);
|
|
6543
6603
|
const reactorClient = reactorClientModule.client;
|
|
6544
6604
|
const syncManager = reactorClientModule.reactorModule?.syncModule?.syncManager;
|
|
6545
6605
|
if (!syncManager) throw new Error("SyncManager not available from ReactorClientModule");
|
|
@@ -6548,7 +6608,7 @@ async function initializeAndStartAPI(clientInitializer, options, processorApp) {
|
|
|
6548
6608
|
const documentModelRegistry = reactorClientModule.reactorModule?.documentModelRegistry;
|
|
6549
6609
|
if (!documentModelRegistry) throw new Error("DocumentModelRegistry not available from ReactorClientModule");
|
|
6550
6610
|
return {
|
|
6551
|
-
...await _setupAPI(reactorClient, syncManager, reactorProcessorManager, httpAdapter, authFetchMiddleware, authService, port, packages, relationalDb, analyticsStore, documentPermissionService, processors, subgraphs, options, auth, processorApp, (reactorClientModule.reactorModule?.readModelCoordinator)?.readModels ?? [], attachments, authorizationService, documentModelRegistry, dbClosers),
|
|
6611
|
+
...await _setupAPI(reactorClient, syncManager, reactorProcessorManager, httpAdapter, authFetchMiddleware, authService, port, packages, relationalDb, analyticsStore, documentPermissionService, processors, subgraphs, options, auth, processorApp, (reactorClientModule.reactorModule?.readModelCoordinator)?.readModels ?? [], attachments, authorizationService, documentModelRegistry, dbClosers, reactorDriveClient),
|
|
6552
6612
|
client: reactorClient,
|
|
6553
6613
|
syncManager,
|
|
6554
6614
|
documentModelRegistry
|
|
@@ -6657,4 +6717,4 @@ var PackageManagementService = class {
|
|
|
6657
6717
|
export { ADMIN_USERS, ActionContextInputSchema, ActionInputSchema, AddRelationshipDocument, AnalyticsSubgraph, AttachmentInputSchema, AuthService, AuthSubgraph, BaseSubgraph, ChannelMetaInputSchema, CreateDocumentDocument, CreateEmptyDocumentDocument, DeleteDocumentDocument, DeleteDocumentsDocument, DocumentChangeType, DocumentChangeTypeSchema, DocumentChangesDocument, DocumentOperationsFilterInputSchema, DocumentPermissionService, FindDocumentsDocument, GetDocumentDocument, GetDocumentIncomingRelationshipsDocument, GetDocumentModelsDocument, GetDocumentOperationsDocument, GetDocumentOutgoingRelationshipsDocument, GetDocumentWithOperationsDocument, GetJobStatusDocument, GraphQLManager, HttpDocumentModelLoader, HttpPackageLoader, ImportPackageLoader, InMemoryPackageStorage, JobChangesDocument, MoveRelationshipDocument, MutateDocumentAsyncDocument, MutateDocumentDocument, OperationContextInputSchema, OperationInputSchema, OperationWithContextInputSchema, OperationsFilterInputSchema, PackageManagementService, PackageManager, PackagesSubgraph, PagingInputSchema, PhDocumentFieldsFragmentDoc, PollSyncEnvelopesDocument, PropagationMode, PropagationModeSchema, PushSyncEnvelopesDocument, ReactorSignerAppInputSchema, ReactorSignerInputSchema, ReactorSignerUserInputSchema, ReactorSubgraph, RemoteCursorInputSchema, RemoteFilterInputSchema, RemoveRelationshipDocument, RenameDocumentDocument, SearchFilterInputSchema, SetPreferredEditorDocument, SyncEnvelopeInputSchema, SyncEnvelopeType, SyncEnvelopeTypeSchema, SystemSubgraph, TouchChannelDocument, TouchChannelInputSchema, ViewFilterInputSchema, buildGraphQlDocument, buildGraphQlDriveDocument, buildGraphqlOperation, buildGraphqlOperations, buildSubgraphSchemaModule, createAuthFetchMiddleware, createGatewayAdapter, createHttpAdapter, createMergedSchema, createReactorGraphQLClient, createSchema, definedNonNullAnySchema, driveIdFromUrl, generateDocumentModelSchema, getAuthContext, getDbClient, getDocumentModelSchemaName, getDocumentModelTypeDefs, getGitHash, getGitUrl, getSdk, getUniqueDocumentModels, getVersion, initAnalyticsStoreSql, initializeAndStartAPI, isDefinedNonNullAny, isSubgraphClass, parseDriveUrl, renderGraphqlPlayground };
|
|
6658
6718
|
|
|
6659
6719
|
//# sourceMappingURL=index.mjs.map
|
|
6660
|
-
//# debugId=
|
|
6720
|
+
//# debugId=7376325d-a64e-53ca-8757-5f06b3be132b
|