@blackcode_sa/metaestetics-api 1.6.14 → 1.6.16

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.
@@ -1,22 +1,62 @@
1
1
  import * as admin from "firebase-admin";
2
2
  import { Timestamp as ClientTimestamp } from "firebase/firestore";
3
3
 
4
+ /**
5
+ * Detect if we're running in a server environment (like Cloud Functions)
6
+ * or compiled for server usage
7
+ */
8
+ const IS_SERVER_ENV =
9
+ process.env.NODE_ENV === "production" ||
10
+ process.env.FUNCTIONS_EMULATOR === "true" ||
11
+ process.env.FIREBASE_CONFIG !== undefined;
12
+
4
13
  /**
5
14
  * Utilities for managing timestamps across client and server-side Firebase code.
6
15
  * This module provides conversion functions to ensure timestamp compatibility
7
16
  * between admin and client Firebase SDKs.
8
17
  */
9
18
  export class TimestampUtils {
19
+ /**
20
+ * Flag to force server mode where admin timestamps are preserved
21
+ * This should be true in Cloud Functions environments
22
+ */
23
+ private static serverMode = IS_SERVER_ENV;
24
+
25
+ /**
26
+ * Enables server mode where admin timestamps are preserved when saving
27
+ * to Firestore via the admin SDK
28
+ */
29
+ static enableServerMode(): void {
30
+ this.serverMode = true;
31
+ }
32
+
33
+ /**
34
+ * Disables server mode - use this only for client-side or mixed environments
35
+ */
36
+ static disableServerMode(): void {
37
+ this.serverMode = false;
38
+ }
39
+
10
40
  /**
11
41
  * Converts an admin Firestore Timestamp to a client Firestore Timestamp
42
+ * In server mode, returns the original admin timestamp for storage consistency
43
+ *
12
44
  * @param adminTimestamp - Admin SDK Timestamp (from firebase-admin)
13
- * @returns A client SDK Timestamp (from firebase/firestore) with same seconds/nanoseconds or null if input is null
45
+ * @returns A client SDK Timestamp (from firebase/firestore) with same seconds/nanoseconds,
46
+ * or the original admin timestamp in server mode,
47
+ * or null if input is null
14
48
  */
15
49
  static adminToClient(
16
50
  adminTimestamp: admin.firestore.Timestamp | null
17
- ): ClientTimestamp | null {
51
+ ): ClientTimestamp | admin.firestore.Timestamp | null {
18
52
  if (!adminTimestamp) return null;
19
53
 
54
+ // In server mode (Cloud Functions), just return the admin timestamp
55
+ if (this.serverMode) {
56
+ return adminTimestamp;
57
+ }
58
+
59
+ // In client mode, convert to client timestamp
20
60
  return new ClientTimestamp(
21
61
  adminTimestamp.seconds,
22
62
  adminTimestamp.nanoseconds
@@ -40,8 +80,21 @@ export class TimestampUtils {
40
80
  }
41
81
 
42
82
  /**
43
- * Creates a client-compatible timestamp for the current time
44
- * @returns A client SDK Timestamp (from firebase/firestore) for the current time
83
+ * Creates a timestamp for the current time in the appropriate format based on environment
84
+ * @returns A timestamp for the current time (admin timestamp in server mode, client in client mode)
85
+ */
86
+ static nowAsTimestamp(): admin.firestore.Timestamp | ClientTimestamp {
87
+ const now = admin.firestore.Timestamp.now();
88
+ // In server mode, return the admin timestamp directly
89
+ if (this.serverMode) {
90
+ return now;
91
+ }
92
+ // In client mode, convert to client timestamp
93
+ return this.adminToClient(now) as ClientTimestamp;
94
+ }
95
+
96
+ /**
97
+ * @deprecated Use nowAsTimestamp() instead for better cross-environment compatibility
45
98
  */
46
99
  static nowAsClient(): ClientTimestamp {
47
100
  const now = admin.firestore.Timestamp.now();
@@ -49,33 +102,87 @@ export class TimestampUtils {
49
102
  }
50
103
 
51
104
  /**
52
- * Converts a Date object to a client Firestore Timestamp
105
+ * Converts a Date object to a timestamp in the appropriate format based on environment
53
106
  * @param date - JavaScript Date object
54
- * @returns A client SDK Timestamp (from firebase/firestore) or null if input is null
107
+ * @returns A timestamp (admin timestamp in server mode, client in client mode) or null if input is null
55
108
  */
56
- static dateToClientTimestamp(date: Date | null): ClientTimestamp | null {
109
+ static dateToTimestamp(
110
+ date: Date | null
111
+ ): admin.firestore.Timestamp | ClientTimestamp | null {
57
112
  if (!date) return null;
58
113
 
114
+ if (this.serverMode) {
115
+ return admin.firestore.Timestamp.fromDate(date);
116
+ }
117
+
59
118
  return ClientTimestamp.fromDate(date);
60
119
  }
61
120
 
62
121
  /**
63
- * Converts a Date object to an admin Firestore Timestamp
64
- * @param date - JavaScript Date object
65
- * @returns An admin SDK Timestamp (from firebase-admin) or null if input is null
122
+ * @deprecated Use dateToTimestamp() instead for better cross-environment compatibility
123
+ */
124
+ static dateToClientTimestamp(date: Date | null): ClientTimestamp | null {
125
+ if (!date) return null;
126
+ return ClientTimestamp.fromDate(date);
127
+ }
128
+
129
+ /**
130
+ * @deprecated Use dateToTimestamp() instead for better cross-environment compatibility
66
131
  */
67
132
  static dateToAdminTimestamp(
68
133
  date: Date | null
69
134
  ): admin.firestore.Timestamp | null {
70
135
  if (!date) return null;
71
-
72
136
  return admin.firestore.Timestamp.fromDate(date);
73
137
  }
74
138
 
75
139
  /**
76
- * Deeply converts all admin Firestore Timestamps in an object to client Firestore Timestamps
77
- * @param obj - Object that may contain admin Firestore Timestamps
78
- * @returns The same object with all admin Timestamps converted to client Timestamps
140
+ * Gets a server timestamp field value for use in create/update operations
141
+ * Works in both admin and client environments
142
+ */
143
+ static serverTimestamp(): admin.firestore.FieldValue | any {
144
+ if (this.serverMode) {
145
+ return admin.firestore.FieldValue.serverTimestamp();
146
+ }
147
+ // In client mode, we'd need to import from firebase/firestore
148
+ // This would be implemented for client environments
149
+ throw new Error("Server timestamp in client mode not implemented");
150
+ }
151
+
152
+ /**
153
+ * For objects with mixed timestamp types, ensures all timestamps are
154
+ * in the correct format for the current environment
155
+ */
156
+ static normalizeTimestamps<T>(obj: T): T {
157
+ if (!obj || typeof obj !== "object") {
158
+ return obj;
159
+ }
160
+
161
+ if (obj instanceof admin.firestore.Timestamp) {
162
+ return this.serverMode ? obj : (this.adminToClient(obj) as unknown as T);
163
+ }
164
+
165
+ if (obj instanceof ClientTimestamp && this.serverMode) {
166
+ return this.clientToAdmin(obj) as unknown as T;
167
+ }
168
+
169
+ if (Array.isArray(obj)) {
170
+ return obj.map((item) => this.normalizeTimestamps(item)) as unknown as T;
171
+ }
172
+
173
+ const result = { ...obj } as any;
174
+
175
+ for (const key in result) {
176
+ if (Object.prototype.hasOwnProperty.call(result, key)) {
177
+ result[key] = this.normalizeTimestamps(result[key]);
178
+ }
179
+ }
180
+
181
+ return result as T;
182
+ }
183
+
184
+ /**
185
+ * @deprecated Use normalizeTimestamps() instead for better cross-environment compatibility
79
186
  */
80
187
  static convertObjectTimestampsAdminToClient<T>(obj: T): T {
81
188
  if (!obj || typeof obj !== "object") {
@@ -104,9 +211,7 @@ export class TimestampUtils {
104
211
  }
105
212
 
106
213
  /**
107
- * Deeply converts all client Firestore Timestamps in an object to admin Firestore Timestamps
108
- * @param obj - Object that may contain client Firestore Timestamps
109
- * @returns The same object with all client Timestamps converted to admin Timestamps
214
+ * @deprecated Use normalizeTimestamps() instead for better cross-environment compatibility
110
215
  */
111
216
  static convertObjectTimestampsClientToAdmin<T>(obj: T): T {
112
217
  if (!obj || typeof obj !== "object") {