@adtrackify/at-service-common 4.0.13 → 4.0.14
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/cjs/__tests__/identity-cache/helpers.spec.js +37 -38
- package/dist/cjs/__tests__/identity-cache/helpers.spec.js.map +1 -1
- package/dist/cjs/__tests__/identity-cache/identity-cache-tier-routing.spec.js +83 -344
- package/dist/cjs/__tests__/identity-cache/identity-cache-tier-routing.spec.js.map +1 -1
- package/dist/cjs/__tests__/identity-cache/identity-client.spec.js +360 -0
- package/dist/cjs/__tests__/identity-cache/identity-client.spec.js.map +1 -0
- package/dist/cjs/__tests__/identity-cache/identity-gateway-service.spec.js +335 -1261
- package/dist/cjs/__tests__/identity-cache/identity-gateway-service.spec.js.map +1 -1
- package/dist/cjs/clients/internal-api/identity-client.d.ts +12 -2
- package/dist/cjs/clients/internal-api/identity-client.js +59 -13
- package/dist/cjs/clients/internal-api/identity-client.js.map +1 -1
- package/dist/cjs/services/db/identity-cache-dynamodb-service/identity-cache-dynamodb-db-service.d.ts +1 -7
- package/dist/cjs/services/db/identity-cache-dynamodb-service/identity-cache-dynamodb-db-service.js +0 -305
- package/dist/cjs/services/db/identity-cache-dynamodb-service/identity-cache-dynamodb-db-service.js.map +1 -1
- package/dist/cjs/services/db/identity-cache-dynamodb-service/identity-gateway-service.d.ts +10 -9
- package/dist/cjs/services/db/identity-cache-dynamodb-service/identity-gateway-service.js +116 -321
- package/dist/cjs/services/db/identity-cache-dynamodb-service/identity-gateway-service.js.map +1 -1
- package/dist/cjs/services/db/identity-cache-dynamodb-service/index.d.ts +0 -1
- package/dist/cjs/services/db/identity-cache-dynamodb-service/index.js +0 -1
- package/dist/cjs/services/db/identity-cache-dynamodb-service/index.js.map +1 -1
- package/dist/cjs/services/db/identity-cache-dynamodb-service/types.d.ts +9 -157
- package/dist/cjs/services/db/identity-cache-dynamodb-service/types.js +1 -15
- package/dist/cjs/services/db/identity-cache-dynamodb-service/types.js.map +1 -1
- package/dist/esm/__tests__/identity-cache/helpers.spec.js +26 -27
- package/dist/esm/__tests__/identity-cache/helpers.spec.js.map +1 -1
- package/dist/esm/__tests__/identity-cache/identity-cache-tier-routing.spec.js +83 -344
- package/dist/esm/__tests__/identity-cache/identity-cache-tier-routing.spec.js.map +1 -1
- package/dist/esm/__tests__/identity-cache/identity-client.spec.js +358 -0
- package/dist/esm/__tests__/identity-cache/identity-client.spec.js.map +1 -0
- package/dist/esm/__tests__/identity-cache/identity-gateway-service.spec.js +335 -1261
- package/dist/esm/__tests__/identity-cache/identity-gateway-service.spec.js.map +1 -1
- package/dist/esm/clients/internal-api/identity-client.d.ts +12 -2
- package/dist/esm/clients/internal-api/identity-client.js +60 -14
- package/dist/esm/clients/internal-api/identity-client.js.map +1 -1
- package/dist/esm/services/db/identity-cache-dynamodb-service/identity-cache-dynamodb-db-service.d.ts +1 -7
- package/dist/esm/services/db/identity-cache-dynamodb-service/identity-cache-dynamodb-db-service.js +1 -303
- package/dist/esm/services/db/identity-cache-dynamodb-service/identity-cache-dynamodb-db-service.js.map +1 -1
- package/dist/esm/services/db/identity-cache-dynamodb-service/identity-gateway-service.d.ts +10 -9
- package/dist/esm/services/db/identity-cache-dynamodb-service/identity-gateway-service.js +119 -321
- package/dist/esm/services/db/identity-cache-dynamodb-service/identity-gateway-service.js.map +1 -1
- package/dist/esm/services/db/identity-cache-dynamodb-service/index.d.ts +0 -1
- package/dist/esm/services/db/identity-cache-dynamodb-service/index.js +0 -1
- package/dist/esm/services/db/identity-cache-dynamodb-service/index.js.map +1 -1
- package/dist/esm/services/db/identity-cache-dynamodb-service/types.d.ts +9 -157
- package/dist/esm/services/db/identity-cache-dynamodb-service/types.js +0 -14
- package/dist/esm/services/db/identity-cache-dynamodb-service/types.js.map +1 -1
- package/package.json +2 -2
- package/dist/cjs/__tests__/identity-cache/identity-cache-dynamodb-db-service-v2-comparison.spec.js +0 -646
- package/dist/cjs/__tests__/identity-cache/identity-cache-dynamodb-db-service-v2-comparison.spec.js.map +0 -1
- package/dist/cjs/__tests__/identity-cache/identity-cache-dynamodb-service-v2-comparison.spec.js +0 -325
- package/dist/cjs/__tests__/identity-cache/identity-cache-dynamodb-service-v2-comparison.spec.js.map +0 -1
- package/dist/cjs/__tests__/identity-cache/identity-cache-dynamodb-service.spec.d.ts +0 -1
- package/dist/cjs/__tests__/identity-cache/identity-cache-dynamodb-service.spec.js +0 -1286
- package/dist/cjs/__tests__/identity-cache/identity-cache-dynamodb-service.spec.js.map +0 -1
- package/dist/cjs/services/db/identity-cache-dynamodb-service/helpers.d.ts +0 -26
- package/dist/cjs/services/db/identity-cache-dynamodb-service/helpers.js +0 -252
- package/dist/cjs/services/db/identity-cache-dynamodb-service/helpers.js.map +0 -1
- package/dist/esm/__tests__/identity-cache/identity-cache-dynamodb-db-service-v2-comparison.spec.d.ts +0 -1
- package/dist/esm/__tests__/identity-cache/identity-cache-dynamodb-db-service-v2-comparison.spec.js +0 -644
- package/dist/esm/__tests__/identity-cache/identity-cache-dynamodb-db-service-v2-comparison.spec.js.map +0 -1
- package/dist/esm/__tests__/identity-cache/identity-cache-dynamodb-service-v2-comparison.spec.d.ts +0 -1
- package/dist/esm/__tests__/identity-cache/identity-cache-dynamodb-service-v2-comparison.spec.js +0 -323
- package/dist/esm/__tests__/identity-cache/identity-cache-dynamodb-service-v2-comparison.spec.js.map +0 -1
- package/dist/esm/__tests__/identity-cache/identity-cache-dynamodb-service.spec.d.ts +0 -1
- package/dist/esm/__tests__/identity-cache/identity-cache-dynamodb-service.spec.js +0 -1284
- package/dist/esm/__tests__/identity-cache/identity-cache-dynamodb-service.spec.js.map +0 -1
- package/dist/esm/services/db/identity-cache-dynamodb-service/helpers.d.ts +0 -26
- package/dist/esm/services/db/identity-cache-dynamodb-service/helpers.js +0 -235
- package/dist/esm/services/db/identity-cache-dynamodb-service/helpers.js.map +0 -1
- /package/dist/cjs/__tests__/identity-cache/{identity-cache-dynamodb-db-service-v2-comparison.spec.d.ts → identity-client.spec.d.ts} +0 -0
- /package/dist/{cjs/__tests__/identity-cache/identity-cache-dynamodb-service-v2-comparison.spec.d.ts → esm/__tests__/identity-cache/identity-client.spec.d.ts} +0 -0
|
@@ -1,7 +1,5 @@
|
|
|
1
1
|
import { ADDRESS_INFO_SOURCE } from '@adtrackify/at-tracking-event-types';
|
|
2
|
-
|
|
3
|
-
import { CACHE_WRITE_REASON } from '../../services/db/identity-cache-dynamodb-service';
|
|
4
|
-
const mockInvokeFunction = jest.fn();
|
|
2
|
+
const mockLambdaInvoke = jest.fn();
|
|
5
3
|
const mockBuildAndSendMessage = jest.fn();
|
|
6
4
|
const mockSQSClientConstructor = jest.fn();
|
|
7
5
|
jest.mock('../../clients/index.js', () => ({
|
|
@@ -15,7 +13,7 @@ jest.mock('../../clients/index.js', () => ({
|
|
|
15
13
|
batchWrite: jest.fn(),
|
|
16
14
|
},
|
|
17
15
|
LambdaInvokeClient: jest.fn().mockImplementation(() => ({
|
|
18
|
-
invokeFunction:
|
|
16
|
+
invokeFunction: mockLambdaInvoke,
|
|
19
17
|
})),
|
|
20
18
|
SQSClient: jest.fn().mockImplementation((_region, _accountId, _queueName) => {
|
|
21
19
|
mockSQSClientConstructor(_region, _accountId, _queueName);
|
|
@@ -33,15 +31,19 @@ jest.mock('../../helpers/index.js', () => ({
|
|
|
33
31
|
error: jest.fn(),
|
|
34
32
|
},
|
|
35
33
|
}));
|
|
34
|
+
const mockGetIdentity = jest.fn();
|
|
35
|
+
jest.mock('../../clients/internal-api/identity-client.js', () => ({
|
|
36
|
+
IdentityClient: jest.fn().mockImplementation(() => ({
|
|
37
|
+
getIdentity: mockGetIdentity,
|
|
38
|
+
})),
|
|
39
|
+
}));
|
|
36
40
|
import { IdentityGatewayService, } from '../../services/db/identity-cache-dynamodb-service/identity-gateway-service.js';
|
|
37
41
|
import { IDENTITY_CACHE_WITH_CACHING_OUTCOME, } from '../../services/db/identity-cache-dynamodb-service/types.js';
|
|
38
|
-
import { IdentityCacheDynamoDbDbService } from '../../services/db/identity-cache-dynamodb-service/identity-cache-dynamodb-db-service.js';
|
|
39
42
|
import { DynamoDbClient, SQSClient } from '../../clients/index.js';
|
|
40
43
|
const mockedDynamoDbClient = DynamoDbClient;
|
|
41
44
|
const _mockedSQSClient = SQSClient;
|
|
42
45
|
describe('Identity Cache Three-Tier Routing', () => {
|
|
43
46
|
const pixelId = 'pixel123';
|
|
44
|
-
const lambdaArn = 'arn:aws:lambda:us-east-1:123456789:function:identity-private';
|
|
45
47
|
beforeEach(() => {
|
|
46
48
|
jest.clearAllMocks();
|
|
47
49
|
mockedDynamoDbClient.safeGet.mockReset();
|
|
@@ -51,13 +53,14 @@ describe('Identity Cache Three-Tier Routing', () => {
|
|
|
51
53
|
mockedDynamoDbClient.safeBatchWrite.mockReset();
|
|
52
54
|
mockedDynamoDbClient.safeQueryByGSI.mockReset();
|
|
53
55
|
mockedDynamoDbClient.batchWrite.mockReset();
|
|
54
|
-
|
|
56
|
+
mockGetIdentity.mockReset();
|
|
55
57
|
mockBuildAndSendMessage.mockReset();
|
|
56
58
|
mockSQSClientConstructor.mockReset();
|
|
57
59
|
_mockedSQSClient.mockClear();
|
|
58
|
-
IdentityGatewayService.
|
|
60
|
+
IdentityGatewayService.identityClient = undefined;
|
|
59
61
|
IdentityGatewayService.sqsClient = undefined;
|
|
60
62
|
IdentityGatewayService.sqsQueueUrl = undefined;
|
|
63
|
+
IdentityGatewayService.configure({ identifyPrivateLambdaArn: 'arn:aws:lambda:us-east-1:123456789:function:identity-private' });
|
|
61
64
|
});
|
|
62
65
|
describe('TIER: VOLATILE_ONLY — Returns merged identity, NO Neptune, NO cache write', () => {
|
|
63
66
|
it('should return merged identity without Neptune call when only ipAddress is stale', async () => {
|
|
@@ -82,10 +85,10 @@ describe('Identity Cache Three-Tier Routing', () => {
|
|
|
82
85
|
updatedAt: new Date().toISOString(),
|
|
83
86
|
};
|
|
84
87
|
mockedDynamoDbClient.safeGet.mockResolvedValueOnce(cachedResponse);
|
|
85
|
-
const result = await IdentityGatewayService.
|
|
88
|
+
const result = await IdentityGatewayService.resolveIdentityWithCaching(pixelId, incomingIdentity);
|
|
86
89
|
expect(result.identity).toBeDefined();
|
|
87
90
|
expect(result.identity?.identityId).toBe('identity456');
|
|
88
|
-
expect(
|
|
91
|
+
expect(mockGetIdentity).not.toHaveBeenCalled();
|
|
89
92
|
expect(mockedDynamoDbClient.safeBatchWrite).not.toHaveBeenCalled();
|
|
90
93
|
});
|
|
91
94
|
it('should return merged identity without Neptune call when only userAgent is stale', async () => {
|
|
@@ -110,9 +113,9 @@ describe('Identity Cache Three-Tier Routing', () => {
|
|
|
110
113
|
updatedAt: new Date().toISOString(),
|
|
111
114
|
};
|
|
112
115
|
mockedDynamoDbClient.safeGet.mockResolvedValueOnce(cachedResponse);
|
|
113
|
-
const result = await IdentityGatewayService.
|
|
116
|
+
const result = await IdentityGatewayService.resolveIdentityWithCaching(pixelId, incomingIdentity);
|
|
114
117
|
expect(result.identity).toBeDefined();
|
|
115
|
-
expect(
|
|
118
|
+
expect(mockGetIdentity).not.toHaveBeenCalled();
|
|
116
119
|
expect(mockedDynamoDbClient.safeBatchWrite).not.toHaveBeenCalled();
|
|
117
120
|
});
|
|
118
121
|
it('should return merged identity without Neptune call when only IP-sourced addresses are stale', async () => {
|
|
@@ -137,117 +140,12 @@ describe('Identity Cache Three-Tier Routing', () => {
|
|
|
137
140
|
updatedAt: new Date().toISOString(),
|
|
138
141
|
};
|
|
139
142
|
mockedDynamoDbClient.safeGet.mockResolvedValueOnce(cachedResponse);
|
|
140
|
-
const result = await IdentityGatewayService.
|
|
143
|
+
const result = await IdentityGatewayService.resolveIdentityWithCaching(pixelId, incomingIdentity);
|
|
141
144
|
expect(result.identity).toBeDefined();
|
|
142
|
-
expect(
|
|
145
|
+
expect(mockGetIdentity).not.toHaveBeenCalled();
|
|
143
146
|
expect(mockedDynamoDbClient.safeBatchWrite).not.toHaveBeenCalled();
|
|
144
147
|
});
|
|
145
148
|
});
|
|
146
|
-
describe('TIER: ADDRESS_UPDATE — Enqueues async update, NO Neptune call, NO sync cache write', () => {
|
|
147
|
-
it('should enqueue async update but skip Neptune when new non-IP address is added', async () => {
|
|
148
|
-
IdentityGatewayService.configure({
|
|
149
|
-
awsRegion: 'us-east-1',
|
|
150
|
-
awsAccountId: '123456789',
|
|
151
|
-
asyncUpdateQueueName: 'test-queue',
|
|
152
|
-
});
|
|
153
|
-
mockBuildAndSendMessage.mockResolvedValueOnce({ MessageId: 'test-msg-id' });
|
|
154
|
-
const incomingIdentity = {
|
|
155
|
-
identityId: 'identity456',
|
|
156
|
-
traits: {
|
|
157
|
-
emails: ['test@email.com'],
|
|
158
|
-
addresses: [{ city: 'Boston', firstName: 'John', s: ADDRESS_INFO_SOURCE.INPUT }],
|
|
159
|
-
},
|
|
160
|
-
};
|
|
161
|
-
const cachedResponse = {
|
|
162
|
-
pk: `identity#${pixelId}#identity456`,
|
|
163
|
-
pixelId,
|
|
164
|
-
identityId: 'identity456',
|
|
165
|
-
response: {
|
|
166
|
-
identityId: 'identity456',
|
|
167
|
-
traits: {
|
|
168
|
-
emails: ['test@email.com'],
|
|
169
|
-
addresses: [],
|
|
170
|
-
},
|
|
171
|
-
},
|
|
172
|
-
updatedAt: new Date().toISOString(),
|
|
173
|
-
};
|
|
174
|
-
mockedDynamoDbClient.safeGet.mockResolvedValueOnce(cachedResponse);
|
|
175
|
-
const result = await IdentityGatewayService.getIdentityWithCachingV2(pixelId, incomingIdentity, lambdaArn);
|
|
176
|
-
expect(result.identity).toBeDefined();
|
|
177
|
-
expect(result.identity?.traits?.addresses).toHaveLength(1);
|
|
178
|
-
expect(mockInvokeFunction).not.toHaveBeenCalled();
|
|
179
|
-
expect(mockedDynamoDbClient.safeBatchWrite).not.toHaveBeenCalled();
|
|
180
|
-
expect(mockBuildAndSendMessage).toHaveBeenCalled();
|
|
181
|
-
});
|
|
182
|
-
it('should enqueue async update and skip Neptune when address with PII but no source is added', async () => {
|
|
183
|
-
IdentityGatewayService.configure({
|
|
184
|
-
awsRegion: 'us-east-1',
|
|
185
|
-
awsAccountId: '123456789',
|
|
186
|
-
asyncUpdateQueueName: 'test-queue',
|
|
187
|
-
});
|
|
188
|
-
mockBuildAndSendMessage.mockResolvedValueOnce({ MessageId: 'test-msg-id' });
|
|
189
|
-
const incomingIdentity = {
|
|
190
|
-
identityId: 'identity456',
|
|
191
|
-
traits: {
|
|
192
|
-
emails: ['test@email.com'],
|
|
193
|
-
addresses: [{ city: 'Miami', lastName: 'Smith' }],
|
|
194
|
-
},
|
|
195
|
-
};
|
|
196
|
-
const cachedResponse = {
|
|
197
|
-
pk: `identity#${pixelId}#identity456`,
|
|
198
|
-
pixelId,
|
|
199
|
-
identityId: 'identity456',
|
|
200
|
-
response: {
|
|
201
|
-
identityId: 'identity456',
|
|
202
|
-
traits: {
|
|
203
|
-
emails: ['test@email.com'],
|
|
204
|
-
addresses: [],
|
|
205
|
-
},
|
|
206
|
-
},
|
|
207
|
-
updatedAt: new Date().toISOString(),
|
|
208
|
-
};
|
|
209
|
-
mockedDynamoDbClient.safeGet.mockResolvedValueOnce(cachedResponse);
|
|
210
|
-
const result = await IdentityGatewayService.getIdentityWithCachingV2(pixelId, incomingIdentity, lambdaArn);
|
|
211
|
-
expect(result.identity).toBeDefined();
|
|
212
|
-
expect(mockInvokeFunction).not.toHaveBeenCalled();
|
|
213
|
-
expect(mockedDynamoDbClient.safeBatchWrite).not.toHaveBeenCalled();
|
|
214
|
-
expect(mockBuildAndSendMessage).toHaveBeenCalled();
|
|
215
|
-
});
|
|
216
|
-
it('should return ADDRESS_UPDATE_ASYNC outcome in summary', async () => {
|
|
217
|
-
IdentityGatewayService.configure({
|
|
218
|
-
awsRegion: 'us-east-1',
|
|
219
|
-
awsAccountId: '123456789',
|
|
220
|
-
asyncUpdateQueueName: 'test-queue',
|
|
221
|
-
});
|
|
222
|
-
mockBuildAndSendMessage.mockResolvedValueOnce({ MessageId: 'test-msg-id' });
|
|
223
|
-
const incomingIdentity = {
|
|
224
|
-
identityId: 'identity456',
|
|
225
|
-
traits: {
|
|
226
|
-
emails: ['test@email.com'],
|
|
227
|
-
addresses: [{ city: 'Seattle', s: ADDRESS_INFO_SOURCE.INPUT }],
|
|
228
|
-
},
|
|
229
|
-
};
|
|
230
|
-
const cachedResponse = {
|
|
231
|
-
pk: `identity#${pixelId}#identity456`,
|
|
232
|
-
pixelId,
|
|
233
|
-
identityId: 'identity456',
|
|
234
|
-
response: {
|
|
235
|
-
identityId: 'identity456',
|
|
236
|
-
traits: {
|
|
237
|
-
emails: ['test@email.com'],
|
|
238
|
-
addresses: [],
|
|
239
|
-
},
|
|
240
|
-
},
|
|
241
|
-
updatedAt: new Date().toISOString(),
|
|
242
|
-
};
|
|
243
|
-
mockedDynamoDbClient.safeGet.mockResolvedValueOnce(cachedResponse);
|
|
244
|
-
const result = await IdentityGatewayService.getIdentityWithCachingV2(pixelId, incomingIdentity, lambdaArn);
|
|
245
|
-
expect(result.summary.outcome).toBe(IDENTITY_CACHE_WITH_CACHING_OUTCOME.ADDRESS_UPDATE_ASYNC);
|
|
246
|
-
expect(result.summary.didSkipNeptune).toBe(true);
|
|
247
|
-
expect(result.summary.didWriteCache).toBe(false);
|
|
248
|
-
expect(result.summary.didEnqueueAsync).toBe(true);
|
|
249
|
-
});
|
|
250
|
-
});
|
|
251
149
|
describe('TIER: IDENTITY_STALE — Calls Neptune AND writes to cache', () => {
|
|
252
150
|
it('should call Neptune and write to cache when emails are stale', async () => {
|
|
253
151
|
const incomingIdentity = {
|
|
@@ -269,18 +167,13 @@ describe('Identity Cache Three-Tier Routing', () => {
|
|
|
269
167
|
updatedAt: new Date().toISOString(),
|
|
270
168
|
};
|
|
271
169
|
mockedDynamoDbClient.safeGet.mockResolvedValueOnce(cachedResponse);
|
|
272
|
-
|
|
273
|
-
|
|
274
|
-
|
|
275
|
-
identity: {
|
|
276
|
-
identityId: 'identity456',
|
|
277
|
-
traits: { emails: ['old@email.com', 'new@email.com', 'resolved@email.com'] },
|
|
278
|
-
},
|
|
279
|
-
}),
|
|
170
|
+
mockGetIdentity.mockResolvedValueOnce({
|
|
171
|
+
identityId: 'identity456',
|
|
172
|
+
traits: { emails: ['old@email.com', 'new@email.com', 'resolved@email.com'] },
|
|
280
173
|
});
|
|
281
|
-
const result = await IdentityGatewayService.
|
|
174
|
+
const result = await IdentityGatewayService.resolveIdentityWithCaching(pixelId, incomingIdentity);
|
|
282
175
|
expect(result.identity).toBeDefined();
|
|
283
|
-
expect(
|
|
176
|
+
expect(mockGetIdentity).toHaveBeenCalled();
|
|
284
177
|
expect(mockedDynamoDbClient.safeBatchWrite).not.toHaveBeenCalled();
|
|
285
178
|
});
|
|
286
179
|
it('should call Neptune and write to cache when phones are stale', async () => {
|
|
@@ -303,18 +196,13 @@ describe('Identity Cache Three-Tier Routing', () => {
|
|
|
303
196
|
updatedAt: new Date().toISOString(),
|
|
304
197
|
};
|
|
305
198
|
mockedDynamoDbClient.safeGet.mockResolvedValueOnce(cachedResponse);
|
|
306
|
-
|
|
307
|
-
|
|
308
|
-
|
|
309
|
-
identity: {
|
|
310
|
-
identityId: 'identity456',
|
|
311
|
-
traits: { phones: ['+1234567890', '+9876543210'] },
|
|
312
|
-
},
|
|
313
|
-
}),
|
|
199
|
+
mockGetIdentity.mockResolvedValueOnce({
|
|
200
|
+
identityId: 'identity456',
|
|
201
|
+
traits: { phones: ['+1234567890', '+9876543210'] },
|
|
314
202
|
});
|
|
315
|
-
const result = await IdentityGatewayService.
|
|
203
|
+
const result = await IdentityGatewayService.resolveIdentityWithCaching(pixelId, incomingIdentity);
|
|
316
204
|
expect(result.identity).toBeDefined();
|
|
317
|
-
expect(
|
|
205
|
+
expect(mockGetIdentity).toHaveBeenCalled();
|
|
318
206
|
expect(mockedDynamoDbClient.safeBatchWrite).not.toHaveBeenCalled();
|
|
319
207
|
});
|
|
320
208
|
it('should return NEPTUNE_WRITE_BACK outcome with staleTraits in summary', async () => {
|
|
@@ -335,20 +223,15 @@ describe('Identity Cache Three-Tier Routing', () => {
|
|
|
335
223
|
updatedAt: new Date().toISOString(),
|
|
336
224
|
};
|
|
337
225
|
mockedDynamoDbClient.safeGet.mockResolvedValueOnce(cachedResponse);
|
|
338
|
-
|
|
339
|
-
|
|
340
|
-
|
|
341
|
-
identity: {
|
|
342
|
-
identityId: 'identity456',
|
|
343
|
-
traits: { emails: ['old@email.com', 'new@email.com'] },
|
|
344
|
-
},
|
|
345
|
-
}),
|
|
226
|
+
mockGetIdentity.mockResolvedValueOnce({
|
|
227
|
+
identityId: 'identity456',
|
|
228
|
+
traits: { emails: ['old@email.com', 'new@email.com'] },
|
|
346
229
|
});
|
|
347
|
-
const result = await IdentityGatewayService.
|
|
348
|
-
expect(result.
|
|
349
|
-
expect(result.
|
|
350
|
-
expect(result.
|
|
351
|
-
expect(result.
|
|
230
|
+
const result = await IdentityGatewayService.resolveIdentityWithCaching(pixelId, incomingIdentity);
|
|
231
|
+
expect(result.outcome).toBe(IDENTITY_CACHE_WITH_CACHING_OUTCOME.NEPTUNE_RESOLVED);
|
|
232
|
+
expect(result.stalenessResult?.staleTraits).toContain('emails');
|
|
233
|
+
expect(result.didCallNeptune).toBe(true);
|
|
234
|
+
expect(result.didWriteCache).toBe(false);
|
|
352
235
|
});
|
|
353
236
|
});
|
|
354
237
|
describe('CACHE_MISS — Calls Neptune AND writes to cache', () => {
|
|
@@ -358,18 +241,13 @@ describe('Identity Cache Three-Tier Routing', () => {
|
|
|
358
241
|
traits: { emails: ['test@email.com'] },
|
|
359
242
|
};
|
|
360
243
|
mockedDynamoDbClient.safeGet.mockResolvedValueOnce(null);
|
|
361
|
-
|
|
362
|
-
|
|
363
|
-
|
|
364
|
-
identity: {
|
|
365
|
-
identityId: 'identity456',
|
|
366
|
-
traits: { emails: ['test@email.com'] },
|
|
367
|
-
},
|
|
368
|
-
}),
|
|
244
|
+
mockGetIdentity.mockResolvedValueOnce({
|
|
245
|
+
identityId: 'identity456',
|
|
246
|
+
traits: { emails: ['test@email.com'] },
|
|
369
247
|
});
|
|
370
|
-
const result = await IdentityGatewayService.
|
|
248
|
+
const result = await IdentityGatewayService.resolveIdentityWithCaching(pixelId, incomingIdentity);
|
|
371
249
|
expect(result.identity).toBeDefined();
|
|
372
|
-
expect(
|
|
250
|
+
expect(mockGetIdentity).toHaveBeenCalled();
|
|
373
251
|
expect(mockedDynamoDbClient.safeBatchWrite).not.toHaveBeenCalled();
|
|
374
252
|
});
|
|
375
253
|
it('should return NEPTUNE_WRITE_BACK outcome for cache miss', async () => {
|
|
@@ -378,19 +256,14 @@ describe('Identity Cache Three-Tier Routing', () => {
|
|
|
378
256
|
traits: { emails: ['test@email.com'] },
|
|
379
257
|
};
|
|
380
258
|
mockedDynamoDbClient.safeGet.mockResolvedValueOnce(null);
|
|
381
|
-
|
|
382
|
-
|
|
383
|
-
|
|
384
|
-
identity: {
|
|
385
|
-
identityId: 'identity456',
|
|
386
|
-
traits: { emails: ['test@email.com'] },
|
|
387
|
-
},
|
|
388
|
-
}),
|
|
259
|
+
mockGetIdentity.mockResolvedValueOnce({
|
|
260
|
+
identityId: 'identity456',
|
|
261
|
+
traits: { emails: ['test@email.com'] },
|
|
389
262
|
});
|
|
390
|
-
const result = await IdentityGatewayService.
|
|
391
|
-
expect(result.
|
|
392
|
-
expect(result.
|
|
393
|
-
expect(result.
|
|
263
|
+
const result = await IdentityGatewayService.resolveIdentityWithCaching(pixelId, incomingIdentity);
|
|
264
|
+
expect(result.outcome).toBe(IDENTITY_CACHE_WITH_CACHING_OUTCOME.NEPTUNE_RESOLVED);
|
|
265
|
+
expect(result.didCallNeptune).toBe(true);
|
|
266
|
+
expect(result.didWriteCache).toBe(false);
|
|
394
267
|
});
|
|
395
268
|
});
|
|
396
269
|
describe('EMAIL_POINTER_DISCOVERY — Calls Neptune with discovered identityId', () => {
|
|
@@ -406,35 +279,28 @@ describe('Identity Cache Three-Tier Routing', () => {
|
|
|
406
279
|
updatedAt: new Date().toISOString(),
|
|
407
280
|
};
|
|
408
281
|
mockedDynamoDbClient.safeGet.mockResolvedValueOnce(pointerRecord);
|
|
409
|
-
|
|
410
|
-
|
|
411
|
-
|
|
412
|
-
identity: {
|
|
413
|
-
identityId: 'discovered-id',
|
|
414
|
-
traits: { emails: ['test@email.com', 'other@email.com'] },
|
|
415
|
-
},
|
|
416
|
-
}),
|
|
282
|
+
mockGetIdentity.mockResolvedValueOnce({
|
|
283
|
+
identityId: 'discovered-id',
|
|
284
|
+
traits: { emails: ['test@email.com', 'other@email.com'] },
|
|
417
285
|
});
|
|
418
|
-
const result = await IdentityGatewayService.
|
|
286
|
+
const result = await IdentityGatewayService.resolveIdentityWithCaching(pixelId, incomingIdentity);
|
|
419
287
|
expect(result.identity?.identityId).toBe('discovered-id');
|
|
420
|
-
expect(
|
|
421
|
-
|
|
422
|
-
|
|
423
|
-
|
|
424
|
-
|
|
425
|
-
},
|
|
288
|
+
expect(mockGetIdentity).toHaveBeenCalledWith(pixelId, expect.objectContaining({
|
|
289
|
+
identity: expect.objectContaining({
|
|
290
|
+
identityId: 'discovered-id',
|
|
291
|
+
traits: expect.objectContaining({ emails: ['test@email.com'] }),
|
|
292
|
+
}),
|
|
426
293
|
}));
|
|
427
294
|
});
|
|
428
295
|
});
|
|
429
296
|
});
|
|
430
297
|
describe('Identity Cache stripAddressTimestamps', () => {
|
|
431
298
|
const pixelId = 'pixel123';
|
|
432
|
-
const lambdaArn = 'arn:aws:lambda:us-east-1:123456789:function:identity-private';
|
|
433
299
|
beforeEach(() => {
|
|
434
300
|
jest.clearAllMocks();
|
|
435
301
|
mockedDynamoDbClient.safeGet.mockReset();
|
|
436
302
|
mockedDynamoDbClient.safeBatchWrite.mockReset();
|
|
437
|
-
|
|
303
|
+
mockGetIdentity.mockReset();
|
|
438
304
|
IdentityGatewayService.lambdaInvokeClient = undefined;
|
|
439
305
|
});
|
|
440
306
|
it('should strip cra and upa from addresses during comparison', async () => {
|
|
@@ -473,9 +339,9 @@ describe('Identity Cache stripAddressTimestamps', () => {
|
|
|
473
339
|
updatedAt: new Date().toISOString(),
|
|
474
340
|
};
|
|
475
341
|
mockedDynamoDbClient.safeGet.mockResolvedValueOnce(cachedResponse);
|
|
476
|
-
const result = await IdentityGatewayService.
|
|
342
|
+
const result = await IdentityGatewayService.resolveIdentityWithCaching(pixelId, incomingIdentity);
|
|
477
343
|
expect(result.identity).toBeDefined();
|
|
478
|
-
expect(
|
|
344
|
+
expect(mockGetIdentity).not.toHaveBeenCalled();
|
|
479
345
|
});
|
|
480
346
|
it('should NOT mutate the original object when stripping timestamps', async () => {
|
|
481
347
|
const originalAddress = {
|
|
@@ -512,7 +378,7 @@ describe('Identity Cache stripAddressTimestamps', () => {
|
|
|
512
378
|
updatedAt: new Date().toISOString(),
|
|
513
379
|
};
|
|
514
380
|
mockedDynamoDbClient.safeGet.mockResolvedValueOnce(cachedResponse);
|
|
515
|
-
await IdentityGatewayService.
|
|
381
|
+
await IdentityGatewayService.resolveIdentityWithCaching(pixelId, incomingIdentity);
|
|
516
382
|
expect(incomingIdentity.traits?.addresses?.[0]).toHaveProperty('cra');
|
|
517
383
|
expect(incomingIdentity.traits?.addresses?.[0]).toHaveProperty('upa');
|
|
518
384
|
expect(cachedResponse.response.traits?.addresses?.[0]).toHaveProperty('cra');
|
|
@@ -538,9 +404,9 @@ describe('Identity Cache stripAddressTimestamps', () => {
|
|
|
538
404
|
updatedAt: new Date().toISOString(),
|
|
539
405
|
};
|
|
540
406
|
mockedDynamoDbClient.safeGet.mockResolvedValueOnce(cachedResponse);
|
|
541
|
-
const result = await IdentityGatewayService.
|
|
407
|
+
const result = await IdentityGatewayService.resolveIdentityWithCaching(pixelId, incomingIdentity);
|
|
542
408
|
expect(result.identity).toBeDefined();
|
|
543
|
-
expect(
|
|
409
|
+
expect(mockGetIdentity).not.toHaveBeenCalled();
|
|
544
410
|
});
|
|
545
411
|
it('should handle identity with empty addresses array', async () => {
|
|
546
412
|
const incomingIdentity = {
|
|
@@ -564,9 +430,9 @@ describe('Identity Cache stripAddressTimestamps', () => {
|
|
|
564
430
|
updatedAt: new Date().toISOString(),
|
|
565
431
|
};
|
|
566
432
|
mockedDynamoDbClient.safeGet.mockResolvedValueOnce(cachedResponse);
|
|
567
|
-
const result = await IdentityGatewayService.
|
|
433
|
+
const result = await IdentityGatewayService.resolveIdentityWithCaching(pixelId, incomingIdentity);
|
|
568
434
|
expect(result.identity).toBeDefined();
|
|
569
|
-
expect(
|
|
435
|
+
expect(mockGetIdentity).not.toHaveBeenCalled();
|
|
570
436
|
});
|
|
571
437
|
it('should handle addresses without cra/upa (no-op)', async () => {
|
|
572
438
|
const incomingIdentity = {
|
|
@@ -590,19 +456,18 @@ describe('Identity Cache stripAddressTimestamps', () => {
|
|
|
590
456
|
updatedAt: new Date().toISOString(),
|
|
591
457
|
};
|
|
592
458
|
mockedDynamoDbClient.safeGet.mockResolvedValueOnce(cachedResponse);
|
|
593
|
-
const result = await IdentityGatewayService.
|
|
459
|
+
const result = await IdentityGatewayService.resolveIdentityWithCaching(pixelId, incomingIdentity);
|
|
594
460
|
expect(result.identity).toBeDefined();
|
|
595
|
-
expect(
|
|
461
|
+
expect(mockGetIdentity).not.toHaveBeenCalled();
|
|
596
462
|
});
|
|
597
463
|
});
|
|
598
464
|
describe('Identity Cache fastDeepEqual with Timestamp Stripping', () => {
|
|
599
465
|
const pixelId = 'pixel123';
|
|
600
|
-
const lambdaArn = 'arn:aws:lambda:us-east-1:123456789:function:identity-private';
|
|
601
466
|
beforeEach(() => {
|
|
602
467
|
jest.clearAllMocks();
|
|
603
468
|
mockedDynamoDbClient.safeGet.mockReset();
|
|
604
469
|
mockedDynamoDbClient.safeBatchWrite.mockReset();
|
|
605
|
-
|
|
470
|
+
mockGetIdentity.mockReset();
|
|
606
471
|
IdentityGatewayService.lambdaInvokeClient = undefined;
|
|
607
472
|
});
|
|
608
473
|
it('should treat cached and merged as equal when they differ ONLY in cra/upa', async () => {
|
|
@@ -645,9 +510,9 @@ describe('Identity Cache fastDeepEqual with Timestamp Stripping', () => {
|
|
|
645
510
|
updatedAt: new Date().toISOString(),
|
|
646
511
|
};
|
|
647
512
|
mockedDynamoDbClient.safeGet.mockResolvedValueOnce(cachedResponse);
|
|
648
|
-
const result = await IdentityGatewayService.
|
|
513
|
+
const result = await IdentityGatewayService.resolveIdentityWithCaching(pixelId, incomingIdentity);
|
|
649
514
|
expect(result.identity).toBeDefined();
|
|
650
|
-
expect(
|
|
515
|
+
expect(mockGetIdentity).not.toHaveBeenCalled();
|
|
651
516
|
expect(mockedDynamoDbClient.safeBatchWrite).not.toHaveBeenCalled();
|
|
652
517
|
});
|
|
653
518
|
it('should treat cached and merged as NOT equal when address content differs (plus cra/upa)', async () => {
|
|
@@ -688,18 +553,17 @@ describe('Identity Cache fastDeepEqual with Timestamp Stripping', () => {
|
|
|
688
553
|
updatedAt: new Date().toISOString(),
|
|
689
554
|
};
|
|
690
555
|
mockedDynamoDbClient.safeGet.mockResolvedValueOnce(cachedResponse);
|
|
691
|
-
const result = await IdentityGatewayService.
|
|
556
|
+
const result = await IdentityGatewayService.resolveIdentityWithCaching(pixelId, incomingIdentity);
|
|
692
557
|
expect(result.identity).toBeDefined();
|
|
693
558
|
});
|
|
694
559
|
});
|
|
695
560
|
describe('Identity Cache Logging Levels', () => {
|
|
696
561
|
const pixelId = 'pixel123';
|
|
697
|
-
const lambdaArn = 'arn:aws:lambda:us-east-1:123456789:function:identity-private';
|
|
698
562
|
beforeEach(() => {
|
|
699
563
|
jest.clearAllMocks();
|
|
700
564
|
mockedDynamoDbClient.safeGet.mockReset();
|
|
701
565
|
mockedDynamoDbClient.safeBatchWrite.mockReset();
|
|
702
|
-
|
|
566
|
+
mockGetIdentity.mockReset();
|
|
703
567
|
IdentityGatewayService.lambdaInvokeClient = undefined;
|
|
704
568
|
});
|
|
705
569
|
it('should return fresh cache hit without calling Neptune or writing cache', async () => {
|
|
@@ -722,45 +586,11 @@ describe('Identity Cache Logging Levels', () => {
|
|
|
722
586
|
updatedAt: new Date().toISOString(),
|
|
723
587
|
};
|
|
724
588
|
mockedDynamoDbClient.safeGet.mockResolvedValueOnce(cachedResponse);
|
|
725
|
-
const result = await IdentityGatewayService.
|
|
726
|
-
expect(result.
|
|
727
|
-
expect(
|
|
589
|
+
const result = await IdentityGatewayService.resolveIdentityWithCaching(pixelId, incomingIdentity);
|
|
590
|
+
expect(result.outcome).toBe(IDENTITY_CACHE_WITH_CACHING_OUTCOME.FRESH_CACHE_HIT);
|
|
591
|
+
expect(mockGetIdentity).not.toHaveBeenCalled();
|
|
728
592
|
expect(mockedDynamoDbClient.safeBatchWrite).not.toHaveBeenCalled();
|
|
729
593
|
});
|
|
730
|
-
it('should return ADDRESS_UPDATE_ASYNC outcome for address update path', async () => {
|
|
731
|
-
IdentityGatewayService.configure({
|
|
732
|
-
awsRegion: 'us-east-1',
|
|
733
|
-
awsAccountId: '123456789',
|
|
734
|
-
asyncUpdateQueueName: 'test-queue',
|
|
735
|
-
});
|
|
736
|
-
mockBuildAndSendMessage.mockResolvedValueOnce({ MessageId: 'test-msg-id' });
|
|
737
|
-
const incomingIdentity = {
|
|
738
|
-
identityId: 'identity456',
|
|
739
|
-
traits: {
|
|
740
|
-
emails: ['test@email.com'],
|
|
741
|
-
addresses: [{ city: 'New City', s: ADDRESS_INFO_SOURCE.INPUT }],
|
|
742
|
-
},
|
|
743
|
-
};
|
|
744
|
-
const cachedResponse = {
|
|
745
|
-
pk: `identity#${pixelId}#identity456`,
|
|
746
|
-
pixelId,
|
|
747
|
-
identityId: 'identity456',
|
|
748
|
-
response: {
|
|
749
|
-
identityId: 'identity456',
|
|
750
|
-
traits: {
|
|
751
|
-
emails: ['test@email.com'],
|
|
752
|
-
addresses: [],
|
|
753
|
-
},
|
|
754
|
-
},
|
|
755
|
-
updatedAt: new Date().toISOString(),
|
|
756
|
-
};
|
|
757
|
-
mockedDynamoDbClient.safeGet.mockResolvedValueOnce(cachedResponse);
|
|
758
|
-
const result = await IdentityGatewayService.getIdentityWithCachingV2(pixelId, incomingIdentity, lambdaArn);
|
|
759
|
-
expect(result.summary.outcome).toBe(IDENTITY_CACHE_WITH_CACHING_OUTCOME.ADDRESS_UPDATE_ASYNC);
|
|
760
|
-
expect(result.summary.didSkipNeptune).toBe(true);
|
|
761
|
-
expect(result.summary.didWriteCache).toBe(false);
|
|
762
|
-
expect(result.summary.didEnqueueAsync).toBe(true);
|
|
763
|
-
});
|
|
764
594
|
it('should return NEPTUNE_WRITE_BACK outcome with traitChanges for stale traits', async () => {
|
|
765
595
|
const incomingIdentity = {
|
|
766
596
|
identityId: 'identity456',
|
|
@@ -781,107 +611,16 @@ describe('Identity Cache Logging Levels', () => {
|
|
|
781
611
|
updatedAt: new Date().toISOString(),
|
|
782
612
|
};
|
|
783
613
|
mockedDynamoDbClient.safeGet.mockResolvedValueOnce(cachedResponse);
|
|
784
|
-
|
|
785
|
-
statusCode: 200,
|
|
786
|
-
body: JSON.stringify({
|
|
787
|
-
identity: {
|
|
788
|
-
identityId: 'identity456',
|
|
789
|
-
traits: { emails: ['old@email.com', 'new@email.com'] },
|
|
790
|
-
},
|
|
791
|
-
}),
|
|
792
|
-
});
|
|
793
|
-
const result = await IdentityGatewayService.getIdentityWithCachingV2(pixelId, incomingIdentity, lambdaArn);
|
|
794
|
-
expect(result.summary.outcome).toBe(IDENTITY_CACHE_WITH_CACHING_OUTCOME.NEPTUNE_RESOLVED);
|
|
795
|
-
expect(result.summary.staleTraits).toContain('emails');
|
|
796
|
-
expect(result.summary.traitChanges).toBeDefined();
|
|
797
|
-
expect(result.summary.didCallNeptune).toBe(true);
|
|
798
|
-
expect(result.summary.didWriteCache).toBe(false);
|
|
799
|
-
});
|
|
800
|
-
});
|
|
801
|
-
describe('getIdentityFromCache staleness tier results', () => {
|
|
802
|
-
const pixelId = 'pixel123';
|
|
803
|
-
beforeEach(() => {
|
|
804
|
-
jest.clearAllMocks();
|
|
805
|
-
mockedDynamoDbClient.safeGet.mockReset();
|
|
806
|
-
});
|
|
807
|
-
it('should return staleTier NONE when cached and incoming are deep equal', async () => {
|
|
808
|
-
const incomingIdentity = {
|
|
809
|
-
identityId: 'identity456',
|
|
810
|
-
traits: {
|
|
811
|
-
emails: ['test@email.com'],
|
|
812
|
-
},
|
|
813
|
-
};
|
|
814
|
-
const cachedResponse = {
|
|
815
|
-
pk: `identity#${pixelId}#identity456`,
|
|
816
|
-
pixelId,
|
|
817
|
-
identityId: 'identity456',
|
|
818
|
-
response: {
|
|
819
|
-
identityId: 'identity456',
|
|
820
|
-
traits: {
|
|
821
|
-
emails: ['test@email.com'],
|
|
822
|
-
},
|
|
823
|
-
},
|
|
824
|
-
updatedAt: new Date().toISOString(),
|
|
825
|
-
};
|
|
826
|
-
mockedDynamoDbClient.safeGet.mockResolvedValueOnce(cachedResponse);
|
|
827
|
-
const result = await IdentityCacheDynamoDbDbService.getIdentityFromCache(pixelId, incomingIdentity);
|
|
828
|
-
expect(result.staleTier).toBe(IDENTITY_CACHE_STALENESS_TIER.NONE);
|
|
829
|
-
expect(result.isCacheStale).toBe(false);
|
|
830
|
-
expect(result.skipNeptune).toBeUndefined();
|
|
831
|
-
});
|
|
832
|
-
it('should return staleTier ADDRESS_UPDATE and skipNeptune=true for new non-IP address', async () => {
|
|
833
|
-
const incomingIdentity = {
|
|
834
|
-
identityId: 'identity456',
|
|
835
|
-
traits: {
|
|
836
|
-
emails: ['test@email.com'],
|
|
837
|
-
addresses: [{ city: 'New City', s: ADDRESS_INFO_SOURCE.INPUT }],
|
|
838
|
-
},
|
|
839
|
-
};
|
|
840
|
-
const cachedResponse = {
|
|
841
|
-
pk: `identity#${pixelId}#identity456`,
|
|
842
|
-
pixelId,
|
|
843
|
-
identityId: 'identity456',
|
|
844
|
-
response: {
|
|
845
|
-
identityId: 'identity456',
|
|
846
|
-
traits: {
|
|
847
|
-
emails: ['test@email.com'],
|
|
848
|
-
addresses: [],
|
|
849
|
-
},
|
|
850
|
-
},
|
|
851
|
-
updatedAt: new Date().toISOString(),
|
|
852
|
-
};
|
|
853
|
-
mockedDynamoDbClient.safeGet.mockResolvedValueOnce(cachedResponse);
|
|
854
|
-
const result = await IdentityCacheDynamoDbDbService.getIdentityFromCache(pixelId, incomingIdentity);
|
|
855
|
-
expect(result.staleTier).toBe(IDENTITY_CACHE_STALENESS_TIER.ADDRESS_UPDATE);
|
|
856
|
-
expect(result.isCacheStale).toBe(true);
|
|
857
|
-
expect(result.skipNeptune).toBe(true);
|
|
858
|
-
expect(result.writeReason).toBe(CACHE_WRITE_REASON.ADDRESS_UPDATE);
|
|
859
|
-
});
|
|
860
|
-
it('should return staleTier IDENTITY_STALE and skipNeptune=false for new email', async () => {
|
|
861
|
-
const incomingIdentity = {
|
|
614
|
+
mockGetIdentity.mockResolvedValueOnce({
|
|
862
615
|
identityId: 'identity456',
|
|
863
|
-
traits: {
|
|
864
|
-
|
|
865
|
-
|
|
866
|
-
|
|
867
|
-
|
|
868
|
-
|
|
869
|
-
|
|
870
|
-
|
|
871
|
-
response: {
|
|
872
|
-
identityId: 'identity456',
|
|
873
|
-
traits: {
|
|
874
|
-
emails: ['old@email.com'],
|
|
875
|
-
},
|
|
876
|
-
},
|
|
877
|
-
updatedAt: new Date().toISOString(),
|
|
878
|
-
};
|
|
879
|
-
mockedDynamoDbClient.safeGet.mockResolvedValueOnce(cachedResponse);
|
|
880
|
-
const result = await IdentityCacheDynamoDbDbService.getIdentityFromCache(pixelId, incomingIdentity);
|
|
881
|
-
expect(result.staleTier).toBe(IDENTITY_CACHE_STALENESS_TIER.IDENTITY_STALE);
|
|
882
|
-
expect(result.isCacheStale).toBe(true);
|
|
883
|
-
expect(result.skipNeptune).toBe(false);
|
|
884
|
-
expect(result.writeReason).toBe(CACHE_WRITE_REASON.STALE_TRAITS);
|
|
616
|
+
traits: { emails: ['old@email.com', 'new@email.com'] },
|
|
617
|
+
});
|
|
618
|
+
const result = await IdentityGatewayService.resolveIdentityWithCaching(pixelId, incomingIdentity);
|
|
619
|
+
expect(result.outcome).toBe(IDENTITY_CACHE_WITH_CACHING_OUTCOME.NEPTUNE_RESOLVED);
|
|
620
|
+
expect(result.stalenessResult?.staleTraits).toContain('emails');
|
|
621
|
+
expect(result.traitChanges).toBeDefined();
|
|
622
|
+
expect(result.didCallNeptune).toBe(true);
|
|
623
|
+
expect(result.didWriteCache).toBe(false);
|
|
885
624
|
});
|
|
886
625
|
});
|
|
887
626
|
//# sourceMappingURL=identity-cache-tier-routing.spec.js.map
|