@friggframework/core 2.0.0--canary.498.336977b.0 → 2.0.0--canary.498.82efe90.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.
package/database/index.js CHANGED
@@ -12,13 +12,14 @@
12
12
  * etc.
13
13
  */
14
14
 
15
- const { mongoose } = require('./mongoose');
16
- const { IndividualUser } = require('./models/IndividualUser');
17
- const { OrganizationUser } = require('./models/OrganizationUser');
18
- const { UserModel } = require('./models/UserModel');
19
- const { WebsocketConnection } = require('./models/WebsocketConnection');
15
+ // Lazy-load mongoose to avoid importing mongodb when using PostgreSQL only
16
+ let _mongoose = null;
17
+ let _IndividualUser = null;
18
+ let _OrganizationUser = null;
19
+ let _UserModel = null;
20
+ let _WebsocketConnection = null;
20
21
 
21
- // Prisma exports
22
+ // Prisma exports (always available)
22
23
  const { prisma } = require('./prisma');
23
24
  const { TokenRepository } = require('../token/repositories/token-repository');
24
25
  const {
@@ -26,12 +27,38 @@ const {
26
27
  } = require('../websocket/repositories/websocket-connection-repository');
27
28
 
28
29
  module.exports = {
29
- mongoose,
30
- IndividualUser,
31
- OrganizationUser,
32
- UserModel,
33
- WebsocketConnection,
34
- // Prisma
30
+ // Lazy-loaded mongoose exports (only load when accessed)
31
+ get mongoose() {
32
+ if (!_mongoose) {
33
+ _mongoose = require('./mongoose').mongoose;
34
+ }
35
+ return _mongoose;
36
+ },
37
+ get IndividualUser() {
38
+ if (!_IndividualUser) {
39
+ _IndividualUser = require('./models/IndividualUser').IndividualUser;
40
+ }
41
+ return _IndividualUser;
42
+ },
43
+ get OrganizationUser() {
44
+ if (!_OrganizationUser) {
45
+ _OrganizationUser = require('./models/OrganizationUser').OrganizationUser;
46
+ }
47
+ return _OrganizationUser;
48
+ },
49
+ get UserModel() {
50
+ if (!_UserModel) {
51
+ _UserModel = require('./models/UserModel').UserModel;
52
+ }
53
+ return _UserModel;
54
+ },
55
+ get WebsocketConnection() {
56
+ if (!_WebsocketConnection) {
57
+ _WebsocketConnection = require('./models/WebsocketConnection').WebsocketConnection;
58
+ }
59
+ return _WebsocketConnection;
60
+ },
61
+ // Prisma (always available)
35
62
  prisma,
36
63
  TokenRepository,
37
64
  WebsocketConnectionRepository,
@@ -71,6 +71,8 @@ const createModuleFactoryWithDefinitions = (
71
71
  };
72
72
 
73
73
  const loadIntegrationForWebhook = async (integrationId) => {
74
+ console.log(`[loadIntegrationForWebhook] Loading integration ${integrationId}`);
75
+
74
76
  const { loadAppDefinition } = require('./app-definition-loader');
75
77
  const { integrations: integrationClasses } = loadAppDefinition();
76
78
 
@@ -92,13 +94,21 @@ const loadIntegrationForWebhook = async (integrationId) => {
92
94
  integrationId
93
95
  );
94
96
 
95
- return await getIntegrationInstance.execute(
97
+ console.log(`[loadIntegrationForWebhook] Found integration record - userId: ${integrationRecord?.userId}, status: ${integrationRecord?.status}`);
98
+
99
+ const instance = await getIntegrationInstance.execute(
96
100
  integrationId,
97
101
  integrationRecord.userId
98
102
  );
103
+
104
+ console.log(`[loadIntegrationForWebhook] Instance created - has entities: ${!!instance.entities}, has config: ${!!instance.config}`);
105
+
106
+ return instance;
99
107
  };
100
108
 
101
109
  const loadIntegrationForProcess = async (processId, integrationClass) => {
110
+ console.log(`[loadIntegrationForProcess] Loading integration for processId: ${processId}`);
111
+
102
112
  const { processRepository, integrationRepository, moduleRepository } =
103
113
  initializeRepositories();
104
114
 
@@ -122,31 +132,45 @@ const loadIntegrationForProcess = async (processId, integrationClass) => {
122
132
  throw new Error(`Process not found: ${processId}`);
123
133
  }
124
134
 
125
- return await getIntegrationInstance.execute(
135
+ console.log(`[loadIntegrationForProcess] Found process - integrationId: ${process.integrationId}, userId: ${process.userId}`);
136
+
137
+ const instance = await getIntegrationInstance.execute(
126
138
  process.integrationId,
127
139
  process.userId
128
140
  );
141
+
142
+ console.log(`[loadIntegrationForProcess] Instance created - has entities: ${!!instance.entities}, has config: ${!!instance.config}`);
143
+ console.log(`[loadIntegrationForProcess] Entity keys: ${Object.keys(instance.entities || {}).join(', ')}`);
144
+
145
+ return instance;
129
146
  };
130
147
 
131
148
  const createQueueWorker = (integrationClass) => {
132
149
  class QueueWorker extends Worker {
133
150
  async _run(params, context) {
134
151
  try {
152
+ console.log(`[QueueWorker] Event: ${params.event}, Data keys: ${Object.keys(params.data || {}).join(', ')}`);
153
+ console.log(`[QueueWorker] processId: ${params.data?.processId}, integrationId: ${params.data?.integrationId}`);
154
+
135
155
  let integrationInstance;
136
-
156
+
137
157
  // Prioritize processId first (for sync handler compatibility),
138
158
  // then integrationId (for ANY event type that needs hydration),
139
159
  // fallback to unhydrated instance
140
160
  if (params.data?.processId) {
161
+ console.log(`[QueueWorker] Hydrating via processId: ${params.data.processId}`);
141
162
  integrationInstance = await loadIntegrationForProcess(
142
163
  params.data.processId,
143
164
  integrationClass
144
165
  );
145
166
  } else if (params.data?.integrationId) {
167
+ console.log(`[QueueWorker] Hydrating via integrationId: ${params.data.integrationId}`);
146
168
  integrationInstance = await loadIntegrationForWebhook(
147
169
  params.data.integrationId
148
170
  );
171
+ console.log(`[QueueWorker] Hydration complete - userId: ${integrationInstance.userId}, config keys: ${Object.keys(integrationInstance.config || {}).join(', ')}`);
149
172
  } else {
173
+ console.log(`[QueueWorker] No processId or integrationId - creating unhydrated instance`);
150
174
  // Instantiates a DRY integration class without database records.
151
175
  // There will be cases where we need to use helpers that the api modules can export.
152
176
  // Like for HubSpot, the answer is to do a reverse lookup for the integration by the entity external ID (HubSpot Portal ID),
@@ -153,6 +153,9 @@ class IntegrationBase {
153
153
  * @param {Array} [payload.modules]
154
154
  */
155
155
  setIntegrationRecord(payload = {}) {
156
+ console.log(`[setIntegrationRecord] Called with payload keys: ${Object.keys(payload).join(', ')}`);
157
+ console.log(`[setIntegrationRecord] payload.modules length: ${payload.modules?.length || 0}`);
158
+
156
159
  if (!payload || Object.keys(payload).length === 0) {
157
160
  throw new Error('setIntegrationRecord requires integration data');
158
161
  }
@@ -160,6 +163,8 @@ class IntegrationBase {
160
163
  const integrationRecord = payload.record;
161
164
  const integrationModules = payload.modules ?? [];
162
165
 
166
+ console.log(`[setIntegrationRecord] integrationModules length: ${integrationModules.length}`);
167
+
163
168
  if (!integrationRecord) {
164
169
  throw new Error('Integration record not provided');
165
170
  }
@@ -175,7 +180,9 @@ class IntegrationBase {
175
180
  this.version = version;
176
181
  this.messages = messages || { errors: [], warnings: [] };
177
182
 
183
+ console.log(`[setIntegrationRecord] About to call _appendModules with ${integrationModules.length} modules`);
178
184
  this.modules = this._appendModules(integrationModules);
185
+ console.log(`[setIntegrationRecord] After _appendModules, this.modules keys: ${Object.keys(this.modules).join(', ')}`);
179
186
 
180
187
  this.record = {
181
188
  id: this.id,
@@ -188,6 +195,7 @@ class IntegrationBase {
188
195
  };
189
196
 
190
197
  this._isHydrated = Boolean(this.id);
198
+ console.log(`[setIntegrationRecord] Hydrated: ${this._isHydrated}`);
191
199
  return this;
192
200
  }
193
201
 
@@ -214,41 +222,57 @@ class IntegrationBase {
214
222
  * @returns {Object} The modules object
215
223
  */
216
224
  _appendModules(integrationModules) {
225
+ console.log(`[_appendModules] Called with ${integrationModules?.length || 0} modules`);
226
+ console.log(`[_appendModules] Definition.modules exists: ${!!this.constructor.Definition?.modules}`);
227
+
217
228
  const modules = {};
218
-
229
+
219
230
  // Build reverse mapping: definition.getName() → referenceKey
220
231
  // e.g., 'quo-attio' → 'quo', 'attio' → 'attio'
221
232
  const moduleNameToKey = {};
222
233
  if (this.constructor.Definition?.modules) {
234
+ console.log(`[_appendModules] Definition.modules keys: ${Object.keys(this.constructor.Definition.modules).join(', ')}`);
223
235
  for (const [key, moduleConfig] of Object.entries(this.constructor.Definition.modules)) {
224
236
  const definition = moduleConfig.definition;
225
237
  if (definition) {
226
238
  // Use getName() if available, fallback to moduleName
227
- const definitionName = typeof definition.getName === 'function'
228
- ? definition.getName()
239
+ const definitionName = typeof definition.getName === 'function'
240
+ ? definition.getName()
229
241
  : definition.moduleName;
230
242
  if (definitionName) {
243
+ console.log(`[_appendModules] Mapping: ${definitionName} → ${key}`);
231
244
  moduleNameToKey[definitionName] = key;
232
245
  }
233
246
  }
234
247
  }
235
248
  }
236
-
249
+
250
+ console.log(`[_appendModules] Built mapping: ${JSON.stringify(moduleNameToKey)}`);
251
+
237
252
  for (const module of integrationModules) {
238
253
  const moduleName =
239
254
  typeof module.getName === 'function'
240
255
  ? module.getName()
241
256
  : module.name;
242
-
257
+
258
+ console.log(`[_appendModules] Processing module with name: ${moduleName}`);
259
+
243
260
  // Use the reference key from Definition.modules if available,
244
261
  // otherwise fall back to moduleName
245
262
  const key = moduleNameToKey[moduleName] || moduleName;
246
-
263
+
264
+ console.log(`[_appendModules] Resolved key: ${key}`);
265
+
247
266
  if (key) {
248
267
  modules[key] = module;
249
268
  this[key] = module;
269
+ console.log(`[_appendModules] Attached module to this.${key}`);
250
270
  }
251
271
  }
272
+
273
+ console.log(`[_appendModules] Returning modules object with keys: ${Object.keys(modules).join(', ')}`);
274
+ console.log(`[_appendModules] this.entities after attachment: ${Object.keys(this.entities || {}).join(', ')}`);
275
+
252
276
  return modules;
253
277
  }
254
278
 
@@ -27,6 +27,8 @@ class GetIntegrationInstance {
27
27
  * @throws {Error} When integration is not found, doesn't belong to user, or integration class is not found.
28
28
  */
29
29
  async execute(integrationId, userId) {
30
+ console.log(`[GetIntegrationInstance] Loading integration ${integrationId} for user ${userId}`);
31
+
30
32
  const integrationRecord =
31
33
  await this.integrationRepository.findIntegrationById(integrationId);
32
34
 
@@ -36,6 +38,8 @@ class GetIntegrationInstance {
36
38
  );
37
39
  }
38
40
 
41
+ console.log(`[GetIntegrationInstance] Found integration record - type: ${integrationRecord.config?.type}, entitiesIds: ${JSON.stringify(integrationRecord.entitiesIds)}`);
42
+
39
43
  const integrationClass = this.integrationClasses.find(
40
44
  (integrationClass) =>
41
45
  integrationClass.Definition.name ===
@@ -54,15 +58,21 @@ class GetIntegrationInstance {
54
58
  );
55
59
  }
56
60
 
61
+ console.log(`[GetIntegrationInstance] Loading ${integrationRecord.entitiesIds?.length || 0} entities/modules`);
62
+
57
63
  const modules = [];
58
64
  for (const entityId of integrationRecord.entitiesIds) {
65
+ console.log(`[GetIntegrationInstance] Loading module for entity ${entityId}`);
59
66
  const moduleInstance = await this.moduleFactory.getModuleInstance(
60
67
  entityId,
61
68
  integrationRecord.userId
62
69
  );
70
+ console.log(`[GetIntegrationInstance] Module loaded - type: ${moduleInstance.constructor.name}`);
63
71
  modules.push(moduleInstance);
64
72
  }
65
73
 
74
+ console.log(`[GetIntegrationInstance] Loaded ${modules.length} modules total`);
75
+
66
76
  const integrationInstance = new integrationClass({
67
77
  id: integrationRecord.id,
68
78
  userId: integrationRecord.userId,
package/package.json CHANGED
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "name": "@friggframework/core",
3
3
  "prettier": "@friggframework/prettier-config",
4
- "version": "2.0.0--canary.498.336977b.0",
4
+ "version": "2.0.0--canary.498.82efe90.0",
5
5
  "dependencies": {
6
6
  "@aws-sdk/client-apigatewaymanagementapi": "^3.588.0",
7
7
  "@aws-sdk/client-kms": "^3.588.0",
@@ -38,9 +38,9 @@
38
38
  }
39
39
  },
40
40
  "devDependencies": {
41
- "@friggframework/eslint-config": "2.0.0--canary.498.336977b.0",
42
- "@friggframework/prettier-config": "2.0.0--canary.498.336977b.0",
43
- "@friggframework/test": "2.0.0--canary.498.336977b.0",
41
+ "@friggframework/eslint-config": "2.0.0--canary.498.82efe90.0",
42
+ "@friggframework/prettier-config": "2.0.0--canary.498.82efe90.0",
43
+ "@friggframework/test": "2.0.0--canary.498.82efe90.0",
44
44
  "@prisma/client": "^6.17.0",
45
45
  "@types/lodash": "4.17.15",
46
46
  "@typescript-eslint/eslint-plugin": "^8.0.0",
@@ -80,5 +80,5 @@
80
80
  "publishConfig": {
81
81
  "access": "public"
82
82
  },
83
- "gitHead": "336977bb0e30f823cbeac47d635858073337ff14"
83
+ "gitHead": "82efe90fa2bee64b1407052191ae8d06307d8106"
84
84
  }