bulltrackers-module 1.0.507 → 1.0.509

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.
@@ -5,7 +5,53 @@
5
5
  */
6
6
 
7
7
  const { FieldValue } = require('@google-cloud/firestore');
8
- const { getCollectionPath, resolvePath, getCollectionMetadata } = require('../../../../../../config/collection_registry');
8
+
9
+ // Try to require registry functions, but they may be injected instead
10
+ let getCollectionPath, resolvePath, getCollectionMetadata;
11
+ try {
12
+ const registry = require('../../../../../../config/collection_registry');
13
+ getCollectionPath = registry.getCollectionPath;
14
+ resolvePath = registry.resolvePath;
15
+ getCollectionMetadata = registry.getCollectionMetadata;
16
+ } catch (error) {
17
+ // Registry will be injected via dependencies
18
+ getCollectionPath = null;
19
+ resolvePath = null;
20
+ getCollectionMetadata = null;
21
+ }
22
+
23
+ /**
24
+ * Get registry functions from options or fallback to module-level
25
+ * @param {object} options - Options object that may contain collectionRegistry
26
+ * @returns {object} - Object with getCollectionPath, resolvePath, getCollectionMetadata
27
+ */
28
+ function getRegistryFunctions(options = {}) {
29
+ // Try to get from options first (injected)
30
+ if (options.collectionRegistry) {
31
+ return {
32
+ getCollectionPath: options.collectionRegistry.getCollectionPath,
33
+ resolvePath: options.collectionRegistry.resolvePath || resolvePath,
34
+ getCollectionMetadata: options.collectionRegistry.getCollectionMetadata || options.collectionRegistry.getCollectionMetadata
35
+ };
36
+ }
37
+
38
+ // Fallback to module-level (if required successfully)
39
+ if (getCollectionPath && resolvePath && getCollectionMetadata) {
40
+ return { getCollectionPath, resolvePath, getCollectionMetadata };
41
+ }
42
+
43
+ // Last resort: try to require again (in case it's available now)
44
+ try {
45
+ const registry = require('../../../../../../config/collection_registry');
46
+ return {
47
+ getCollectionPath: registry.getCollectionPath,
48
+ resolvePath: registry.resolvePath,
49
+ getCollectionMetadata: registry.getCollectionMetadata
50
+ };
51
+ } catch (error) {
52
+ throw new Error('Collection registry functions not available. Please provide collectionRegistry in dependencies.');
53
+ }
54
+ }
9
55
 
10
56
  /**
11
57
  * Get eToro CID from Firebase UID
@@ -30,11 +76,13 @@ async function getCidFromFirebaseUid(db, firebaseUid) {
30
76
  * @param {string} category - Registry category (e.g., 'signedInUsers')
31
77
  * @param {string} subcategory - Subcategory name (e.g., 'notifications')
32
78
  * @param {object} params - Dynamic segment values (e.g., { cid: '123' })
79
+ * @param {object} options - Options object that may contain collectionRegistry
33
80
  * @returns {string} - Resolved path
34
81
  */
35
- function getNewPath(category, subcategory, params = {}) {
82
+ function getNewPath(category, subcategory, params = {}, options = {}) {
36
83
  try {
37
- return getCollectionPath(category, subcategory, params);
84
+ const { getCollectionPath: getPath } = getRegistryFunctions(options);
85
+ return getPath(category, subcategory, params);
38
86
  } catch (error) {
39
87
  console.error(`[getNewPath] Error resolving path for ${category}/${subcategory}:`, error.message);
40
88
  throw error;
@@ -64,11 +112,12 @@ function getNewPath(category, subcategory, params = {}) {
64
112
  * @param {string} subcategory - Registry subcategory (e.g., 'notifications', 'alerts') - optional
65
113
  * @returns {string|null} - Legacy path template or null if no legacy path exists
66
114
  */
67
- function getLegacyPath(dataType, userCid, config = {}, params = {}, category = null, subcategory = null) {
115
+ function getLegacyPath(dataType, userCid, config = {}, params = {}, category = null, subcategory = null, options = {}) {
68
116
  // Try to get legacy paths from collection registry first
69
117
  if (category && subcategory) {
70
118
  try {
71
- const metadata = getCollectionMetadata(category, subcategory);
119
+ const { getCollectionMetadata: getMetadata, resolvePath: resolve } = getRegistryFunctions(options);
120
+ const metadata = getMetadata(category, subcategory);
72
121
  if (metadata && metadata.legacyPaths && metadata.legacyPaths.length > 0) {
73
122
  // Use first legacy path from registry (can be enhanced to try multiple)
74
123
  let legacyPathTemplate = metadata.legacyPaths[0];
@@ -92,7 +141,7 @@ function getLegacyPath(dataType, userCid, config = {}, params = {}, category = n
92
141
  };
93
142
 
94
143
  // Resolve path template
95
- legacyPathTemplate = resolvePath(legacyPathTemplate, resolvedParams);
144
+ legacyPathTemplate = resolve(legacyPathTemplate, resolvedParams);
96
145
 
97
146
  // Replace any remaining placeholders
98
147
  for (const [key, value] of Object.entries(resolvedParams)) {
@@ -183,15 +232,19 @@ async function readWithMigration(db, category, subcategory, params, options = {}
183
232
  dataType = null,
184
233
  config = {},
185
234
  logger = null,
186
- documentId = null
235
+ documentId = null,
236
+ collectionRegistry = null
187
237
  } = options;
188
238
 
239
+ // Add collectionRegistry to options for registry function access
240
+ const registryOptions = { collectionRegistry };
241
+
189
242
  const userCid = params.cid || params.userCid;
190
243
 
191
244
  // Get new path from registry
192
245
  let newPath;
193
246
  try {
194
- newPath = getNewPath(category, subcategory, params);
247
+ newPath = getNewPath(category, subcategory, params, registryOptions);
195
248
  } catch (error) {
196
249
  if (logger) logger.log('WARN', `[readWithMigration] Could not resolve new path for ${category}/${subcategory}: ${error.message}`);
197
250
  newPath = null;
@@ -224,7 +277,7 @@ async function readWithMigration(db, category, subcategory, params, options = {}
224
277
 
225
278
  // Fallback to legacy path
226
279
  if (dataType && userCid) {
227
- const legacyPathTemplate = getLegacyPath(dataType, userCid, config, params);
280
+ const legacyPathTemplate = getLegacyPath(dataType, userCid, config, params, category, subcategory, registryOptions);
228
281
  if (legacyPathTemplate) {
229
282
  try {
230
283
  // Resolve legacy path (may have additional params like date, username)
@@ -388,20 +441,25 @@ async function writeWithMigration(db, category, subcategory, params, data, optio
388
441
  dataType = null,
389
442
  config = {},
390
443
  documentId = null,
391
- dualWrite = true // Default to dual write during migration period
444
+ dualWrite = true, // Default to dual write during migration period
445
+ collectionRegistry = null
392
446
  } = options;
393
447
 
448
+ // Add collectionRegistry to options for registry function access
449
+ const registryOptions = { collectionRegistry };
450
+
394
451
  const userCid = params.cid || params.userCid;
395
452
 
396
453
  // Get new path
397
- const newPath = getNewPath(category, subcategory, params);
454
+ const newPath = getNewPath(category, subcategory, params, registryOptions);
398
455
 
399
456
  // Get legacy path if dual write is enabled
400
457
  let legacyPath = null;
401
458
  if (dualWrite && dataType && userCid) {
402
- legacyPath = getLegacyPath(dataType, userCid, config);
459
+ const { resolvePath: resolve } = getRegistryFunctions(registryOptions);
460
+ legacyPath = getLegacyPath(dataType, userCid, config, params, null, null, registryOptions);
403
461
  if (legacyPath) {
404
- legacyPath = resolvePath(legacyPath, params);
462
+ legacyPath = resolve(legacyPath, params);
405
463
  }
406
464
  }
407
465
 
@@ -463,14 +521,14 @@ async function writeWithMigration(db, category, subcategory, params, data, optio
463
521
 
464
522
  /**
465
523
  * Get collection path helper (for backward compatibility)
466
- * @param {object} collectionRegistry - Collection registry (not used, kept for compatibility)
524
+ * @param {object} collectionRegistry - Collection registry (injected)
467
525
  * @param {string} category - Registry category
468
526
  * @param {string} subcategory - Subcategory name
469
527
  * @param {object} params - Path parameters
470
528
  * @returns {string} - Resolved path
471
529
  */
472
530
  function getCollectionPathHelper(collectionRegistry, category, subcategory, params = {}) {
473
- return getNewPath(category, subcategory, params);
531
+ return getNewPath(category, subcategory, params, { collectionRegistry });
474
532
  }
475
533
 
476
534
  module.exports = {
@@ -5,7 +5,7 @@
5
5
 
6
6
  const { findLatestPortfolioDate } = require('../core/data_lookup_helpers');
7
7
  const { checkIfUserIsPI } = require('../core/user_status_helpers');
8
- const { getEffectiveCid, getDevOverride } = require('../dev_helpers');
8
+ const { getEffectiveCid, getDevOverride } = require('../dev/dev_helpers');
9
9
 
10
10
  /**
11
11
  * GET /user/me/portfolio
@@ -26,7 +26,8 @@ async function getPiAnalytics(req, res, dependencies, config) {
26
26
  isCollection: false,
27
27
  dataType: 'piAnalytics',
28
28
  config,
29
- documentId: String(cid)
29
+ documentId: String(cid),
30
+ collectionRegistry: dependencies.collectionRegistry
30
31
  }
31
32
  );
32
33
 
@@ -50,7 +50,8 @@ async function trackProfileView(req, res, dependencies, config) {
50
50
  isCollection: false,
51
51
  dataType: 'piProfileViews',
52
52
  config,
53
- documentId: today
53
+ documentId: today,
54
+ collectionRegistry: dependencies.collectionRegistry
54
55
  }
55
56
  );
56
57
 
@@ -77,7 +78,8 @@ async function trackProfileView(req, res, dependencies, config) {
77
78
  dataType: 'piProfileViews',
78
79
  config,
79
80
  documentId: today,
80
- dualWrite: true
81
+ dualWrite: true,
82
+ collectionRegistry: dependencies.collectionRegistry
81
83
  }
82
84
  );
83
85
 
@@ -105,7 +107,8 @@ async function trackProfileView(req, res, dependencies, config) {
105
107
  dataType: 'piIndividualViews',
106
108
  config,
107
109
  documentId: viewId,
108
- dualWrite: true
110
+ dualWrite: true,
111
+ collectionRegistry: dependencies.collectionRegistry
109
112
  }
110
113
  );
111
114
  }
@@ -62,6 +62,7 @@ async function getUserVerification(req, res, dependencies, config) {
62
62
  'verification',
63
63
  { cid: effectiveCid },
64
64
  {
65
+ collectionRegistry: dependencies.collectionRegistry,
65
66
  isCollection: false,
66
67
  dataType: 'verification',
67
68
  config,
@@ -29,7 +29,8 @@ async function getUserRecommendations(req, res, dependencies, config, type = 'he
29
29
  dataType: 'recommendations',
30
30
  config,
31
31
  logger,
32
- documentId: type
32
+ documentId: type,
33
+ collectionRegistry: dependencies.collectionRegistry
33
34
  }
34
35
  );
35
36
 
@@ -86,7 +86,8 @@ async function checkPisInRankings(req, res, dependencies, config) {
86
86
  dataType: 'watchlists',
87
87
  config,
88
88
  logger,
89
- documentId: id
89
+ documentId: id,
90
+ collectionRegistry: dependencies.collectionRegistry
90
91
  }
91
92
  );
92
93
 
@@ -31,7 +31,8 @@ async function getWatchlistTriggerCounts(req, res, dependencies, config) {
31
31
  dataType: 'watchlists',
32
32
  config,
33
33
  logger,
34
- documentId: id
34
+ documentId: id,
35
+ collectionRegistry: dependencies.collectionRegistry
35
36
  }
36
37
  );
37
38
 
@@ -33,7 +33,8 @@ async function getWatchlist(req, res, dependencies, config) {
33
33
  isCollection: true,
34
34
  dataType: 'watchlists',
35
35
  config,
36
- logger
36
+ logger,
37
+ collectionRegistry: dependencies.collectionRegistry
37
38
  }
38
39
  );
39
40
 
@@ -115,7 +116,8 @@ async function updateWatchlist(req, res, dependencies, config) {
115
116
  dataType: 'watchlists',
116
117
  config,
117
118
  documentId: entryId,
118
- dualWrite: true
119
+ dualWrite: true,
120
+ collectionRegistry: dependencies.collectionRegistry
119
121
  }
120
122
  );
121
123
 
@@ -211,7 +211,8 @@ async function autoGenerateWatchlist(req, res, dependencies, config) {
211
211
  isCollection: true,
212
212
  dataType: 'watchlists',
213
213
  config,
214
- logger
214
+ logger,
215
+ collectionRegistry: dependencies.collectionRegistry
215
216
  }
216
217
  );
217
218
 
@@ -237,7 +238,8 @@ async function autoGenerateWatchlist(req, res, dependencies, config) {
237
238
  dataType: 'watchlists',
238
239
  config,
239
240
  documentId: watchlistId,
240
- dualWrite: true
241
+ dualWrite: true,
242
+ collectionRegistry: dependencies.collectionRegistry
241
243
  }
242
244
  );
243
245
  logger.log('SUCCESS', `[autoGenerateWatchlist] Updated auto-generated watchlist ${watchlistId} for user ${userCid}`);
@@ -278,6 +280,7 @@ async function autoGenerateWatchlist(req, res, dependencies, config) {
278
280
  merge: false,
279
281
  dataType: 'watchlists',
280
282
  config,
283
+ collectionRegistry: dependencies.collectionRegistry,
281
284
  documentId: watchlistId,
282
285
  dualWrite: true
283
286
  }
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "bulltrackers-module",
3
- "version": "1.0.507",
3
+ "version": "1.0.509",
4
4
  "description": "Helper Functions for Bulltrackers.",
5
5
  "main": "index.js",
6
6
  "files": [