@naturalcycles/js-lib 14.85.0 → 14.85.1
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/decorators/asyncMemo.decorator.d.ts +5 -2
- package/dist/decorators/asyncMemo.decorator.js +5 -2
- package/dist/decorators/memo.decorator.d.ts +5 -2
- package/dist/decorators/memo.decorator.js +19 -5
- package/dist/decorators/memoFn.js +19 -5
- package/dist/decorators/memoFnAsync.js +4 -1
- package/dist-esm/decorators/asyncMemo.decorator.js +5 -2
- package/dist-esm/decorators/memo.decorator.js +19 -5
- package/dist-esm/decorators/memoFn.js +19 -5
- package/dist-esm/decorators/memoFnAsync.js +4 -1
- package/package.json +1 -1
- package/src/decorators/asyncMemo.decorator.ts +11 -4
- package/src/decorators/memo.decorator.ts +24 -8
- package/src/decorators/memoFn.ts +19 -6
- package/src/decorators/memoFnAsync.ts +5 -1
|
@@ -12,9 +12,12 @@ export interface AsyncMemoOptions {
|
|
|
12
12
|
*/
|
|
13
13
|
cacheKeyFn?: (args: any[]) => any;
|
|
14
14
|
/**
|
|
15
|
-
*
|
|
15
|
+
* Default true.
|
|
16
16
|
*
|
|
17
|
-
*
|
|
17
|
+
* Set to `false` to skip caching rejected promises (errors).
|
|
18
|
+
*
|
|
19
|
+
* True will ensure "max 1 execution", but will "remember" rejection.
|
|
20
|
+
* False will allow >1 execution in case of errors.
|
|
18
21
|
*/
|
|
19
22
|
cacheRejections?: boolean;
|
|
20
23
|
/**
|
|
@@ -18,7 +18,7 @@ const _AsyncMemo = (opt = {}) => (target, key, descriptor) => {
|
|
|
18
18
|
const originalFn = descriptor.value;
|
|
19
19
|
// Map from "instance" of the Class where @_AsyncMemo is applied to AsyncMemoCache instance.
|
|
20
20
|
const cache = new Map();
|
|
21
|
-
const { logHit = false, logMiss = false, logArgs = true, logger = console, cacheFactory = () => new memo_util_1.MapMemoCache(), cacheKeyFn = memo_util_1.jsonMemoSerializer, cacheRejections =
|
|
21
|
+
const { logHit = false, logMiss = false, logArgs = true, logger = console, cacheFactory = () => new memo_util_1.MapMemoCache(), cacheKeyFn = memo_util_1.jsonMemoSerializer, cacheRejections = true, } = opt;
|
|
22
22
|
const keyStr = String(key);
|
|
23
23
|
const methodSignature = (0, decorator_util_1._getTargetMethodSignature)(target, keyStr);
|
|
24
24
|
descriptor.value = async function (...args) {
|
|
@@ -42,7 +42,10 @@ const _AsyncMemo = (opt = {}) => (target, key, descriptor) => {
|
|
|
42
42
|
if (logHit) {
|
|
43
43
|
logger.log(`${(0, decorator_util_1._getMethodSignature)(ctx, keyStr)}(${(0, decorator_util_1._getArgsSignature)(args, logArgs)}) @_AsyncMemo hit`);
|
|
44
44
|
}
|
|
45
|
-
|
|
45
|
+
if (value instanceof Error) {
|
|
46
|
+
throw value;
|
|
47
|
+
}
|
|
48
|
+
return value;
|
|
46
49
|
}
|
|
47
50
|
// Here we know it's a MISS, let's execute the real method
|
|
48
51
|
const started = Date.now();
|
|
@@ -12,8 +12,11 @@ export interface MemoOptions {
|
|
|
12
12
|
*/
|
|
13
13
|
cacheKeyFn?: (args: any[]) => any;
|
|
14
14
|
/**
|
|
15
|
-
* Defaults to
|
|
16
|
-
* Set to
|
|
15
|
+
* Defaults to true.
|
|
16
|
+
* Set to false to skip caching errors.
|
|
17
|
+
*
|
|
18
|
+
* True will ensure "max 1 execution", but will "remember" errors.
|
|
19
|
+
* False will allow >1 execution in case of errors.
|
|
17
20
|
*/
|
|
18
21
|
cacheErrors?: boolean;
|
|
19
22
|
/**
|
|
@@ -37,12 +37,13 @@ const _Memo = (opt = {}) => (target, key, descriptor) => {
|
|
|
37
37
|
// UPD: tests show that normal Map also doesn't leak (to be tested further)
|
|
38
38
|
// Normal Map is needed to allow .dropCache()
|
|
39
39
|
const cache = new Map();
|
|
40
|
-
const { logHit = false, logMiss = false, logArgs = true, logger = console, cacheFactory = () => new memo_util_1.MapMemoCache(), cacheKeyFn = memo_util_1.jsonMemoSerializer, cacheErrors =
|
|
40
|
+
const { logHit = false, logMiss = false, logArgs = true, logger = console, cacheFactory = () => new memo_util_1.MapMemoCache(), cacheKeyFn = memo_util_1.jsonMemoSerializer, cacheErrors = true, } = opt;
|
|
41
41
|
const keyStr = String(key);
|
|
42
42
|
const methodSignature = (0, decorator_util_1._getTargetMethodSignature)(target, keyStr);
|
|
43
43
|
descriptor.value = function (...args) {
|
|
44
44
|
const ctx = this;
|
|
45
45
|
const cacheKey = cacheKeyFn(args);
|
|
46
|
+
let value;
|
|
46
47
|
if (!cache.has(ctx)) {
|
|
47
48
|
cache.set(ctx, cacheFactory());
|
|
48
49
|
}
|
|
@@ -50,18 +51,31 @@ const _Memo = (opt = {}) => (target, key, descriptor) => {
|
|
|
50
51
|
if (logHit) {
|
|
51
52
|
logger.log(`${(0, decorator_util_1._getMethodSignature)(ctx, keyStr)}(${(0, decorator_util_1._getArgsSignature)(args, logArgs)}) @_Memo hit`);
|
|
52
53
|
}
|
|
53
|
-
|
|
54
|
+
value = cache.get(ctx).get(cacheKey);
|
|
55
|
+
if (value instanceof Error) {
|
|
56
|
+
throw value;
|
|
57
|
+
}
|
|
58
|
+
return value;
|
|
54
59
|
}
|
|
55
60
|
const started = Date.now();
|
|
56
|
-
let value;
|
|
57
61
|
try {
|
|
58
62
|
value = originalFn.apply(ctx, args);
|
|
59
|
-
|
|
63
|
+
try {
|
|
64
|
+
cache.get(ctx).set(cacheKey, value);
|
|
65
|
+
}
|
|
66
|
+
catch (err) {
|
|
67
|
+
logger.error(err);
|
|
68
|
+
}
|
|
60
69
|
return value;
|
|
61
70
|
}
|
|
62
71
|
catch (err) {
|
|
63
72
|
if (cacheErrors) {
|
|
64
|
-
|
|
73
|
+
try {
|
|
74
|
+
cache.get(ctx).set(cacheKey, err);
|
|
75
|
+
}
|
|
76
|
+
catch (err) {
|
|
77
|
+
logger.error(err);
|
|
78
|
+
}
|
|
65
79
|
}
|
|
66
80
|
throw err;
|
|
67
81
|
}
|
|
@@ -10,28 +10,42 @@ const memo_util_1 = require("./memo.util");
|
|
|
10
10
|
* Technically, you can use it with Async functions, but it'll return the Promise without awaiting it.
|
|
11
11
|
*/
|
|
12
12
|
function _memoFn(fn, opt = {}) {
|
|
13
|
-
const { logHit = false, logMiss = false, logArgs = true, logger = console, cacheErrors =
|
|
13
|
+
const { logHit = false, logMiss = false, logArgs = true, logger = console, cacheErrors = true, cacheFactory = () => new memo_util_1.MapMemoCache(), cacheKeyFn = memo_util_1.jsonMemoSerializer, } = opt;
|
|
14
14
|
const cache = cacheFactory();
|
|
15
15
|
const fnName = fn.name;
|
|
16
16
|
const memoizedFn = function (...args) {
|
|
17
17
|
const ctx = this;
|
|
18
18
|
const cacheKey = cacheKeyFn(args);
|
|
19
|
+
let value;
|
|
19
20
|
if (cache.has(cacheKey)) {
|
|
20
21
|
if (logHit) {
|
|
21
22
|
logger.log(`${fnName}(${(0, decorator_util_1._getArgsSignature)(args, logArgs)}) memoFn hit`);
|
|
22
23
|
}
|
|
23
|
-
|
|
24
|
+
value = cache.get(cacheKey);
|
|
25
|
+
if (value instanceof Error) {
|
|
26
|
+
throw value;
|
|
27
|
+
}
|
|
28
|
+
return value;
|
|
24
29
|
}
|
|
25
30
|
const started = Date.now();
|
|
26
|
-
let value;
|
|
27
31
|
try {
|
|
28
32
|
value = fn.apply(ctx, args);
|
|
29
|
-
|
|
33
|
+
try {
|
|
34
|
+
cache.set(cacheKey, value);
|
|
35
|
+
}
|
|
36
|
+
catch (err) {
|
|
37
|
+
logger.error(err);
|
|
38
|
+
}
|
|
30
39
|
return value;
|
|
31
40
|
}
|
|
32
41
|
catch (err) {
|
|
33
42
|
if (cacheErrors) {
|
|
34
|
-
|
|
43
|
+
try {
|
|
44
|
+
cache.set(cacheKey, err);
|
|
45
|
+
}
|
|
46
|
+
catch (err) {
|
|
47
|
+
logger.error(err);
|
|
48
|
+
}
|
|
35
49
|
}
|
|
36
50
|
throw err;
|
|
37
51
|
}
|
|
@@ -9,7 +9,7 @@ const memo_util_1 = require("./memo.util");
|
|
|
9
9
|
* To support Async functions - use _memoFnAsync
|
|
10
10
|
*/
|
|
11
11
|
function _memoFnAsync(fn, opt = {}) {
|
|
12
|
-
const { logHit = false, logMiss = false, logArgs = true, logger = console, cacheRejections =
|
|
12
|
+
const { logHit = false, logMiss = false, logArgs = true, logger = console, cacheRejections = true, cacheFactory = () => new memo_util_1.MapMemoCache(), cacheKeyFn = memo_util_1.jsonMemoSerializer, } = opt;
|
|
13
13
|
const cache = cacheFactory();
|
|
14
14
|
const fnName = fn.name;
|
|
15
15
|
const memoizedFn = async function (...args) {
|
|
@@ -26,6 +26,9 @@ function _memoFnAsync(fn, opt = {}) {
|
|
|
26
26
|
if (logHit) {
|
|
27
27
|
logger.log(`${fnName}(${(0, decorator_util_1._getArgsSignature)(args, logArgs)}) memoFnAsync hit`);
|
|
28
28
|
}
|
|
29
|
+
if (value instanceof Error) {
|
|
30
|
+
throw value;
|
|
31
|
+
}
|
|
29
32
|
return value;
|
|
30
33
|
}
|
|
31
34
|
const started = Date.now();
|
|
@@ -15,7 +15,7 @@ export const _AsyncMemo = (opt = {}) => (target, key, descriptor) => {
|
|
|
15
15
|
const originalFn = descriptor.value;
|
|
16
16
|
// Map from "instance" of the Class where @_AsyncMemo is applied to AsyncMemoCache instance.
|
|
17
17
|
const cache = new Map();
|
|
18
|
-
const { logHit = false, logMiss = false, logArgs = true, logger = console, cacheFactory = () => new MapMemoCache(), cacheKeyFn = jsonMemoSerializer, cacheRejections =
|
|
18
|
+
const { logHit = false, logMiss = false, logArgs = true, logger = console, cacheFactory = () => new MapMemoCache(), cacheKeyFn = jsonMemoSerializer, cacheRejections = true, } = opt;
|
|
19
19
|
const keyStr = String(key);
|
|
20
20
|
const methodSignature = _getTargetMethodSignature(target, keyStr);
|
|
21
21
|
descriptor.value = async function (...args) {
|
|
@@ -39,7 +39,10 @@ export const _AsyncMemo = (opt = {}) => (target, key, descriptor) => {
|
|
|
39
39
|
if (logHit) {
|
|
40
40
|
logger.log(`${_getMethodSignature(ctx, keyStr)}(${_getArgsSignature(args, logArgs)}) @_AsyncMemo hit`);
|
|
41
41
|
}
|
|
42
|
-
|
|
42
|
+
if (value instanceof Error) {
|
|
43
|
+
throw value;
|
|
44
|
+
}
|
|
45
|
+
return value;
|
|
43
46
|
}
|
|
44
47
|
// Here we know it's a MISS, let's execute the real method
|
|
45
48
|
const started = Date.now();
|
|
@@ -34,12 +34,13 @@ export const _Memo = (opt = {}) => (target, key, descriptor) => {
|
|
|
34
34
|
// UPD: tests show that normal Map also doesn't leak (to be tested further)
|
|
35
35
|
// Normal Map is needed to allow .dropCache()
|
|
36
36
|
const cache = new Map();
|
|
37
|
-
const { logHit = false, logMiss = false, logArgs = true, logger = console, cacheFactory = () => new MapMemoCache(), cacheKeyFn = jsonMemoSerializer, cacheErrors =
|
|
37
|
+
const { logHit = false, logMiss = false, logArgs = true, logger = console, cacheFactory = () => new MapMemoCache(), cacheKeyFn = jsonMemoSerializer, cacheErrors = true, } = opt;
|
|
38
38
|
const keyStr = String(key);
|
|
39
39
|
const methodSignature = _getTargetMethodSignature(target, keyStr);
|
|
40
40
|
descriptor.value = function (...args) {
|
|
41
41
|
const ctx = this;
|
|
42
42
|
const cacheKey = cacheKeyFn(args);
|
|
43
|
+
let value;
|
|
43
44
|
if (!cache.has(ctx)) {
|
|
44
45
|
cache.set(ctx, cacheFactory());
|
|
45
46
|
}
|
|
@@ -47,18 +48,31 @@ export const _Memo = (opt = {}) => (target, key, descriptor) => {
|
|
|
47
48
|
if (logHit) {
|
|
48
49
|
logger.log(`${_getMethodSignature(ctx, keyStr)}(${_getArgsSignature(args, logArgs)}) @_Memo hit`);
|
|
49
50
|
}
|
|
50
|
-
|
|
51
|
+
value = cache.get(ctx).get(cacheKey);
|
|
52
|
+
if (value instanceof Error) {
|
|
53
|
+
throw value;
|
|
54
|
+
}
|
|
55
|
+
return value;
|
|
51
56
|
}
|
|
52
57
|
const started = Date.now();
|
|
53
|
-
let value;
|
|
54
58
|
try {
|
|
55
59
|
value = originalFn.apply(ctx, args);
|
|
56
|
-
|
|
60
|
+
try {
|
|
61
|
+
cache.get(ctx).set(cacheKey, value);
|
|
62
|
+
}
|
|
63
|
+
catch (err) {
|
|
64
|
+
logger.error(err);
|
|
65
|
+
}
|
|
57
66
|
return value;
|
|
58
67
|
}
|
|
59
68
|
catch (err) {
|
|
60
69
|
if (cacheErrors) {
|
|
61
|
-
|
|
70
|
+
try {
|
|
71
|
+
cache.get(ctx).set(cacheKey, err);
|
|
72
|
+
}
|
|
73
|
+
catch (err) {
|
|
74
|
+
logger.error(err);
|
|
75
|
+
}
|
|
62
76
|
}
|
|
63
77
|
throw err;
|
|
64
78
|
}
|
|
@@ -7,28 +7,42 @@ import { jsonMemoSerializer, MapMemoCache } from './memo.util';
|
|
|
7
7
|
* Technically, you can use it with Async functions, but it'll return the Promise without awaiting it.
|
|
8
8
|
*/
|
|
9
9
|
export function _memoFn(fn, opt = {}) {
|
|
10
|
-
const { logHit = false, logMiss = false, logArgs = true, logger = console, cacheErrors =
|
|
10
|
+
const { logHit = false, logMiss = false, logArgs = true, logger = console, cacheErrors = true, cacheFactory = () => new MapMemoCache(), cacheKeyFn = jsonMemoSerializer, } = opt;
|
|
11
11
|
const cache = cacheFactory();
|
|
12
12
|
const fnName = fn.name;
|
|
13
13
|
const memoizedFn = function (...args) {
|
|
14
14
|
const ctx = this;
|
|
15
15
|
const cacheKey = cacheKeyFn(args);
|
|
16
|
+
let value;
|
|
16
17
|
if (cache.has(cacheKey)) {
|
|
17
18
|
if (logHit) {
|
|
18
19
|
logger.log(`${fnName}(${_getArgsSignature(args, logArgs)}) memoFn hit`);
|
|
19
20
|
}
|
|
20
|
-
|
|
21
|
+
value = cache.get(cacheKey);
|
|
22
|
+
if (value instanceof Error) {
|
|
23
|
+
throw value;
|
|
24
|
+
}
|
|
25
|
+
return value;
|
|
21
26
|
}
|
|
22
27
|
const started = Date.now();
|
|
23
|
-
let value;
|
|
24
28
|
try {
|
|
25
29
|
value = fn.apply(ctx, args);
|
|
26
|
-
|
|
30
|
+
try {
|
|
31
|
+
cache.set(cacheKey, value);
|
|
32
|
+
}
|
|
33
|
+
catch (err) {
|
|
34
|
+
logger.error(err);
|
|
35
|
+
}
|
|
27
36
|
return value;
|
|
28
37
|
}
|
|
29
38
|
catch (err) {
|
|
30
39
|
if (cacheErrors) {
|
|
31
|
-
|
|
40
|
+
try {
|
|
41
|
+
cache.set(cacheKey, err);
|
|
42
|
+
}
|
|
43
|
+
catch (err) {
|
|
44
|
+
logger.error(err);
|
|
45
|
+
}
|
|
32
46
|
}
|
|
33
47
|
throw err;
|
|
34
48
|
}
|
|
@@ -6,7 +6,7 @@ import { jsonMemoSerializer, MapMemoCache } from './memo.util';
|
|
|
6
6
|
* To support Async functions - use _memoFnAsync
|
|
7
7
|
*/
|
|
8
8
|
export function _memoFnAsync(fn, opt = {}) {
|
|
9
|
-
const { logHit = false, logMiss = false, logArgs = true, logger = console, cacheRejections =
|
|
9
|
+
const { logHit = false, logMiss = false, logArgs = true, logger = console, cacheRejections = true, cacheFactory = () => new MapMemoCache(), cacheKeyFn = jsonMemoSerializer, } = opt;
|
|
10
10
|
const cache = cacheFactory();
|
|
11
11
|
const fnName = fn.name;
|
|
12
12
|
const memoizedFn = async function (...args) {
|
|
@@ -23,6 +23,9 @@ export function _memoFnAsync(fn, opt = {}) {
|
|
|
23
23
|
if (logHit) {
|
|
24
24
|
logger.log(`${fnName}(${_getArgsSignature(args, logArgs)}) memoFnAsync hit`);
|
|
25
25
|
}
|
|
26
|
+
if (value instanceof Error) {
|
|
27
|
+
throw value;
|
|
28
|
+
}
|
|
26
29
|
return value;
|
|
27
30
|
}
|
|
28
31
|
const started = Date.now();
|
package/package.json
CHANGED
|
@@ -18,9 +18,12 @@ export interface AsyncMemoOptions {
|
|
|
18
18
|
cacheKeyFn?: (args: any[]) => any
|
|
19
19
|
|
|
20
20
|
/**
|
|
21
|
-
*
|
|
21
|
+
* Default true.
|
|
22
22
|
*
|
|
23
|
-
*
|
|
23
|
+
* Set to `false` to skip caching rejected promises (errors).
|
|
24
|
+
*
|
|
25
|
+
* True will ensure "max 1 execution", but will "remember" rejection.
|
|
26
|
+
* False will allow >1 execution in case of errors.
|
|
24
27
|
*/
|
|
25
28
|
cacheRejections?: boolean
|
|
26
29
|
|
|
@@ -73,7 +76,7 @@ export const _AsyncMemo =
|
|
|
73
76
|
logger = console,
|
|
74
77
|
cacheFactory = () => new MapMemoCache(),
|
|
75
78
|
cacheKeyFn = jsonMemoSerializer,
|
|
76
|
-
cacheRejections =
|
|
79
|
+
cacheRejections = true,
|
|
77
80
|
} = opt
|
|
78
81
|
|
|
79
82
|
const keyStr = String(key)
|
|
@@ -110,7 +113,11 @@ export const _AsyncMemo =
|
|
|
110
113
|
)
|
|
111
114
|
}
|
|
112
115
|
|
|
113
|
-
|
|
116
|
+
if (value instanceof Error) {
|
|
117
|
+
throw value
|
|
118
|
+
}
|
|
119
|
+
|
|
120
|
+
return value
|
|
114
121
|
}
|
|
115
122
|
|
|
116
123
|
// Here we know it's a MISS, let's execute the real method
|
|
@@ -18,8 +18,11 @@ export interface MemoOptions {
|
|
|
18
18
|
cacheKeyFn?: (args: any[]) => any
|
|
19
19
|
|
|
20
20
|
/**
|
|
21
|
-
* Defaults to
|
|
22
|
-
* Set to
|
|
21
|
+
* Defaults to true.
|
|
22
|
+
* Set to false to skip caching errors.
|
|
23
|
+
*
|
|
24
|
+
* True will ensure "max 1 execution", but will "remember" errors.
|
|
25
|
+
* False will allow >1 execution in case of errors.
|
|
23
26
|
*/
|
|
24
27
|
cacheErrors?: boolean
|
|
25
28
|
|
|
@@ -89,7 +92,7 @@ export const _Memo =
|
|
|
89
92
|
logger = console,
|
|
90
93
|
cacheFactory = () => new MapMemoCache(),
|
|
91
94
|
cacheKeyFn = jsonMemoSerializer,
|
|
92
|
-
cacheErrors =
|
|
95
|
+
cacheErrors = true,
|
|
93
96
|
} = opt
|
|
94
97
|
|
|
95
98
|
const keyStr = String(key)
|
|
@@ -97,8 +100,8 @@ export const _Memo =
|
|
|
97
100
|
|
|
98
101
|
descriptor.value = function (this: typeof target, ...args: any[]): any {
|
|
99
102
|
const ctx = this
|
|
100
|
-
|
|
101
103
|
const cacheKey = cacheKeyFn(args)
|
|
104
|
+
let value: any
|
|
102
105
|
|
|
103
106
|
if (!cache.has(ctx)) {
|
|
104
107
|
cache.set(ctx, cacheFactory())
|
|
@@ -109,21 +112,34 @@ export const _Memo =
|
|
|
109
112
|
)
|
|
110
113
|
}
|
|
111
114
|
|
|
112
|
-
|
|
115
|
+
value = cache.get(ctx)!.get(cacheKey)
|
|
116
|
+
|
|
117
|
+
if (value instanceof Error) {
|
|
118
|
+
throw value
|
|
119
|
+
}
|
|
120
|
+
|
|
121
|
+
return value
|
|
113
122
|
}
|
|
114
123
|
|
|
115
124
|
const started = Date.now()
|
|
116
|
-
let value: any
|
|
117
125
|
|
|
118
126
|
try {
|
|
119
127
|
value = originalFn.apply(ctx, args)
|
|
120
128
|
|
|
121
|
-
|
|
129
|
+
try {
|
|
130
|
+
cache.get(ctx)!.set(cacheKey, value)
|
|
131
|
+
} catch (err) {
|
|
132
|
+
logger.error(err)
|
|
133
|
+
}
|
|
122
134
|
|
|
123
135
|
return value
|
|
124
136
|
} catch (err) {
|
|
125
137
|
if (cacheErrors) {
|
|
126
|
-
|
|
138
|
+
try {
|
|
139
|
+
cache.get(ctx)!.set(cacheKey, err)
|
|
140
|
+
} catch (err) {
|
|
141
|
+
logger.error(err)
|
|
142
|
+
}
|
|
127
143
|
}
|
|
128
144
|
|
|
129
145
|
throw err
|
package/src/decorators/memoFn.ts
CHANGED
|
@@ -21,7 +21,7 @@ export function _memoFn<T extends (...args: any[]) => any>(
|
|
|
21
21
|
logMiss = false,
|
|
22
22
|
logArgs = true,
|
|
23
23
|
logger = console,
|
|
24
|
-
cacheErrors =
|
|
24
|
+
cacheErrors = true,
|
|
25
25
|
cacheFactory = () => new MapMemoCache(),
|
|
26
26
|
cacheKeyFn = jsonMemoSerializer,
|
|
27
27
|
} = opt
|
|
@@ -32,28 +32,41 @@ export function _memoFn<T extends (...args: any[]) => any>(
|
|
|
32
32
|
const memoizedFn = function (this: any, ...args: any[]): T {
|
|
33
33
|
const ctx = this
|
|
34
34
|
const cacheKey = cacheKeyFn(args)
|
|
35
|
+
let value: any
|
|
35
36
|
|
|
36
37
|
if (cache.has(cacheKey)) {
|
|
37
38
|
if (logHit) {
|
|
38
39
|
logger.log(`${fnName}(${_getArgsSignature(args, logArgs)}) memoFn hit`)
|
|
39
40
|
}
|
|
40
41
|
|
|
41
|
-
|
|
42
|
+
value = cache.get(cacheKey)
|
|
43
|
+
|
|
44
|
+
if (value instanceof Error) {
|
|
45
|
+
throw value
|
|
46
|
+
}
|
|
47
|
+
|
|
48
|
+
return value
|
|
42
49
|
}
|
|
43
50
|
|
|
44
51
|
const started = Date.now()
|
|
45
52
|
|
|
46
|
-
let value: any
|
|
47
|
-
|
|
48
53
|
try {
|
|
49
54
|
value = fn.apply(ctx, args)
|
|
50
55
|
|
|
51
|
-
|
|
56
|
+
try {
|
|
57
|
+
cache.set(cacheKey, value)
|
|
58
|
+
} catch (err) {
|
|
59
|
+
logger.error(err)
|
|
60
|
+
}
|
|
52
61
|
|
|
53
62
|
return value
|
|
54
63
|
} catch (err) {
|
|
55
64
|
if (cacheErrors) {
|
|
56
|
-
|
|
65
|
+
try {
|
|
66
|
+
cache.set(cacheKey, err)
|
|
67
|
+
} catch (err) {
|
|
68
|
+
logger.error(err)
|
|
69
|
+
}
|
|
57
70
|
}
|
|
58
71
|
|
|
59
72
|
throw err
|
|
@@ -20,7 +20,7 @@ export function _memoFnAsync<T extends (...args: any[]) => Promise<any>>(
|
|
|
20
20
|
logMiss = false,
|
|
21
21
|
logArgs = true,
|
|
22
22
|
logger = console,
|
|
23
|
-
cacheRejections =
|
|
23
|
+
cacheRejections = true,
|
|
24
24
|
cacheFactory = () => new MapMemoCache(),
|
|
25
25
|
cacheKeyFn = jsonMemoSerializer,
|
|
26
26
|
} = opt
|
|
@@ -44,6 +44,10 @@ export function _memoFnAsync<T extends (...args: any[]) => Promise<any>>(
|
|
|
44
44
|
logger.log(`${fnName}(${_getArgsSignature(args, logArgs)}) memoFnAsync hit`)
|
|
45
45
|
}
|
|
46
46
|
|
|
47
|
+
if (value instanceof Error) {
|
|
48
|
+
throw value
|
|
49
|
+
}
|
|
50
|
+
|
|
47
51
|
return value
|
|
48
52
|
}
|
|
49
53
|
|