@expo/entity-cache-adapter-local-memory 0.32.0 → 0.34.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/build/LocalMemoryCacheAdapterProvider.d.ts +13 -3
- package/build/LocalMemoryCacheAdapterProvider.js +14 -5
- package/build/LocalMemoryCacheAdapterProvider.js.map +1 -1
- package/build/__tests__/GenericLocalMemoryCacher-full-test.js +16 -45
- package/build/__tests__/GenericLocalMemoryCacher-full-test.js.map +1 -1
- package/build/testfixtures/createLocalMemoryTestEntityCompanionProvider.d.ts +1 -1
- package/build/testfixtures/createLocalMemoryTestEntityCompanionProvider.js +5 -5
- package/build/testfixtures/createLocalMemoryTestEntityCompanionProvider.js.map +1 -1
- package/package.json +3 -3
- package/src/LocalMemoryCacheAdapterProvider.ts +20 -15
- package/src/__tests__/GenericLocalMemoryCacher-full-test.ts +55 -64
- package/src/testfixtures/createLocalMemoryTestEntityCompanionProvider.ts +3 -3
|
@@ -1,12 +1,22 @@
|
|
|
1
1
|
import { IEntityCacheAdapter, EntityConfiguration, IEntityCacheAdapterProvider } from '@expo/entity';
|
|
2
|
+
/**
|
|
3
|
+
* Vends local memory cache adapters. An instance of this class may be shared across requests to
|
|
4
|
+
* share the local memory cache.
|
|
5
|
+
*/
|
|
2
6
|
export default class LocalMemoryCacheAdapterProvider implements IEntityCacheAdapterProvider {
|
|
3
7
|
private readonly localMemoryCacheCreator;
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
8
|
+
/**
|
|
9
|
+
* @returns a no-op local memory cache adapter provider, or one that doesn't cache locally.
|
|
10
|
+
*/
|
|
11
|
+
static createNoOpProvider(): IEntityCacheAdapterProvider;
|
|
12
|
+
/**
|
|
13
|
+
* @returns a local memory cache adapter provider configured with the supplied options.
|
|
14
|
+
*/
|
|
15
|
+
static createProviderWithOptions(options?: {
|
|
7
16
|
maxSize?: number;
|
|
8
17
|
ttlSeconds?: number;
|
|
9
18
|
}): IEntityCacheAdapterProvider;
|
|
19
|
+
private localMemoryCacheAdapterMap;
|
|
10
20
|
private constructor();
|
|
11
21
|
getCacheAdapter<TFields>(entityConfiguration: EntityConfiguration<TFields>): IEntityCacheAdapter<TFields>;
|
|
12
22
|
}
|
|
@@ -5,24 +5,33 @@ var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
|
5
5
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
6
6
|
const entity_1 = require("@expo/entity");
|
|
7
7
|
const GenericLocalMemoryCacher_1 = __importDefault(require("./GenericLocalMemoryCacher"));
|
|
8
|
+
/**
|
|
9
|
+
* Vends local memory cache adapters. An instance of this class may be shared across requests to
|
|
10
|
+
* share the local memory cache.
|
|
11
|
+
*/
|
|
8
12
|
class LocalMemoryCacheAdapterProvider {
|
|
9
|
-
|
|
13
|
+
/**
|
|
14
|
+
* @returns a no-op local memory cache adapter provider, or one that doesn't cache locally.
|
|
15
|
+
*/
|
|
16
|
+
static createNoOpProvider() {
|
|
10
17
|
return new LocalMemoryCacheAdapterProvider(() => GenericLocalMemoryCacher_1.default.createNoOpCache());
|
|
11
18
|
}
|
|
12
|
-
|
|
19
|
+
/**
|
|
20
|
+
* @returns a local memory cache adapter provider configured with the supplied options.
|
|
21
|
+
*/
|
|
22
|
+
static createProviderWithOptions(options = {}) {
|
|
13
23
|
return new LocalMemoryCacheAdapterProvider(() => GenericLocalMemoryCacher_1.default.createLRUCache(options));
|
|
14
24
|
}
|
|
15
25
|
constructor(localMemoryCacheCreator) {
|
|
16
26
|
this.localMemoryCacheCreator = localMemoryCacheCreator;
|
|
27
|
+
this.localMemoryCacheAdapterMap = new Map();
|
|
17
28
|
}
|
|
18
29
|
getCacheAdapter(entityConfiguration) {
|
|
19
|
-
return (0, entity_1.computeIfAbsent)(
|
|
30
|
+
return (0, entity_1.computeIfAbsent)(this.localMemoryCacheAdapterMap, entityConfiguration.tableName, () => {
|
|
20
31
|
const localMemoryCache = this.localMemoryCacheCreator();
|
|
21
32
|
return new entity_1.GenericEntityCacheAdapter(new GenericLocalMemoryCacher_1.default(entityConfiguration, localMemoryCache));
|
|
22
33
|
});
|
|
23
34
|
}
|
|
24
35
|
}
|
|
25
|
-
// local memory cache adapters should be shared/reused across requests
|
|
26
|
-
LocalMemoryCacheAdapterProvider.localMemoryCacheAdapterMap = new Map();
|
|
27
36
|
exports.default = LocalMemoryCacheAdapterProvider;
|
|
28
37
|
//# sourceMappingURL=LocalMemoryCacheAdapterProvider.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"LocalMemoryCacheAdapterProvider.js","sourceRoot":"","sources":["../src/LocalMemoryCacheAdapterProvider.ts"],"names":[],"mappings":";;;;;AAAA,yCAMsB;AAEtB,0FAAwF;AAExF,MAAqB,+BAA+B;
|
|
1
|
+
{"version":3,"file":"LocalMemoryCacheAdapterProvider.js","sourceRoot":"","sources":["../src/LocalMemoryCacheAdapterProvider.ts"],"names":[],"mappings":";;;;;AAAA,yCAMsB;AAEtB,0FAAwF;AAExF;;;GAGG;AACH,MAAqB,+BAA+B;IAClD;;OAEG;IACH,MAAM,CAAC,kBAAkB;QACvB,OAAO,IAAI,+BAA+B,CAAC,GAAY,EAAE,CACvD,kCAAwB,CAAC,eAAe,EAAW,CACpD,CAAC;IACJ,CAAC;IAED;;OAEG;IACH,MAAM,CAAC,yBAAyB,CAC9B,UAAqD,EAAE;QAEvD,OAAO,IAAI,+BAA+B,CAAC,GAAY,EAAE,CACvD,kCAAwB,CAAC,cAAc,CAAU,OAAO,CAAC,CAC1D,CAAC;IACJ,CAAC;IAID,YACmB,uBAAiE;QAAjE,4BAAuB,GAAvB,uBAAuB,CAA0C;QAH5E,+BAA0B,GAAG,IAAI,GAAG,EAA0C,CAAC;IAIpF,CAAC;IAEG,eAAe,CACpB,mBAAiD;QAEjD,OAAO,IAAA,wBAAe,EAAC,IAAI,CAAC,0BAA0B,EAAE,mBAAmB,CAAC,SAAS,EAAE,GAAG,EAAE;YAC1F,MAAM,gBAAgB,GAAG,IAAI,CAAC,uBAAuB,EAAW,CAAC;YACjE,OAAO,IAAI,kCAAyB,CAClC,IAAI,kCAAwB,CAAC,mBAAmB,EAAE,gBAAgB,CAAC,CACpE,CAAC;QACJ,CAAC,CAAC,CAAC;IACL,CAAC;CACF;AArCD,kDAqCC"}
|
|
@@ -6,27 +6,25 @@ Object.defineProperty(exports, "__esModule", { value: true });
|
|
|
6
6
|
const entity_1 = require("@expo/entity");
|
|
7
7
|
const uuid_1 = require("uuid");
|
|
8
8
|
const GenericLocalMemoryCacher_1 = __importDefault(require("../GenericLocalMemoryCacher"));
|
|
9
|
-
const LocalMemoryCacheAdapterProvider_1 = __importDefault(require("../LocalMemoryCacheAdapterProvider"));
|
|
10
9
|
const LocalMemoryTestEntity_1 = __importDefault(require("../testfixtures/LocalMemoryTestEntity"));
|
|
11
10
|
const createLocalMemoryTestEntityCompanionProvider_1 = require("../testfixtures/createLocalMemoryTestEntityCompanionProvider");
|
|
12
11
|
describe(GenericLocalMemoryCacher_1.default, () => {
|
|
13
|
-
beforeEach(async () => {
|
|
14
|
-
LocalMemoryCacheAdapterProvider_1.default['localMemoryCacheAdapterMap'].clear();
|
|
15
|
-
});
|
|
16
12
|
it('has correct caching behavior', async () => {
|
|
17
|
-
const
|
|
13
|
+
const entityCompanionProvider = (0, createLocalMemoryTestEntityCompanionProvider_1.createLocalMemoryTestEntityCompanionProvider)();
|
|
14
|
+
const viewerContext = new entity_1.ViewerContext(entityCompanionProvider);
|
|
18
15
|
const genericCacher = viewerContext.entityCompanionProvider.getCompanionForEntity(LocalMemoryTestEntity_1.default)['tableDataCoordinator']['cacheAdapter']['genericCacher'];
|
|
19
16
|
const cacheKeyMaker = genericCacher['makeCacheKey'].bind(genericCacher);
|
|
20
17
|
const date = new Date();
|
|
21
|
-
const entity1Created = await LocalMemoryTestEntity_1.default.creator(viewerContext)
|
|
18
|
+
const entity1Created = await LocalMemoryTestEntity_1.default.creator(viewerContext, viewerContext.getNonTransactionalQueryContextForDatabaseAdaptorFlavor('postgres'))
|
|
22
19
|
.setField('name', 'blah')
|
|
23
20
|
.setField('dateField', date)
|
|
24
21
|
.enforceCreateAsync();
|
|
25
22
|
// loading an entity should put it in cache
|
|
26
|
-
const entity1 = await LocalMemoryTestEntity_1.default.loader(viewerContext)
|
|
23
|
+
const entity1 = await LocalMemoryTestEntity_1.default.loader(viewerContext, viewerContext.getNonTransactionalQueryContextForDatabaseAdaptorFlavor('postgres'))
|
|
27
24
|
.enforcing()
|
|
28
25
|
.loadByIDAsync(entity1Created.getID());
|
|
29
|
-
const
|
|
26
|
+
const localMemoryCacheAdapterProvider = entityCompanionProvider['cacheAdapterFlavors'].get('local-memory').cacheAdapterProvider;
|
|
27
|
+
const entitySpecificGenericCacher = localMemoryCacheAdapterProvider['localMemoryCacheAdapterMap'].get(viewerContext.entityCompanionProvider.getCompanionForEntity(LocalMemoryTestEntity_1.default)
|
|
30
28
|
.entityCompanionDefinition.entityConfiguration.tableName)['genericCacher'];
|
|
31
29
|
const cachedResult = await entitySpecificGenericCacher.loadManyAsync([
|
|
32
30
|
cacheKeyMaker('id', entity1.getID()),
|
|
@@ -42,7 +40,7 @@ describe(GenericLocalMemoryCacher_1.default, () => {
|
|
|
42
40
|
});
|
|
43
41
|
// simulate non existent db fetch, should write negative result ('') to cache
|
|
44
42
|
const nonExistentId = (0, uuid_1.v4)();
|
|
45
|
-
const entityNonExistentResult = await LocalMemoryTestEntity_1.default.loader(viewerContext).loadByIDAsync(nonExistentId);
|
|
43
|
+
const entityNonExistentResult = await LocalMemoryTestEntity_1.default.loader(viewerContext, viewerContext.getNonTransactionalQueryContextForDatabaseAdaptorFlavor('postgres')).loadByIDAsync(nonExistentId);
|
|
46
44
|
expect(entityNonExistentResult.ok).toBe(false);
|
|
47
45
|
const nonExistentCachedResult = await entitySpecificGenericCacher.loadManyAsync([
|
|
48
46
|
cacheKeyMaker('id', nonExistentId),
|
|
@@ -51,59 +49,32 @@ describe(GenericLocalMemoryCacher_1.default, () => {
|
|
|
51
49
|
status: entity_1.CacheStatus.NEGATIVE,
|
|
52
50
|
});
|
|
53
51
|
// load again through entities framework to ensure it reads negative result
|
|
54
|
-
const entityNonExistentResult2 = await LocalMemoryTestEntity_1.default.loader(viewerContext).loadByIDAsync(nonExistentId);
|
|
52
|
+
const entityNonExistentResult2 = await LocalMemoryTestEntity_1.default.loader(viewerContext, viewerContext.getNonTransactionalQueryContextForDatabaseAdaptorFlavor('postgres')).loadByIDAsync(nonExistentId);
|
|
55
53
|
expect(entityNonExistentResult2.ok).toBe(false);
|
|
56
54
|
// invalidate from cache to ensure it invalidates correctly
|
|
57
|
-
await LocalMemoryTestEntity_1.default.loader(viewerContext).invalidateFieldsAsync(entity1.getAllFields());
|
|
55
|
+
await LocalMemoryTestEntity_1.default.loader(viewerContext, viewerContext.getNonTransactionalQueryContextForDatabaseAdaptorFlavor('postgres')).invalidateFieldsAsync(entity1.getAllFields());
|
|
58
56
|
const cachedResultMiss = await entitySpecificGenericCacher.loadManyAsync([
|
|
59
57
|
cacheKeyMaker('id', entity1.getID()),
|
|
60
58
|
]);
|
|
61
59
|
const cachedValueMiss = cachedResultMiss.get(cacheKeyMaker('id', entity1.getID()));
|
|
62
60
|
expect(cachedValueMiss).toMatchObject({ status: entity_1.CacheStatus.MISS });
|
|
63
61
|
});
|
|
64
|
-
it('shares the cache between different requests', async () => {
|
|
65
|
-
const genericLocalMemoryCacherLoadManySpy = jest.spyOn(GenericLocalMemoryCacher_1.default.prototype, 'loadManyAsync');
|
|
66
|
-
const viewerContext = new entity_1.ViewerContext((0, createLocalMemoryTestEntityCompanionProvider_1.createLocalMemoryTestEntityCompanionProvider)());
|
|
67
|
-
const date = new Date();
|
|
68
|
-
const entity1Created = await LocalMemoryTestEntity_1.default.creator(viewerContext)
|
|
69
|
-
.setField('name', 'blah')
|
|
70
|
-
.setField('dateField', date)
|
|
71
|
-
.enforceCreateAsync();
|
|
72
|
-
// loading an entity should put it in cache
|
|
73
|
-
await LocalMemoryTestEntity_1.default.loader(viewerContext)
|
|
74
|
-
.enforcing()
|
|
75
|
-
.loadByIDAsync(entity1Created.getID());
|
|
76
|
-
// load entity with a different request
|
|
77
|
-
const viewerContext2 = new entity_1.ViewerContext((0, createLocalMemoryTestEntityCompanionProvider_1.createLocalMemoryTestEntityCompanionProvider)());
|
|
78
|
-
const entity1WithVc2 = await LocalMemoryTestEntity_1.default.loader(viewerContext2)
|
|
79
|
-
.enforcing()
|
|
80
|
-
.loadByIDAsync(entity1Created.getID());
|
|
81
|
-
const genericCacher = viewerContext.entityCompanionProvider.getCompanionForEntity(LocalMemoryTestEntity_1.default)['tableDataCoordinator']['cacheAdapter']['genericCacher'];
|
|
82
|
-
const cacheKeyMaker = genericCacher['makeCacheKey'].bind(genericCacher);
|
|
83
|
-
expect(entity1WithVc2.getAllFields()).toMatchObject({
|
|
84
|
-
id: entity1WithVc2.getID(),
|
|
85
|
-
name: 'blah',
|
|
86
|
-
dateField: date,
|
|
87
|
-
});
|
|
88
|
-
expect(genericLocalMemoryCacherLoadManySpy).toBeCalledWith([
|
|
89
|
-
cacheKeyMaker('id', entity1WithVc2.getID()),
|
|
90
|
-
]);
|
|
91
|
-
expect(genericLocalMemoryCacherLoadManySpy).toBeCalledTimes(2);
|
|
92
|
-
});
|
|
93
62
|
it('respects the parameters of a noop cache', async () => {
|
|
94
|
-
const
|
|
63
|
+
const entityCompanionProvider = (0, createLocalMemoryTestEntityCompanionProvider_1.createNoOpLocalMemoryIntegrationTestEntityCompanionProvider)();
|
|
64
|
+
const viewerContext = new entity_1.ViewerContext(entityCompanionProvider);
|
|
95
65
|
const genericCacher = viewerContext.entityCompanionProvider.getCompanionForEntity(LocalMemoryTestEntity_1.default)['tableDataCoordinator']['cacheAdapter']['genericCacher'];
|
|
96
66
|
const cacheKeyMaker = genericCacher['makeCacheKey'].bind(genericCacher);
|
|
97
67
|
const date = new Date();
|
|
98
|
-
const entity1Created = await LocalMemoryTestEntity_1.default.creator(viewerContext)
|
|
68
|
+
const entity1Created = await LocalMemoryTestEntity_1.default.creator(viewerContext, viewerContext.getNonTransactionalQueryContextForDatabaseAdaptorFlavor('postgres'))
|
|
99
69
|
.setField('name', 'blah')
|
|
100
70
|
.setField('dateField', date)
|
|
101
71
|
.enforceCreateAsync();
|
|
102
72
|
// loading an entity will try to put it in cache but it's a noop cache, so it should be a miss
|
|
103
|
-
const entity1 = await LocalMemoryTestEntity_1.default.loader(viewerContext)
|
|
73
|
+
const entity1 = await LocalMemoryTestEntity_1.default.loader(viewerContext, viewerContext.getNonTransactionalQueryContextForDatabaseAdaptorFlavor('postgres'))
|
|
104
74
|
.enforcing()
|
|
105
75
|
.loadByIDAsync(entity1Created.getID());
|
|
106
|
-
const
|
|
76
|
+
const localMemoryCacheAdapterProvider = entityCompanionProvider['cacheAdapterFlavors'].get('local-memory').cacheAdapterProvider;
|
|
77
|
+
const entitySpecificGenericCacher = localMemoryCacheAdapterProvider['localMemoryCacheAdapterMap'].get(viewerContext.entityCompanionProvider.getCompanionForEntity(LocalMemoryTestEntity_1.default)
|
|
107
78
|
.entityCompanionDefinition.entityConfiguration.tableName)['genericCacher'];
|
|
108
79
|
const cachedResult = await entitySpecificGenericCacher.loadManyAsync([
|
|
109
80
|
cacheKeyMaker('id', entity1.getID()),
|
|
@@ -114,7 +85,7 @@ describe(GenericLocalMemoryCacher_1.default, () => {
|
|
|
114
85
|
});
|
|
115
86
|
// a non existent db fetch should try to write negative result ('') but it's a noop cache, so it should be a miss
|
|
116
87
|
const nonExistentId = (0, uuid_1.v4)();
|
|
117
|
-
const entityNonExistentResult = await LocalMemoryTestEntity_1.default.loader(viewerContext).loadByIDAsync(nonExistentId);
|
|
88
|
+
const entityNonExistentResult = await LocalMemoryTestEntity_1.default.loader(viewerContext, viewerContext.getNonTransactionalQueryContextForDatabaseAdaptorFlavor('postgres')).loadByIDAsync(nonExistentId);
|
|
118
89
|
expect(entityNonExistentResult.ok).toBe(false);
|
|
119
90
|
const nonExistentCachedResult = await entitySpecificGenericCacher.loadManyAsync([
|
|
120
91
|
cacheKeyMaker('id', nonExistentId),
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"GenericLocalMemoryCacher-full-test.js","sourceRoot":"","sources":["../../src/__tests__/GenericLocalMemoryCacher-full-test.ts"],"names":[],"mappings":";;;;;AAAA,
|
|
1
|
+
{"version":3,"file":"GenericLocalMemoryCacher-full-test.js","sourceRoot":"","sources":["../../src/__tests__/GenericLocalMemoryCacher-full-test.ts"],"names":[],"mappings":"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"}
|
|
@@ -3,4 +3,4 @@ export declare const createLocalMemoryTestEntityCompanionProvider: (localMemoryO
|
|
|
3
3
|
maxSize?: number;
|
|
4
4
|
ttlSeconds?: number;
|
|
5
5
|
}, metricsAdapter?: IEntityMetricsAdapter) => EntityCompanionProvider;
|
|
6
|
-
export declare const
|
|
6
|
+
export declare const createNoOpLocalMemoryIntegrationTestEntityCompanionProvider: (metricsAdapter?: IEntityMetricsAdapter) => EntityCompanionProvider;
|
|
@@ -3,13 +3,13 @@ var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
|
3
3
|
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
4
4
|
};
|
|
5
5
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
6
|
-
exports.
|
|
6
|
+
exports.createNoOpLocalMemoryIntegrationTestEntityCompanionProvider = exports.createLocalMemoryTestEntityCompanionProvider = void 0;
|
|
7
7
|
const entity_1 = require("@expo/entity");
|
|
8
8
|
const LocalMemoryCacheAdapterProvider_1 = __importDefault(require("../LocalMemoryCacheAdapterProvider"));
|
|
9
9
|
const createLocalMemoryTestEntityCompanionProvider = (localMemoryOptions = {}, metricsAdapter = new entity_1.NoOpEntityMetricsAdapter()) => {
|
|
10
10
|
const localMemoryCacheAdapterProvider = localMemoryOptions.maxSize === 0 && localMemoryOptions.ttlSeconds === 0
|
|
11
|
-
? LocalMemoryCacheAdapterProvider_1.default.
|
|
12
|
-
: LocalMemoryCacheAdapterProvider_1.default.
|
|
11
|
+
? LocalMemoryCacheAdapterProvider_1.default.createNoOpProvider()
|
|
12
|
+
: LocalMemoryCacheAdapterProvider_1.default.createProviderWithOptions(localMemoryOptions);
|
|
13
13
|
return new entity_1.EntityCompanionProvider(metricsAdapter, new Map([
|
|
14
14
|
[
|
|
15
15
|
'postgres',
|
|
@@ -28,8 +28,8 @@ const createLocalMemoryTestEntityCompanionProvider = (localMemoryOptions = {}, m
|
|
|
28
28
|
]));
|
|
29
29
|
};
|
|
30
30
|
exports.createLocalMemoryTestEntityCompanionProvider = createLocalMemoryTestEntityCompanionProvider;
|
|
31
|
-
const
|
|
31
|
+
const createNoOpLocalMemoryIntegrationTestEntityCompanionProvider = (metricsAdapter = new entity_1.NoOpEntityMetricsAdapter()) => {
|
|
32
32
|
return (0, exports.createLocalMemoryTestEntityCompanionProvider)({ maxSize: 0, ttlSeconds: 0 }, metricsAdapter);
|
|
33
33
|
};
|
|
34
|
-
exports.
|
|
34
|
+
exports.createNoOpLocalMemoryIntegrationTestEntityCompanionProvider = createNoOpLocalMemoryIntegrationTestEntityCompanionProvider;
|
|
35
35
|
//# sourceMappingURL=createLocalMemoryTestEntityCompanionProvider.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"createLocalMemoryTestEntityCompanionProvider.js","sourceRoot":"","sources":["../../src/testfixtures/createLocalMemoryTestEntityCompanionProvider.ts"],"names":[],"mappings":";;;;;;AAAA,yCAMsB;AAEtB,yGAAiF;AAE1E,MAAM,4CAA4C,GAAG,CAC1D,qBAAgE,EAAE,EAClE,iBAAwC,IAAI,iCAAwB,EAAE,EAC7C,EAAE;IAC3B,MAAM,+BAA+B,GACnC,kBAAkB,CAAC,OAAO,KAAK,CAAC,IAAI,kBAAkB,CAAC,UAAU,KAAK,CAAC;QACrE,CAAC,CAAC,yCAA+B,CAAC,
|
|
1
|
+
{"version":3,"file":"createLocalMemoryTestEntityCompanionProvider.js","sourceRoot":"","sources":["../../src/testfixtures/createLocalMemoryTestEntityCompanionProvider.ts"],"names":[],"mappings":";;;;;;AAAA,yCAMsB;AAEtB,yGAAiF;AAE1E,MAAM,4CAA4C,GAAG,CAC1D,qBAAgE,EAAE,EAClE,iBAAwC,IAAI,iCAAwB,EAAE,EAC7C,EAAE;IAC3B,MAAM,+BAA+B,GACnC,kBAAkB,CAAC,OAAO,KAAK,CAAC,IAAI,kBAAkB,CAAC,UAAU,KAAK,CAAC;QACrE,CAAC,CAAC,yCAA+B,CAAC,kBAAkB,EAAE;QACtD,CAAC,CAAC,yCAA+B,CAAC,yBAAyB,CAAC,kBAAkB,CAAC,CAAC;IACpF,OAAO,IAAI,gCAAuB,CAChC,cAAc,EACd,IAAI,GAAG,CAAC;QACN;YACE,UAAU;YACV;gBACE,eAAe,EAAE,IAAI,oCAA2B,EAAE;gBAClD,oBAAoB,EAAE,iCAAwB;aAC/C;SACF;KACF,CAAC,EACF,IAAI,GAAG,CAAC;QACN;YACE,cAAc;YACd;gBACE,oBAAoB,EAAE,+BAA+B;aACtD;SACF;KACF,CAAC,CACH,CAAC;AACJ,CAAC,CAAC;AA5BW,QAAA,4CAA4C,gDA4BvD;AAEK,MAAM,2DAA2D,GAAG,CACzE,iBAAwC,IAAI,iCAAwB,EAAE,EAC7C,EAAE;IAC3B,OAAO,IAAA,oDAA4C,EACjD,EAAE,OAAO,EAAE,CAAC,EAAE,UAAU,EAAE,CAAC,EAAE,EAC7B,cAAc,CACf,CAAC;AACJ,CAAC,CAAC;AAPW,QAAA,2DAA2D,+DAOtE"}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@expo/entity-cache-adapter-local-memory",
|
|
3
|
-
"version": "0.
|
|
3
|
+
"version": "0.34.0",
|
|
4
4
|
"description": "Cross-request local memory cache adapter for @expo/entity",
|
|
5
5
|
"files": [
|
|
6
6
|
"build",
|
|
@@ -33,7 +33,7 @@
|
|
|
33
33
|
"lru-cache": "^6.0.0"
|
|
34
34
|
},
|
|
35
35
|
"devDependencies": {
|
|
36
|
-
"@expo/entity": "^0.
|
|
36
|
+
"@expo/entity": "^0.34.0"
|
|
37
37
|
},
|
|
38
|
-
"gitHead": "
|
|
38
|
+
"gitHead": "0fa6f554a27359aede6bd3f7d4578fadfda98bcb"
|
|
39
39
|
}
|
|
@@ -8,17 +8,24 @@ import {
|
|
|
8
8
|
|
|
9
9
|
import GenericLocalMemoryCacher, { LocalMemoryCache } from './GenericLocalMemoryCacher';
|
|
10
10
|
|
|
11
|
+
/**
|
|
12
|
+
* Vends local memory cache adapters. An instance of this class may be shared across requests to
|
|
13
|
+
* share the local memory cache.
|
|
14
|
+
*/
|
|
11
15
|
export default class LocalMemoryCacheAdapterProvider implements IEntityCacheAdapterProvider {
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
static
|
|
16
|
+
/**
|
|
17
|
+
* @returns a no-op local memory cache adapter provider, or one that doesn't cache locally.
|
|
18
|
+
*/
|
|
19
|
+
static createNoOpProvider(): IEntityCacheAdapterProvider {
|
|
16
20
|
return new LocalMemoryCacheAdapterProvider(<TFields>() =>
|
|
17
21
|
GenericLocalMemoryCacher.createNoOpCache<TFields>()
|
|
18
22
|
);
|
|
19
23
|
}
|
|
20
24
|
|
|
21
|
-
|
|
25
|
+
/**
|
|
26
|
+
* @returns a local memory cache adapter provider configured with the supplied options.
|
|
27
|
+
*/
|
|
28
|
+
static createProviderWithOptions(
|
|
22
29
|
options: { maxSize?: number; ttlSeconds?: number } = {}
|
|
23
30
|
): IEntityCacheAdapterProvider {
|
|
24
31
|
return new LocalMemoryCacheAdapterProvider(<TFields>() =>
|
|
@@ -26,6 +33,8 @@ export default class LocalMemoryCacheAdapterProvider implements IEntityCacheAdap
|
|
|
26
33
|
);
|
|
27
34
|
}
|
|
28
35
|
|
|
36
|
+
private localMemoryCacheAdapterMap = new Map<string, GenericEntityCacheAdapter<any>>();
|
|
37
|
+
|
|
29
38
|
private constructor(
|
|
30
39
|
private readonly localMemoryCacheCreator: <TFields>() => LocalMemoryCache<TFields>
|
|
31
40
|
) {}
|
|
@@ -33,15 +42,11 @@ export default class LocalMemoryCacheAdapterProvider implements IEntityCacheAdap
|
|
|
33
42
|
public getCacheAdapter<TFields>(
|
|
34
43
|
entityConfiguration: EntityConfiguration<TFields>
|
|
35
44
|
): IEntityCacheAdapter<TFields> {
|
|
36
|
-
return computeIfAbsent(
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
new GenericLocalMemoryCacher(entityConfiguration, localMemoryCache)
|
|
43
|
-
);
|
|
44
|
-
}
|
|
45
|
-
);
|
|
45
|
+
return computeIfAbsent(this.localMemoryCacheAdapterMap, entityConfiguration.tableName, () => {
|
|
46
|
+
const localMemoryCache = this.localMemoryCacheCreator<TFields>();
|
|
47
|
+
return new GenericEntityCacheAdapter(
|
|
48
|
+
new GenericLocalMemoryCacher(entityConfiguration, localMemoryCache)
|
|
49
|
+
);
|
|
50
|
+
});
|
|
46
51
|
}
|
|
47
52
|
}
|
|
@@ -1,4 +1,9 @@
|
|
|
1
|
-
import {
|
|
1
|
+
import {
|
|
2
|
+
CacheAdapterFlavor,
|
|
3
|
+
CacheAdapterFlavorDefinition,
|
|
4
|
+
CacheStatus,
|
|
5
|
+
ViewerContext,
|
|
6
|
+
} from '@expo/entity';
|
|
2
7
|
import { v4 as uuidv4 } from 'uuid';
|
|
3
8
|
|
|
4
9
|
import GenericLocalMemoryCacher from '../GenericLocalMemoryCacher';
|
|
@@ -6,16 +11,13 @@ import LocalMemoryCacheAdapterProvider from '../LocalMemoryCacheAdapterProvider'
|
|
|
6
11
|
import LocalMemoryTestEntity from '../testfixtures/LocalMemoryTestEntity';
|
|
7
12
|
import {
|
|
8
13
|
createLocalMemoryTestEntityCompanionProvider,
|
|
9
|
-
|
|
14
|
+
createNoOpLocalMemoryIntegrationTestEntityCompanionProvider,
|
|
10
15
|
} from '../testfixtures/createLocalMemoryTestEntityCompanionProvider';
|
|
11
16
|
|
|
12
17
|
describe(GenericLocalMemoryCacher, () => {
|
|
13
|
-
beforeEach(async () => {
|
|
14
|
-
LocalMemoryCacheAdapterProvider['localMemoryCacheAdapterMap'].clear();
|
|
15
|
-
});
|
|
16
|
-
|
|
17
18
|
it('has correct caching behavior', async () => {
|
|
18
|
-
const
|
|
19
|
+
const entityCompanionProvider = createLocalMemoryTestEntityCompanionProvider();
|
|
20
|
+
const viewerContext = new ViewerContext(entityCompanionProvider);
|
|
19
21
|
const genericCacher =
|
|
20
22
|
viewerContext.entityCompanionProvider.getCompanionForEntity(LocalMemoryTestEntity)[
|
|
21
23
|
'tableDataCoordinator'
|
|
@@ -23,17 +25,29 @@ describe(GenericLocalMemoryCacher, () => {
|
|
|
23
25
|
const cacheKeyMaker = genericCacher['makeCacheKey'].bind(genericCacher);
|
|
24
26
|
|
|
25
27
|
const date = new Date();
|
|
26
|
-
const entity1Created = await LocalMemoryTestEntity.creator(
|
|
28
|
+
const entity1Created = await LocalMemoryTestEntity.creator(
|
|
29
|
+
viewerContext,
|
|
30
|
+
viewerContext.getNonTransactionalQueryContextForDatabaseAdaptorFlavor('postgres')
|
|
31
|
+
)
|
|
27
32
|
.setField('name', 'blah')
|
|
28
33
|
.setField('dateField', date)
|
|
29
34
|
.enforceCreateAsync();
|
|
30
35
|
|
|
31
36
|
// loading an entity should put it in cache
|
|
32
|
-
const entity1 = await LocalMemoryTestEntity.loader(
|
|
37
|
+
const entity1 = await LocalMemoryTestEntity.loader(
|
|
38
|
+
viewerContext,
|
|
39
|
+
viewerContext.getNonTransactionalQueryContextForDatabaseAdaptorFlavor('postgres')
|
|
40
|
+
)
|
|
33
41
|
.enforcing()
|
|
34
42
|
.loadByIDAsync(entity1Created.getID());
|
|
35
43
|
|
|
36
|
-
const
|
|
44
|
+
const localMemoryCacheAdapterProvider = (
|
|
45
|
+
entityCompanionProvider['cacheAdapterFlavors'] as ReadonlyMap<
|
|
46
|
+
CacheAdapterFlavor,
|
|
47
|
+
CacheAdapterFlavorDefinition
|
|
48
|
+
>
|
|
49
|
+
).get('local-memory')!.cacheAdapterProvider as LocalMemoryCacheAdapterProvider;
|
|
50
|
+
const entitySpecificGenericCacher = localMemoryCacheAdapterProvider[
|
|
37
51
|
'localMemoryCacheAdapterMap'
|
|
38
52
|
].get(
|
|
39
53
|
viewerContext.entityCompanionProvider.getCompanionForEntity(LocalMemoryTestEntity)
|
|
@@ -55,9 +69,10 @@ describe(GenericLocalMemoryCacher, () => {
|
|
|
55
69
|
// simulate non existent db fetch, should write negative result ('') to cache
|
|
56
70
|
const nonExistentId = uuidv4();
|
|
57
71
|
|
|
58
|
-
const entityNonExistentResult = await LocalMemoryTestEntity.loader(
|
|
59
|
-
|
|
60
|
-
|
|
72
|
+
const entityNonExistentResult = await LocalMemoryTestEntity.loader(
|
|
73
|
+
viewerContext,
|
|
74
|
+
viewerContext.getNonTransactionalQueryContextForDatabaseAdaptorFlavor('postgres')
|
|
75
|
+
).loadByIDAsync(nonExistentId);
|
|
61
76
|
expect(entityNonExistentResult.ok).toBe(false);
|
|
62
77
|
|
|
63
78
|
const nonExistentCachedResult = await entitySpecificGenericCacher.loadManyAsync([
|
|
@@ -69,12 +84,16 @@ describe(GenericLocalMemoryCacher, () => {
|
|
|
69
84
|
|
|
70
85
|
// load again through entities framework to ensure it reads negative result
|
|
71
86
|
const entityNonExistentResult2 = await LocalMemoryTestEntity.loader(
|
|
72
|
-
viewerContext
|
|
87
|
+
viewerContext,
|
|
88
|
+
viewerContext.getNonTransactionalQueryContextForDatabaseAdaptorFlavor('postgres')
|
|
73
89
|
).loadByIDAsync(nonExistentId);
|
|
74
90
|
expect(entityNonExistentResult2.ok).toBe(false);
|
|
75
91
|
|
|
76
92
|
// invalidate from cache to ensure it invalidates correctly
|
|
77
|
-
await LocalMemoryTestEntity.loader(
|
|
93
|
+
await LocalMemoryTestEntity.loader(
|
|
94
|
+
viewerContext,
|
|
95
|
+
viewerContext.getNonTransactionalQueryContextForDatabaseAdaptorFlavor('postgres')
|
|
96
|
+
).invalidateFieldsAsync(entity1.getAllFields());
|
|
78
97
|
const cachedResultMiss = await entitySpecificGenericCacher.loadManyAsync([
|
|
79
98
|
cacheKeyMaker('id', entity1.getID()),
|
|
80
99
|
]);
|
|
@@ -82,50 +101,9 @@ describe(GenericLocalMemoryCacher, () => {
|
|
|
82
101
|
expect(cachedValueMiss).toMatchObject({ status: CacheStatus.MISS });
|
|
83
102
|
});
|
|
84
103
|
|
|
85
|
-
it('shares the cache between different requests', async () => {
|
|
86
|
-
const genericLocalMemoryCacherLoadManySpy = jest.spyOn(
|
|
87
|
-
GenericLocalMemoryCacher.prototype as unknown as any,
|
|
88
|
-
'loadManyAsync'
|
|
89
|
-
);
|
|
90
|
-
const viewerContext = new ViewerContext(createLocalMemoryTestEntityCompanionProvider());
|
|
91
|
-
|
|
92
|
-
const date = new Date();
|
|
93
|
-
const entity1Created = await LocalMemoryTestEntity.creator(viewerContext)
|
|
94
|
-
.setField('name', 'blah')
|
|
95
|
-
.setField('dateField', date)
|
|
96
|
-
.enforceCreateAsync();
|
|
97
|
-
|
|
98
|
-
// loading an entity should put it in cache
|
|
99
|
-
await LocalMemoryTestEntity.loader(viewerContext)
|
|
100
|
-
.enforcing()
|
|
101
|
-
.loadByIDAsync(entity1Created.getID());
|
|
102
|
-
|
|
103
|
-
// load entity with a different request
|
|
104
|
-
const viewerContext2 = new ViewerContext(createLocalMemoryTestEntityCompanionProvider());
|
|
105
|
-
const entity1WithVc2 = await LocalMemoryTestEntity.loader(viewerContext2)
|
|
106
|
-
.enforcing()
|
|
107
|
-
.loadByIDAsync(entity1Created.getID());
|
|
108
|
-
|
|
109
|
-
const genericCacher =
|
|
110
|
-
viewerContext.entityCompanionProvider.getCompanionForEntity(LocalMemoryTestEntity)[
|
|
111
|
-
'tableDataCoordinator'
|
|
112
|
-
]['cacheAdapter']['genericCacher'];
|
|
113
|
-
const cacheKeyMaker = genericCacher['makeCacheKey'].bind(genericCacher);
|
|
114
|
-
expect(entity1WithVc2.getAllFields()).toMatchObject({
|
|
115
|
-
id: entity1WithVc2.getID(),
|
|
116
|
-
name: 'blah',
|
|
117
|
-
dateField: date,
|
|
118
|
-
});
|
|
119
|
-
expect(genericLocalMemoryCacherLoadManySpy).toBeCalledWith([
|
|
120
|
-
cacheKeyMaker('id', entity1WithVc2.getID()),
|
|
121
|
-
]);
|
|
122
|
-
expect(genericLocalMemoryCacherLoadManySpy).toBeCalledTimes(2);
|
|
123
|
-
});
|
|
124
|
-
|
|
125
104
|
it('respects the parameters of a noop cache', async () => {
|
|
126
|
-
const
|
|
127
|
-
|
|
128
|
-
);
|
|
105
|
+
const entityCompanionProvider = createNoOpLocalMemoryIntegrationTestEntityCompanionProvider();
|
|
106
|
+
const viewerContext = new ViewerContext(entityCompanionProvider);
|
|
129
107
|
const genericCacher =
|
|
130
108
|
viewerContext.entityCompanionProvider.getCompanionForEntity(LocalMemoryTestEntity)[
|
|
131
109
|
'tableDataCoordinator'
|
|
@@ -133,17 +111,29 @@ describe(GenericLocalMemoryCacher, () => {
|
|
|
133
111
|
const cacheKeyMaker = genericCacher['makeCacheKey'].bind(genericCacher);
|
|
134
112
|
|
|
135
113
|
const date = new Date();
|
|
136
|
-
const entity1Created = await LocalMemoryTestEntity.creator(
|
|
114
|
+
const entity1Created = await LocalMemoryTestEntity.creator(
|
|
115
|
+
viewerContext,
|
|
116
|
+
viewerContext.getNonTransactionalQueryContextForDatabaseAdaptorFlavor('postgres')
|
|
117
|
+
)
|
|
137
118
|
.setField('name', 'blah')
|
|
138
119
|
.setField('dateField', date)
|
|
139
120
|
.enforceCreateAsync();
|
|
140
121
|
|
|
141
122
|
// loading an entity will try to put it in cache but it's a noop cache, so it should be a miss
|
|
142
|
-
const entity1 = await LocalMemoryTestEntity.loader(
|
|
123
|
+
const entity1 = await LocalMemoryTestEntity.loader(
|
|
124
|
+
viewerContext,
|
|
125
|
+
viewerContext.getNonTransactionalQueryContextForDatabaseAdaptorFlavor('postgres')
|
|
126
|
+
)
|
|
143
127
|
.enforcing()
|
|
144
128
|
.loadByIDAsync(entity1Created.getID());
|
|
145
129
|
|
|
146
|
-
const
|
|
130
|
+
const localMemoryCacheAdapterProvider = (
|
|
131
|
+
entityCompanionProvider['cacheAdapterFlavors'] as ReadonlyMap<
|
|
132
|
+
CacheAdapterFlavor,
|
|
133
|
+
CacheAdapterFlavorDefinition
|
|
134
|
+
>
|
|
135
|
+
).get('local-memory')!.cacheAdapterProvider as LocalMemoryCacheAdapterProvider;
|
|
136
|
+
const entitySpecificGenericCacher = localMemoryCacheAdapterProvider[
|
|
147
137
|
'localMemoryCacheAdapterMap'
|
|
148
138
|
].get(
|
|
149
139
|
viewerContext.entityCompanionProvider.getCompanionForEntity(LocalMemoryTestEntity)
|
|
@@ -160,9 +150,10 @@ describe(GenericLocalMemoryCacher, () => {
|
|
|
160
150
|
// a non existent db fetch should try to write negative result ('') but it's a noop cache, so it should be a miss
|
|
161
151
|
const nonExistentId = uuidv4();
|
|
162
152
|
|
|
163
|
-
const entityNonExistentResult = await LocalMemoryTestEntity.loader(
|
|
164
|
-
|
|
165
|
-
|
|
153
|
+
const entityNonExistentResult = await LocalMemoryTestEntity.loader(
|
|
154
|
+
viewerContext,
|
|
155
|
+
viewerContext.getNonTransactionalQueryContextForDatabaseAdaptorFlavor('postgres')
|
|
156
|
+
).loadByIDAsync(nonExistentId);
|
|
166
157
|
expect(entityNonExistentResult.ok).toBe(false);
|
|
167
158
|
|
|
168
159
|
const nonExistentCachedResult = await entitySpecificGenericCacher.loadManyAsync([
|
|
@@ -14,8 +14,8 @@ export const createLocalMemoryTestEntityCompanionProvider = (
|
|
|
14
14
|
): EntityCompanionProvider => {
|
|
15
15
|
const localMemoryCacheAdapterProvider =
|
|
16
16
|
localMemoryOptions.maxSize === 0 && localMemoryOptions.ttlSeconds === 0
|
|
17
|
-
? LocalMemoryCacheAdapterProvider.
|
|
18
|
-
: LocalMemoryCacheAdapterProvider.
|
|
17
|
+
? LocalMemoryCacheAdapterProvider.createNoOpProvider()
|
|
18
|
+
: LocalMemoryCacheAdapterProvider.createProviderWithOptions(localMemoryOptions);
|
|
19
19
|
return new EntityCompanionProvider(
|
|
20
20
|
metricsAdapter,
|
|
21
21
|
new Map([
|
|
@@ -38,7 +38,7 @@ export const createLocalMemoryTestEntityCompanionProvider = (
|
|
|
38
38
|
);
|
|
39
39
|
};
|
|
40
40
|
|
|
41
|
-
export const
|
|
41
|
+
export const createNoOpLocalMemoryIntegrationTestEntityCompanionProvider = (
|
|
42
42
|
metricsAdapter: IEntityMetricsAdapter = new NoOpEntityMetricsAdapter()
|
|
43
43
|
): EntityCompanionProvider => {
|
|
44
44
|
return createLocalMemoryTestEntityCompanionProvider(
|