@c9up/echo 0.1.4 → 0.1.5
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/CacheManager.d.ts +16 -4
- package/dist/CacheManager.d.ts.map +1 -1
- package/dist/CacheManager.js +20 -3
- package/dist/CacheManager.js.map +1 -1
- package/dist/drivers/MemoryDriver.d.ts.map +1 -1
- package/dist/drivers/MemoryDriver.js +21 -2
- package/dist/drivers/MemoryDriver.js.map +1 -1
- package/dist/drivers/RedisDriver.d.ts.map +1 -1
- package/dist/drivers/RedisDriver.js +14 -2
- package/dist/drivers/RedisDriver.js.map +1 -1
- package/dist/index.d.ts +9 -1
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +9 -1
- package/dist/index.js.map +1 -1
- package/package.json +1 -1
- package/src/CacheManager.ts +22 -4
- package/src/drivers/MemoryDriver.ts +20 -2
- package/src/drivers/RedisDriver.ts +13 -2
- package/src/index.ts +13 -1
package/dist/CacheManager.d.ts
CHANGED
|
@@ -13,7 +13,7 @@ export interface CacheConfig {
|
|
|
13
13
|
prefix?: string;
|
|
14
14
|
ttl?: number;
|
|
15
15
|
}
|
|
16
|
-
export declare class CacheManager
|
|
16
|
+
export declare class CacheManager {
|
|
17
17
|
private driver;
|
|
18
18
|
private prefix;
|
|
19
19
|
private defaultTtl;
|
|
@@ -22,15 +22,27 @@ export declare class CacheManager implements CacheDriver {
|
|
|
22
22
|
get<T = unknown>(key: string): Promise<T | null>;
|
|
23
23
|
set(key: string, value: unknown, ttlSeconds?: number): Promise<void>;
|
|
24
24
|
delete(key: string): Promise<boolean>;
|
|
25
|
-
|
|
25
|
+
/** Clear the whole cache (AdonisJS `cache.clear()`). */
|
|
26
|
+
clear(): Promise<void>;
|
|
26
27
|
has(key: string): Promise<boolean>;
|
|
28
|
+
/**
|
|
29
|
+
* A cache view scoped under an extra key prefix (AdonisJS `cache.namespace()`).
|
|
30
|
+
* `cache.namespace('users').get('42')` reads/writes `users:42` (composed with
|
|
31
|
+
* any existing prefix). Shares the same driver + default TTL.
|
|
32
|
+
*/
|
|
33
|
+
namespace(ns: string): CacheManager;
|
|
27
34
|
/** Set a value with tags for grouped invalidation. */
|
|
28
35
|
setWithTags(key: string, value: unknown, tags: string[], ttlSeconds?: number): Promise<void>;
|
|
29
36
|
/** Flush only entries with matching tags. */
|
|
30
37
|
flushTags(tags: string[]): Promise<void>;
|
|
31
38
|
/** In-flight promises for stampede prevention. Each factory is typed per-call; the map is keyed by prefixed cache key. */
|
|
32
39
|
private inflight;
|
|
33
|
-
/**
|
|
34
|
-
|
|
40
|
+
/**
|
|
41
|
+
* Fetch from cache, or compute via `factory` and store (AdonisJS
|
|
42
|
+
* `cache.getOrSet`). Single-flight: concurrent misses share one factory call.
|
|
43
|
+
* (Positional `(key, ttl, factory)` is a deliberate simplification over
|
|
44
|
+
* Adonis's object form — echo keeps a leaner cache surface.)
|
|
45
|
+
*/
|
|
46
|
+
getOrSet<T>(key: string, ttl: number, factory: () => Promise<T>): Promise<T>;
|
|
35
47
|
}
|
|
36
48
|
//# sourceMappingURL=CacheManager.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"CacheManager.d.ts","sourceRoot":"","sources":["../src/CacheManager.ts"],"names":[],"mappings":"AAAA;;GAEG;AAEH,MAAM,WAAW,WAAW;IAC3B,GAAG,CAAC,CAAC,GAAG,OAAO,EAAE,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC,CAAC,GAAG,IAAI,CAAC,CAAC;IACjD,GAAG,CAAC,GAAG,EAAE,MAAM,EAAE,KAAK,EAAE,OAAO,EAAE,UAAU,CAAC,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC,CAAC;IACrE,MAAM,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC,OAAO,CAAC,CAAC;IACtC,KAAK,IAAI,OAAO,CAAC,IAAI,CAAC,CAAC;IACvB,GAAG,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC,OAAO,CAAC,CAAC;CACnC;AAoBD,MAAM,WAAW,WAAW;IAC3B,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB,GAAG,CAAC,EAAE,MAAM,CAAC;CACb;AAED,qBAAa,
|
|
1
|
+
{"version":3,"file":"CacheManager.d.ts","sourceRoot":"","sources":["../src/CacheManager.ts"],"names":[],"mappings":"AAAA;;GAEG;AAEH,MAAM,WAAW,WAAW;IAC3B,GAAG,CAAC,CAAC,GAAG,OAAO,EAAE,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC,CAAC,GAAG,IAAI,CAAC,CAAC;IACjD,GAAG,CAAC,GAAG,EAAE,MAAM,EAAE,KAAK,EAAE,OAAO,EAAE,UAAU,CAAC,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC,CAAC;IACrE,MAAM,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC,OAAO,CAAC,CAAC;IACtC,KAAK,IAAI,OAAO,CAAC,IAAI,CAAC,CAAC;IACvB,GAAG,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC,OAAO,CAAC,CAAC;CACnC;AAoBD,MAAM,WAAW,WAAW;IAC3B,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB,GAAG,CAAC,EAAE,MAAM,CAAC;CACb;AAED,qBAAa,YAAY;IACxB,OAAO,CAAC,MAAM,CAAc;IAC5B,OAAO,CAAC,MAAM,CAAS;IACvB,OAAO,CAAC,UAAU,CAAS;gBAEf,MAAM,EAAE,WAAW,EAAE,MAAM,CAAC,EAAE,WAAW;IAMrD,OAAO,CAAC,SAAS;IAIX,GAAG,CAAC,CAAC,GAAG,OAAO,EAAE,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC,CAAC,GAAG,IAAI,CAAC;IAIhD,GAAG,CAAC,GAAG,EAAE,MAAM,EAAE,KAAK,EAAE,OAAO,EAAE,UAAU,CAAC,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC;IAapE,MAAM,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC,OAAO,CAAC;IAI3C,wDAAwD;IAClD,KAAK,IAAI,OAAO,CAAC,IAAI,CAAC;IAItB,GAAG,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC,OAAO,CAAC;IAIxC;;;;OAIG;IACH,SAAS,CAAC,EAAE,EAAE,MAAM,GAAG,YAAY;IAOnC,sDAAsD;IAChD,WAAW,CAChB,GAAG,EAAE,MAAM,EACX,KAAK,EAAE,OAAO,EACd,IAAI,EAAE,MAAM,EAAE,EACd,UAAU,CAAC,EAAE,MAAM,GACjB,OAAO,CAAC,IAAI,CAAC;IAmBhB,6CAA6C;IACvC,SAAS,CAAC,IAAI,EAAE,MAAM,EAAE,GAAG,OAAO,CAAC,IAAI,CAAC;IAS9C,0HAA0H;IAC1H,OAAO,CAAC,QAAQ,CAA4C;IAE5D;;;;;OAKG;IACG,QAAQ,CAAC,CAAC,EACf,GAAG,EAAE,MAAM,EACX,GAAG,EAAE,MAAM,EACX,OAAO,EAAE,MAAM,OAAO,CAAC,CAAC,CAAC,GACvB,OAAO,CAAC,CAAC,CAAC;CA0Bb"}
|
package/dist/CacheManager.js
CHANGED
|
@@ -30,12 +30,24 @@ export class CacheManager {
|
|
|
30
30
|
async delete(key) {
|
|
31
31
|
return this.driver.delete(this.prefixKey(key));
|
|
32
32
|
}
|
|
33
|
-
|
|
33
|
+
/** Clear the whole cache (AdonisJS `cache.clear()`). */
|
|
34
|
+
async clear() {
|
|
34
35
|
return this.driver.flush();
|
|
35
36
|
}
|
|
36
37
|
async has(key) {
|
|
37
38
|
return this.driver.has(this.prefixKey(key));
|
|
38
39
|
}
|
|
40
|
+
/**
|
|
41
|
+
* A cache view scoped under an extra key prefix (AdonisJS `cache.namespace()`).
|
|
42
|
+
* `cache.namespace('users').get('42')` reads/writes `users:42` (composed with
|
|
43
|
+
* any existing prefix). Shares the same driver + default TTL.
|
|
44
|
+
*/
|
|
45
|
+
namespace(ns) {
|
|
46
|
+
return new CacheManager(this.driver, {
|
|
47
|
+
prefix: this.prefix ? `${this.prefix}:${ns}` : ns,
|
|
48
|
+
ttl: this.defaultTtl,
|
|
49
|
+
});
|
|
50
|
+
}
|
|
39
51
|
/** Set a value with tags for grouped invalidation. */
|
|
40
52
|
async setWithTags(key, value, tags, ttlSeconds) {
|
|
41
53
|
if (value === null || value === undefined) {
|
|
@@ -55,8 +67,13 @@ export class CacheManager {
|
|
|
55
67
|
}
|
|
56
68
|
/** In-flight promises for stampede prevention. Each factory is typed per-call; the map is keyed by prefixed cache key. */
|
|
57
69
|
inflight = new Map();
|
|
58
|
-
/**
|
|
59
|
-
|
|
70
|
+
/**
|
|
71
|
+
* Fetch from cache, or compute via `factory` and store (AdonisJS
|
|
72
|
+
* `cache.getOrSet`). Single-flight: concurrent misses share one factory call.
|
|
73
|
+
* (Positional `(key, ttl, factory)` is a deliberate simplification over
|
|
74
|
+
* Adonis's object form — echo keeps a leaner cache surface.)
|
|
75
|
+
*/
|
|
76
|
+
async getOrSet(key, ttl, factory) {
|
|
60
77
|
const prefixed = this.prefixKey(key);
|
|
61
78
|
const existing = this.inflight.get(prefixed);
|
|
62
79
|
if (existing)
|
package/dist/CacheManager.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"CacheManager.js","sourceRoot":"","sources":["../src/CacheManager.ts"],"names":[],"mappings":"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
|
|
1
|
+
{"version":3,"file":"CacheManager.js","sourceRoot":"","sources":["../src/CacheManager.ts"],"names":[],"mappings":"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"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"MemoryDriver.d.ts","sourceRoot":"","sources":["../../src/drivers/MemoryDriver.ts"],"names":[],"mappings":"AAAA;;;GAGG;AAEH,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,oBAAoB,CAAC;AAQtD,qBAAa,YAAa,YAAW,WAAW;;gBAKnC,eAAe,SAAS;IAiBpC,OAAO,IAAI,IAAI;IAIT,GAAG,CAAC,CAAC,GAAG,OAAO,EAAE,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC,CAAC,GAAG,IAAI,CAAC;
|
|
1
|
+
{"version":3,"file":"MemoryDriver.d.ts","sourceRoot":"","sources":["../../src/drivers/MemoryDriver.ts"],"names":[],"mappings":"AAAA;;;GAGG;AAEH,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,oBAAoB,CAAC;AAQtD,qBAAa,YAAa,YAAW,WAAW;;gBAKnC,eAAe,SAAS;IAiBpC,OAAO,IAAI,IAAI;IAIT,GAAG,CAAC,CAAC,GAAG,OAAO,EAAE,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC,CAAC,GAAG,IAAI,CAAC;IAqBhD,GAAG,CAAC,GAAG,EAAE,MAAM,EAAE,KAAK,EAAE,OAAO,EAAE,UAAU,CAAC,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC;IAkBpE,MAAM,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC,OAAO,CAAC;IAUrC,KAAK,IAAI,OAAO,CAAC,IAAI,CAAC;IAKtB,GAAG,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC,OAAO,CAAC;IAKxC,4CAA4C;IACtC,WAAW,CAChB,GAAG,EAAE,MAAM,EACX,KAAK,EAAE,OAAO,EACd,IAAI,EAAE,MAAM,EAAE,EACd,UAAU,CAAC,EAAE,MAAM,GACjB,OAAO,CAAC,IAAI,CAAC;IA+BhB,2DAA2D;IACrD,SAAS,CAAC,IAAI,EAAE,MAAM,EAAE,GAAG,OAAO,CAAC,IAAI,CAAC;CAgC9C"}
|
|
@@ -11,7 +11,7 @@ export class MemoryDriver {
|
|
|
11
11
|
const now = Date.now();
|
|
12
12
|
for (const [key, entry] of this.#store) {
|
|
13
13
|
if (entry.expiresAt > 0 && entry.expiresAt < now) {
|
|
14
|
-
this.#
|
|
14
|
+
this.#evict(key, entry);
|
|
15
15
|
}
|
|
16
16
|
}
|
|
17
17
|
}, sweepIntervalMs);
|
|
@@ -28,16 +28,35 @@ export class MemoryDriver {
|
|
|
28
28
|
if (!entry)
|
|
29
29
|
return null;
|
|
30
30
|
if (entry.expiresAt > 0 && entry.expiresAt < Date.now()) {
|
|
31
|
-
this.#
|
|
31
|
+
this.#evict(key, entry);
|
|
32
32
|
return null;
|
|
33
33
|
}
|
|
34
34
|
return entry.value;
|
|
35
35
|
}
|
|
36
|
+
/**
|
|
37
|
+
* Delete an entry AND scrub its tag-index refs. TTL expiry (sweep + lazy
|
|
38
|
+
* get) must go through this — a bare `#store.delete` left dangling refs in
|
|
39
|
+
* `#tagIndex`, which a later `set(key, vNew)` reusing the key would turn into
|
|
40
|
+
* a wrong-purge under flushTags (audit 2026-06-13).
|
|
41
|
+
*/
|
|
42
|
+
#evict(key, entry) {
|
|
43
|
+
for (const tag of entry.tags)
|
|
44
|
+
this.#tagIndex.get(tag)?.delete(key);
|
|
45
|
+
this.#store.delete(key);
|
|
46
|
+
}
|
|
36
47
|
async set(key, value, ttlSeconds) {
|
|
37
48
|
if (value === null || value === undefined) {
|
|
38
49
|
throw new TypeError("Echo: caching null/undefined values is not supported");
|
|
39
50
|
}
|
|
40
51
|
const expiresAt = ttlSeconds != null && ttlSeconds > 0 ? Date.now() + ttlSeconds * 1000 : 0;
|
|
52
|
+
// Reconcile the tag index: overwriting a previously-tagged key with an
|
|
53
|
+
// untagged value must drop its old tag-index refs, or a later flushTags
|
|
54
|
+
// would purge this fresh value (the F3 fix only covered setWithTags).
|
|
55
|
+
const prev = this.#store.get(key);
|
|
56
|
+
if (prev !== undefined) {
|
|
57
|
+
for (const t of prev.tags)
|
|
58
|
+
this.#tagIndex.get(t)?.delete(key);
|
|
59
|
+
}
|
|
41
60
|
this.#store.set(key, { value, expiresAt, tags: [] });
|
|
42
61
|
}
|
|
43
62
|
async delete(key) {
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"MemoryDriver.js","sourceRoot":"","sources":["../../src/drivers/MemoryDriver.ts"],"names":[],"mappings":"AAAA;;;GAGG;AAUH,MAAM,OAAO,YAAY;IACxB,MAAM,GAA4B,IAAI,GAAG,EAAE,CAAC;IAC5C,SAAS,GAA6B,IAAI,GAAG,EAAE,CAAC;IAChD,cAAc,CAAiC;IAE/C,YAAY,eAAe,GAAG,MAAM;QACnC,IAAI,CAAC,cAAc,GAAG,WAAW,CAAC,GAAG,EAAE;YACtC,MAAM,GAAG,GAAG,IAAI,CAAC,GAAG,EAAE,CAAC;YACvB,KAAK,MAAM,CAAC,GAAG,EAAE,KAAK,CAAC,IAAI,IAAI,CAAC,MAAM,EAAE,CAAC;gBACxC,IAAI,KAAK,CAAC,SAAS,GAAG,CAAC,IAAI,KAAK,CAAC,SAAS,GAAG,GAAG,EAAE,CAAC;oBAClD,IAAI,CAAC,MAAM,CAAC,
|
|
1
|
+
{"version":3,"file":"MemoryDriver.js","sourceRoot":"","sources":["../../src/drivers/MemoryDriver.ts"],"names":[],"mappings":"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"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"RedisDriver.d.ts","sourceRoot":"","sources":["../../src/drivers/RedisDriver.ts"],"names":[],"mappings":"AAAA;;;;;;;GAOG;AAEH,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,oBAAoB,CAAC;AAEtD,+EAA+E;AAC/E,MAAM,WAAW,WAAW;IAC3B,GAAG,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC,MAAM,GAAG,IAAI,CAAC,CAAC;IACzC,GAAG,CAAC,GAAG,EAAE,MAAM,EAAE,KAAK,EAAE,MAAM,EAAE,GAAG,IAAI,EAAE,OAAO,EAAE,GAAG,OAAO,CAAC,OAAO,CAAC,CAAC;IACtE,GAAG,CAAC,GAAG,EAAE,MAAM,GAAG,MAAM,EAAE,GAAG,OAAO,CAAC,MAAM,CAAC,CAAC;IAC7C,MAAM,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC,MAAM,CAAC,CAAC;IACrC,IAAI,CAAC,OAAO,EAAE,MAAM,GAAG,OAAO,CAAC,MAAM,EAAE,CAAC,CAAC;IACzC,IAAI,CAAC,GAAG,EAAE,MAAM,EAAE,GAAG,OAAO,EAAE,MAAM,EAAE,GAAG,OAAO,CAAC,MAAM,CAAC,CAAC;IACzD,IAAI,CAAC,GAAG,EAAE,MAAM,EAAE,GAAG,OAAO,EAAE,MAAM,EAAE,GAAG,OAAO,CAAC,MAAM,CAAC,CAAC;IACzD,QAAQ,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC,MAAM,EAAE,CAAC,CAAC;IACzC,MAAM,CAAC,GAAG,EAAE,MAAM,EAAE,OAAO,EAAE,MAAM,GAAG,OAAO,CAAC,MAAM,CAAC,CAAC;IACtD,GAAG,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC,MAAM,CAAC,CAAC;IAClC,IAAI,CAAC,CACJ,MAAM,EAAE,MAAM,EACd,WAAW,EAAE,OAAO,EACpB,OAAO,EAAE,MAAM,EACf,WAAW,EAAE,OAAO,EACpB,KAAK,EAAE,MAAM,GACX,OAAO,CAAC,CAAC,MAAM,EAAE,MAAM,EAAE,CAAC,CAAC,CAAC;CAC/B;AAED,qBAAa,WAAY,YAAW,WAAW;;gBAIlC,MAAM,EAAE,WAAW,EAAE,MAAM,SAAW;IAqB5C,MAAM,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC,OAAO,CAAC;IAerC,GAAG,CAAC,CAAC,GAAG,OAAO,EAAE,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC,CAAC,GAAG,IAAI,CAAC;IAMhD,GAAG,CAAC,GAAG,EAAE,MAAM,EAAE,KAAK,EAAE,OAAO,EAAE,UAAU,CAAC,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC;
|
|
1
|
+
{"version":3,"file":"RedisDriver.d.ts","sourceRoot":"","sources":["../../src/drivers/RedisDriver.ts"],"names":[],"mappings":"AAAA;;;;;;;GAOG;AAEH,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,oBAAoB,CAAC;AAEtD,+EAA+E;AAC/E,MAAM,WAAW,WAAW;IAC3B,GAAG,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC,MAAM,GAAG,IAAI,CAAC,CAAC;IACzC,GAAG,CAAC,GAAG,EAAE,MAAM,EAAE,KAAK,EAAE,MAAM,EAAE,GAAG,IAAI,EAAE,OAAO,EAAE,GAAG,OAAO,CAAC,OAAO,CAAC,CAAC;IACtE,GAAG,CAAC,GAAG,EAAE,MAAM,GAAG,MAAM,EAAE,GAAG,OAAO,CAAC,MAAM,CAAC,CAAC;IAC7C,MAAM,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC,MAAM,CAAC,CAAC;IACrC,IAAI,CAAC,OAAO,EAAE,MAAM,GAAG,OAAO,CAAC,MAAM,EAAE,CAAC,CAAC;IACzC,IAAI,CAAC,GAAG,EAAE,MAAM,EAAE,GAAG,OAAO,EAAE,MAAM,EAAE,GAAG,OAAO,CAAC,MAAM,CAAC,CAAC;IACzD,IAAI,CAAC,GAAG,EAAE,MAAM,EAAE,GAAG,OAAO,EAAE,MAAM,EAAE,GAAG,OAAO,CAAC,MAAM,CAAC,CAAC;IACzD,QAAQ,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC,MAAM,EAAE,CAAC,CAAC;IACzC,MAAM,CAAC,GAAG,EAAE,MAAM,EAAE,OAAO,EAAE,MAAM,GAAG,OAAO,CAAC,MAAM,CAAC,CAAC;IACtD,GAAG,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC,MAAM,CAAC,CAAC;IAClC,IAAI,CAAC,CACJ,MAAM,EAAE,MAAM,EACd,WAAW,EAAE,OAAO,EACpB,OAAO,EAAE,MAAM,EACf,WAAW,EAAE,OAAO,EACpB,KAAK,EAAE,MAAM,GACX,OAAO,CAAC,CAAC,MAAM,EAAE,MAAM,EAAE,CAAC,CAAC,CAAC;CAC/B;AAED,qBAAa,WAAY,YAAW,WAAW;;gBAIlC,MAAM,EAAE,WAAW,EAAE,MAAM,SAAW;IAqB5C,MAAM,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC,OAAO,CAAC;IAerC,GAAG,CAAC,CAAC,GAAG,OAAO,EAAE,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC,CAAC,GAAG,IAAI,CAAC;IAMhD,GAAG,CAAC,GAAG,EAAE,MAAM,EAAE,KAAK,EAAE,OAAO,EAAE,UAAU,CAAC,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC;IAoBpE,KAAK,IAAI,OAAO,CAAC,IAAI,CAAC;IAwBtB,GAAG,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC,OAAO,CAAC;IAKxC;;;;;;;OAOG;IACG,WAAW,CAChB,GAAG,EAAE,MAAM,EACX,KAAK,EAAE,OAAO,EACd,IAAI,EAAE,MAAM,EAAE,EACd,UAAU,CAAC,EAAE,MAAM,GACjB,OAAO,CAAC,IAAI,CAAC;IA6ChB;;;;;;OAMG;IACG,SAAS,CAAC,IAAI,EAAE,MAAM,EAAE,GAAG,OAAO,CAAC,IAAI,CAAC;CA6B9C"}
|
|
@@ -48,12 +48,24 @@ export class RedisDriver {
|
|
|
48
48
|
return JSON.parse(raw);
|
|
49
49
|
}
|
|
50
50
|
async set(key, value, ttlSeconds) {
|
|
51
|
+
const fullKey = this.#key(key);
|
|
52
|
+
// Reconcile tags: overwriting a previously-tagged key with an untagged
|
|
53
|
+
// value must drop it from its old tag sets + meta index, or a later
|
|
54
|
+
// flushTags would wrongly purge this fresh value (set() never touched the
|
|
55
|
+
// tag/meta keys, unlike delete()).
|
|
56
|
+
const metaKey = this.#metaKey(key);
|
|
57
|
+
const prevTags = await this.#client.smembers(metaKey);
|
|
58
|
+
for (const tag of prevTags) {
|
|
59
|
+
await this.#client.srem(`${this.#prefix}tag:${tag}`, fullKey);
|
|
60
|
+
}
|
|
61
|
+
if (prevTags.length > 0)
|
|
62
|
+
await this.#client.del(metaKey);
|
|
51
63
|
const serialized = JSON.stringify(value);
|
|
52
64
|
if (ttlSeconds && ttlSeconds > 0) {
|
|
53
|
-
await this.#client.set(
|
|
65
|
+
await this.#client.set(fullKey, serialized, "EX", ttlSeconds);
|
|
54
66
|
}
|
|
55
67
|
else {
|
|
56
|
-
await this.#client.set(
|
|
68
|
+
await this.#client.set(fullKey, serialized);
|
|
57
69
|
}
|
|
58
70
|
}
|
|
59
71
|
async flush() {
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"RedisDriver.js","sourceRoot":"","sources":["../../src/drivers/RedisDriver.ts"],"names":[],"mappings":"AAAA;;;;;;;GAOG;AAyBH,MAAM,OAAO,WAAW;IACvB,OAAO,CAAc;IACrB,OAAO,CAAS;IAEhB,YAAY,MAAmB,EAAE,MAAM,GAAG,QAAQ;QACjD,IAAI,CAAC,OAAO,GAAG,MAAM,CAAC;QACtB,IAAI,CAAC,OAAO,GAAG,MAAM,CAAC;IACvB,CAAC;IAED,IAAI,CAAC,CAAS;QACb,OAAO,GAAG,IAAI,CAAC,OAAO,GAAG,CAAC,EAAE,CAAC;IAC9B,CAAC;IAED;;;;;;;OAOG;IACH,QAAQ,CAAC,CAAS;QACjB,OAAO,GAAG,IAAI,CAAC,OAAO,aAAa,CAAC,EAAE,CAAC;IACxC,CAAC;IAED,KAAK,CAAC,MAAM,CAAC,GAAW;QACvB,MAAM,OAAO,GAAG,IAAI,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC;QAC/B,MAAM,OAAO,GAAG,IAAI,CAAC,QAAQ,CAAC,GAAG,CAAC,CAAC;QACnC,MAAM,IAAI,GAAG,MAAM,IAAI,CAAC,OAAO,CAAC,QAAQ,CAAC,OAAO,CAAC,CAAC;QAClD,KAAK,MAAM,GAAG,IAAI,IAAI,EAAE,CAAC;YACxB,MAAM,MAAM,GAAG,GAAG,IAAI,CAAC,OAAO,OAAO,GAAG,EAAE,CAAC;YAC3C,MAAM,IAAI,CAAC,OAAO,CAAC,IAAI,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;QAC1C,CAAC;QACD,IAAI,IAAI,CAAC,MAAM,GAAG,CAAC,EAAE,CAAC;YACrB,MAAM,IAAI,CAAC,OAAO,CAAC,GAAG,CAAC,OAAO,CAAC,CAAC;QACjC,CAAC;QACD,MAAM,KAAK,GAAG,MAAM,IAAI,CAAC,OAAO,CAAC,GAAG,CAAC,OAAO,CAAC,CAAC;QAC9C,OAAO,KAAK,GAAG,CAAC,CAAC;IAClB,CAAC;IAED,KAAK,CAAC,GAAG,CAAc,GAAW;QACjC,MAAM,GAAG,GAAG,MAAM,IAAI,CAAC,OAAO,CAAC,GAAG,CAAC,IAAI,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC,CAAC;QACnD,IAAI,GAAG,KAAK,IAAI;YAAE,OAAO,IAAI,CAAC;QAC9B,OAAO,IAAI,CAAC,KAAK,CAAC,GAAG,CAAM,CAAC;IAC7B,CAAC;IAED,KAAK,CAAC,GAAG,CAAC,GAAW,EAAE,KAAc,EAAE,UAAmB;QACzD,MAAM,
|
|
1
|
+
{"version":3,"file":"RedisDriver.js","sourceRoot":"","sources":["../../src/drivers/RedisDriver.ts"],"names":[],"mappings":"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"}
|
package/dist/index.d.ts
CHANGED
|
@@ -1,7 +1,8 @@
|
|
|
1
1
|
/**
|
|
2
2
|
* @c9up/echo — Cache layer for the Ream framework.
|
|
3
3
|
*
|
|
4
|
-
* Provides get/set/delete/
|
|
4
|
+
* Provides get/set/delete/clear/getOrSet/namespace/tags with pluggable drivers
|
|
5
|
+
* (Memory, Redis).
|
|
5
6
|
*
|
|
6
7
|
* @implements MISS-10
|
|
7
8
|
*/
|
|
@@ -10,4 +11,11 @@ export { CacheManager } from "./CacheManager.js";
|
|
|
10
11
|
export { MemoryDriver } from "./drivers/MemoryDriver.js";
|
|
11
12
|
export type { RedisClient } from "./drivers/RedisDriver.js";
|
|
12
13
|
export { RedisDriver } from "./drivers/RedisDriver.js";
|
|
14
|
+
export type { EchoProviderConfig } from "./EchoProvider.js";
|
|
15
|
+
import type { EchoProviderConfig } from "./EchoProvider.js";
|
|
16
|
+
/**
|
|
17
|
+
* Author-time config helper for `config/cache.ts` — AdonisJS cache `defineConfig`
|
|
18
|
+
* parity. Identity at runtime; the generic preserves literal types for inference.
|
|
19
|
+
*/
|
|
20
|
+
export declare function defineConfig<T extends EchoProviderConfig>(config: T): T;
|
|
13
21
|
//# sourceMappingURL=index.d.ts.map
|
package/dist/index.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA;;;;;;;GAOG;AAEH,YAAY,EAAE,WAAW,EAAE,WAAW,EAAE,MAAM,mBAAmB,CAAC;AAClE,OAAO,EAAE,YAAY,EAAE,MAAM,mBAAmB,CAAC;AACjD,OAAO,EAAE,YAAY,EAAE,MAAM,2BAA2B,CAAC;AACzD,YAAY,EAAE,WAAW,EAAE,MAAM,0BAA0B,CAAC;AAC5D,OAAO,EAAE,WAAW,EAAE,MAAM,0BAA0B,CAAC;AACvD,YAAY,EAAE,kBAAkB,EAAE,MAAM,mBAAmB,CAAC;AAE5D,OAAO,KAAK,EAAE,kBAAkB,EAAE,MAAM,mBAAmB,CAAC;AAE5D;;;GAGG;AACH,wBAAgB,YAAY,CAAC,CAAC,SAAS,kBAAkB,EAAE,MAAM,EAAE,CAAC,GAAG,CAAC,CAEvE"}
|
package/dist/index.js
CHANGED
|
@@ -1,11 +1,19 @@
|
|
|
1
1
|
/**
|
|
2
2
|
* @c9up/echo — Cache layer for the Ream framework.
|
|
3
3
|
*
|
|
4
|
-
* Provides get/set/delete/
|
|
4
|
+
* Provides get/set/delete/clear/getOrSet/namespace/tags with pluggable drivers
|
|
5
|
+
* (Memory, Redis).
|
|
5
6
|
*
|
|
6
7
|
* @implements MISS-10
|
|
7
8
|
*/
|
|
8
9
|
export { CacheManager } from "./CacheManager.js";
|
|
9
10
|
export { MemoryDriver } from "./drivers/MemoryDriver.js";
|
|
10
11
|
export { RedisDriver } from "./drivers/RedisDriver.js";
|
|
12
|
+
/**
|
|
13
|
+
* Author-time config helper for `config/cache.ts` — AdonisJS cache `defineConfig`
|
|
14
|
+
* parity. Identity at runtime; the generic preserves literal types for inference.
|
|
15
|
+
*/
|
|
16
|
+
export function defineConfig(config) {
|
|
17
|
+
return config;
|
|
18
|
+
}
|
|
11
19
|
//# sourceMappingURL=index.js.map
|
package/dist/index.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA;;;;;;;GAOG;AAGH,OAAO,EAAE,YAAY,EAAE,MAAM,mBAAmB,CAAC;AACjD,OAAO,EAAE,YAAY,EAAE,MAAM,2BAA2B,CAAC;AAEzD,OAAO,EAAE,WAAW,EAAE,MAAM,0BAA0B,CAAC;AAKvD;;;GAGG;AACH,MAAM,UAAU,YAAY,CAA+B,MAAS;IACnE,OAAO,MAAM,CAAC;AACf,CAAC"}
|
package/package.json
CHANGED
package/src/CacheManager.ts
CHANGED
|
@@ -34,7 +34,7 @@ export interface CacheConfig {
|
|
|
34
34
|
ttl?: number;
|
|
35
35
|
}
|
|
36
36
|
|
|
37
|
-
export class CacheManager
|
|
37
|
+
export class CacheManager {
|
|
38
38
|
private driver: CacheDriver;
|
|
39
39
|
private prefix: string;
|
|
40
40
|
private defaultTtl: number;
|
|
@@ -70,7 +70,8 @@ export class CacheManager implements CacheDriver {
|
|
|
70
70
|
return this.driver.delete(this.prefixKey(key));
|
|
71
71
|
}
|
|
72
72
|
|
|
73
|
-
|
|
73
|
+
/** Clear the whole cache (AdonisJS `cache.clear()`). */
|
|
74
|
+
async clear(): Promise<void> {
|
|
74
75
|
return this.driver.flush();
|
|
75
76
|
}
|
|
76
77
|
|
|
@@ -78,6 +79,18 @@ export class CacheManager implements CacheDriver {
|
|
|
78
79
|
return this.driver.has(this.prefixKey(key));
|
|
79
80
|
}
|
|
80
81
|
|
|
82
|
+
/**
|
|
83
|
+
* A cache view scoped under an extra key prefix (AdonisJS `cache.namespace()`).
|
|
84
|
+
* `cache.namespace('users').get('42')` reads/writes `users:42` (composed with
|
|
85
|
+
* any existing prefix). Shares the same driver + default TTL.
|
|
86
|
+
*/
|
|
87
|
+
namespace(ns: string): CacheManager {
|
|
88
|
+
return new CacheManager(this.driver, {
|
|
89
|
+
prefix: this.prefix ? `${this.prefix}:${ns}` : ns,
|
|
90
|
+
ttl: this.defaultTtl,
|
|
91
|
+
});
|
|
92
|
+
}
|
|
93
|
+
|
|
81
94
|
/** Set a value with tags for grouped invalidation. */
|
|
82
95
|
async setWithTags(
|
|
83
96
|
key: string,
|
|
@@ -116,8 +129,13 @@ export class CacheManager implements CacheDriver {
|
|
|
116
129
|
/** In-flight promises for stampede prevention. Each factory is typed per-call; the map is keyed by prefixed cache key. */
|
|
117
130
|
private inflight: Map<string, Promise<unknown>> = new Map();
|
|
118
131
|
|
|
119
|
-
/**
|
|
120
|
-
|
|
132
|
+
/**
|
|
133
|
+
* Fetch from cache, or compute via `factory` and store (AdonisJS
|
|
134
|
+
* `cache.getOrSet`). Single-flight: concurrent misses share one factory call.
|
|
135
|
+
* (Positional `(key, ttl, factory)` is a deliberate simplification over
|
|
136
|
+
* Adonis's object form — echo keeps a leaner cache surface.)
|
|
137
|
+
*/
|
|
138
|
+
async getOrSet<T>(
|
|
121
139
|
key: string,
|
|
122
140
|
ttl: number,
|
|
123
141
|
factory: () => Promise<T>,
|
|
@@ -21,7 +21,7 @@ export class MemoryDriver implements CacheDriver {
|
|
|
21
21
|
const now = Date.now();
|
|
22
22
|
for (const [key, entry] of this.#store) {
|
|
23
23
|
if (entry.expiresAt > 0 && entry.expiresAt < now) {
|
|
24
|
-
this.#
|
|
24
|
+
this.#evict(key, entry);
|
|
25
25
|
}
|
|
26
26
|
}
|
|
27
27
|
}, sweepIntervalMs);
|
|
@@ -41,12 +41,23 @@ export class MemoryDriver implements CacheDriver {
|
|
|
41
41
|
const entry = this.#store.get(key);
|
|
42
42
|
if (!entry) return null;
|
|
43
43
|
if (entry.expiresAt > 0 && entry.expiresAt < Date.now()) {
|
|
44
|
-
this.#
|
|
44
|
+
this.#evict(key, entry);
|
|
45
45
|
return null;
|
|
46
46
|
}
|
|
47
47
|
return entry.value as T;
|
|
48
48
|
}
|
|
49
49
|
|
|
50
|
+
/**
|
|
51
|
+
* Delete an entry AND scrub its tag-index refs. TTL expiry (sweep + lazy
|
|
52
|
+
* get) must go through this — a bare `#store.delete` left dangling refs in
|
|
53
|
+
* `#tagIndex`, which a later `set(key, vNew)` reusing the key would turn into
|
|
54
|
+
* a wrong-purge under flushTags (audit 2026-06-13).
|
|
55
|
+
*/
|
|
56
|
+
#evict(key: string, entry: CacheEntry): void {
|
|
57
|
+
for (const tag of entry.tags) this.#tagIndex.get(tag)?.delete(key);
|
|
58
|
+
this.#store.delete(key);
|
|
59
|
+
}
|
|
60
|
+
|
|
50
61
|
async set(key: string, value: unknown, ttlSeconds?: number): Promise<void> {
|
|
51
62
|
if (value === null || value === undefined) {
|
|
52
63
|
throw new TypeError(
|
|
@@ -55,6 +66,13 @@ export class MemoryDriver implements CacheDriver {
|
|
|
55
66
|
}
|
|
56
67
|
const expiresAt =
|
|
57
68
|
ttlSeconds != null && ttlSeconds > 0 ? Date.now() + ttlSeconds * 1000 : 0;
|
|
69
|
+
// Reconcile the tag index: overwriting a previously-tagged key with an
|
|
70
|
+
// untagged value must drop its old tag-index refs, or a later flushTags
|
|
71
|
+
// would purge this fresh value (the F3 fix only covered setWithTags).
|
|
72
|
+
const prev = this.#store.get(key);
|
|
73
|
+
if (prev !== undefined) {
|
|
74
|
+
for (const t of prev.tags) this.#tagIndex.get(t)?.delete(key);
|
|
75
|
+
}
|
|
58
76
|
this.#store.set(key, { value, expiresAt, tags: [] });
|
|
59
77
|
}
|
|
60
78
|
|
|
@@ -77,11 +77,22 @@ export class RedisDriver implements CacheDriver {
|
|
|
77
77
|
}
|
|
78
78
|
|
|
79
79
|
async set(key: string, value: unknown, ttlSeconds?: number): Promise<void> {
|
|
80
|
+
const fullKey = this.#key(key);
|
|
81
|
+
// Reconcile tags: overwriting a previously-tagged key with an untagged
|
|
82
|
+
// value must drop it from its old tag sets + meta index, or a later
|
|
83
|
+
// flushTags would wrongly purge this fresh value (set() never touched the
|
|
84
|
+
// tag/meta keys, unlike delete()).
|
|
85
|
+
const metaKey = this.#metaKey(key);
|
|
86
|
+
const prevTags = await this.#client.smembers(metaKey);
|
|
87
|
+
for (const tag of prevTags) {
|
|
88
|
+
await this.#client.srem(`${this.#prefix}tag:${tag}`, fullKey);
|
|
89
|
+
}
|
|
90
|
+
if (prevTags.length > 0) await this.#client.del(metaKey);
|
|
80
91
|
const serialized = JSON.stringify(value);
|
|
81
92
|
if (ttlSeconds && ttlSeconds > 0) {
|
|
82
|
-
await this.#client.set(
|
|
93
|
+
await this.#client.set(fullKey, serialized, "EX", ttlSeconds);
|
|
83
94
|
} else {
|
|
84
|
-
await this.#client.set(
|
|
95
|
+
await this.#client.set(fullKey, serialized);
|
|
85
96
|
}
|
|
86
97
|
}
|
|
87
98
|
|
package/src/index.ts
CHANGED
|
@@ -1,7 +1,8 @@
|
|
|
1
1
|
/**
|
|
2
2
|
* @c9up/echo — Cache layer for the Ream framework.
|
|
3
3
|
*
|
|
4
|
-
* Provides get/set/delete/
|
|
4
|
+
* Provides get/set/delete/clear/getOrSet/namespace/tags with pluggable drivers
|
|
5
|
+
* (Memory, Redis).
|
|
5
6
|
*
|
|
6
7
|
* @implements MISS-10
|
|
7
8
|
*/
|
|
@@ -11,3 +12,14 @@ export { CacheManager } from "./CacheManager.js";
|
|
|
11
12
|
export { MemoryDriver } from "./drivers/MemoryDriver.js";
|
|
12
13
|
export type { RedisClient } from "./drivers/RedisDriver.js";
|
|
13
14
|
export { RedisDriver } from "./drivers/RedisDriver.js";
|
|
15
|
+
export type { EchoProviderConfig } from "./EchoProvider.js";
|
|
16
|
+
|
|
17
|
+
import type { EchoProviderConfig } from "./EchoProvider.js";
|
|
18
|
+
|
|
19
|
+
/**
|
|
20
|
+
* Author-time config helper for `config/cache.ts` — AdonisJS cache `defineConfig`
|
|
21
|
+
* parity. Identity at runtime; the generic preserves literal types for inference.
|
|
22
|
+
*/
|
|
23
|
+
export function defineConfig<T extends EchoProviderConfig>(config: T): T {
|
|
24
|
+
return config;
|
|
25
|
+
}
|