@memberjunction/server 5.40.2 → 5.42.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (129) hide show
  1. package/dist/agentSessions/HostInstance.d.ts +19 -0
  2. package/dist/agentSessions/HostInstance.d.ts.map +1 -0
  3. package/dist/agentSessions/HostInstance.js +48 -0
  4. package/dist/agentSessions/HostInstance.js.map +1 -0
  5. package/dist/agentSessions/SessionJanitor.d.ts +97 -0
  6. package/dist/agentSessions/SessionJanitor.d.ts.map +1 -0
  7. package/dist/agentSessions/SessionJanitor.js +222 -0
  8. package/dist/agentSessions/SessionJanitor.js.map +1 -0
  9. package/dist/agentSessions/SessionManager.d.ts +142 -0
  10. package/dist/agentSessions/SessionManager.d.ts.map +1 -0
  11. package/dist/agentSessions/SessionManager.js +308 -0
  12. package/dist/agentSessions/SessionManager.js.map +1 -0
  13. package/dist/agentSessions/index.d.ts +5 -0
  14. package/dist/agentSessions/index.d.ts.map +1 -0
  15. package/dist/agentSessions/index.js +31 -0
  16. package/dist/agentSessions/index.js.map +1 -0
  17. package/dist/agentSessions/remoteBrowserGoalEngine.d.ts +102 -0
  18. package/dist/agentSessions/remoteBrowserGoalEngine.d.ts.map +1 -0
  19. package/dist/agentSessions/remoteBrowserGoalEngine.js +164 -0
  20. package/dist/agentSessions/remoteBrowserGoalEngine.js.map +1 -0
  21. package/dist/agentSessions/remoteBrowserGoalRegistry.d.ts +66 -0
  22. package/dist/agentSessions/remoteBrowserGoalRegistry.d.ts.map +1 -0
  23. package/dist/agentSessions/remoteBrowserGoalRegistry.js +86 -0
  24. package/dist/agentSessions/remoteBrowserGoalRegistry.js.map +1 -0
  25. package/dist/auth/initializeProviders.d.ts.map +1 -1
  26. package/dist/auth/initializeProviders.js +4 -2
  27. package/dist/auth/initializeProviders.js.map +1 -1
  28. package/dist/config.d.ts +7 -0
  29. package/dist/config.d.ts.map +1 -1
  30. package/dist/config.js +12 -2
  31. package/dist/config.js.map +1 -1
  32. package/dist/context.d.ts.map +1 -1
  33. package/dist/context.js +41 -7
  34. package/dist/context.js.map +1 -1
  35. package/dist/generated/generated.d.ts +1296 -49
  36. package/dist/generated/generated.d.ts.map +1 -1
  37. package/dist/generated/generated.js +50343 -43421
  38. package/dist/generated/generated.js.map +1 -1
  39. package/dist/generic/ResolverBase.js +1 -1
  40. package/dist/generic/ResolverBase.js.map +1 -1
  41. package/dist/generic/RunViewResolver.js +9 -10
  42. package/dist/generic/RunViewResolver.js.map +1 -1
  43. package/dist/index.d.ts +4 -0
  44. package/dist/index.d.ts.map +1 -1
  45. package/dist/index.js +127 -54
  46. package/dist/index.js.map +1 -1
  47. package/dist/integration/CustomColumnPromoter.d.ts +108 -0
  48. package/dist/integration/CustomColumnPromoter.d.ts.map +1 -0
  49. package/dist/integration/CustomColumnPromoter.js +508 -0
  50. package/dist/integration/CustomColumnPromoter.js.map +1 -0
  51. package/dist/logging/StartupLogger.d.ts +177 -0
  52. package/dist/logging/StartupLogger.d.ts.map +1 -0
  53. package/dist/logging/StartupLogger.js +354 -0
  54. package/dist/logging/StartupLogger.js.map +1 -0
  55. package/dist/logging/variablesLoggingMiddleware.d.ts.map +1 -1
  56. package/dist/logging/variablesLoggingMiddleware.js +21 -2
  57. package/dist/logging/variablesLoggingMiddleware.js.map +1 -1
  58. package/dist/resolvers/AgentSessionResolver.d.ts +42 -0
  59. package/dist/resolvers/AgentSessionResolver.d.ts.map +1 -0
  60. package/dist/resolvers/AgentSessionResolver.js +152 -0
  61. package/dist/resolvers/AgentSessionResolver.js.map +1 -0
  62. package/dist/resolvers/EntityPermissionResolver.d.ts +16 -0
  63. package/dist/resolvers/EntityPermissionResolver.d.ts.map +1 -0
  64. package/dist/resolvers/EntityPermissionResolver.js +95 -0
  65. package/dist/resolvers/EntityPermissionResolver.js.map +1 -0
  66. package/dist/resolvers/ExecuteRemoteOperationResolver.d.ts +27 -0
  67. package/dist/resolvers/ExecuteRemoteOperationResolver.d.ts.map +1 -0
  68. package/dist/resolvers/ExecuteRemoteOperationResolver.js +136 -0
  69. package/dist/resolvers/ExecuteRemoteOperationResolver.js.map +1 -0
  70. package/dist/resolvers/IntegrationDiscoveryResolver.d.ts +101 -1
  71. package/dist/resolvers/IntegrationDiscoveryResolver.d.ts.map +1 -1
  72. package/dist/resolvers/IntegrationDiscoveryResolver.js +544 -42
  73. package/dist/resolvers/IntegrationDiscoveryResolver.js.map +1 -1
  74. package/dist/resolvers/RealtimeBridgeResolver.d.ts +121 -0
  75. package/dist/resolvers/RealtimeBridgeResolver.d.ts.map +1 -0
  76. package/dist/resolvers/RealtimeBridgeResolver.js +533 -0
  77. package/dist/resolvers/RealtimeBridgeResolver.js.map +1 -0
  78. package/dist/resolvers/RealtimeClientSessionResolver.d.ts +688 -0
  79. package/dist/resolvers/RealtimeClientSessionResolver.d.ts.map +1 -0
  80. package/dist/resolvers/RealtimeClientSessionResolver.js +1774 -0
  81. package/dist/resolvers/RealtimeClientSessionResolver.js.map +1 -0
  82. package/dist/resolvers/RemoteBrowserActionResolver.d.ts +432 -0
  83. package/dist/resolvers/RemoteBrowserActionResolver.d.ts.map +1 -0
  84. package/dist/resolvers/RemoteBrowserActionResolver.js +1108 -0
  85. package/dist/resolvers/RemoteBrowserActionResolver.js.map +1 -0
  86. package/dist/resolvers/RunAIAgentResolver.d.ts.map +1 -1
  87. package/dist/resolvers/RunAIAgentResolver.js +0 -7
  88. package/dist/resolvers/RunAIAgentResolver.js.map +1 -1
  89. package/dist/rest/setupRESTEndpoints.d.ts.map +1 -1
  90. package/dist/rest/setupRESTEndpoints.js +5 -3
  91. package/dist/rest/setupRESTEndpoints.js.map +1 -1
  92. package/dist/services/ScheduledJobsService.d.ts.map +1 -1
  93. package/dist/services/ScheduledJobsService.js +6 -5
  94. package/dist/services/ScheduledJobsService.js.map +1 -1
  95. package/package.json +83 -74
  96. package/src/__tests__/RealtimeBridgeResolver.test.ts +100 -0
  97. package/src/__tests__/RealtimeClientSessionResolver.test.ts +2605 -0
  98. package/src/__tests__/RemoteBrowserAudioStream.test.ts +181 -0
  99. package/src/__tests__/RemoteBrowserGoalEngine.test.ts +144 -0
  100. package/src/__tests__/SessionJanitor.test.ts +234 -0
  101. package/src/__tests__/SessionManager.test.ts +465 -0
  102. package/src/__tests__/remoteBrowserGoalRegistry.test.ts +81 -0
  103. package/src/__tests__/subscriptionRedaction.test.ts +5 -0
  104. package/src/agentSessions/HostInstance.ts +53 -0
  105. package/src/agentSessions/SessionJanitor.ts +267 -0
  106. package/src/agentSessions/SessionManager.ts +446 -0
  107. package/src/agentSessions/index.ts +32 -0
  108. package/src/agentSessions/remoteBrowserGoalEngine.ts +191 -0
  109. package/src/agentSessions/remoteBrowserGoalRegistry.ts +122 -0
  110. package/src/auth/initializeProviders.ts +4 -2
  111. package/src/config.ts +13 -2
  112. package/src/context.ts +42 -7
  113. package/src/generated/generated.ts +33808 -29025
  114. package/src/generic/ResolverBase.ts +1 -1
  115. package/src/generic/RunViewResolver.ts +9 -9
  116. package/src/index.ts +128 -54
  117. package/src/integration/CustomColumnPromoter.ts +597 -0
  118. package/src/logging/StartupLogger.ts +441 -0
  119. package/src/logging/variablesLoggingMiddleware.ts +25 -5
  120. package/src/resolvers/AgentSessionResolver.ts +138 -0
  121. package/src/resolvers/EntityPermissionResolver.ts +73 -0
  122. package/src/resolvers/ExecuteRemoteOperationResolver.ts +108 -0
  123. package/src/resolvers/IntegrationDiscoveryResolver.ts +396 -37
  124. package/src/resolvers/RealtimeBridgeResolver.ts +450 -0
  125. package/src/resolvers/RealtimeClientSessionResolver.ts +2162 -0
  126. package/src/resolvers/RemoteBrowserActionResolver.ts +1122 -0
  127. package/src/resolvers/RunAIAgentResolver.ts +1 -9
  128. package/src/rest/setupRESTEndpoints.ts +5 -3
  129. package/src/services/ScheduledJobsService.ts +6 -5
@@ -0,0 +1 @@
1
+ {"version":3,"file":"AgentSessionResolver.d.ts","sourceRoot":"","sources":["../../src/resolvers/AgentSessionResolver.ts"],"names":[],"mappings":"AAcA,OAAO,EAAE,UAAU,EAAE,MAAM,aAAa,CAAC;AAIzC,OAAO,EAAE,YAAY,EAAE,MAAM,4BAA4B,CAAC;AAI1D,gEAAgE;AAChE,qBACa,uBAAuB;IAChC,uCAAuC;IAEvC,cAAc,EAAE,MAAM,CAAC;IAEvB,+EAA+E;IAE/E,MAAM,EAAE,MAAM,CAAC;IAEf,uFAAuF;IAEvF,cAAc,EAAE,MAAM,CAAC;CAC1B;AAED;;;;GAIG;AACH,qBACa,oBAAqB,SAAQ,YAAY;IAClD,OAAO,CAAC,QAAQ,CAAC,cAAc,CAAwB;IAEvD;;;OAGG;IAEG,iBAAiB,CACH,OAAO,EAAE,MAAM,EACxB,EAAE,WAAW,EAAE,SAAS,EAAE,EAAE,UAAU,EACF,cAAc,CAAC,EAAE,MAAM,EACxB,aAAa,CAAC,EAAE,MAAM,EACzB,UAAU,CAAC,EAAE,MAAM,GAC3D,OAAO,CAAC,uBAAuB,CAAC;IAkBnC;;;OAGG;IAEG,iBAAiB,CACI,cAAc,EAAE,MAAM,EACtC,EAAE,WAAW,EAAE,SAAS,EAAE,EAAE,UAAU,GAC9C,OAAO,CAAC,OAAO,CAAC;IAMnB;;;OAGG;IAEG,qBAAqB,CACA,cAAc,EAAE,MAAM,EACtC,EAAE,WAAW,EAAE,SAAS,EAAE,EAAE,UAAU,GAC9C,OAAO,CAAC,OAAO,CAAC;IAQnB,iGAAiG;IACjG,OAAO,CAAC,sBAAsB;IAW9B;;;OAGG;YACW,eAAe;CAehC"}
@@ -0,0 +1,152 @@
1
+ var __decorate = (this && this.__decorate) || function (decorators, target, key, desc) {
2
+ var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
3
+ if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
4
+ else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
5
+ return c > 3 && r && Object.defineProperty(target, key, r), r;
6
+ };
7
+ var __metadata = (this && this.__metadata) || function (k, v) {
8
+ if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
9
+ };
10
+ var __param = (this && this.__param) || function (paramIndex, decorator) {
11
+ return function (target, key) { decorator(target, key, paramIndex); }
12
+ };
13
+ /**
14
+ * @fileoverview GraphQL resolver for the AI Agent Session record lifecycle.
15
+ *
16
+ * Exposes start / close / heartbeat mutations over {@link SessionManager}, each running under the
17
+ * request's `contextUser` + request-scoped `IMetadataProvider`. Enforces two authorization gates:
18
+ * - **Open**: `CanRun` on the target agent (delegated to {@link SessionManager.CreateSession}).
19
+ * - **Close / Heartbeat**: inbound ownership — the session's `UserID` must equal `contextUser.ID`.
20
+ *
21
+ * The audio/media transport and the long-lived realtime run are out of scope here (P5); this
22
+ * resolver only manipulates the durable session record.
23
+ *
24
+ * @module @memberjunction/server
25
+ */
26
+ import { Resolver, Mutation, Arg, Ctx, ObjectType, Field } from 'type-graphql';
27
+ import { LogError } from '@memberjunction/core';
28
+ import { UUIDsEqual } from '@memberjunction/global';
29
+ import { ResolverBase } from '../generic/ResolverBase.js';
30
+ import { GetReadWriteProvider } from '../util.js';
31
+ import { SessionManager, SessionAuthorizationError } from '../agentSessions/index.js';
32
+ /** Result of {@link AgentSessionResolver.StartAgentSession}. */
33
+ let StartAgentSessionResult = class StartAgentSessionResult {
34
+ };
35
+ __decorate([
36
+ Field(),
37
+ __metadata("design:type", String)
38
+ ], StartAgentSessionResult.prototype, "agentSessionId", void 0);
39
+ __decorate([
40
+ Field(),
41
+ __metadata("design:type", String)
42
+ ], StartAgentSessionResult.prototype, "status", void 0);
43
+ __decorate([
44
+ Field(),
45
+ __metadata("design:type", String)
46
+ ], StartAgentSessionResult.prototype, "conversationId", void 0);
47
+ StartAgentSessionResult = __decorate([
48
+ ObjectType()
49
+ ], StartAgentSessionResult);
50
+ export { StartAgentSessionResult };
51
+ /**
52
+ * Resolver for the AI Agent Session record lifecycle. A single {@link SessionManager} instance is
53
+ * shared across requests — it holds no per-user/provider state (only heartbeat-coalescing
54
+ * timestamps), and every method is passed the request `contextUser` + provider explicitly.
55
+ */
56
+ let AgentSessionResolver = class AgentSessionResolver extends ResolverBase {
57
+ constructor() {
58
+ super(...arguments);
59
+ this.sessionManager = new SessionManager();
60
+ }
61
+ /**
62
+ * Open a new session for an agent. Authorization (`CanRun`) is enforced inside
63
+ * {@link SessionManager.CreateSession}; a denial surfaces as a thrown error and no row is written.
64
+ */
65
+ async StartAgentSession(agentId, { userPayload, providers }, conversationId, lastSessionId, configJson) {
66
+ const { contextUser, provider } = this.requireUserAndProvider(userPayload, providers);
67
+ try {
68
+ const session = await this.sessionManager.CreateSession({ agentID: agentId, userID: contextUser.ID, conversationID: conversationId, lastSessionID: lastSessionId, config: configJson }, contextUser, provider);
69
+ return { agentSessionId: session.ID, status: session.Status, conversationId: session.ConversationID ?? '' };
70
+ }
71
+ catch (err) {
72
+ if (err instanceof SessionAuthorizationError) {
73
+ throw new Error(err.message); // authorization denial — no session created
74
+ }
75
+ throw err;
76
+ }
77
+ }
78
+ /**
79
+ * Close a session. Rejects unless the caller owns it. Returns `true` on a successful (or
80
+ * idempotent) close, `false` if the session can't be loaded.
81
+ */
82
+ async CloseAgentSession(agentSessionId, { userPayload, providers }) {
83
+ const { contextUser, provider } = this.requireUserAndProvider(userPayload, providers);
84
+ await this.assertOwnership(agentSessionId, contextUser, provider);
85
+ return this.sessionManager.CloseSession(agentSessionId, contextUser, provider);
86
+ }
87
+ /**
88
+ * Record activity on a session (coalesced). Rejects unless the caller owns it. Returns `true`
89
+ * when the heartbeat was accepted (written or coalesced), `false` if the session is gone/closed.
90
+ */
91
+ async AgentSessionHeartbeat(agentSessionId, { userPayload, providers }) {
92
+ const { contextUser, provider } = this.requireUserAndProvider(userPayload, providers);
93
+ await this.assertOwnership(agentSessionId, contextUser, provider);
94
+ return this.sessionManager.Heartbeat(agentSessionId, contextUser, provider);
95
+ }
96
+ // ----- internals -------------------------------------------------------------------------
97
+ /** Resolve the request user + read-write provider, throwing a clear error if unauthenticated. */
98
+ requireUserAndProvider(userPayload, providers) {
99
+ const contextUser = this.GetUserFromPayload(userPayload);
100
+ if (!contextUser) {
101
+ throw new Error('Not authenticated: no user context for agent session operation');
102
+ }
103
+ return { contextUser, provider: GetReadWriteProvider(providers) };
104
+ }
105
+ /**
106
+ * Inbound ownership gate (the one genuinely new session-authz primitive): the session's `UserID`
107
+ * must equal the caller's. Throws on mismatch or when the session can't be loaded.
108
+ */
109
+ async assertOwnership(agentSessionId, contextUser, provider) {
110
+ const session = await provider.GetEntityObject('MJ: AI Agent Sessions', contextUser);
111
+ const loaded = await session.Load(agentSessionId);
112
+ if (!loaded) {
113
+ throw new Error(`Agent session ${agentSessionId} not found`);
114
+ }
115
+ if (!UUIDsEqual(session.UserID, contextUser.ID)) {
116
+ LogError(`AgentSessionResolver: ownership check failed — user ${contextUser.ID} attempted to operate on session ${agentSessionId} owned by ${session.UserID}`);
117
+ throw new Error('Not authorized: you do not own this agent session');
118
+ }
119
+ }
120
+ };
121
+ __decorate([
122
+ Mutation(() => StartAgentSessionResult),
123
+ __param(0, Arg('agentId')),
124
+ __param(1, Ctx()),
125
+ __param(2, Arg('conversationId', { nullable: true })),
126
+ __param(3, Arg('lastSessionId', { nullable: true })),
127
+ __param(4, Arg('configJson', { nullable: true })),
128
+ __metadata("design:type", Function),
129
+ __metadata("design:paramtypes", [String, Object, String, String, String]),
130
+ __metadata("design:returntype", Promise)
131
+ ], AgentSessionResolver.prototype, "StartAgentSession", null);
132
+ __decorate([
133
+ Mutation(() => Boolean),
134
+ __param(0, Arg('agentSessionId')),
135
+ __param(1, Ctx()),
136
+ __metadata("design:type", Function),
137
+ __metadata("design:paramtypes", [String, Object]),
138
+ __metadata("design:returntype", Promise)
139
+ ], AgentSessionResolver.prototype, "CloseAgentSession", null);
140
+ __decorate([
141
+ Mutation(() => Boolean),
142
+ __param(0, Arg('agentSessionId')),
143
+ __param(1, Ctx()),
144
+ __metadata("design:type", Function),
145
+ __metadata("design:paramtypes", [String, Object]),
146
+ __metadata("design:returntype", Promise)
147
+ ], AgentSessionResolver.prototype, "AgentSessionHeartbeat", null);
148
+ AgentSessionResolver = __decorate([
149
+ Resolver()
150
+ ], AgentSessionResolver);
151
+ export { AgentSessionResolver };
152
+ //# sourceMappingURL=AgentSessionResolver.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"AgentSessionResolver.js","sourceRoot":"","sources":["../../src/resolvers/AgentSessionResolver.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,16 @@
1
+ import { AppContext } from '../types.js';
2
+ import { ResolverBase } from '../generic/ResolverBase.js';
3
+ declare class EntityPermissionResult {
4
+ EntityName: string;
5
+ CanRead: boolean;
6
+ }
7
+ declare class CheckEntityPermissionsResult {
8
+ Success: boolean;
9
+ Results: EntityPermissionResult[];
10
+ ErrorMessage?: string;
11
+ }
12
+ export declare class EntityPermissionResolver extends ResolverBase {
13
+ CheckEntityPermissionsSystemUser(entityNames: string[], userEmail: string, context: AppContext): Promise<CheckEntityPermissionsResult>;
14
+ }
15
+ export {};
16
+ //# sourceMappingURL=EntityPermissionResolver.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"EntityPermissionResolver.d.ts","sourceRoot":"","sources":["../../src/resolvers/EntityPermissionResolver.ts"],"names":[],"mappings":"AAEA,OAAO,EAAE,UAAU,EAAE,MAAM,aAAa,CAAC;AACzC,OAAO,EAAE,YAAY,EAAE,MAAM,4BAA4B,CAAC;AAK1D,cACM,sBAAsB;IAEhB,UAAU,EAAE,MAAM,CAAC;IAGnB,OAAO,EAAE,OAAO,CAAC;CAC5B;AAED,cACM,4BAA4B;IAEtB,OAAO,EAAE,OAAO,CAAC;IAGjB,OAAO,EAAE,sBAAsB,EAAE,CAAC;IAG1C,YAAY,CAAC,EAAE,MAAM,CAAC;CACzB;AAED,qBACa,wBAAyB,SAAQ,YAAY;IAIhD,gCAAgC,CACE,WAAW,EAAE,MAAM,EAAE,EACzB,SAAS,EAAE,MAAM,EAC1C,OAAO,EAAE,UAAU,GAC3B,OAAO,CAAC,4BAA4B,CAAC;CAkC3C"}
@@ -0,0 +1,95 @@
1
+ var __decorate = (this && this.__decorate) || function (decorators, target, key, desc) {
2
+ var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
3
+ if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
4
+ else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
5
+ return c > 3 && r && Object.defineProperty(target, key, r), r;
6
+ };
7
+ var __metadata = (this && this.__metadata) || function (k, v) {
8
+ if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
9
+ };
10
+ var __param = (this && this.__param) || function (paramIndex, decorator) {
11
+ return function (target, key) { decorator(target, key, paramIndex); }
12
+ };
13
+ import { Arg, Ctx, Field, ObjectType, Query, Resolver } from 'type-graphql';
14
+ import { LogError } from '@memberjunction/core';
15
+ import { ResolverBase } from '../generic/ResolverBase.js';
16
+ import { RequireSystemUser } from '../directives/RequireSystemUser.js';
17
+ import { GetReadOnlyProvider } from '../util.js';
18
+ import { UserCache } from '@memberjunction/sqlserver-dataprovider';
19
+ let EntityPermissionResult = class EntityPermissionResult {
20
+ };
21
+ __decorate([
22
+ Field(() => String),
23
+ __metadata("design:type", String)
24
+ ], EntityPermissionResult.prototype, "EntityName", void 0);
25
+ __decorate([
26
+ Field(() => Boolean),
27
+ __metadata("design:type", Boolean)
28
+ ], EntityPermissionResult.prototype, "CanRead", void 0);
29
+ EntityPermissionResult = __decorate([
30
+ ObjectType()
31
+ ], EntityPermissionResult);
32
+ let CheckEntityPermissionsResult = class CheckEntityPermissionsResult {
33
+ };
34
+ __decorate([
35
+ Field(() => Boolean),
36
+ __metadata("design:type", Boolean)
37
+ ], CheckEntityPermissionsResult.prototype, "Success", void 0);
38
+ __decorate([
39
+ Field(() => [EntityPermissionResult]),
40
+ __metadata("design:type", Array)
41
+ ], CheckEntityPermissionsResult.prototype, "Results", void 0);
42
+ __decorate([
43
+ Field(() => String, { nullable: true }),
44
+ __metadata("design:type", String)
45
+ ], CheckEntityPermissionsResult.prototype, "ErrorMessage", void 0);
46
+ CheckEntityPermissionsResult = __decorate([
47
+ ObjectType()
48
+ ], CheckEntityPermissionsResult);
49
+ let EntityPermissionResolver = class EntityPermissionResolver extends ResolverBase {
50
+ async CheckEntityPermissionsSystemUser(entityNames, userEmail, context) {
51
+ try {
52
+ const user = UserCache.Instance.Users.find(u => u.Email.toLowerCase().trim() === userEmail.toLowerCase().trim());
53
+ if (!user) {
54
+ return { Success: false, Results: [], ErrorMessage: `User not found: ${userEmail}` };
55
+ }
56
+ // Use the per-request provider (not the global default) so entity metadata + permission
57
+ // evaluation resolve against the connection servicing THIS request.
58
+ const md = GetReadOnlyProvider(context.providers, { allowFallbackToReadWrite: true });
59
+ const results = [];
60
+ for (const name of entityNames) {
61
+ const entityInfo = md.EntityByName(name);
62
+ if (!entityInfo) {
63
+ results.push({ EntityName: name, CanRead: false });
64
+ continue;
65
+ }
66
+ const perms = entityInfo.GetUserPermisions(user);
67
+ results.push({ EntityName: name, CanRead: perms?.CanRead ?? false });
68
+ }
69
+ return { Success: true, Results: results };
70
+ }
71
+ catch (err) {
72
+ LogError(err);
73
+ return {
74
+ Success: false,
75
+ Results: [],
76
+ ErrorMessage: `EntityPermissionResolver::CheckEntityPermissionsSystemUser --- ${err instanceof Error ? err.message : String(err)}`
77
+ };
78
+ }
79
+ }
80
+ };
81
+ __decorate([
82
+ RequireSystemUser(),
83
+ Query(() => CheckEntityPermissionsResult),
84
+ __param(0, Arg('EntityNames', () => [String])),
85
+ __param(1, Arg('UserEmail', () => String)),
86
+ __param(2, Ctx()),
87
+ __metadata("design:type", Function),
88
+ __metadata("design:paramtypes", [Array, String, Object]),
89
+ __metadata("design:returntype", Promise)
90
+ ], EntityPermissionResolver.prototype, "CheckEntityPermissionsSystemUser", null);
91
+ EntityPermissionResolver = __decorate([
92
+ Resolver()
93
+ ], EntityPermissionResolver);
94
+ export { EntityPermissionResolver };
95
+ //# sourceMappingURL=EntityPermissionResolver.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"EntityPermissionResolver.js","sourceRoot":"","sources":["../../src/resolvers/EntityPermissionResolver.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,27 @@
1
+ import { ResolverBase } from '../generic/ResolverBase.js';
2
+ import { AppContext } from '../types.js';
3
+ /** Input for the generic Remote Operation transport mutation. */
4
+ export declare class ExecuteRemoteOperationInput {
5
+ operationKey: string;
6
+ inputJSON: string;
7
+ invokeMode: string;
8
+ }
9
+ /** Result of the generic Remote Operation transport mutation. */
10
+ export declare class ExecuteRemoteOperationResultType {
11
+ success: boolean;
12
+ resultCode?: string;
13
+ outputJSON?: string;
14
+ handle?: string;
15
+ errorMessage?: string;
16
+ }
17
+ /**
18
+ * The single generic server entry point for Remote Operations. Resolves the operation by key,
19
+ * applies the framework authorization gates (API-key scope, system-user, then the operation's own
20
+ * `Authorize`), and routes the operation through the per-request provider — which executes it
21
+ * in-process. Only registered, active operations are reachable, so the public `RouteOperation`
22
+ * power-tool is safe by construction.
23
+ */
24
+ export declare class ExecuteRemoteOperationResolver extends ResolverBase {
25
+ ExecuteRemoteOperation(input: ExecuteRemoteOperationInput, ctx: AppContext): Promise<ExecuteRemoteOperationResultType>;
26
+ }
27
+ //# sourceMappingURL=ExecuteRemoteOperationResolver.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"ExecuteRemoteOperationResolver.d.ts","sourceRoot":"","sources":["../../src/resolvers/ExecuteRemoteOperationResolver.ts"],"names":[],"mappings":"AAGA,OAAO,EAAE,YAAY,EAAE,MAAM,4BAA4B,CAAC;AAC1D,OAAO,EAAE,UAAU,EAAE,MAAM,aAAa,CAAC;AAGzC,iEAAiE;AACjE,qBACa,2BAA2B;IAEpC,YAAY,EAAE,MAAM,CAAC;IAGrB,SAAS,EAAE,MAAM,CAAC;IAGlB,UAAU,EAAE,MAAM,CAAC;CACtB;AAED,iEAAiE;AACjE,qBACa,gCAAgC;IAEzC,OAAO,EAAE,OAAO,CAAC;IAGjB,UAAU,CAAC,EAAE,MAAM,CAAC;IAGpB,UAAU,CAAC,EAAE,MAAM,CAAC;IAGpB,MAAM,CAAC,EAAE,MAAM,CAAC;IAGhB,YAAY,CAAC,EAAE,MAAM,CAAC;CACzB;AAED;;;;;;GAMG;AACH,qBACa,8BAA+B,SAAQ,YAAY;IAEtD,sBAAsB,CACV,KAAK,EAAE,2BAA2B,EACzC,GAAG,EAAE,UAAU,GACvB,OAAO,CAAC,gCAAgC,CAAC;CAkD/C"}
@@ -0,0 +1,136 @@
1
+ var __decorate = (this && this.__decorate) || function (decorators, target, key, desc) {
2
+ var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
3
+ if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
4
+ else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
5
+ return c > 3 && r && Object.defineProperty(target, key, r), r;
6
+ };
7
+ var __metadata = (this && this.__metadata) || function (k, v) {
8
+ if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
9
+ };
10
+ var __param = (this && this.__param) || function (paramIndex, decorator) {
11
+ return function (target, key) { decorator(target, key, paramIndex); }
12
+ };
13
+ import { Arg, Ctx, Field, InputType, Mutation, ObjectType, Resolver } from 'type-graphql';
14
+ import { MJGlobal } from '@memberjunction/global';
15
+ import { BaseRemotableOperation } from '@memberjunction/core';
16
+ import { ResolverBase } from '../generic/ResolverBase.js';
17
+ import { GetReadWriteProvider } from '../util.js';
18
+ /** Input for the generic Remote Operation transport mutation. */
19
+ let ExecuteRemoteOperationInput = class ExecuteRemoteOperationInput {
20
+ };
21
+ __decorate([
22
+ Field(),
23
+ __metadata("design:type", String)
24
+ ], ExecuteRemoteOperationInput.prototype, "operationKey", void 0);
25
+ __decorate([
26
+ Field(),
27
+ __metadata("design:type", String)
28
+ ], ExecuteRemoteOperationInput.prototype, "inputJSON", void 0);
29
+ __decorate([
30
+ Field(),
31
+ __metadata("design:type", String)
32
+ ], ExecuteRemoteOperationInput.prototype, "invokeMode", void 0);
33
+ ExecuteRemoteOperationInput = __decorate([
34
+ InputType()
35
+ ], ExecuteRemoteOperationInput);
36
+ export { ExecuteRemoteOperationInput };
37
+ /** Result of the generic Remote Operation transport mutation. */
38
+ let ExecuteRemoteOperationResultType = class ExecuteRemoteOperationResultType {
39
+ };
40
+ __decorate([
41
+ Field(() => Boolean),
42
+ __metadata("design:type", Boolean)
43
+ ], ExecuteRemoteOperationResultType.prototype, "success", void 0);
44
+ __decorate([
45
+ Field(() => String, { nullable: true }),
46
+ __metadata("design:type", String)
47
+ ], ExecuteRemoteOperationResultType.prototype, "resultCode", void 0);
48
+ __decorate([
49
+ Field(() => String, { nullable: true }),
50
+ __metadata("design:type", String)
51
+ ], ExecuteRemoteOperationResultType.prototype, "outputJSON", void 0);
52
+ __decorate([
53
+ Field(() => String, { nullable: true }),
54
+ __metadata("design:type", String)
55
+ ], ExecuteRemoteOperationResultType.prototype, "handle", void 0);
56
+ __decorate([
57
+ Field(() => String, { nullable: true }),
58
+ __metadata("design:type", String)
59
+ ], ExecuteRemoteOperationResultType.prototype, "errorMessage", void 0);
60
+ ExecuteRemoteOperationResultType = __decorate([
61
+ ObjectType()
62
+ ], ExecuteRemoteOperationResultType);
63
+ export { ExecuteRemoteOperationResultType };
64
+ /**
65
+ * The single generic server entry point for Remote Operations. Resolves the operation by key,
66
+ * applies the framework authorization gates (API-key scope, system-user, then the operation's own
67
+ * `Authorize`), and routes the operation through the per-request provider — which executes it
68
+ * in-process. Only registered, active operations are reachable, so the public `RouteOperation`
69
+ * power-tool is safe by construction.
70
+ */
71
+ let ExecuteRemoteOperationResolver = class ExecuteRemoteOperationResolver extends ResolverBase {
72
+ async ExecuteRemoteOperation(input, ctx) {
73
+ try {
74
+ const key = input.operationKey?.trim();
75
+ if (!key) {
76
+ return fail('INVALID_OPERATION_KEY', 'operationKey is required');
77
+ }
78
+ // Resolve the operation's declaration so we can apply its scope / system-user gates.
79
+ const registration = MJGlobal.Instance.ClassFactory.GetRegistration(BaseRemotableOperation, key);
80
+ if (!registration) {
81
+ return fail('UNKNOWN_OPERATION', `Remote operation '${key}' is not registered`);
82
+ }
83
+ const opDecl = MJGlobal.Instance.ClassFactory.CreateInstance(BaseRemotableOperation, key);
84
+ // (1) API-key scope gate — a no-op for interactive OAuth/JWT users.
85
+ if (opDecl?.RequiredScope) {
86
+ await this.CheckAPIKeyScopeAuthorization(opDecl.RequiredScope, key, ctx.userPayload);
87
+ }
88
+ // (2) System-user gate.
89
+ if (opDecl?.RequiresSystemUser && !ctx.userPayload.isSystemUser) {
90
+ return fail('FORBIDDEN', `Operation '${key}' may only be invoked by the system user`);
91
+ }
92
+ // (3) Resolve the acting user (works for OAuth/JWT and API-key sessions alike).
93
+ const user = this.GetUserFromPayload(ctx.userPayload);
94
+ if (!user) {
95
+ return fail('NO_USER', 'Not authenticated');
96
+ }
97
+ let parsedInput;
98
+ try {
99
+ parsedInput = input.inputJSON ? JSON.parse(input.inputJSON) : {};
100
+ }
101
+ catch (e) {
102
+ return fail('INVALID_INPUT_JSON', `Invalid input JSON: ${e instanceof Error ? e.message : String(e)}`);
103
+ }
104
+ // Route through the per-request provider (server in-process path; runs the op's Authorize + InternalExecute).
105
+ const provider = GetReadWriteProvider(ctx.providers);
106
+ const result = await provider.RouteOperation(key, parsedInput, { user, mode: input.invokeMode });
107
+ return {
108
+ success: result.Success,
109
+ resultCode: result.ResultCode,
110
+ outputJSON: result.Output !== undefined ? JSON.stringify(result.Output) : undefined,
111
+ handle: result.Handle,
112
+ errorMessage: result.ErrorMessage,
113
+ };
114
+ }
115
+ catch (e) {
116
+ return fail('ERROR', e instanceof Error ? e.message : String(e));
117
+ }
118
+ }
119
+ };
120
+ __decorate([
121
+ Mutation(() => ExecuteRemoteOperationResultType),
122
+ __param(0, Arg('input')),
123
+ __param(1, Ctx()),
124
+ __metadata("design:type", Function),
125
+ __metadata("design:paramtypes", [ExecuteRemoteOperationInput, Object]),
126
+ __metadata("design:returntype", Promise)
127
+ ], ExecuteRemoteOperationResolver.prototype, "ExecuteRemoteOperation", null);
128
+ ExecuteRemoteOperationResolver = __decorate([
129
+ Resolver()
130
+ ], ExecuteRemoteOperationResolver);
131
+ export { ExecuteRemoteOperationResolver };
132
+ /** Builds a failed result. */
133
+ function fail(resultCode, errorMessage) {
134
+ return { success: false, resultCode, errorMessage };
135
+ }
136
+ //# sourceMappingURL=ExecuteRemoteOperationResolver.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"ExecuteRemoteOperationResolver.js","sourceRoot":"","sources":["../../src/resolvers/ExecuteRemoteOperationResolver.ts"],"names":[],"mappings":"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"}
@@ -300,6 +300,60 @@ declare class MutationResultOutput {
300
300
  Success: boolean;
301
301
  Message: string;
302
302
  }
303
+ declare class IntegrationSyncConfigInput {
304
+ SyncConcurrency?: number;
305
+ MaxConcurrency?: number;
306
+ RateLimitTokensPerSec?: number;
307
+ RateLimitBurst?: number;
308
+ CrossLayerPipeline?: boolean;
309
+ PartitionReconcile?: boolean;
310
+ DiscoveryTimeBudgetMs?: number;
311
+ DiscoveryBatchSize?: number;
312
+ DiscoveryMaxRecords?: number;
313
+ DeactivateAbsent?: boolean;
314
+ }
315
+ declare class IntegrationSyncConfigOutput {
316
+ Success: boolean;
317
+ Message: string;
318
+ SyncConcurrency?: number;
319
+ MaxConcurrency?: number;
320
+ RateLimitTokensPerSec?: number;
321
+ RateLimitBurst?: number;
322
+ CrossLayerPipeline?: boolean;
323
+ PartitionReconcile?: boolean;
324
+ DiscoveryTimeBudgetMs?: number;
325
+ DiscoveryBatchSize?: number;
326
+ DiscoveryMaxRecords?: number;
327
+ DeactivateAbsent?: boolean;
328
+ }
329
+ declare class CustomColumnCandidate {
330
+ EntityName: string;
331
+ /** The source field key as captured in the overflow column. */
332
+ SourceKey: string;
333
+ /** The sanitized, collision-resolved column name that would be created. */
334
+ ColumnName: string;
335
+ /** Inferred schema-field type family ('string' | 'number' | 'boolean' | 'datetime'). */
336
+ InferredType: string;
337
+ /** true = the real column does not exist yet (ADD COLUMN); false = recovery (column exists, mapping missing). */
338
+ NeedsColumn: boolean;
339
+ }
340
+ declare class CustomColumnCandidatesOutput {
341
+ Success: boolean;
342
+ Message: string;
343
+ Candidates: CustomColumnCandidate[];
344
+ }
345
+ declare class PromotedColumn {
346
+ EntityName: string;
347
+ ColumnName: string;
348
+ }
349
+ declare class PromoteCustomColumnsOutput {
350
+ Success: boolean;
351
+ Message: string;
352
+ Promoted: boolean;
353
+ ColumnsAdded: PromotedColumn[];
354
+ /** true when an RSU schema change ran (a server restart may be pending to expose the new columns). */
355
+ SchemaUpdatePending: boolean;
356
+ }
303
357
  declare class FieldMapInput {
304
358
  SourceFieldName: string;
305
359
  DestinationFieldName: string;
@@ -345,6 +399,10 @@ declare class CreateScheduleInput {
345
399
  Description?: string;
346
400
  SyncDirection?: string;
347
401
  FullSync?: boolean;
402
+ /** §13 — 'sync' (default; moves data via RunSync) or 'discovery' (schema-only RefreshConnectorSchema on cron, evolving the IO/IOF catalog — no RSU, no data sync). */
403
+ JobKind?: string;
404
+ /** Discovery-job only: deactivate objects/fields absent from an authoritative refresh (reversible). Default true. */
405
+ DeactivateAbsent?: boolean;
348
406
  }
349
407
  declare class CreateScheduleOutput {
350
408
  Success: boolean;
@@ -598,7 +656,7 @@ export declare class IntegrationDiscoveryResolver extends ResolverBase {
598
656
  * both on stdout (visible in the MJAPI log file) and in a per-run
599
657
  * `<cwd>/logs/integration-runs/<runID>/progress.jsonl` artifact.
600
658
  */
601
- IntegrationRefreshConnectorSchema(companyIntegrationID: string, universalPKConvention: string | undefined, ctx: AppContext): Promise<RefreshConnectorSchemaOutput>;
659
+ IntegrationRefreshConnectorSchema(companyIntegrationID: string, universalPKConvention: string | undefined, deactivateAbsent: boolean | undefined, ctx: AppContext): Promise<RefreshConnectorSchemaOutput>;
602
660
  /**
603
661
  * Generates + persists strongly-typed Action metadata on demand for an
604
662
  * integration object. When `verb` is supplied, a single Action is generated
@@ -838,6 +896,37 @@ export declare class IntegrationDiscoveryResolver extends ResolverBase {
838
896
  * Updates credential values and/or configuration on an existing CompanyIntegration.
839
897
  */
840
898
  IntegrationUpdateConnection(companyIntegrationID: string, credentialValues: string, configuration: string, externalSystemID: string, testConnection: boolean, runSchemaRefresh: boolean, universalPKConvention: string | undefined, ctx: AppContext): Promise<MutationResultOutput>;
899
+ /**
900
+ * Sets the per-connection sync tuning (rate limit, concurrency, time budget, pipeline flags) as
901
+ * STRUCTURED typed fields, merged into CompanyIntegration.Configuration (other keys preserved).
902
+ * These are the exact keys the IntegrationEngine reads at runtime, so they become customizable
903
+ * via the API instead of hidden code constants. Returns the merged config typed.
904
+ */
905
+ IntegrationSetSyncConfig(companyIntegrationID: string, config: IntegrationSyncConfigInput, ctx: AppContext): Promise<IntegrationSyncConfigOutput>;
906
+ /** Reads the per-connection sync tuning back as STRUCTURED typed fields. */
907
+ IntegrationGetSyncConfig(companyIntegrationID: string, ctx: AppContext): Promise<IntegrationSyncConfigOutput>;
908
+ /** Reads a single boolean key from a CompanyIntegration.Configuration JSON string (undefined if absent/malformed). */
909
+ private readConfigBool;
910
+ /** Extracts the typed sync-config fields from a parsed Configuration object (type-guarded). */
911
+ private readSyncConfig;
912
+ /** The MJ entity names this connection has entity maps for (for whole-connection scope). */
913
+ private getMappedEntityNames;
914
+ /**
915
+ * Lists the custom-column CANDIDATES captured in the overflow column awaiting promotion — the "new
916
+ * columns found" for a connection. READ-ONLY (no schema change, no RSU). Scope to one entity via
917
+ * entityName, or omit to list across all the connection's mapped entities. Computed live (overflow keys
918
+ * minus already-mapped/already-a-column), so it is inherently deduped against anything a concurrent
919
+ * discovery already promoted.
920
+ */
921
+ IntegrationListCustomColumnCandidates(companyIntegrationID: string, entityName: string | undefined, ctx: AppContext): Promise<CustomColumnCandidatesOutput>;
922
+ /**
923
+ * On-demand promotion of captured custom columns: runs RSU (ADD COLUMN + register EntityField + field map),
924
+ * which may require a server restart to expose them over GraphQL. This is the USER-ACCEPTED trigger — by
925
+ * default a sync only CAPTURES to the overflow column (auto-promote is opt-in per connection via
926
+ * Configuration.autoPromoteCustomColumns). Scope via entityNames, or omit to promote across all mapped
927
+ * entities. Idempotent: already-promoted/mapped keys are skipped (safe to re-run / run alongside discovery).
928
+ */
929
+ IntegrationPromoteCustomColumns(companyIntegrationID: string, entityNames: string[] | undefined, ctx: AppContext): Promise<PromoteCustomColumnsOutput>;
841
930
  /**
842
931
  * Soft-deletes a CompanyIntegration by setting IsActive=false.
843
932
  */
@@ -895,6 +984,17 @@ export declare class IntegrationDiscoveryResolver extends ResolverBase {
895
984
  * Build schema artifacts for a single connector's objects.
896
985
  * Shared by IntegrationApplySchema (single) and IntegrationApplySchemaBatch (batch).
897
986
  */
987
+ /**
988
+ * §B — enforce OPTIONAL table/column caps at the create-tables (RSU) gate. These are OPERATOR
989
+ * (deployment) guardrails read from ENV — `MJ_INTEGRATION_MAX_TABLES` / `MJ_INTEGRATION_MAX_COLUMNS_PER_TABLE`
990
+ * (absent or ≤0 = unbounded, the common case). They are DELIBERATELY env-only, NOT per-connection
991
+ * `Configuration`/GraphQL: a guardrail a user can raise via the same API they apply with is toothless.
992
+ * THROWS a clear error when the selection exceeds a cap so NOTHING partial is created — the caller surfaces
993
+ * it and the user narrows the selection (the cap itself is an operator concern). NEVER truncates. Discovery
994
+ * still surfaces every object/field; only materialization is capped. Per-table column count = the selected
995
+ * field subset, or the object's full discovered field count when all fields are selected.
996
+ */
997
+ private enforceSchemaLimits;
898
998
  private buildSchemaForConnector;
899
999
  /**
900
1000
  * Starts an async integration sync. Returns immediately with the run ID.