@tanstack/query-core 5.55.2 → 5.55.4
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/legacy/notifyManager.cjs +40 -34
- package/build/legacy/notifyManager.cjs.map +1 -1
- package/build/legacy/notifyManager.d.cts +22 -0
- package/build/legacy/notifyManager.d.ts +22 -0
- package/build/legacy/notifyManager.js +40 -34
- package/build/legacy/notifyManager.js.map +1 -1
- package/build/legacy/utils.cjs +2 -3
- package/build/legacy/utils.cjs.map +1 -1
- package/build/legacy/utils.js +2 -3
- package/build/legacy/utils.js.map +1 -1
- package/build/modern/notifyManager.cjs +40 -34
- package/build/modern/notifyManager.cjs.map +1 -1
- package/build/modern/notifyManager.d.cts +22 -0
- package/build/modern/notifyManager.d.ts +22 -0
- package/build/modern/notifyManager.js +40 -34
- package/build/modern/notifyManager.js.map +1 -1
- package/build/modern/utils.cjs +2 -3
- package/build/modern/utils.cjs.map +1 -1
- package/build/modern/utils.js +2 -3
- package/build/modern/utils.js.map +1 -1
- package/package.json +1 -1
- package/src/__tests__/query.test.tsx +30 -20
- package/src/notifyManager.ts +42 -53
- package/src/utils.ts +2 -4
|
@@ -34,22 +34,6 @@ function createNotifyManager() {
|
|
|
34
34
|
callback();
|
|
35
35
|
};
|
|
36
36
|
let scheduleFn = (cb) => setTimeout(cb, 0);
|
|
37
|
-
const setScheduler = (fn) => {
|
|
38
|
-
scheduleFn = fn;
|
|
39
|
-
};
|
|
40
|
-
const batch = (callback) => {
|
|
41
|
-
let result;
|
|
42
|
-
transactions++;
|
|
43
|
-
try {
|
|
44
|
-
result = callback();
|
|
45
|
-
} finally {
|
|
46
|
-
transactions--;
|
|
47
|
-
if (!transactions) {
|
|
48
|
-
flush();
|
|
49
|
-
}
|
|
50
|
-
}
|
|
51
|
-
return result;
|
|
52
|
-
};
|
|
53
37
|
const schedule = (callback) => {
|
|
54
38
|
if (transactions) {
|
|
55
39
|
queue.push(callback);
|
|
@@ -59,13 +43,6 @@ function createNotifyManager() {
|
|
|
59
43
|
});
|
|
60
44
|
}
|
|
61
45
|
};
|
|
62
|
-
const batchCalls = (callback) => {
|
|
63
|
-
return (...args) => {
|
|
64
|
-
schedule(() => {
|
|
65
|
-
callback(...args);
|
|
66
|
-
});
|
|
67
|
-
};
|
|
68
|
-
};
|
|
69
46
|
const flush = () => {
|
|
70
47
|
const originalQueue = queue;
|
|
71
48
|
queue = [];
|
|
@@ -79,19 +56,48 @@ function createNotifyManager() {
|
|
|
79
56
|
});
|
|
80
57
|
}
|
|
81
58
|
};
|
|
82
|
-
const setNotifyFunction = (fn) => {
|
|
83
|
-
notifyFn = fn;
|
|
84
|
-
};
|
|
85
|
-
const setBatchNotifyFunction = (fn) => {
|
|
86
|
-
batchNotifyFn = fn;
|
|
87
|
-
};
|
|
88
59
|
return {
|
|
89
|
-
batch
|
|
90
|
-
|
|
60
|
+
batch: (callback) => {
|
|
61
|
+
let result;
|
|
62
|
+
transactions++;
|
|
63
|
+
try {
|
|
64
|
+
result = callback();
|
|
65
|
+
} finally {
|
|
66
|
+
transactions--;
|
|
67
|
+
if (!transactions) {
|
|
68
|
+
flush();
|
|
69
|
+
}
|
|
70
|
+
}
|
|
71
|
+
return result;
|
|
72
|
+
},
|
|
73
|
+
/**
|
|
74
|
+
* All calls to the wrapped function will be batched.
|
|
75
|
+
*/
|
|
76
|
+
batchCalls: (callback) => {
|
|
77
|
+
return (...args) => {
|
|
78
|
+
schedule(() => {
|
|
79
|
+
callback(...args);
|
|
80
|
+
});
|
|
81
|
+
};
|
|
82
|
+
},
|
|
91
83
|
schedule,
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
|
|
84
|
+
/**
|
|
85
|
+
* Use this method to set a custom notify function.
|
|
86
|
+
* This can be used to for example wrap notifications with `React.act` while running tests.
|
|
87
|
+
*/
|
|
88
|
+
setNotifyFunction: (fn) => {
|
|
89
|
+
notifyFn = fn;
|
|
90
|
+
},
|
|
91
|
+
/**
|
|
92
|
+
* Use this method to set a custom function to batch notifications together into a single tick.
|
|
93
|
+
* By default React Query will use the batch function provided by ReactDOM or React Native.
|
|
94
|
+
*/
|
|
95
|
+
setBatchNotifyFunction: (fn) => {
|
|
96
|
+
batchNotifyFn = fn;
|
|
97
|
+
},
|
|
98
|
+
setScheduler: (fn) => {
|
|
99
|
+
scheduleFn = fn;
|
|
100
|
+
}
|
|
95
101
|
};
|
|
96
102
|
}
|
|
97
103
|
var notifyManager = createNotifyManager();
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../../src/notifyManager.ts"],"sourcesContent":["// TYPES\n\ntype NotifyCallback = () => void\n\ntype NotifyFunction = (callback: () => void) => void\n\ntype BatchNotifyFunction = (callback: () => void) => void\n\ntype BatchCallsCallback<T extends Array<unknown>> = (...args: T) => void\n\ntype ScheduleFunction = (callback: () => void) => void\n\nexport function createNotifyManager() {\n let queue: Array<NotifyCallback> = []\n let transactions = 0\n let notifyFn: NotifyFunction = (callback) => {\n callback()\n }\n let batchNotifyFn: BatchNotifyFunction = (callback: () => void) => {\n callback()\n }\n let scheduleFn: ScheduleFunction = (cb) => setTimeout(cb, 0)\n\n const
|
|
1
|
+
{"version":3,"sources":["../../src/notifyManager.ts"],"sourcesContent":["// TYPES\n\ntype NotifyCallback = () => void\n\ntype NotifyFunction = (callback: () => void) => void\n\ntype BatchNotifyFunction = (callback: () => void) => void\n\ntype BatchCallsCallback<T extends Array<unknown>> = (...args: T) => void\n\ntype ScheduleFunction = (callback: () => void) => void\n\nexport function createNotifyManager() {\n let queue: Array<NotifyCallback> = []\n let transactions = 0\n let notifyFn: NotifyFunction = (callback) => {\n callback()\n }\n let batchNotifyFn: BatchNotifyFunction = (callback: () => void) => {\n callback()\n }\n let scheduleFn: ScheduleFunction = (cb) => setTimeout(cb, 0)\n\n const schedule = (callback: NotifyCallback): void => {\n if (transactions) {\n queue.push(callback)\n } else {\n scheduleFn(() => {\n notifyFn(callback)\n })\n }\n }\n const flush = (): void => {\n const originalQueue = queue\n queue = []\n if (originalQueue.length) {\n scheduleFn(() => {\n batchNotifyFn(() => {\n originalQueue.forEach((callback) => {\n notifyFn(callback)\n })\n })\n })\n }\n }\n\n return {\n batch: <T>(callback: () => T): T => {\n let result\n transactions++\n try {\n result = callback()\n } finally {\n transactions--\n if (!transactions) {\n flush()\n }\n }\n return result\n },\n /**\n * All calls to the wrapped function will be batched.\n */\n batchCalls: <T extends Array<unknown>>(\n callback: BatchCallsCallback<T>,\n ): BatchCallsCallback<T> => {\n return (...args) => {\n schedule(() => {\n callback(...args)\n })\n }\n },\n schedule,\n /**\n * Use this method to set a custom notify function.\n * This can be used to for example wrap notifications with `React.act` while running tests.\n */\n setNotifyFunction: (fn: NotifyFunction) => {\n notifyFn = fn\n },\n /**\n * Use this method to set a custom function to batch notifications together into a single tick.\n * By default React Query will use the batch function provided by ReactDOM or React Native.\n */\n setBatchNotifyFunction: (fn: BatchNotifyFunction) => {\n batchNotifyFn = fn\n },\n setScheduler: (fn: ScheduleFunction) => {\n scheduleFn = fn\n },\n } as const\n}\n\n// SINGLETON\nexport const notifyManager = createNotifyManager()\n"],"mappings":";;;;;;;;;;;;;;;;;;;;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAYO,SAAS,sBAAsB;AACpC,MAAI,QAA+B,CAAC;AACpC,MAAI,eAAe;AACnB,MAAI,WAA2B,CAAC,aAAa;AAC3C,aAAS;AAAA,EACX;AACA,MAAI,gBAAqC,CAAC,aAAyB;AACjE,aAAS;AAAA,EACX;AACA,MAAI,aAA+B,CAAC,OAAO,WAAW,IAAI,CAAC;AAE3D,QAAM,WAAW,CAAC,aAAmC;AACnD,QAAI,cAAc;AAChB,YAAM,KAAK,QAAQ;AAAA,IACrB,OAAO;AACL,iBAAW,MAAM;AACf,iBAAS,QAAQ;AAAA,MACnB,CAAC;AAAA,IACH;AAAA,EACF;AACA,QAAM,QAAQ,MAAY;AACxB,UAAM,gBAAgB;AACtB,YAAQ,CAAC;AACT,QAAI,cAAc,QAAQ;AACxB,iBAAW,MAAM;AACf,sBAAc,MAAM;AAClB,wBAAc,QAAQ,CAAC,aAAa;AAClC,qBAAS,QAAQ;AAAA,UACnB,CAAC;AAAA,QACH,CAAC;AAAA,MACH,CAAC;AAAA,IACH;AAAA,EACF;AAEA,SAAO;AAAA,IACL,OAAO,CAAI,aAAyB;AAClC,UAAI;AACJ;AACA,UAAI;AACF,iBAAS,SAAS;AAAA,MACpB,UAAE;AACA;AACA,YAAI,CAAC,cAAc;AACjB,gBAAM;AAAA,QACR;AAAA,MACF;AACA,aAAO;AAAA,IACT;AAAA;AAAA;AAAA;AAAA,IAIA,YAAY,CACV,aAC0B;AAC1B,aAAO,IAAI,SAAS;AAClB,iBAAS,MAAM;AACb,mBAAS,GAAG,IAAI;AAAA,QAClB,CAAC;AAAA,MACH;AAAA,IACF;AAAA,IACA;AAAA;AAAA;AAAA;AAAA;AAAA,IAKA,mBAAmB,CAAC,OAAuB;AACzC,iBAAW;AAAA,IACb;AAAA;AAAA;AAAA;AAAA;AAAA,IAKA,wBAAwB,CAAC,OAA4B;AACnD,sBAAgB;AAAA,IAClB;AAAA,IACA,cAAc,CAAC,OAAyB;AACtC,mBAAa;AAAA,IACf;AAAA,EACF;AACF;AAGO,IAAM,gBAAgB,oBAAoB;","names":[]}
|
|
@@ -5,17 +5,39 @@ type BatchCallsCallback<T extends Array<unknown>> = (...args: T) => void;
|
|
|
5
5
|
type ScheduleFunction = (callback: () => void) => void;
|
|
6
6
|
declare function createNotifyManager(): {
|
|
7
7
|
readonly batch: <T>(callback: () => T) => T;
|
|
8
|
+
/**
|
|
9
|
+
* All calls to the wrapped function will be batched.
|
|
10
|
+
*/
|
|
8
11
|
readonly batchCalls: <T_1 extends unknown[]>(callback: BatchCallsCallback<T_1>) => BatchCallsCallback<T_1>;
|
|
9
12
|
readonly schedule: (callback: NotifyCallback) => void;
|
|
13
|
+
/**
|
|
14
|
+
* Use this method to set a custom notify function.
|
|
15
|
+
* This can be used to for example wrap notifications with `React.act` while running tests.
|
|
16
|
+
*/
|
|
10
17
|
readonly setNotifyFunction: (fn: NotifyFunction) => void;
|
|
18
|
+
/**
|
|
19
|
+
* Use this method to set a custom function to batch notifications together into a single tick.
|
|
20
|
+
* By default React Query will use the batch function provided by ReactDOM or React Native.
|
|
21
|
+
*/
|
|
11
22
|
readonly setBatchNotifyFunction: (fn: BatchNotifyFunction) => void;
|
|
12
23
|
readonly setScheduler: (fn: ScheduleFunction) => void;
|
|
13
24
|
};
|
|
14
25
|
declare const notifyManager: {
|
|
15
26
|
readonly batch: <T>(callback: () => T) => T;
|
|
27
|
+
/**
|
|
28
|
+
* All calls to the wrapped function will be batched.
|
|
29
|
+
*/
|
|
16
30
|
readonly batchCalls: <T_1 extends unknown[]>(callback: BatchCallsCallback<T_1>) => BatchCallsCallback<T_1>;
|
|
17
31
|
readonly schedule: (callback: NotifyCallback) => void;
|
|
32
|
+
/**
|
|
33
|
+
* Use this method to set a custom notify function.
|
|
34
|
+
* This can be used to for example wrap notifications with `React.act` while running tests.
|
|
35
|
+
*/
|
|
18
36
|
readonly setNotifyFunction: (fn: NotifyFunction) => void;
|
|
37
|
+
/**
|
|
38
|
+
* Use this method to set a custom function to batch notifications together into a single tick.
|
|
39
|
+
* By default React Query will use the batch function provided by ReactDOM or React Native.
|
|
40
|
+
*/
|
|
19
41
|
readonly setBatchNotifyFunction: (fn: BatchNotifyFunction) => void;
|
|
20
42
|
readonly setScheduler: (fn: ScheduleFunction) => void;
|
|
21
43
|
};
|
|
@@ -5,17 +5,39 @@ type BatchCallsCallback<T extends Array<unknown>> = (...args: T) => void;
|
|
|
5
5
|
type ScheduleFunction = (callback: () => void) => void;
|
|
6
6
|
declare function createNotifyManager(): {
|
|
7
7
|
readonly batch: <T>(callback: () => T) => T;
|
|
8
|
+
/**
|
|
9
|
+
* All calls to the wrapped function will be batched.
|
|
10
|
+
*/
|
|
8
11
|
readonly batchCalls: <T_1 extends unknown[]>(callback: BatchCallsCallback<T_1>) => BatchCallsCallback<T_1>;
|
|
9
12
|
readonly schedule: (callback: NotifyCallback) => void;
|
|
13
|
+
/**
|
|
14
|
+
* Use this method to set a custom notify function.
|
|
15
|
+
* This can be used to for example wrap notifications with `React.act` while running tests.
|
|
16
|
+
*/
|
|
10
17
|
readonly setNotifyFunction: (fn: NotifyFunction) => void;
|
|
18
|
+
/**
|
|
19
|
+
* Use this method to set a custom function to batch notifications together into a single tick.
|
|
20
|
+
* By default React Query will use the batch function provided by ReactDOM or React Native.
|
|
21
|
+
*/
|
|
11
22
|
readonly setBatchNotifyFunction: (fn: BatchNotifyFunction) => void;
|
|
12
23
|
readonly setScheduler: (fn: ScheduleFunction) => void;
|
|
13
24
|
};
|
|
14
25
|
declare const notifyManager: {
|
|
15
26
|
readonly batch: <T>(callback: () => T) => T;
|
|
27
|
+
/**
|
|
28
|
+
* All calls to the wrapped function will be batched.
|
|
29
|
+
*/
|
|
16
30
|
readonly batchCalls: <T_1 extends unknown[]>(callback: BatchCallsCallback<T_1>) => BatchCallsCallback<T_1>;
|
|
17
31
|
readonly schedule: (callback: NotifyCallback) => void;
|
|
32
|
+
/**
|
|
33
|
+
* Use this method to set a custom notify function.
|
|
34
|
+
* This can be used to for example wrap notifications with `React.act` while running tests.
|
|
35
|
+
*/
|
|
18
36
|
readonly setNotifyFunction: (fn: NotifyFunction) => void;
|
|
37
|
+
/**
|
|
38
|
+
* Use this method to set a custom function to batch notifications together into a single tick.
|
|
39
|
+
* By default React Query will use the batch function provided by ReactDOM or React Native.
|
|
40
|
+
*/
|
|
19
41
|
readonly setBatchNotifyFunction: (fn: BatchNotifyFunction) => void;
|
|
20
42
|
readonly setScheduler: (fn: ScheduleFunction) => void;
|
|
21
43
|
};
|
|
@@ -11,22 +11,6 @@ function createNotifyManager() {
|
|
|
11
11
|
callback();
|
|
12
12
|
};
|
|
13
13
|
let scheduleFn = (cb) => setTimeout(cb, 0);
|
|
14
|
-
const setScheduler = (fn) => {
|
|
15
|
-
scheduleFn = fn;
|
|
16
|
-
};
|
|
17
|
-
const batch = (callback) => {
|
|
18
|
-
let result;
|
|
19
|
-
transactions++;
|
|
20
|
-
try {
|
|
21
|
-
result = callback();
|
|
22
|
-
} finally {
|
|
23
|
-
transactions--;
|
|
24
|
-
if (!transactions) {
|
|
25
|
-
flush();
|
|
26
|
-
}
|
|
27
|
-
}
|
|
28
|
-
return result;
|
|
29
|
-
};
|
|
30
14
|
const schedule = (callback) => {
|
|
31
15
|
if (transactions) {
|
|
32
16
|
queue.push(callback);
|
|
@@ -36,13 +20,6 @@ function createNotifyManager() {
|
|
|
36
20
|
});
|
|
37
21
|
}
|
|
38
22
|
};
|
|
39
|
-
const batchCalls = (callback) => {
|
|
40
|
-
return (...args) => {
|
|
41
|
-
schedule(() => {
|
|
42
|
-
callback(...args);
|
|
43
|
-
});
|
|
44
|
-
};
|
|
45
|
-
};
|
|
46
23
|
const flush = () => {
|
|
47
24
|
const originalQueue = queue;
|
|
48
25
|
queue = [];
|
|
@@ -56,19 +33,48 @@ function createNotifyManager() {
|
|
|
56
33
|
});
|
|
57
34
|
}
|
|
58
35
|
};
|
|
59
|
-
const setNotifyFunction = (fn) => {
|
|
60
|
-
notifyFn = fn;
|
|
61
|
-
};
|
|
62
|
-
const setBatchNotifyFunction = (fn) => {
|
|
63
|
-
batchNotifyFn = fn;
|
|
64
|
-
};
|
|
65
36
|
return {
|
|
66
|
-
batch
|
|
67
|
-
|
|
37
|
+
batch: (callback) => {
|
|
38
|
+
let result;
|
|
39
|
+
transactions++;
|
|
40
|
+
try {
|
|
41
|
+
result = callback();
|
|
42
|
+
} finally {
|
|
43
|
+
transactions--;
|
|
44
|
+
if (!transactions) {
|
|
45
|
+
flush();
|
|
46
|
+
}
|
|
47
|
+
}
|
|
48
|
+
return result;
|
|
49
|
+
},
|
|
50
|
+
/**
|
|
51
|
+
* All calls to the wrapped function will be batched.
|
|
52
|
+
*/
|
|
53
|
+
batchCalls: (callback) => {
|
|
54
|
+
return (...args) => {
|
|
55
|
+
schedule(() => {
|
|
56
|
+
callback(...args);
|
|
57
|
+
});
|
|
58
|
+
};
|
|
59
|
+
},
|
|
68
60
|
schedule,
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
61
|
+
/**
|
|
62
|
+
* Use this method to set a custom notify function.
|
|
63
|
+
* This can be used to for example wrap notifications with `React.act` while running tests.
|
|
64
|
+
*/
|
|
65
|
+
setNotifyFunction: (fn) => {
|
|
66
|
+
notifyFn = fn;
|
|
67
|
+
},
|
|
68
|
+
/**
|
|
69
|
+
* Use this method to set a custom function to batch notifications together into a single tick.
|
|
70
|
+
* By default React Query will use the batch function provided by ReactDOM or React Native.
|
|
71
|
+
*/
|
|
72
|
+
setBatchNotifyFunction: (fn) => {
|
|
73
|
+
batchNotifyFn = fn;
|
|
74
|
+
},
|
|
75
|
+
setScheduler: (fn) => {
|
|
76
|
+
scheduleFn = fn;
|
|
77
|
+
}
|
|
72
78
|
};
|
|
73
79
|
}
|
|
74
80
|
var notifyManager = createNotifyManager();
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../../src/notifyManager.ts"],"sourcesContent":["// TYPES\n\ntype NotifyCallback = () => void\n\ntype NotifyFunction = (callback: () => void) => void\n\ntype BatchNotifyFunction = (callback: () => void) => void\n\ntype BatchCallsCallback<T extends Array<unknown>> = (...args: T) => void\n\ntype ScheduleFunction = (callback: () => void) => void\n\nexport function createNotifyManager() {\n let queue: Array<NotifyCallback> = []\n let transactions = 0\n let notifyFn: NotifyFunction = (callback) => {\n callback()\n }\n let batchNotifyFn: BatchNotifyFunction = (callback: () => void) => {\n callback()\n }\n let scheduleFn: ScheduleFunction = (cb) => setTimeout(cb, 0)\n\n const
|
|
1
|
+
{"version":3,"sources":["../../src/notifyManager.ts"],"sourcesContent":["// TYPES\n\ntype NotifyCallback = () => void\n\ntype NotifyFunction = (callback: () => void) => void\n\ntype BatchNotifyFunction = (callback: () => void) => void\n\ntype BatchCallsCallback<T extends Array<unknown>> = (...args: T) => void\n\ntype ScheduleFunction = (callback: () => void) => void\n\nexport function createNotifyManager() {\n let queue: Array<NotifyCallback> = []\n let transactions = 0\n let notifyFn: NotifyFunction = (callback) => {\n callback()\n }\n let batchNotifyFn: BatchNotifyFunction = (callback: () => void) => {\n callback()\n }\n let scheduleFn: ScheduleFunction = (cb) => setTimeout(cb, 0)\n\n const schedule = (callback: NotifyCallback): void => {\n if (transactions) {\n queue.push(callback)\n } else {\n scheduleFn(() => {\n notifyFn(callback)\n })\n }\n }\n const flush = (): void => {\n const originalQueue = queue\n queue = []\n if (originalQueue.length) {\n scheduleFn(() => {\n batchNotifyFn(() => {\n originalQueue.forEach((callback) => {\n notifyFn(callback)\n })\n })\n })\n }\n }\n\n return {\n batch: <T>(callback: () => T): T => {\n let result\n transactions++\n try {\n result = callback()\n } finally {\n transactions--\n if (!transactions) {\n flush()\n }\n }\n return result\n },\n /**\n * All calls to the wrapped function will be batched.\n */\n batchCalls: <T extends Array<unknown>>(\n callback: BatchCallsCallback<T>,\n ): BatchCallsCallback<T> => {\n return (...args) => {\n schedule(() => {\n callback(...args)\n })\n }\n },\n schedule,\n /**\n * Use this method to set a custom notify function.\n * This can be used to for example wrap notifications with `React.act` while running tests.\n */\n setNotifyFunction: (fn: NotifyFunction) => {\n notifyFn = fn\n },\n /**\n * Use this method to set a custom function to batch notifications together into a single tick.\n * By default React Query will use the batch function provided by ReactDOM or React Native.\n */\n setBatchNotifyFunction: (fn: BatchNotifyFunction) => {\n batchNotifyFn = fn\n },\n setScheduler: (fn: ScheduleFunction) => {\n scheduleFn = fn\n },\n } as const\n}\n\n// SINGLETON\nexport const notifyManager = createNotifyManager()\n"],"mappings":";;;AAYO,SAAS,sBAAsB;AACpC,MAAI,QAA+B,CAAC;AACpC,MAAI,eAAe;AACnB,MAAI,WAA2B,CAAC,aAAa;AAC3C,aAAS;AAAA,EACX;AACA,MAAI,gBAAqC,CAAC,aAAyB;AACjE,aAAS;AAAA,EACX;AACA,MAAI,aAA+B,CAAC,OAAO,WAAW,IAAI,CAAC;AAE3D,QAAM,WAAW,CAAC,aAAmC;AACnD,QAAI,cAAc;AAChB,YAAM,KAAK,QAAQ;AAAA,IACrB,OAAO;AACL,iBAAW,MAAM;AACf,iBAAS,QAAQ;AAAA,MACnB,CAAC;AAAA,IACH;AAAA,EACF;AACA,QAAM,QAAQ,MAAY;AACxB,UAAM,gBAAgB;AACtB,YAAQ,CAAC;AACT,QAAI,cAAc,QAAQ;AACxB,iBAAW,MAAM;AACf,sBAAc,MAAM;AAClB,wBAAc,QAAQ,CAAC,aAAa;AAClC,qBAAS,QAAQ;AAAA,UACnB,CAAC;AAAA,QACH,CAAC;AAAA,MACH,CAAC;AAAA,IACH;AAAA,EACF;AAEA,SAAO;AAAA,IACL,OAAO,CAAI,aAAyB;AAClC,UAAI;AACJ;AACA,UAAI;AACF,iBAAS,SAAS;AAAA,MACpB,UAAE;AACA;AACA,YAAI,CAAC,cAAc;AACjB,gBAAM;AAAA,QACR;AAAA,MACF;AACA,aAAO;AAAA,IACT;AAAA;AAAA;AAAA;AAAA,IAIA,YAAY,CACV,aAC0B;AAC1B,aAAO,IAAI,SAAS;AAClB,iBAAS,MAAM;AACb,mBAAS,GAAG,IAAI;AAAA,QAClB,CAAC;AAAA,MACH;AAAA,IACF;AAAA,IACA;AAAA;AAAA;AAAA;AAAA;AAAA,IAKA,mBAAmB,CAAC,OAAuB;AACzC,iBAAW;AAAA,IACb;AAAA;AAAA;AAAA;AAAA;AAAA,IAKA,wBAAwB,CAAC,OAA4B;AACnD,sBAAgB;AAAA,IAClB;AAAA,IACA,cAAc,CAAC,OAAyB;AACtC,mBAAa;AAAA,IACf;AAAA,EACF;AACF;AAGO,IAAM,gBAAgB,oBAAoB;","names":[]}
|
package/build/legacy/utils.cjs
CHANGED
|
@@ -225,11 +225,10 @@ function replaceData(prevData, data, options) {
|
|
|
225
225
|
} else if (options.structuralSharing !== false) {
|
|
226
226
|
if (process.env.NODE_ENV !== "production") {
|
|
227
227
|
try {
|
|
228
|
-
|
|
229
|
-
JSON.stringify(data);
|
|
228
|
+
return replaceEqualDeep(prevData, data);
|
|
230
229
|
} catch (error) {
|
|
231
230
|
console.error(
|
|
232
|
-
`
|
|
231
|
+
`Structural sharing requires data to be JSON serializable. To fix this, turn off structuralSharing or return JSON-serializable data from your queryFn. [${options.queryHash}]: ${error}`
|
|
233
232
|
);
|
|
234
233
|
}
|
|
235
234
|
}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../../src/utils.ts"],"sourcesContent":["import type {\n DefaultError,\n Enabled,\n FetchStatus,\n MutationKey,\n MutationStatus,\n QueryFunction,\n QueryKey,\n QueryOptions,\n StaleTime,\n} from './types'\nimport type { Mutation } from './mutation'\nimport type { FetchOptions, Query } from './query'\n\n// TYPES\n\nexport interface QueryFilters {\n /**\n * Filter to active queries, inactive queries or all queries\n */\n type?: QueryTypeFilter\n /**\n * Match query key exactly\n */\n exact?: boolean\n /**\n * Include queries matching this predicate function\n */\n predicate?: (query: Query) => boolean\n /**\n * Include queries matching this query key\n */\n queryKey?: QueryKey\n /**\n * Include or exclude stale queries\n */\n stale?: boolean\n /**\n * Include queries matching their fetchStatus\n */\n fetchStatus?: FetchStatus\n}\n\nexport interface MutationFilters {\n /**\n * Match mutation key exactly\n */\n exact?: boolean\n /**\n * Include mutations matching this predicate function\n */\n predicate?: (mutation: Mutation<any, any, any>) => boolean\n /**\n * Include mutations matching this mutation key\n */\n mutationKey?: MutationKey\n /**\n * Filter by mutation status\n */\n status?: MutationStatus\n}\n\nexport type Updater<TInput, TOutput> = TOutput | ((input: TInput) => TOutput)\n\nexport type QueryTypeFilter = 'all' | 'active' | 'inactive'\n\n// UTILS\n\nexport const isServer = typeof window === 'undefined' || 'Deno' in globalThis\n\nexport function noop(): undefined {\n return undefined\n}\n\nexport function functionalUpdate<TInput, TOutput>(\n updater: Updater<TInput, TOutput>,\n input: TInput,\n): TOutput {\n return typeof updater === 'function'\n ? (updater as (_: TInput) => TOutput)(input)\n : updater\n}\n\nexport function isValidTimeout(value: unknown): value is number {\n return typeof value === 'number' && value >= 0 && value !== Infinity\n}\n\nexport function timeUntilStale(updatedAt: number, staleTime?: number): number {\n return Math.max(updatedAt + (staleTime || 0) - Date.now(), 0)\n}\n\nexport function resolveStaleTime<\n TQueryFnData = unknown,\n TError = DefaultError,\n TData = TQueryFnData,\n TQueryKey extends QueryKey = QueryKey,\n>(\n staleTime: undefined | StaleTime<TQueryFnData, TError, TData, TQueryKey>,\n query: Query<TQueryFnData, TError, TData, TQueryKey>,\n): number | undefined {\n return typeof staleTime === 'function' ? staleTime(query) : staleTime\n}\n\nexport function resolveEnabled<\n TQueryFnData = unknown,\n TError = DefaultError,\n TData = TQueryFnData,\n TQueryKey extends QueryKey = QueryKey,\n>(\n enabled: undefined | Enabled<TQueryFnData, TError, TData, TQueryKey>,\n query: Query<TQueryFnData, TError, TData, TQueryKey>,\n): boolean | undefined {\n return typeof enabled === 'function' ? enabled(query) : enabled\n}\n\nexport function matchQuery(\n filters: QueryFilters,\n query: Query<any, any, any, any>,\n): boolean {\n const {\n type = 'all',\n exact,\n fetchStatus,\n predicate,\n queryKey,\n stale,\n } = filters\n\n if (queryKey) {\n if (exact) {\n if (query.queryHash !== hashQueryKeyByOptions(queryKey, query.options)) {\n return false\n }\n } else if (!partialMatchKey(query.queryKey, queryKey)) {\n return false\n }\n }\n\n if (type !== 'all') {\n const isActive = query.isActive()\n if (type === 'active' && !isActive) {\n return false\n }\n if (type === 'inactive' && isActive) {\n return false\n }\n }\n\n if (typeof stale === 'boolean' && query.isStale() !== stale) {\n return false\n }\n\n if (fetchStatus && fetchStatus !== query.state.fetchStatus) {\n return false\n }\n\n if (predicate && !predicate(query)) {\n return false\n }\n\n return true\n}\n\nexport function matchMutation(\n filters: MutationFilters,\n mutation: Mutation<any, any>,\n): boolean {\n const { exact, status, predicate, mutationKey } = filters\n if (mutationKey) {\n if (!mutation.options.mutationKey) {\n return false\n }\n if (exact) {\n if (hashKey(mutation.options.mutationKey) !== hashKey(mutationKey)) {\n return false\n }\n } else if (!partialMatchKey(mutation.options.mutationKey, mutationKey)) {\n return false\n }\n }\n\n if (status && mutation.state.status !== status) {\n return false\n }\n\n if (predicate && !predicate(mutation)) {\n return false\n }\n\n return true\n}\n\nexport function hashQueryKeyByOptions<TQueryKey extends QueryKey = QueryKey>(\n queryKey: TQueryKey,\n options?: Pick<QueryOptions<any, any, any, any>, 'queryKeyHashFn'>,\n): string {\n const hashFn = options?.queryKeyHashFn || hashKey\n return hashFn(queryKey)\n}\n\n/**\n * Default query & mutation keys hash function.\n * Hashes the value into a stable hash.\n */\nexport function hashKey(queryKey: QueryKey | MutationKey): string {\n return JSON.stringify(queryKey, (_, val) =>\n isPlainObject(val)\n ? Object.keys(val)\n .sort()\n .reduce((result, key) => {\n result[key] = val[key]\n return result\n }, {} as any)\n : val,\n )\n}\n\n/**\n * Checks if key `b` partially matches with key `a`.\n */\nexport function partialMatchKey(a: QueryKey, b: QueryKey): boolean\nexport function partialMatchKey(a: any, b: any): boolean {\n if (a === b) {\n return true\n }\n\n if (typeof a !== typeof b) {\n return false\n }\n\n if (a && b && typeof a === 'object' && typeof b === 'object') {\n return !Object.keys(b).some((key) => !partialMatchKey(a[key], b[key]))\n }\n\n return false\n}\n\n/**\n * This function returns `a` if `b` is deeply equal.\n * If not, it will replace any deeply equal children of `b` with those of `a`.\n * This can be used for structural sharing between JSON values for example.\n */\nexport function replaceEqualDeep<T>(a: unknown, b: T): T\nexport function replaceEqualDeep(a: any, b: any): any {\n if (a === b) {\n return a\n }\n\n const array = isPlainArray(a) && isPlainArray(b)\n\n if (array || (isPlainObject(a) && isPlainObject(b))) {\n const aItems = array ? a : Object.keys(a)\n const aSize = aItems.length\n const bItems = array ? b : Object.keys(b)\n const bSize = bItems.length\n const copy: any = array ? [] : {}\n\n let equalItems = 0\n\n for (let i = 0; i < bSize; i++) {\n const key = array ? i : bItems[i]\n if (\n ((!array && aItems.includes(key)) || array) &&\n a[key] === undefined &&\n b[key] === undefined\n ) {\n copy[key] = undefined\n equalItems++\n } else {\n copy[key] = replaceEqualDeep(a[key], b[key])\n if (copy[key] === a[key] && a[key] !== undefined) {\n equalItems++\n }\n }\n }\n\n return aSize === bSize && equalItems === aSize ? a : copy\n }\n\n return b\n}\n\n/**\n * Shallow compare objects.\n */\nexport function shallowEqualObjects<T extends Record<string, any>>(\n a: T,\n b: T | undefined,\n): boolean {\n if (!b || Object.keys(a).length !== Object.keys(b).length) {\n return false\n }\n\n for (const key in a) {\n if (a[key] !== b[key]) {\n return false\n }\n }\n\n return true\n}\n\nexport function isPlainArray(value: unknown) {\n return Array.isArray(value) && value.length === Object.keys(value).length\n}\n\n// Copied from: https://github.com/jonschlinkert/is-plain-object\n// eslint-disable-next-line @typescript-eslint/no-wrapper-object-types\nexport function isPlainObject(o: any): o is Object {\n if (!hasObjectPrototype(o)) {\n return false\n }\n\n // If has no constructor\n const ctor = o.constructor\n if (ctor === undefined) {\n return true\n }\n\n // If has modified prototype\n const prot = ctor.prototype\n if (!hasObjectPrototype(prot)) {\n return false\n }\n\n // If constructor does not have an Object-specific method\n if (!prot.hasOwnProperty('isPrototypeOf')) {\n return false\n }\n\n // Handles Objects created by Object.create(<arbitrary prototype>)\n if (Object.getPrototypeOf(o) !== Object.prototype) {\n return false\n }\n\n // Most likely a plain Object\n return true\n}\n\nfunction hasObjectPrototype(o: any): boolean {\n return Object.prototype.toString.call(o) === '[object Object]'\n}\n\nexport function sleep(timeout: number): Promise<void> {\n return new Promise((resolve) => {\n setTimeout(resolve, timeout)\n })\n}\n\nexport function replaceData<\n TData,\n TOptions extends QueryOptions<any, any, any, any>,\n>(prevData: TData | undefined, data: TData, options: TOptions): TData {\n if (typeof options.structuralSharing === 'function') {\n return options.structuralSharing(prevData, data) as TData\n } else if (options.structuralSharing !== false) {\n if (process.env.NODE_ENV !== 'production') {\n try {\n JSON.stringify(prevData)\n JSON.stringify(data)\n } catch (error) {\n console.error(\n `StructuralSharing requires data to be JSON serializable. To fix this, turn off structuralSharing or return JSON-serializable data from your queryFn. [${options.queryHash}]: ${error}`,\n )\n }\n }\n\n // Structurally share data between prev and new data if needed\n return replaceEqualDeep(prevData, data)\n }\n return data\n}\n\nexport function keepPreviousData<T>(\n previousData: T | undefined,\n): T | undefined {\n return previousData\n}\n\nexport function addToEnd<T>(items: Array<T>, item: T, max = 0): Array<T> {\n const newItems = [...items, item]\n return max && newItems.length > max ? newItems.slice(1) : newItems\n}\n\nexport function addToStart<T>(items: Array<T>, item: T, max = 0): Array<T> {\n const newItems = [item, ...items]\n return max && newItems.length > max ? newItems.slice(0, -1) : newItems\n}\n\nexport const skipToken = Symbol()\nexport type SkipToken = typeof skipToken\n\nexport function ensureQueryFn<\n TQueryFnData = unknown,\n TQueryKey extends QueryKey = QueryKey,\n>(\n options: {\n queryFn?: QueryFunction<TQueryFnData, TQueryKey> | SkipToken\n queryHash?: string\n },\n fetchOptions?: FetchOptions<TQueryFnData>,\n): QueryFunction<TQueryFnData, TQueryKey> {\n if (process.env.NODE_ENV !== 'production') {\n if (options.queryFn === skipToken) {\n console.error(\n `Attempted to invoke queryFn when set to skipToken. This is likely a configuration error. Query hash: '${options.queryHash}'`,\n )\n }\n }\n\n // if we attempt to retry a fetch that was triggered from an initialPromise\n // when we don't have a queryFn yet, we can't retry, so we just return the already rejected initialPromise\n // if an observer has already mounted, we will be able to retry with that queryFn\n if (!options.queryFn && fetchOptions?.initialPromise) {\n return () => fetchOptions.initialPromise!\n }\n\n if (!options.queryFn || options.queryFn === skipToken) {\n return () =>\n Promise.reject(new Error(`Missing queryFn: '${options.queryHash}'`))\n }\n\n return options.queryFn\n}\n"],"mappings":"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","names":[]}
|
|
1
|
+
{"version":3,"sources":["../../src/utils.ts"],"sourcesContent":["import type {\n DefaultError,\n Enabled,\n FetchStatus,\n MutationKey,\n MutationStatus,\n QueryFunction,\n QueryKey,\n QueryOptions,\n StaleTime,\n} from './types'\nimport type { Mutation } from './mutation'\nimport type { FetchOptions, Query } from './query'\n\n// TYPES\n\nexport interface QueryFilters {\n /**\n * Filter to active queries, inactive queries or all queries\n */\n type?: QueryTypeFilter\n /**\n * Match query key exactly\n */\n exact?: boolean\n /**\n * Include queries matching this predicate function\n */\n predicate?: (query: Query) => boolean\n /**\n * Include queries matching this query key\n */\n queryKey?: QueryKey\n /**\n * Include or exclude stale queries\n */\n stale?: boolean\n /**\n * Include queries matching their fetchStatus\n */\n fetchStatus?: FetchStatus\n}\n\nexport interface MutationFilters {\n /**\n * Match mutation key exactly\n */\n exact?: boolean\n /**\n * Include mutations matching this predicate function\n */\n predicate?: (mutation: Mutation<any, any, any>) => boolean\n /**\n * Include mutations matching this mutation key\n */\n mutationKey?: MutationKey\n /**\n * Filter by mutation status\n */\n status?: MutationStatus\n}\n\nexport type Updater<TInput, TOutput> = TOutput | ((input: TInput) => TOutput)\n\nexport type QueryTypeFilter = 'all' | 'active' | 'inactive'\n\n// UTILS\n\nexport const isServer = typeof window === 'undefined' || 'Deno' in globalThis\n\nexport function noop(): undefined {\n return undefined\n}\n\nexport function functionalUpdate<TInput, TOutput>(\n updater: Updater<TInput, TOutput>,\n input: TInput,\n): TOutput {\n return typeof updater === 'function'\n ? (updater as (_: TInput) => TOutput)(input)\n : updater\n}\n\nexport function isValidTimeout(value: unknown): value is number {\n return typeof value === 'number' && value >= 0 && value !== Infinity\n}\n\nexport function timeUntilStale(updatedAt: number, staleTime?: number): number {\n return Math.max(updatedAt + (staleTime || 0) - Date.now(), 0)\n}\n\nexport function resolveStaleTime<\n TQueryFnData = unknown,\n TError = DefaultError,\n TData = TQueryFnData,\n TQueryKey extends QueryKey = QueryKey,\n>(\n staleTime: undefined | StaleTime<TQueryFnData, TError, TData, TQueryKey>,\n query: Query<TQueryFnData, TError, TData, TQueryKey>,\n): number | undefined {\n return typeof staleTime === 'function' ? staleTime(query) : staleTime\n}\n\nexport function resolveEnabled<\n TQueryFnData = unknown,\n TError = DefaultError,\n TData = TQueryFnData,\n TQueryKey extends QueryKey = QueryKey,\n>(\n enabled: undefined | Enabled<TQueryFnData, TError, TData, TQueryKey>,\n query: Query<TQueryFnData, TError, TData, TQueryKey>,\n): boolean | undefined {\n return typeof enabled === 'function' ? enabled(query) : enabled\n}\n\nexport function matchQuery(\n filters: QueryFilters,\n query: Query<any, any, any, any>,\n): boolean {\n const {\n type = 'all',\n exact,\n fetchStatus,\n predicate,\n queryKey,\n stale,\n } = filters\n\n if (queryKey) {\n if (exact) {\n if (query.queryHash !== hashQueryKeyByOptions(queryKey, query.options)) {\n return false\n }\n } else if (!partialMatchKey(query.queryKey, queryKey)) {\n return false\n }\n }\n\n if (type !== 'all') {\n const isActive = query.isActive()\n if (type === 'active' && !isActive) {\n return false\n }\n if (type === 'inactive' && isActive) {\n return false\n }\n }\n\n if (typeof stale === 'boolean' && query.isStale() !== stale) {\n return false\n }\n\n if (fetchStatus && fetchStatus !== query.state.fetchStatus) {\n return false\n }\n\n if (predicate && !predicate(query)) {\n return false\n }\n\n return true\n}\n\nexport function matchMutation(\n filters: MutationFilters,\n mutation: Mutation<any, any>,\n): boolean {\n const { exact, status, predicate, mutationKey } = filters\n if (mutationKey) {\n if (!mutation.options.mutationKey) {\n return false\n }\n if (exact) {\n if (hashKey(mutation.options.mutationKey) !== hashKey(mutationKey)) {\n return false\n }\n } else if (!partialMatchKey(mutation.options.mutationKey, mutationKey)) {\n return false\n }\n }\n\n if (status && mutation.state.status !== status) {\n return false\n }\n\n if (predicate && !predicate(mutation)) {\n return false\n }\n\n return true\n}\n\nexport function hashQueryKeyByOptions<TQueryKey extends QueryKey = QueryKey>(\n queryKey: TQueryKey,\n options?: Pick<QueryOptions<any, any, any, any>, 'queryKeyHashFn'>,\n): string {\n const hashFn = options?.queryKeyHashFn || hashKey\n return hashFn(queryKey)\n}\n\n/**\n * Default query & mutation keys hash function.\n * Hashes the value into a stable hash.\n */\nexport function hashKey(queryKey: QueryKey | MutationKey): string {\n return JSON.stringify(queryKey, (_, val) =>\n isPlainObject(val)\n ? Object.keys(val)\n .sort()\n .reduce((result, key) => {\n result[key] = val[key]\n return result\n }, {} as any)\n : val,\n )\n}\n\n/**\n * Checks if key `b` partially matches with key `a`.\n */\nexport function partialMatchKey(a: QueryKey, b: QueryKey): boolean\nexport function partialMatchKey(a: any, b: any): boolean {\n if (a === b) {\n return true\n }\n\n if (typeof a !== typeof b) {\n return false\n }\n\n if (a && b && typeof a === 'object' && typeof b === 'object') {\n return !Object.keys(b).some((key) => !partialMatchKey(a[key], b[key]))\n }\n\n return false\n}\n\n/**\n * This function returns `a` if `b` is deeply equal.\n * If not, it will replace any deeply equal children of `b` with those of `a`.\n * This can be used for structural sharing between JSON values for example.\n */\nexport function replaceEqualDeep<T>(a: unknown, b: T): T\nexport function replaceEqualDeep(a: any, b: any): any {\n if (a === b) {\n return a\n }\n\n const array = isPlainArray(a) && isPlainArray(b)\n\n if (array || (isPlainObject(a) && isPlainObject(b))) {\n const aItems = array ? a : Object.keys(a)\n const aSize = aItems.length\n const bItems = array ? b : Object.keys(b)\n const bSize = bItems.length\n const copy: any = array ? [] : {}\n\n let equalItems = 0\n\n for (let i = 0; i < bSize; i++) {\n const key = array ? i : bItems[i]\n if (\n ((!array && aItems.includes(key)) || array) &&\n a[key] === undefined &&\n b[key] === undefined\n ) {\n copy[key] = undefined\n equalItems++\n } else {\n copy[key] = replaceEqualDeep(a[key], b[key])\n if (copy[key] === a[key] && a[key] !== undefined) {\n equalItems++\n }\n }\n }\n\n return aSize === bSize && equalItems === aSize ? a : copy\n }\n\n return b\n}\n\n/**\n * Shallow compare objects.\n */\nexport function shallowEqualObjects<T extends Record<string, any>>(\n a: T,\n b: T | undefined,\n): boolean {\n if (!b || Object.keys(a).length !== Object.keys(b).length) {\n return false\n }\n\n for (const key in a) {\n if (a[key] !== b[key]) {\n return false\n }\n }\n\n return true\n}\n\nexport function isPlainArray(value: unknown) {\n return Array.isArray(value) && value.length === Object.keys(value).length\n}\n\n// Copied from: https://github.com/jonschlinkert/is-plain-object\n// eslint-disable-next-line @typescript-eslint/no-wrapper-object-types\nexport function isPlainObject(o: any): o is Object {\n if (!hasObjectPrototype(o)) {\n return false\n }\n\n // If has no constructor\n const ctor = o.constructor\n if (ctor === undefined) {\n return true\n }\n\n // If has modified prototype\n const prot = ctor.prototype\n if (!hasObjectPrototype(prot)) {\n return false\n }\n\n // If constructor does not have an Object-specific method\n if (!prot.hasOwnProperty('isPrototypeOf')) {\n return false\n }\n\n // Handles Objects created by Object.create(<arbitrary prototype>)\n if (Object.getPrototypeOf(o) !== Object.prototype) {\n return false\n }\n\n // Most likely a plain Object\n return true\n}\n\nfunction hasObjectPrototype(o: any): boolean {\n return Object.prototype.toString.call(o) === '[object Object]'\n}\n\nexport function sleep(timeout: number): Promise<void> {\n return new Promise((resolve) => {\n setTimeout(resolve, timeout)\n })\n}\n\nexport function replaceData<\n TData,\n TOptions extends QueryOptions<any, any, any, any>,\n>(prevData: TData | undefined, data: TData, options: TOptions): TData {\n if (typeof options.structuralSharing === 'function') {\n return options.structuralSharing(prevData, data) as TData\n } else if (options.structuralSharing !== false) {\n if (process.env.NODE_ENV !== 'production') {\n try {\n return replaceEqualDeep(prevData, data)\n } catch (error) {\n console.error(\n `Structural sharing requires data to be JSON serializable. To fix this, turn off structuralSharing or return JSON-serializable data from your queryFn. [${options.queryHash}]: ${error}`,\n )\n }\n }\n // Structurally share data between prev and new data if needed\n return replaceEqualDeep(prevData, data)\n }\n return data\n}\n\nexport function keepPreviousData<T>(\n previousData: T | undefined,\n): T | undefined {\n return previousData\n}\n\nexport function addToEnd<T>(items: Array<T>, item: T, max = 0): Array<T> {\n const newItems = [...items, item]\n return max && newItems.length > max ? newItems.slice(1) : newItems\n}\n\nexport function addToStart<T>(items: Array<T>, item: T, max = 0): Array<T> {\n const newItems = [item, ...items]\n return max && newItems.length > max ? newItems.slice(0, -1) : newItems\n}\n\nexport const skipToken = Symbol()\nexport type SkipToken = typeof skipToken\n\nexport function ensureQueryFn<\n TQueryFnData = unknown,\n TQueryKey extends QueryKey = QueryKey,\n>(\n options: {\n queryFn?: QueryFunction<TQueryFnData, TQueryKey> | SkipToken\n queryHash?: string\n },\n fetchOptions?: FetchOptions<TQueryFnData>,\n): QueryFunction<TQueryFnData, TQueryKey> {\n if (process.env.NODE_ENV !== 'production') {\n if (options.queryFn === skipToken) {\n console.error(\n `Attempted to invoke queryFn when set to skipToken. This is likely a configuration error. Query hash: '${options.queryHash}'`,\n )\n }\n }\n\n // if we attempt to retry a fetch that was triggered from an initialPromise\n // when we don't have a queryFn yet, we can't retry, so we just return the already rejected initialPromise\n // if an observer has already mounted, we will be able to retry with that queryFn\n if (!options.queryFn && fetchOptions?.initialPromise) {\n return () => fetchOptions.initialPromise!\n }\n\n if (!options.queryFn || options.queryFn === skipToken) {\n return () =>\n Promise.reject(new Error(`Missing queryFn: '${options.queryHash}'`))\n }\n\n return options.queryFn\n}\n"],"mappings":"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","names":[]}
|
package/build/legacy/utils.js
CHANGED
|
@@ -181,11 +181,10 @@ function replaceData(prevData, data, options) {
|
|
|
181
181
|
} else if (options.structuralSharing !== false) {
|
|
182
182
|
if (process.env.NODE_ENV !== "production") {
|
|
183
183
|
try {
|
|
184
|
-
|
|
185
|
-
JSON.stringify(data);
|
|
184
|
+
return replaceEqualDeep(prevData, data);
|
|
186
185
|
} catch (error) {
|
|
187
186
|
console.error(
|
|
188
|
-
`
|
|
187
|
+
`Structural sharing requires data to be JSON serializable. To fix this, turn off structuralSharing or return JSON-serializable data from your queryFn. [${options.queryHash}]: ${error}`
|
|
189
188
|
);
|
|
190
189
|
}
|
|
191
190
|
}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../../src/utils.ts"],"sourcesContent":["import type {\n DefaultError,\n Enabled,\n FetchStatus,\n MutationKey,\n MutationStatus,\n QueryFunction,\n QueryKey,\n QueryOptions,\n StaleTime,\n} from './types'\nimport type { Mutation } from './mutation'\nimport type { FetchOptions, Query } from './query'\n\n// TYPES\n\nexport interface QueryFilters {\n /**\n * Filter to active queries, inactive queries or all queries\n */\n type?: QueryTypeFilter\n /**\n * Match query key exactly\n */\n exact?: boolean\n /**\n * Include queries matching this predicate function\n */\n predicate?: (query: Query) => boolean\n /**\n * Include queries matching this query key\n */\n queryKey?: QueryKey\n /**\n * Include or exclude stale queries\n */\n stale?: boolean\n /**\n * Include queries matching their fetchStatus\n */\n fetchStatus?: FetchStatus\n}\n\nexport interface MutationFilters {\n /**\n * Match mutation key exactly\n */\n exact?: boolean\n /**\n * Include mutations matching this predicate function\n */\n predicate?: (mutation: Mutation<any, any, any>) => boolean\n /**\n * Include mutations matching this mutation key\n */\n mutationKey?: MutationKey\n /**\n * Filter by mutation status\n */\n status?: MutationStatus\n}\n\nexport type Updater<TInput, TOutput> = TOutput | ((input: TInput) => TOutput)\n\nexport type QueryTypeFilter = 'all' | 'active' | 'inactive'\n\n// UTILS\n\nexport const isServer = typeof window === 'undefined' || 'Deno' in globalThis\n\nexport function noop(): undefined {\n return undefined\n}\n\nexport function functionalUpdate<TInput, TOutput>(\n updater: Updater<TInput, TOutput>,\n input: TInput,\n): TOutput {\n return typeof updater === 'function'\n ? (updater as (_: TInput) => TOutput)(input)\n : updater\n}\n\nexport function isValidTimeout(value: unknown): value is number {\n return typeof value === 'number' && value >= 0 && value !== Infinity\n}\n\nexport function timeUntilStale(updatedAt: number, staleTime?: number): number {\n return Math.max(updatedAt + (staleTime || 0) - Date.now(), 0)\n}\n\nexport function resolveStaleTime<\n TQueryFnData = unknown,\n TError = DefaultError,\n TData = TQueryFnData,\n TQueryKey extends QueryKey = QueryKey,\n>(\n staleTime: undefined | StaleTime<TQueryFnData, TError, TData, TQueryKey>,\n query: Query<TQueryFnData, TError, TData, TQueryKey>,\n): number | undefined {\n return typeof staleTime === 'function' ? staleTime(query) : staleTime\n}\n\nexport function resolveEnabled<\n TQueryFnData = unknown,\n TError = DefaultError,\n TData = TQueryFnData,\n TQueryKey extends QueryKey = QueryKey,\n>(\n enabled: undefined | Enabled<TQueryFnData, TError, TData, TQueryKey>,\n query: Query<TQueryFnData, TError, TData, TQueryKey>,\n): boolean | undefined {\n return typeof enabled === 'function' ? enabled(query) : enabled\n}\n\nexport function matchQuery(\n filters: QueryFilters,\n query: Query<any, any, any, any>,\n): boolean {\n const {\n type = 'all',\n exact,\n fetchStatus,\n predicate,\n queryKey,\n stale,\n } = filters\n\n if (queryKey) {\n if (exact) {\n if (query.queryHash !== hashQueryKeyByOptions(queryKey, query.options)) {\n return false\n }\n } else if (!partialMatchKey(query.queryKey, queryKey)) {\n return false\n }\n }\n\n if (type !== 'all') {\n const isActive = query.isActive()\n if (type === 'active' && !isActive) {\n return false\n }\n if (type === 'inactive' && isActive) {\n return false\n }\n }\n\n if (typeof stale === 'boolean' && query.isStale() !== stale) {\n return false\n }\n\n if (fetchStatus && fetchStatus !== query.state.fetchStatus) {\n return false\n }\n\n if (predicate && !predicate(query)) {\n return false\n }\n\n return true\n}\n\nexport function matchMutation(\n filters: MutationFilters,\n mutation: Mutation<any, any>,\n): boolean {\n const { exact, status, predicate, mutationKey } = filters\n if (mutationKey) {\n if (!mutation.options.mutationKey) {\n return false\n }\n if (exact) {\n if (hashKey(mutation.options.mutationKey) !== hashKey(mutationKey)) {\n return false\n }\n } else if (!partialMatchKey(mutation.options.mutationKey, mutationKey)) {\n return false\n }\n }\n\n if (status && mutation.state.status !== status) {\n return false\n }\n\n if (predicate && !predicate(mutation)) {\n return false\n }\n\n return true\n}\n\nexport function hashQueryKeyByOptions<TQueryKey extends QueryKey = QueryKey>(\n queryKey: TQueryKey,\n options?: Pick<QueryOptions<any, any, any, any>, 'queryKeyHashFn'>,\n): string {\n const hashFn = options?.queryKeyHashFn || hashKey\n return hashFn(queryKey)\n}\n\n/**\n * Default query & mutation keys hash function.\n * Hashes the value into a stable hash.\n */\nexport function hashKey(queryKey: QueryKey | MutationKey): string {\n return JSON.stringify(queryKey, (_, val) =>\n isPlainObject(val)\n ? Object.keys(val)\n .sort()\n .reduce((result, key) => {\n result[key] = val[key]\n return result\n }, {} as any)\n : val,\n )\n}\n\n/**\n * Checks if key `b` partially matches with key `a`.\n */\nexport function partialMatchKey(a: QueryKey, b: QueryKey): boolean\nexport function partialMatchKey(a: any, b: any): boolean {\n if (a === b) {\n return true\n }\n\n if (typeof a !== typeof b) {\n return false\n }\n\n if (a && b && typeof a === 'object' && typeof b === 'object') {\n return !Object.keys(b).some((key) => !partialMatchKey(a[key], b[key]))\n }\n\n return false\n}\n\n/**\n * This function returns `a` if `b` is deeply equal.\n * If not, it will replace any deeply equal children of `b` with those of `a`.\n * This can be used for structural sharing between JSON values for example.\n */\nexport function replaceEqualDeep<T>(a: unknown, b: T): T\nexport function replaceEqualDeep(a: any, b: any): any {\n if (a === b) {\n return a\n }\n\n const array = isPlainArray(a) && isPlainArray(b)\n\n if (array || (isPlainObject(a) && isPlainObject(b))) {\n const aItems = array ? a : Object.keys(a)\n const aSize = aItems.length\n const bItems = array ? b : Object.keys(b)\n const bSize = bItems.length\n const copy: any = array ? [] : {}\n\n let equalItems = 0\n\n for (let i = 0; i < bSize; i++) {\n const key = array ? i : bItems[i]\n if (\n ((!array && aItems.includes(key)) || array) &&\n a[key] === undefined &&\n b[key] === undefined\n ) {\n copy[key] = undefined\n equalItems++\n } else {\n copy[key] = replaceEqualDeep(a[key], b[key])\n if (copy[key] === a[key] && a[key] !== undefined) {\n equalItems++\n }\n }\n }\n\n return aSize === bSize && equalItems === aSize ? a : copy\n }\n\n return b\n}\n\n/**\n * Shallow compare objects.\n */\nexport function shallowEqualObjects<T extends Record<string, any>>(\n a: T,\n b: T | undefined,\n): boolean {\n if (!b || Object.keys(a).length !== Object.keys(b).length) {\n return false\n }\n\n for (const key in a) {\n if (a[key] !== b[key]) {\n return false\n }\n }\n\n return true\n}\n\nexport function isPlainArray(value: unknown) {\n return Array.isArray(value) && value.length === Object.keys(value).length\n}\n\n// Copied from: https://github.com/jonschlinkert/is-plain-object\n// eslint-disable-next-line @typescript-eslint/no-wrapper-object-types\nexport function isPlainObject(o: any): o is Object {\n if (!hasObjectPrototype(o)) {\n return false\n }\n\n // If has no constructor\n const ctor = o.constructor\n if (ctor === undefined) {\n return true\n }\n\n // If has modified prototype\n const prot = ctor.prototype\n if (!hasObjectPrototype(prot)) {\n return false\n }\n\n // If constructor does not have an Object-specific method\n if (!prot.hasOwnProperty('isPrototypeOf')) {\n return false\n }\n\n // Handles Objects created by Object.create(<arbitrary prototype>)\n if (Object.getPrototypeOf(o) !== Object.prototype) {\n return false\n }\n\n // Most likely a plain Object\n return true\n}\n\nfunction hasObjectPrototype(o: any): boolean {\n return Object.prototype.toString.call(o) === '[object Object]'\n}\n\nexport function sleep(timeout: number): Promise<void> {\n return new Promise((resolve) => {\n setTimeout(resolve, timeout)\n })\n}\n\nexport function replaceData<\n TData,\n TOptions extends QueryOptions<any, any, any, any>,\n>(prevData: TData | undefined, data: TData, options: TOptions): TData {\n if (typeof options.structuralSharing === 'function') {\n return options.structuralSharing(prevData, data) as TData\n } else if (options.structuralSharing !== false) {\n if (process.env.NODE_ENV !== 'production') {\n try {\n JSON.stringify(prevData)\n JSON.stringify(data)\n } catch (error) {\n console.error(\n `StructuralSharing requires data to be JSON serializable. To fix this, turn off structuralSharing or return JSON-serializable data from your queryFn. [${options.queryHash}]: ${error}`,\n )\n }\n }\n\n // Structurally share data between prev and new data if needed\n return replaceEqualDeep(prevData, data)\n }\n return data\n}\n\nexport function keepPreviousData<T>(\n previousData: T | undefined,\n): T | undefined {\n return previousData\n}\n\nexport function addToEnd<T>(items: Array<T>, item: T, max = 0): Array<T> {\n const newItems = [...items, item]\n return max && newItems.length > max ? newItems.slice(1) : newItems\n}\n\nexport function addToStart<T>(items: Array<T>, item: T, max = 0): Array<T> {\n const newItems = [item, ...items]\n return max && newItems.length > max ? newItems.slice(0, -1) : newItems\n}\n\nexport const skipToken = Symbol()\nexport type SkipToken = typeof skipToken\n\nexport function ensureQueryFn<\n TQueryFnData = unknown,\n TQueryKey extends QueryKey = QueryKey,\n>(\n options: {\n queryFn?: QueryFunction<TQueryFnData, TQueryKey> | SkipToken\n queryHash?: string\n },\n fetchOptions?: FetchOptions<TQueryFnData>,\n): QueryFunction<TQueryFnData, TQueryKey> {\n if (process.env.NODE_ENV !== 'production') {\n if (options.queryFn === skipToken) {\n console.error(\n `Attempted to invoke queryFn when set to skipToken. This is likely a configuration error. Query hash: '${options.queryHash}'`,\n )\n }\n }\n\n // if we attempt to retry a fetch that was triggered from an initialPromise\n // when we don't have a queryFn yet, we can't retry, so we just return the already rejected initialPromise\n // if an observer has already mounted, we will be able to retry with that queryFn\n if (!options.queryFn && fetchOptions?.initialPromise) {\n return () => fetchOptions.initialPromise!\n }\n\n if (!options.queryFn || options.queryFn === skipToken) {\n return () =>\n Promise.reject(new Error(`Missing queryFn: '${options.queryHash}'`))\n }\n\n return options.queryFn\n}\n"],"mappings":"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","names":[]}
|
|
1
|
+
{"version":3,"sources":["../../src/utils.ts"],"sourcesContent":["import type {\n DefaultError,\n Enabled,\n FetchStatus,\n MutationKey,\n MutationStatus,\n QueryFunction,\n QueryKey,\n QueryOptions,\n StaleTime,\n} from './types'\nimport type { Mutation } from './mutation'\nimport type { FetchOptions, Query } from './query'\n\n// TYPES\n\nexport interface QueryFilters {\n /**\n * Filter to active queries, inactive queries or all queries\n */\n type?: QueryTypeFilter\n /**\n * Match query key exactly\n */\n exact?: boolean\n /**\n * Include queries matching this predicate function\n */\n predicate?: (query: Query) => boolean\n /**\n * Include queries matching this query key\n */\n queryKey?: QueryKey\n /**\n * Include or exclude stale queries\n */\n stale?: boolean\n /**\n * Include queries matching their fetchStatus\n */\n fetchStatus?: FetchStatus\n}\n\nexport interface MutationFilters {\n /**\n * Match mutation key exactly\n */\n exact?: boolean\n /**\n * Include mutations matching this predicate function\n */\n predicate?: (mutation: Mutation<any, any, any>) => boolean\n /**\n * Include mutations matching this mutation key\n */\n mutationKey?: MutationKey\n /**\n * Filter by mutation status\n */\n status?: MutationStatus\n}\n\nexport type Updater<TInput, TOutput> = TOutput | ((input: TInput) => TOutput)\n\nexport type QueryTypeFilter = 'all' | 'active' | 'inactive'\n\n// UTILS\n\nexport const isServer = typeof window === 'undefined' || 'Deno' in globalThis\n\nexport function noop(): undefined {\n return undefined\n}\n\nexport function functionalUpdate<TInput, TOutput>(\n updater: Updater<TInput, TOutput>,\n input: TInput,\n): TOutput {\n return typeof updater === 'function'\n ? (updater as (_: TInput) => TOutput)(input)\n : updater\n}\n\nexport function isValidTimeout(value: unknown): value is number {\n return typeof value === 'number' && value >= 0 && value !== Infinity\n}\n\nexport function timeUntilStale(updatedAt: number, staleTime?: number): number {\n return Math.max(updatedAt + (staleTime || 0) - Date.now(), 0)\n}\n\nexport function resolveStaleTime<\n TQueryFnData = unknown,\n TError = DefaultError,\n TData = TQueryFnData,\n TQueryKey extends QueryKey = QueryKey,\n>(\n staleTime: undefined | StaleTime<TQueryFnData, TError, TData, TQueryKey>,\n query: Query<TQueryFnData, TError, TData, TQueryKey>,\n): number | undefined {\n return typeof staleTime === 'function' ? staleTime(query) : staleTime\n}\n\nexport function resolveEnabled<\n TQueryFnData = unknown,\n TError = DefaultError,\n TData = TQueryFnData,\n TQueryKey extends QueryKey = QueryKey,\n>(\n enabled: undefined | Enabled<TQueryFnData, TError, TData, TQueryKey>,\n query: Query<TQueryFnData, TError, TData, TQueryKey>,\n): boolean | undefined {\n return typeof enabled === 'function' ? enabled(query) : enabled\n}\n\nexport function matchQuery(\n filters: QueryFilters,\n query: Query<any, any, any, any>,\n): boolean {\n const {\n type = 'all',\n exact,\n fetchStatus,\n predicate,\n queryKey,\n stale,\n } = filters\n\n if (queryKey) {\n if (exact) {\n if (query.queryHash !== hashQueryKeyByOptions(queryKey, query.options)) {\n return false\n }\n } else if (!partialMatchKey(query.queryKey, queryKey)) {\n return false\n }\n }\n\n if (type !== 'all') {\n const isActive = query.isActive()\n if (type === 'active' && !isActive) {\n return false\n }\n if (type === 'inactive' && isActive) {\n return false\n }\n }\n\n if (typeof stale === 'boolean' && query.isStale() !== stale) {\n return false\n }\n\n if (fetchStatus && fetchStatus !== query.state.fetchStatus) {\n return false\n }\n\n if (predicate && !predicate(query)) {\n return false\n }\n\n return true\n}\n\nexport function matchMutation(\n filters: MutationFilters,\n mutation: Mutation<any, any>,\n): boolean {\n const { exact, status, predicate, mutationKey } = filters\n if (mutationKey) {\n if (!mutation.options.mutationKey) {\n return false\n }\n if (exact) {\n if (hashKey(mutation.options.mutationKey) !== hashKey(mutationKey)) {\n return false\n }\n } else if (!partialMatchKey(mutation.options.mutationKey, mutationKey)) {\n return false\n }\n }\n\n if (status && mutation.state.status !== status) {\n return false\n }\n\n if (predicate && !predicate(mutation)) {\n return false\n }\n\n return true\n}\n\nexport function hashQueryKeyByOptions<TQueryKey extends QueryKey = QueryKey>(\n queryKey: TQueryKey,\n options?: Pick<QueryOptions<any, any, any, any>, 'queryKeyHashFn'>,\n): string {\n const hashFn = options?.queryKeyHashFn || hashKey\n return hashFn(queryKey)\n}\n\n/**\n * Default query & mutation keys hash function.\n * Hashes the value into a stable hash.\n */\nexport function hashKey(queryKey: QueryKey | MutationKey): string {\n return JSON.stringify(queryKey, (_, val) =>\n isPlainObject(val)\n ? Object.keys(val)\n .sort()\n .reduce((result, key) => {\n result[key] = val[key]\n return result\n }, {} as any)\n : val,\n )\n}\n\n/**\n * Checks if key `b` partially matches with key `a`.\n */\nexport function partialMatchKey(a: QueryKey, b: QueryKey): boolean\nexport function partialMatchKey(a: any, b: any): boolean {\n if (a === b) {\n return true\n }\n\n if (typeof a !== typeof b) {\n return false\n }\n\n if (a && b && typeof a === 'object' && typeof b === 'object') {\n return !Object.keys(b).some((key) => !partialMatchKey(a[key], b[key]))\n }\n\n return false\n}\n\n/**\n * This function returns `a` if `b` is deeply equal.\n * If not, it will replace any deeply equal children of `b` with those of `a`.\n * This can be used for structural sharing between JSON values for example.\n */\nexport function replaceEqualDeep<T>(a: unknown, b: T): T\nexport function replaceEqualDeep(a: any, b: any): any {\n if (a === b) {\n return a\n }\n\n const array = isPlainArray(a) && isPlainArray(b)\n\n if (array || (isPlainObject(a) && isPlainObject(b))) {\n const aItems = array ? a : Object.keys(a)\n const aSize = aItems.length\n const bItems = array ? b : Object.keys(b)\n const bSize = bItems.length\n const copy: any = array ? [] : {}\n\n let equalItems = 0\n\n for (let i = 0; i < bSize; i++) {\n const key = array ? i : bItems[i]\n if (\n ((!array && aItems.includes(key)) || array) &&\n a[key] === undefined &&\n b[key] === undefined\n ) {\n copy[key] = undefined\n equalItems++\n } else {\n copy[key] = replaceEqualDeep(a[key], b[key])\n if (copy[key] === a[key] && a[key] !== undefined) {\n equalItems++\n }\n }\n }\n\n return aSize === bSize && equalItems === aSize ? a : copy\n }\n\n return b\n}\n\n/**\n * Shallow compare objects.\n */\nexport function shallowEqualObjects<T extends Record<string, any>>(\n a: T,\n b: T | undefined,\n): boolean {\n if (!b || Object.keys(a).length !== Object.keys(b).length) {\n return false\n }\n\n for (const key in a) {\n if (a[key] !== b[key]) {\n return false\n }\n }\n\n return true\n}\n\nexport function isPlainArray(value: unknown) {\n return Array.isArray(value) && value.length === Object.keys(value).length\n}\n\n// Copied from: https://github.com/jonschlinkert/is-plain-object\n// eslint-disable-next-line @typescript-eslint/no-wrapper-object-types\nexport function isPlainObject(o: any): o is Object {\n if (!hasObjectPrototype(o)) {\n return false\n }\n\n // If has no constructor\n const ctor = o.constructor\n if (ctor === undefined) {\n return true\n }\n\n // If has modified prototype\n const prot = ctor.prototype\n if (!hasObjectPrototype(prot)) {\n return false\n }\n\n // If constructor does not have an Object-specific method\n if (!prot.hasOwnProperty('isPrototypeOf')) {\n return false\n }\n\n // Handles Objects created by Object.create(<arbitrary prototype>)\n if (Object.getPrototypeOf(o) !== Object.prototype) {\n return false\n }\n\n // Most likely a plain Object\n return true\n}\n\nfunction hasObjectPrototype(o: any): boolean {\n return Object.prototype.toString.call(o) === '[object Object]'\n}\n\nexport function sleep(timeout: number): Promise<void> {\n return new Promise((resolve) => {\n setTimeout(resolve, timeout)\n })\n}\n\nexport function replaceData<\n TData,\n TOptions extends QueryOptions<any, any, any, any>,\n>(prevData: TData | undefined, data: TData, options: TOptions): TData {\n if (typeof options.structuralSharing === 'function') {\n return options.structuralSharing(prevData, data) as TData\n } else if (options.structuralSharing !== false) {\n if (process.env.NODE_ENV !== 'production') {\n try {\n return replaceEqualDeep(prevData, data)\n } catch (error) {\n console.error(\n `Structural sharing requires data to be JSON serializable. To fix this, turn off structuralSharing or return JSON-serializable data from your queryFn. [${options.queryHash}]: ${error}`,\n )\n }\n }\n // Structurally share data between prev and new data if needed\n return replaceEqualDeep(prevData, data)\n }\n return data\n}\n\nexport function keepPreviousData<T>(\n previousData: T | undefined,\n): T | undefined {\n return previousData\n}\n\nexport function addToEnd<T>(items: Array<T>, item: T, max = 0): Array<T> {\n const newItems = [...items, item]\n return max && newItems.length > max ? newItems.slice(1) : newItems\n}\n\nexport function addToStart<T>(items: Array<T>, item: T, max = 0): Array<T> {\n const newItems = [item, ...items]\n return max && newItems.length > max ? newItems.slice(0, -1) : newItems\n}\n\nexport const skipToken = Symbol()\nexport type SkipToken = typeof skipToken\n\nexport function ensureQueryFn<\n TQueryFnData = unknown,\n TQueryKey extends QueryKey = QueryKey,\n>(\n options: {\n queryFn?: QueryFunction<TQueryFnData, TQueryKey> | SkipToken\n queryHash?: string\n },\n fetchOptions?: FetchOptions<TQueryFnData>,\n): QueryFunction<TQueryFnData, TQueryKey> {\n if (process.env.NODE_ENV !== 'production') {\n if (options.queryFn === skipToken) {\n console.error(\n `Attempted to invoke queryFn when set to skipToken. This is likely a configuration error. Query hash: '${options.queryHash}'`,\n )\n }\n }\n\n // if we attempt to retry a fetch that was triggered from an initialPromise\n // when we don't have a queryFn yet, we can't retry, so we just return the already rejected initialPromise\n // if an observer has already mounted, we will be able to retry with that queryFn\n if (!options.queryFn && fetchOptions?.initialPromise) {\n return () => fetchOptions.initialPromise!\n }\n\n if (!options.queryFn || options.queryFn === skipToken) {\n return () =>\n Promise.reject(new Error(`Missing queryFn: '${options.queryHash}'`))\n }\n\n return options.queryFn\n}\n"],"mappings":"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","names":[]}
|
|
@@ -34,22 +34,6 @@ function createNotifyManager() {
|
|
|
34
34
|
callback();
|
|
35
35
|
};
|
|
36
36
|
let scheduleFn = (cb) => setTimeout(cb, 0);
|
|
37
|
-
const setScheduler = (fn) => {
|
|
38
|
-
scheduleFn = fn;
|
|
39
|
-
};
|
|
40
|
-
const batch = (callback) => {
|
|
41
|
-
let result;
|
|
42
|
-
transactions++;
|
|
43
|
-
try {
|
|
44
|
-
result = callback();
|
|
45
|
-
} finally {
|
|
46
|
-
transactions--;
|
|
47
|
-
if (!transactions) {
|
|
48
|
-
flush();
|
|
49
|
-
}
|
|
50
|
-
}
|
|
51
|
-
return result;
|
|
52
|
-
};
|
|
53
37
|
const schedule = (callback) => {
|
|
54
38
|
if (transactions) {
|
|
55
39
|
queue.push(callback);
|
|
@@ -59,13 +43,6 @@ function createNotifyManager() {
|
|
|
59
43
|
});
|
|
60
44
|
}
|
|
61
45
|
};
|
|
62
|
-
const batchCalls = (callback) => {
|
|
63
|
-
return (...args) => {
|
|
64
|
-
schedule(() => {
|
|
65
|
-
callback(...args);
|
|
66
|
-
});
|
|
67
|
-
};
|
|
68
|
-
};
|
|
69
46
|
const flush = () => {
|
|
70
47
|
const originalQueue = queue;
|
|
71
48
|
queue = [];
|
|
@@ -79,19 +56,48 @@ function createNotifyManager() {
|
|
|
79
56
|
});
|
|
80
57
|
}
|
|
81
58
|
};
|
|
82
|
-
const setNotifyFunction = (fn) => {
|
|
83
|
-
notifyFn = fn;
|
|
84
|
-
};
|
|
85
|
-
const setBatchNotifyFunction = (fn) => {
|
|
86
|
-
batchNotifyFn = fn;
|
|
87
|
-
};
|
|
88
59
|
return {
|
|
89
|
-
batch
|
|
90
|
-
|
|
60
|
+
batch: (callback) => {
|
|
61
|
+
let result;
|
|
62
|
+
transactions++;
|
|
63
|
+
try {
|
|
64
|
+
result = callback();
|
|
65
|
+
} finally {
|
|
66
|
+
transactions--;
|
|
67
|
+
if (!transactions) {
|
|
68
|
+
flush();
|
|
69
|
+
}
|
|
70
|
+
}
|
|
71
|
+
return result;
|
|
72
|
+
},
|
|
73
|
+
/**
|
|
74
|
+
* All calls to the wrapped function will be batched.
|
|
75
|
+
*/
|
|
76
|
+
batchCalls: (callback) => {
|
|
77
|
+
return (...args) => {
|
|
78
|
+
schedule(() => {
|
|
79
|
+
callback(...args);
|
|
80
|
+
});
|
|
81
|
+
};
|
|
82
|
+
},
|
|
91
83
|
schedule,
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
|
|
84
|
+
/**
|
|
85
|
+
* Use this method to set a custom notify function.
|
|
86
|
+
* This can be used to for example wrap notifications with `React.act` while running tests.
|
|
87
|
+
*/
|
|
88
|
+
setNotifyFunction: (fn) => {
|
|
89
|
+
notifyFn = fn;
|
|
90
|
+
},
|
|
91
|
+
/**
|
|
92
|
+
* Use this method to set a custom function to batch notifications together into a single tick.
|
|
93
|
+
* By default React Query will use the batch function provided by ReactDOM or React Native.
|
|
94
|
+
*/
|
|
95
|
+
setBatchNotifyFunction: (fn) => {
|
|
96
|
+
batchNotifyFn = fn;
|
|
97
|
+
},
|
|
98
|
+
setScheduler: (fn) => {
|
|
99
|
+
scheduleFn = fn;
|
|
100
|
+
}
|
|
95
101
|
};
|
|
96
102
|
}
|
|
97
103
|
var notifyManager = createNotifyManager();
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../../src/notifyManager.ts"],"sourcesContent":["// TYPES\n\ntype NotifyCallback = () => void\n\ntype NotifyFunction = (callback: () => void) => void\n\ntype BatchNotifyFunction = (callback: () => void) => void\n\ntype BatchCallsCallback<T extends Array<unknown>> = (...args: T) => void\n\ntype ScheduleFunction = (callback: () => void) => void\n\nexport function createNotifyManager() {\n let queue: Array<NotifyCallback> = []\n let transactions = 0\n let notifyFn: NotifyFunction = (callback) => {\n callback()\n }\n let batchNotifyFn: BatchNotifyFunction = (callback: () => void) => {\n callback()\n }\n let scheduleFn: ScheduleFunction = (cb) => setTimeout(cb, 0)\n\n const
|
|
1
|
+
{"version":3,"sources":["../../src/notifyManager.ts"],"sourcesContent":["// TYPES\n\ntype NotifyCallback = () => void\n\ntype NotifyFunction = (callback: () => void) => void\n\ntype BatchNotifyFunction = (callback: () => void) => void\n\ntype BatchCallsCallback<T extends Array<unknown>> = (...args: T) => void\n\ntype ScheduleFunction = (callback: () => void) => void\n\nexport function createNotifyManager() {\n let queue: Array<NotifyCallback> = []\n let transactions = 0\n let notifyFn: NotifyFunction = (callback) => {\n callback()\n }\n let batchNotifyFn: BatchNotifyFunction = (callback: () => void) => {\n callback()\n }\n let scheduleFn: ScheduleFunction = (cb) => setTimeout(cb, 0)\n\n const schedule = (callback: NotifyCallback): void => {\n if (transactions) {\n queue.push(callback)\n } else {\n scheduleFn(() => {\n notifyFn(callback)\n })\n }\n }\n const flush = (): void => {\n const originalQueue = queue\n queue = []\n if (originalQueue.length) {\n scheduleFn(() => {\n batchNotifyFn(() => {\n originalQueue.forEach((callback) => {\n notifyFn(callback)\n })\n })\n })\n }\n }\n\n return {\n batch: <T>(callback: () => T): T => {\n let result\n transactions++\n try {\n result = callback()\n } finally {\n transactions--\n if (!transactions) {\n flush()\n }\n }\n return result\n },\n /**\n * All calls to the wrapped function will be batched.\n */\n batchCalls: <T extends Array<unknown>>(\n callback: BatchCallsCallback<T>,\n ): BatchCallsCallback<T> => {\n return (...args) => {\n schedule(() => {\n callback(...args)\n })\n }\n },\n schedule,\n /**\n * Use this method to set a custom notify function.\n * This can be used to for example wrap notifications with `React.act` while running tests.\n */\n setNotifyFunction: (fn: NotifyFunction) => {\n notifyFn = fn\n },\n /**\n * Use this method to set a custom function to batch notifications together into a single tick.\n * By default React Query will use the batch function provided by ReactDOM or React Native.\n */\n setBatchNotifyFunction: (fn: BatchNotifyFunction) => {\n batchNotifyFn = fn\n },\n setScheduler: (fn: ScheduleFunction) => {\n scheduleFn = fn\n },\n } as const\n}\n\n// SINGLETON\nexport const notifyManager = createNotifyManager()\n"],"mappings":";;;;;;;;;;;;;;;;;;;;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAYO,SAAS,sBAAsB;AACpC,MAAI,QAA+B,CAAC;AACpC,MAAI,eAAe;AACnB,MAAI,WAA2B,CAAC,aAAa;AAC3C,aAAS;AAAA,EACX;AACA,MAAI,gBAAqC,CAAC,aAAyB;AACjE,aAAS;AAAA,EACX;AACA,MAAI,aAA+B,CAAC,OAAO,WAAW,IAAI,CAAC;AAE3D,QAAM,WAAW,CAAC,aAAmC;AACnD,QAAI,cAAc;AAChB,YAAM,KAAK,QAAQ;AAAA,IACrB,OAAO;AACL,iBAAW,MAAM;AACf,iBAAS,QAAQ;AAAA,MACnB,CAAC;AAAA,IACH;AAAA,EACF;AACA,QAAM,QAAQ,MAAY;AACxB,UAAM,gBAAgB;AACtB,YAAQ,CAAC;AACT,QAAI,cAAc,QAAQ;AACxB,iBAAW,MAAM;AACf,sBAAc,MAAM;AAClB,wBAAc,QAAQ,CAAC,aAAa;AAClC,qBAAS,QAAQ;AAAA,UACnB,CAAC;AAAA,QACH,CAAC;AAAA,MACH,CAAC;AAAA,IACH;AAAA,EACF;AAEA,SAAO;AAAA,IACL,OAAO,CAAI,aAAyB;AAClC,UAAI;AACJ;AACA,UAAI;AACF,iBAAS,SAAS;AAAA,MACpB,UAAE;AACA;AACA,YAAI,CAAC,cAAc;AACjB,gBAAM;AAAA,QACR;AAAA,MACF;AACA,aAAO;AAAA,IACT;AAAA;AAAA;AAAA;AAAA,IAIA,YAAY,CACV,aAC0B;AAC1B,aAAO,IAAI,SAAS;AAClB,iBAAS,MAAM;AACb,mBAAS,GAAG,IAAI;AAAA,QAClB,CAAC;AAAA,MACH;AAAA,IACF;AAAA,IACA;AAAA;AAAA;AAAA;AAAA;AAAA,IAKA,mBAAmB,CAAC,OAAuB;AACzC,iBAAW;AAAA,IACb;AAAA;AAAA;AAAA;AAAA;AAAA,IAKA,wBAAwB,CAAC,OAA4B;AACnD,sBAAgB;AAAA,IAClB;AAAA,IACA,cAAc,CAAC,OAAyB;AACtC,mBAAa;AAAA,IACf;AAAA,EACF;AACF;AAGO,IAAM,gBAAgB,oBAAoB;","names":[]}
|
|
@@ -5,17 +5,39 @@ type BatchCallsCallback<T extends Array<unknown>> = (...args: T) => void;
|
|
|
5
5
|
type ScheduleFunction = (callback: () => void) => void;
|
|
6
6
|
declare function createNotifyManager(): {
|
|
7
7
|
readonly batch: <T>(callback: () => T) => T;
|
|
8
|
+
/**
|
|
9
|
+
* All calls to the wrapped function will be batched.
|
|
10
|
+
*/
|
|
8
11
|
readonly batchCalls: <T_1 extends unknown[]>(callback: BatchCallsCallback<T_1>) => BatchCallsCallback<T_1>;
|
|
9
12
|
readonly schedule: (callback: NotifyCallback) => void;
|
|
13
|
+
/**
|
|
14
|
+
* Use this method to set a custom notify function.
|
|
15
|
+
* This can be used to for example wrap notifications with `React.act` while running tests.
|
|
16
|
+
*/
|
|
10
17
|
readonly setNotifyFunction: (fn: NotifyFunction) => void;
|
|
18
|
+
/**
|
|
19
|
+
* Use this method to set a custom function to batch notifications together into a single tick.
|
|
20
|
+
* By default React Query will use the batch function provided by ReactDOM or React Native.
|
|
21
|
+
*/
|
|
11
22
|
readonly setBatchNotifyFunction: (fn: BatchNotifyFunction) => void;
|
|
12
23
|
readonly setScheduler: (fn: ScheduleFunction) => void;
|
|
13
24
|
};
|
|
14
25
|
declare const notifyManager: {
|
|
15
26
|
readonly batch: <T>(callback: () => T) => T;
|
|
27
|
+
/**
|
|
28
|
+
* All calls to the wrapped function will be batched.
|
|
29
|
+
*/
|
|
16
30
|
readonly batchCalls: <T_1 extends unknown[]>(callback: BatchCallsCallback<T_1>) => BatchCallsCallback<T_1>;
|
|
17
31
|
readonly schedule: (callback: NotifyCallback) => void;
|
|
32
|
+
/**
|
|
33
|
+
* Use this method to set a custom notify function.
|
|
34
|
+
* This can be used to for example wrap notifications with `React.act` while running tests.
|
|
35
|
+
*/
|
|
18
36
|
readonly setNotifyFunction: (fn: NotifyFunction) => void;
|
|
37
|
+
/**
|
|
38
|
+
* Use this method to set a custom function to batch notifications together into a single tick.
|
|
39
|
+
* By default React Query will use the batch function provided by ReactDOM or React Native.
|
|
40
|
+
*/
|
|
19
41
|
readonly setBatchNotifyFunction: (fn: BatchNotifyFunction) => void;
|
|
20
42
|
readonly setScheduler: (fn: ScheduleFunction) => void;
|
|
21
43
|
};
|
|
@@ -5,17 +5,39 @@ type BatchCallsCallback<T extends Array<unknown>> = (...args: T) => void;
|
|
|
5
5
|
type ScheduleFunction = (callback: () => void) => void;
|
|
6
6
|
declare function createNotifyManager(): {
|
|
7
7
|
readonly batch: <T>(callback: () => T) => T;
|
|
8
|
+
/**
|
|
9
|
+
* All calls to the wrapped function will be batched.
|
|
10
|
+
*/
|
|
8
11
|
readonly batchCalls: <T_1 extends unknown[]>(callback: BatchCallsCallback<T_1>) => BatchCallsCallback<T_1>;
|
|
9
12
|
readonly schedule: (callback: NotifyCallback) => void;
|
|
13
|
+
/**
|
|
14
|
+
* Use this method to set a custom notify function.
|
|
15
|
+
* This can be used to for example wrap notifications with `React.act` while running tests.
|
|
16
|
+
*/
|
|
10
17
|
readonly setNotifyFunction: (fn: NotifyFunction) => void;
|
|
18
|
+
/**
|
|
19
|
+
* Use this method to set a custom function to batch notifications together into a single tick.
|
|
20
|
+
* By default React Query will use the batch function provided by ReactDOM or React Native.
|
|
21
|
+
*/
|
|
11
22
|
readonly setBatchNotifyFunction: (fn: BatchNotifyFunction) => void;
|
|
12
23
|
readonly setScheduler: (fn: ScheduleFunction) => void;
|
|
13
24
|
};
|
|
14
25
|
declare const notifyManager: {
|
|
15
26
|
readonly batch: <T>(callback: () => T) => T;
|
|
27
|
+
/**
|
|
28
|
+
* All calls to the wrapped function will be batched.
|
|
29
|
+
*/
|
|
16
30
|
readonly batchCalls: <T_1 extends unknown[]>(callback: BatchCallsCallback<T_1>) => BatchCallsCallback<T_1>;
|
|
17
31
|
readonly schedule: (callback: NotifyCallback) => void;
|
|
32
|
+
/**
|
|
33
|
+
* Use this method to set a custom notify function.
|
|
34
|
+
* This can be used to for example wrap notifications with `React.act` while running tests.
|
|
35
|
+
*/
|
|
18
36
|
readonly setNotifyFunction: (fn: NotifyFunction) => void;
|
|
37
|
+
/**
|
|
38
|
+
* Use this method to set a custom function to batch notifications together into a single tick.
|
|
39
|
+
* By default React Query will use the batch function provided by ReactDOM or React Native.
|
|
40
|
+
*/
|
|
19
41
|
readonly setBatchNotifyFunction: (fn: BatchNotifyFunction) => void;
|
|
20
42
|
readonly setScheduler: (fn: ScheduleFunction) => void;
|
|
21
43
|
};
|
|
@@ -9,22 +9,6 @@ function createNotifyManager() {
|
|
|
9
9
|
callback();
|
|
10
10
|
};
|
|
11
11
|
let scheduleFn = (cb) => setTimeout(cb, 0);
|
|
12
|
-
const setScheduler = (fn) => {
|
|
13
|
-
scheduleFn = fn;
|
|
14
|
-
};
|
|
15
|
-
const batch = (callback) => {
|
|
16
|
-
let result;
|
|
17
|
-
transactions++;
|
|
18
|
-
try {
|
|
19
|
-
result = callback();
|
|
20
|
-
} finally {
|
|
21
|
-
transactions--;
|
|
22
|
-
if (!transactions) {
|
|
23
|
-
flush();
|
|
24
|
-
}
|
|
25
|
-
}
|
|
26
|
-
return result;
|
|
27
|
-
};
|
|
28
12
|
const schedule = (callback) => {
|
|
29
13
|
if (transactions) {
|
|
30
14
|
queue.push(callback);
|
|
@@ -34,13 +18,6 @@ function createNotifyManager() {
|
|
|
34
18
|
});
|
|
35
19
|
}
|
|
36
20
|
};
|
|
37
|
-
const batchCalls = (callback) => {
|
|
38
|
-
return (...args) => {
|
|
39
|
-
schedule(() => {
|
|
40
|
-
callback(...args);
|
|
41
|
-
});
|
|
42
|
-
};
|
|
43
|
-
};
|
|
44
21
|
const flush = () => {
|
|
45
22
|
const originalQueue = queue;
|
|
46
23
|
queue = [];
|
|
@@ -54,19 +31,48 @@ function createNotifyManager() {
|
|
|
54
31
|
});
|
|
55
32
|
}
|
|
56
33
|
};
|
|
57
|
-
const setNotifyFunction = (fn) => {
|
|
58
|
-
notifyFn = fn;
|
|
59
|
-
};
|
|
60
|
-
const setBatchNotifyFunction = (fn) => {
|
|
61
|
-
batchNotifyFn = fn;
|
|
62
|
-
};
|
|
63
34
|
return {
|
|
64
|
-
batch
|
|
65
|
-
|
|
35
|
+
batch: (callback) => {
|
|
36
|
+
let result;
|
|
37
|
+
transactions++;
|
|
38
|
+
try {
|
|
39
|
+
result = callback();
|
|
40
|
+
} finally {
|
|
41
|
+
transactions--;
|
|
42
|
+
if (!transactions) {
|
|
43
|
+
flush();
|
|
44
|
+
}
|
|
45
|
+
}
|
|
46
|
+
return result;
|
|
47
|
+
},
|
|
48
|
+
/**
|
|
49
|
+
* All calls to the wrapped function will be batched.
|
|
50
|
+
*/
|
|
51
|
+
batchCalls: (callback) => {
|
|
52
|
+
return (...args) => {
|
|
53
|
+
schedule(() => {
|
|
54
|
+
callback(...args);
|
|
55
|
+
});
|
|
56
|
+
};
|
|
57
|
+
},
|
|
66
58
|
schedule,
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
59
|
+
/**
|
|
60
|
+
* Use this method to set a custom notify function.
|
|
61
|
+
* This can be used to for example wrap notifications with `React.act` while running tests.
|
|
62
|
+
*/
|
|
63
|
+
setNotifyFunction: (fn) => {
|
|
64
|
+
notifyFn = fn;
|
|
65
|
+
},
|
|
66
|
+
/**
|
|
67
|
+
* Use this method to set a custom function to batch notifications together into a single tick.
|
|
68
|
+
* By default React Query will use the batch function provided by ReactDOM or React Native.
|
|
69
|
+
*/
|
|
70
|
+
setBatchNotifyFunction: (fn) => {
|
|
71
|
+
batchNotifyFn = fn;
|
|
72
|
+
},
|
|
73
|
+
setScheduler: (fn) => {
|
|
74
|
+
scheduleFn = fn;
|
|
75
|
+
}
|
|
70
76
|
};
|
|
71
77
|
}
|
|
72
78
|
var notifyManager = createNotifyManager();
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../../src/notifyManager.ts"],"sourcesContent":["// TYPES\n\ntype NotifyCallback = () => void\n\ntype NotifyFunction = (callback: () => void) => void\n\ntype BatchNotifyFunction = (callback: () => void) => void\n\ntype BatchCallsCallback<T extends Array<unknown>> = (...args: T) => void\n\ntype ScheduleFunction = (callback: () => void) => void\n\nexport function createNotifyManager() {\n let queue: Array<NotifyCallback> = []\n let transactions = 0\n let notifyFn: NotifyFunction = (callback) => {\n callback()\n }\n let batchNotifyFn: BatchNotifyFunction = (callback: () => void) => {\n callback()\n }\n let scheduleFn: ScheduleFunction = (cb) => setTimeout(cb, 0)\n\n const
|
|
1
|
+
{"version":3,"sources":["../../src/notifyManager.ts"],"sourcesContent":["// TYPES\n\ntype NotifyCallback = () => void\n\ntype NotifyFunction = (callback: () => void) => void\n\ntype BatchNotifyFunction = (callback: () => void) => void\n\ntype BatchCallsCallback<T extends Array<unknown>> = (...args: T) => void\n\ntype ScheduleFunction = (callback: () => void) => void\n\nexport function createNotifyManager() {\n let queue: Array<NotifyCallback> = []\n let transactions = 0\n let notifyFn: NotifyFunction = (callback) => {\n callback()\n }\n let batchNotifyFn: BatchNotifyFunction = (callback: () => void) => {\n callback()\n }\n let scheduleFn: ScheduleFunction = (cb) => setTimeout(cb, 0)\n\n const schedule = (callback: NotifyCallback): void => {\n if (transactions) {\n queue.push(callback)\n } else {\n scheduleFn(() => {\n notifyFn(callback)\n })\n }\n }\n const flush = (): void => {\n const originalQueue = queue\n queue = []\n if (originalQueue.length) {\n scheduleFn(() => {\n batchNotifyFn(() => {\n originalQueue.forEach((callback) => {\n notifyFn(callback)\n })\n })\n })\n }\n }\n\n return {\n batch: <T>(callback: () => T): T => {\n let result\n transactions++\n try {\n result = callback()\n } finally {\n transactions--\n if (!transactions) {\n flush()\n }\n }\n return result\n },\n /**\n * All calls to the wrapped function will be batched.\n */\n batchCalls: <T extends Array<unknown>>(\n callback: BatchCallsCallback<T>,\n ): BatchCallsCallback<T> => {\n return (...args) => {\n schedule(() => {\n callback(...args)\n })\n }\n },\n schedule,\n /**\n * Use this method to set a custom notify function.\n * This can be used to for example wrap notifications with `React.act` while running tests.\n */\n setNotifyFunction: (fn: NotifyFunction) => {\n notifyFn = fn\n },\n /**\n * Use this method to set a custom function to batch notifications together into a single tick.\n * By default React Query will use the batch function provided by ReactDOM or React Native.\n */\n setBatchNotifyFunction: (fn: BatchNotifyFunction) => {\n batchNotifyFn = fn\n },\n setScheduler: (fn: ScheduleFunction) => {\n scheduleFn = fn\n },\n } as const\n}\n\n// SINGLETON\nexport const notifyManager = createNotifyManager()\n"],"mappings":";AAYO,SAAS,sBAAsB;AACpC,MAAI,QAA+B,CAAC;AACpC,MAAI,eAAe;AACnB,MAAI,WAA2B,CAAC,aAAa;AAC3C,aAAS;AAAA,EACX;AACA,MAAI,gBAAqC,CAAC,aAAyB;AACjE,aAAS;AAAA,EACX;AACA,MAAI,aAA+B,CAAC,OAAO,WAAW,IAAI,CAAC;AAE3D,QAAM,WAAW,CAAC,aAAmC;AACnD,QAAI,cAAc;AAChB,YAAM,KAAK,QAAQ;AAAA,IACrB,OAAO;AACL,iBAAW,MAAM;AACf,iBAAS,QAAQ;AAAA,MACnB,CAAC;AAAA,IACH;AAAA,EACF;AACA,QAAM,QAAQ,MAAY;AACxB,UAAM,gBAAgB;AACtB,YAAQ,CAAC;AACT,QAAI,cAAc,QAAQ;AACxB,iBAAW,MAAM;AACf,sBAAc,MAAM;AAClB,wBAAc,QAAQ,CAAC,aAAa;AAClC,qBAAS,QAAQ;AAAA,UACnB,CAAC;AAAA,QACH,CAAC;AAAA,MACH,CAAC;AAAA,IACH;AAAA,EACF;AAEA,SAAO;AAAA,IACL,OAAO,CAAI,aAAyB;AAClC,UAAI;AACJ;AACA,UAAI;AACF,iBAAS,SAAS;AAAA,MACpB,UAAE;AACA;AACA,YAAI,CAAC,cAAc;AACjB,gBAAM;AAAA,QACR;AAAA,MACF;AACA,aAAO;AAAA,IACT;AAAA;AAAA;AAAA;AAAA,IAIA,YAAY,CACV,aAC0B;AAC1B,aAAO,IAAI,SAAS;AAClB,iBAAS,MAAM;AACb,mBAAS,GAAG,IAAI;AAAA,QAClB,CAAC;AAAA,MACH;AAAA,IACF;AAAA,IACA;AAAA;AAAA;AAAA;AAAA;AAAA,IAKA,mBAAmB,CAAC,OAAuB;AACzC,iBAAW;AAAA,IACb;AAAA;AAAA;AAAA;AAAA;AAAA,IAKA,wBAAwB,CAAC,OAA4B;AACnD,sBAAgB;AAAA,IAClB;AAAA,IACA,cAAc,CAAC,OAAyB;AACtC,mBAAa;AAAA,IACf;AAAA,EACF;AACF;AAGO,IAAM,gBAAgB,oBAAoB;","names":[]}
|
package/build/modern/utils.cjs
CHANGED
|
@@ -225,11 +225,10 @@ function replaceData(prevData, data, options) {
|
|
|
225
225
|
} else if (options.structuralSharing !== false) {
|
|
226
226
|
if (process.env.NODE_ENV !== "production") {
|
|
227
227
|
try {
|
|
228
|
-
|
|
229
|
-
JSON.stringify(data);
|
|
228
|
+
return replaceEqualDeep(prevData, data);
|
|
230
229
|
} catch (error) {
|
|
231
230
|
console.error(
|
|
232
|
-
`
|
|
231
|
+
`Structural sharing requires data to be JSON serializable. To fix this, turn off structuralSharing or return JSON-serializable data from your queryFn. [${options.queryHash}]: ${error}`
|
|
233
232
|
);
|
|
234
233
|
}
|
|
235
234
|
}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../../src/utils.ts"],"sourcesContent":["import type {\n DefaultError,\n Enabled,\n FetchStatus,\n MutationKey,\n MutationStatus,\n QueryFunction,\n QueryKey,\n QueryOptions,\n StaleTime,\n} from './types'\nimport type { Mutation } from './mutation'\nimport type { FetchOptions, Query } from './query'\n\n// TYPES\n\nexport interface QueryFilters {\n /**\n * Filter to active queries, inactive queries or all queries\n */\n type?: QueryTypeFilter\n /**\n * Match query key exactly\n */\n exact?: boolean\n /**\n * Include queries matching this predicate function\n */\n predicate?: (query: Query) => boolean\n /**\n * Include queries matching this query key\n */\n queryKey?: QueryKey\n /**\n * Include or exclude stale queries\n */\n stale?: boolean\n /**\n * Include queries matching their fetchStatus\n */\n fetchStatus?: FetchStatus\n}\n\nexport interface MutationFilters {\n /**\n * Match mutation key exactly\n */\n exact?: boolean\n /**\n * Include mutations matching this predicate function\n */\n predicate?: (mutation: Mutation<any, any, any>) => boolean\n /**\n * Include mutations matching this mutation key\n */\n mutationKey?: MutationKey\n /**\n * Filter by mutation status\n */\n status?: MutationStatus\n}\n\nexport type Updater<TInput, TOutput> = TOutput | ((input: TInput) => TOutput)\n\nexport type QueryTypeFilter = 'all' | 'active' | 'inactive'\n\n// UTILS\n\nexport const isServer = typeof window === 'undefined' || 'Deno' in globalThis\n\nexport function noop(): undefined {\n return undefined\n}\n\nexport function functionalUpdate<TInput, TOutput>(\n updater: Updater<TInput, TOutput>,\n input: TInput,\n): TOutput {\n return typeof updater === 'function'\n ? (updater as (_: TInput) => TOutput)(input)\n : updater\n}\n\nexport function isValidTimeout(value: unknown): value is number {\n return typeof value === 'number' && value >= 0 && value !== Infinity\n}\n\nexport function timeUntilStale(updatedAt: number, staleTime?: number): number {\n return Math.max(updatedAt + (staleTime || 0) - Date.now(), 0)\n}\n\nexport function resolveStaleTime<\n TQueryFnData = unknown,\n TError = DefaultError,\n TData = TQueryFnData,\n TQueryKey extends QueryKey = QueryKey,\n>(\n staleTime: undefined | StaleTime<TQueryFnData, TError, TData, TQueryKey>,\n query: Query<TQueryFnData, TError, TData, TQueryKey>,\n): number | undefined {\n return typeof staleTime === 'function' ? staleTime(query) : staleTime\n}\n\nexport function resolveEnabled<\n TQueryFnData = unknown,\n TError = DefaultError,\n TData = TQueryFnData,\n TQueryKey extends QueryKey = QueryKey,\n>(\n enabled: undefined | Enabled<TQueryFnData, TError, TData, TQueryKey>,\n query: Query<TQueryFnData, TError, TData, TQueryKey>,\n): boolean | undefined {\n return typeof enabled === 'function' ? enabled(query) : enabled\n}\n\nexport function matchQuery(\n filters: QueryFilters,\n query: Query<any, any, any, any>,\n): boolean {\n const {\n type = 'all',\n exact,\n fetchStatus,\n predicate,\n queryKey,\n stale,\n } = filters\n\n if (queryKey) {\n if (exact) {\n if (query.queryHash !== hashQueryKeyByOptions(queryKey, query.options)) {\n return false\n }\n } else if (!partialMatchKey(query.queryKey, queryKey)) {\n return false\n }\n }\n\n if (type !== 'all') {\n const isActive = query.isActive()\n if (type === 'active' && !isActive) {\n return false\n }\n if (type === 'inactive' && isActive) {\n return false\n }\n }\n\n if (typeof stale === 'boolean' && query.isStale() !== stale) {\n return false\n }\n\n if (fetchStatus && fetchStatus !== query.state.fetchStatus) {\n return false\n }\n\n if (predicate && !predicate(query)) {\n return false\n }\n\n return true\n}\n\nexport function matchMutation(\n filters: MutationFilters,\n mutation: Mutation<any, any>,\n): boolean {\n const { exact, status, predicate, mutationKey } = filters\n if (mutationKey) {\n if (!mutation.options.mutationKey) {\n return false\n }\n if (exact) {\n if (hashKey(mutation.options.mutationKey) !== hashKey(mutationKey)) {\n return false\n }\n } else if (!partialMatchKey(mutation.options.mutationKey, mutationKey)) {\n return false\n }\n }\n\n if (status && mutation.state.status !== status) {\n return false\n }\n\n if (predicate && !predicate(mutation)) {\n return false\n }\n\n return true\n}\n\nexport function hashQueryKeyByOptions<TQueryKey extends QueryKey = QueryKey>(\n queryKey: TQueryKey,\n options?: Pick<QueryOptions<any, any, any, any>, 'queryKeyHashFn'>,\n): string {\n const hashFn = options?.queryKeyHashFn || hashKey\n return hashFn(queryKey)\n}\n\n/**\n * Default query & mutation keys hash function.\n * Hashes the value into a stable hash.\n */\nexport function hashKey(queryKey: QueryKey | MutationKey): string {\n return JSON.stringify(queryKey, (_, val) =>\n isPlainObject(val)\n ? Object.keys(val)\n .sort()\n .reduce((result, key) => {\n result[key] = val[key]\n return result\n }, {} as any)\n : val,\n )\n}\n\n/**\n * Checks if key `b` partially matches with key `a`.\n */\nexport function partialMatchKey(a: QueryKey, b: QueryKey): boolean\nexport function partialMatchKey(a: any, b: any): boolean {\n if (a === b) {\n return true\n }\n\n if (typeof a !== typeof b) {\n return false\n }\n\n if (a && b && typeof a === 'object' && typeof b === 'object') {\n return !Object.keys(b).some((key) => !partialMatchKey(a[key], b[key]))\n }\n\n return false\n}\n\n/**\n * This function returns `a` if `b` is deeply equal.\n * If not, it will replace any deeply equal children of `b` with those of `a`.\n * This can be used for structural sharing between JSON values for example.\n */\nexport function replaceEqualDeep<T>(a: unknown, b: T): T\nexport function replaceEqualDeep(a: any, b: any): any {\n if (a === b) {\n return a\n }\n\n const array = isPlainArray(a) && isPlainArray(b)\n\n if (array || (isPlainObject(a) && isPlainObject(b))) {\n const aItems = array ? a : Object.keys(a)\n const aSize = aItems.length\n const bItems = array ? b : Object.keys(b)\n const bSize = bItems.length\n const copy: any = array ? [] : {}\n\n let equalItems = 0\n\n for (let i = 0; i < bSize; i++) {\n const key = array ? i : bItems[i]\n if (\n ((!array && aItems.includes(key)) || array) &&\n a[key] === undefined &&\n b[key] === undefined\n ) {\n copy[key] = undefined\n equalItems++\n } else {\n copy[key] = replaceEqualDeep(a[key], b[key])\n if (copy[key] === a[key] && a[key] !== undefined) {\n equalItems++\n }\n }\n }\n\n return aSize === bSize && equalItems === aSize ? a : copy\n }\n\n return b\n}\n\n/**\n * Shallow compare objects.\n */\nexport function shallowEqualObjects<T extends Record<string, any>>(\n a: T,\n b: T | undefined,\n): boolean {\n if (!b || Object.keys(a).length !== Object.keys(b).length) {\n return false\n }\n\n for (const key in a) {\n if (a[key] !== b[key]) {\n return false\n }\n }\n\n return true\n}\n\nexport function isPlainArray(value: unknown) {\n return Array.isArray(value) && value.length === Object.keys(value).length\n}\n\n// Copied from: https://github.com/jonschlinkert/is-plain-object\n// eslint-disable-next-line @typescript-eslint/no-wrapper-object-types\nexport function isPlainObject(o: any): o is Object {\n if (!hasObjectPrototype(o)) {\n return false\n }\n\n // If has no constructor\n const ctor = o.constructor\n if (ctor === undefined) {\n return true\n }\n\n // If has modified prototype\n const prot = ctor.prototype\n if (!hasObjectPrototype(prot)) {\n return false\n }\n\n // If constructor does not have an Object-specific method\n if (!prot.hasOwnProperty('isPrototypeOf')) {\n return false\n }\n\n // Handles Objects created by Object.create(<arbitrary prototype>)\n if (Object.getPrototypeOf(o) !== Object.prototype) {\n return false\n }\n\n // Most likely a plain Object\n return true\n}\n\nfunction hasObjectPrototype(o: any): boolean {\n return Object.prototype.toString.call(o) === '[object Object]'\n}\n\nexport function sleep(timeout: number): Promise<void> {\n return new Promise((resolve) => {\n setTimeout(resolve, timeout)\n })\n}\n\nexport function replaceData<\n TData,\n TOptions extends QueryOptions<any, any, any, any>,\n>(prevData: TData | undefined, data: TData, options: TOptions): TData {\n if (typeof options.structuralSharing === 'function') {\n return options.structuralSharing(prevData, data) as TData\n } else if (options.structuralSharing !== false) {\n if (process.env.NODE_ENV !== 'production') {\n try {\n JSON.stringify(prevData)\n JSON.stringify(data)\n } catch (error) {\n console.error(\n `StructuralSharing requires data to be JSON serializable. To fix this, turn off structuralSharing or return JSON-serializable data from your queryFn. [${options.queryHash}]: ${error}`,\n )\n }\n }\n\n // Structurally share data between prev and new data if needed\n return replaceEqualDeep(prevData, data)\n }\n return data\n}\n\nexport function keepPreviousData<T>(\n previousData: T | undefined,\n): T | undefined {\n return previousData\n}\n\nexport function addToEnd<T>(items: Array<T>, item: T, max = 0): Array<T> {\n const newItems = [...items, item]\n return max && newItems.length > max ? newItems.slice(1) : newItems\n}\n\nexport function addToStart<T>(items: Array<T>, item: T, max = 0): Array<T> {\n const newItems = [item, ...items]\n return max && newItems.length > max ? newItems.slice(0, -1) : newItems\n}\n\nexport const skipToken = Symbol()\nexport type SkipToken = typeof skipToken\n\nexport function ensureQueryFn<\n TQueryFnData = unknown,\n TQueryKey extends QueryKey = QueryKey,\n>(\n options: {\n queryFn?: QueryFunction<TQueryFnData, TQueryKey> | SkipToken\n queryHash?: string\n },\n fetchOptions?: FetchOptions<TQueryFnData>,\n): QueryFunction<TQueryFnData, TQueryKey> {\n if (process.env.NODE_ENV !== 'production') {\n if (options.queryFn === skipToken) {\n console.error(\n `Attempted to invoke queryFn when set to skipToken. This is likely a configuration error. Query hash: '${options.queryHash}'`,\n )\n }\n }\n\n // if we attempt to retry a fetch that was triggered from an initialPromise\n // when we don't have a queryFn yet, we can't retry, so we just return the already rejected initialPromise\n // if an observer has already mounted, we will be able to retry with that queryFn\n if (!options.queryFn && fetchOptions?.initialPromise) {\n return () => fetchOptions.initialPromise!\n }\n\n if (!options.queryFn || options.queryFn === skipToken) {\n return () =>\n Promise.reject(new Error(`Missing queryFn: '${options.queryHash}'`))\n }\n\n return options.queryFn\n}\n"],"mappings":"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","names":[]}
|
|
1
|
+
{"version":3,"sources":["../../src/utils.ts"],"sourcesContent":["import type {\n DefaultError,\n Enabled,\n FetchStatus,\n MutationKey,\n MutationStatus,\n QueryFunction,\n QueryKey,\n QueryOptions,\n StaleTime,\n} from './types'\nimport type { Mutation } from './mutation'\nimport type { FetchOptions, Query } from './query'\n\n// TYPES\n\nexport interface QueryFilters {\n /**\n * Filter to active queries, inactive queries or all queries\n */\n type?: QueryTypeFilter\n /**\n * Match query key exactly\n */\n exact?: boolean\n /**\n * Include queries matching this predicate function\n */\n predicate?: (query: Query) => boolean\n /**\n * Include queries matching this query key\n */\n queryKey?: QueryKey\n /**\n * Include or exclude stale queries\n */\n stale?: boolean\n /**\n * Include queries matching their fetchStatus\n */\n fetchStatus?: FetchStatus\n}\n\nexport interface MutationFilters {\n /**\n * Match mutation key exactly\n */\n exact?: boolean\n /**\n * Include mutations matching this predicate function\n */\n predicate?: (mutation: Mutation<any, any, any>) => boolean\n /**\n * Include mutations matching this mutation key\n */\n mutationKey?: MutationKey\n /**\n * Filter by mutation status\n */\n status?: MutationStatus\n}\n\nexport type Updater<TInput, TOutput> = TOutput | ((input: TInput) => TOutput)\n\nexport type QueryTypeFilter = 'all' | 'active' | 'inactive'\n\n// UTILS\n\nexport const isServer = typeof window === 'undefined' || 'Deno' in globalThis\n\nexport function noop(): undefined {\n return undefined\n}\n\nexport function functionalUpdate<TInput, TOutput>(\n updater: Updater<TInput, TOutput>,\n input: TInput,\n): TOutput {\n return typeof updater === 'function'\n ? (updater as (_: TInput) => TOutput)(input)\n : updater\n}\n\nexport function isValidTimeout(value: unknown): value is number {\n return typeof value === 'number' && value >= 0 && value !== Infinity\n}\n\nexport function timeUntilStale(updatedAt: number, staleTime?: number): number {\n return Math.max(updatedAt + (staleTime || 0) - Date.now(), 0)\n}\n\nexport function resolveStaleTime<\n TQueryFnData = unknown,\n TError = DefaultError,\n TData = TQueryFnData,\n TQueryKey extends QueryKey = QueryKey,\n>(\n staleTime: undefined | StaleTime<TQueryFnData, TError, TData, TQueryKey>,\n query: Query<TQueryFnData, TError, TData, TQueryKey>,\n): number | undefined {\n return typeof staleTime === 'function' ? staleTime(query) : staleTime\n}\n\nexport function resolveEnabled<\n TQueryFnData = unknown,\n TError = DefaultError,\n TData = TQueryFnData,\n TQueryKey extends QueryKey = QueryKey,\n>(\n enabled: undefined | Enabled<TQueryFnData, TError, TData, TQueryKey>,\n query: Query<TQueryFnData, TError, TData, TQueryKey>,\n): boolean | undefined {\n return typeof enabled === 'function' ? enabled(query) : enabled\n}\n\nexport function matchQuery(\n filters: QueryFilters,\n query: Query<any, any, any, any>,\n): boolean {\n const {\n type = 'all',\n exact,\n fetchStatus,\n predicate,\n queryKey,\n stale,\n } = filters\n\n if (queryKey) {\n if (exact) {\n if (query.queryHash !== hashQueryKeyByOptions(queryKey, query.options)) {\n return false\n }\n } else if (!partialMatchKey(query.queryKey, queryKey)) {\n return false\n }\n }\n\n if (type !== 'all') {\n const isActive = query.isActive()\n if (type === 'active' && !isActive) {\n return false\n }\n if (type === 'inactive' && isActive) {\n return false\n }\n }\n\n if (typeof stale === 'boolean' && query.isStale() !== stale) {\n return false\n }\n\n if (fetchStatus && fetchStatus !== query.state.fetchStatus) {\n return false\n }\n\n if (predicate && !predicate(query)) {\n return false\n }\n\n return true\n}\n\nexport function matchMutation(\n filters: MutationFilters,\n mutation: Mutation<any, any>,\n): boolean {\n const { exact, status, predicate, mutationKey } = filters\n if (mutationKey) {\n if (!mutation.options.mutationKey) {\n return false\n }\n if (exact) {\n if (hashKey(mutation.options.mutationKey) !== hashKey(mutationKey)) {\n return false\n }\n } else if (!partialMatchKey(mutation.options.mutationKey, mutationKey)) {\n return false\n }\n }\n\n if (status && mutation.state.status !== status) {\n return false\n }\n\n if (predicate && !predicate(mutation)) {\n return false\n }\n\n return true\n}\n\nexport function hashQueryKeyByOptions<TQueryKey extends QueryKey = QueryKey>(\n queryKey: TQueryKey,\n options?: Pick<QueryOptions<any, any, any, any>, 'queryKeyHashFn'>,\n): string {\n const hashFn = options?.queryKeyHashFn || hashKey\n return hashFn(queryKey)\n}\n\n/**\n * Default query & mutation keys hash function.\n * Hashes the value into a stable hash.\n */\nexport function hashKey(queryKey: QueryKey | MutationKey): string {\n return JSON.stringify(queryKey, (_, val) =>\n isPlainObject(val)\n ? Object.keys(val)\n .sort()\n .reduce((result, key) => {\n result[key] = val[key]\n return result\n }, {} as any)\n : val,\n )\n}\n\n/**\n * Checks if key `b` partially matches with key `a`.\n */\nexport function partialMatchKey(a: QueryKey, b: QueryKey): boolean\nexport function partialMatchKey(a: any, b: any): boolean {\n if (a === b) {\n return true\n }\n\n if (typeof a !== typeof b) {\n return false\n }\n\n if (a && b && typeof a === 'object' && typeof b === 'object') {\n return !Object.keys(b).some((key) => !partialMatchKey(a[key], b[key]))\n }\n\n return false\n}\n\n/**\n * This function returns `a` if `b` is deeply equal.\n * If not, it will replace any deeply equal children of `b` with those of `a`.\n * This can be used for structural sharing between JSON values for example.\n */\nexport function replaceEqualDeep<T>(a: unknown, b: T): T\nexport function replaceEqualDeep(a: any, b: any): any {\n if (a === b) {\n return a\n }\n\n const array = isPlainArray(a) && isPlainArray(b)\n\n if (array || (isPlainObject(a) && isPlainObject(b))) {\n const aItems = array ? a : Object.keys(a)\n const aSize = aItems.length\n const bItems = array ? b : Object.keys(b)\n const bSize = bItems.length\n const copy: any = array ? [] : {}\n\n let equalItems = 0\n\n for (let i = 0; i < bSize; i++) {\n const key = array ? i : bItems[i]\n if (\n ((!array && aItems.includes(key)) || array) &&\n a[key] === undefined &&\n b[key] === undefined\n ) {\n copy[key] = undefined\n equalItems++\n } else {\n copy[key] = replaceEqualDeep(a[key], b[key])\n if (copy[key] === a[key] && a[key] !== undefined) {\n equalItems++\n }\n }\n }\n\n return aSize === bSize && equalItems === aSize ? a : copy\n }\n\n return b\n}\n\n/**\n * Shallow compare objects.\n */\nexport function shallowEqualObjects<T extends Record<string, any>>(\n a: T,\n b: T | undefined,\n): boolean {\n if (!b || Object.keys(a).length !== Object.keys(b).length) {\n return false\n }\n\n for (const key in a) {\n if (a[key] !== b[key]) {\n return false\n }\n }\n\n return true\n}\n\nexport function isPlainArray(value: unknown) {\n return Array.isArray(value) && value.length === Object.keys(value).length\n}\n\n// Copied from: https://github.com/jonschlinkert/is-plain-object\n// eslint-disable-next-line @typescript-eslint/no-wrapper-object-types\nexport function isPlainObject(o: any): o is Object {\n if (!hasObjectPrototype(o)) {\n return false\n }\n\n // If has no constructor\n const ctor = o.constructor\n if (ctor === undefined) {\n return true\n }\n\n // If has modified prototype\n const prot = ctor.prototype\n if (!hasObjectPrototype(prot)) {\n return false\n }\n\n // If constructor does not have an Object-specific method\n if (!prot.hasOwnProperty('isPrototypeOf')) {\n return false\n }\n\n // Handles Objects created by Object.create(<arbitrary prototype>)\n if (Object.getPrototypeOf(o) !== Object.prototype) {\n return false\n }\n\n // Most likely a plain Object\n return true\n}\n\nfunction hasObjectPrototype(o: any): boolean {\n return Object.prototype.toString.call(o) === '[object Object]'\n}\n\nexport function sleep(timeout: number): Promise<void> {\n return new Promise((resolve) => {\n setTimeout(resolve, timeout)\n })\n}\n\nexport function replaceData<\n TData,\n TOptions extends QueryOptions<any, any, any, any>,\n>(prevData: TData | undefined, data: TData, options: TOptions): TData {\n if (typeof options.structuralSharing === 'function') {\n return options.structuralSharing(prevData, data) as TData\n } else if (options.structuralSharing !== false) {\n if (process.env.NODE_ENV !== 'production') {\n try {\n return replaceEqualDeep(prevData, data)\n } catch (error) {\n console.error(\n `Structural sharing requires data to be JSON serializable. To fix this, turn off structuralSharing or return JSON-serializable data from your queryFn. [${options.queryHash}]: ${error}`,\n )\n }\n }\n // Structurally share data between prev and new data if needed\n return replaceEqualDeep(prevData, data)\n }\n return data\n}\n\nexport function keepPreviousData<T>(\n previousData: T | undefined,\n): T | undefined {\n return previousData\n}\n\nexport function addToEnd<T>(items: Array<T>, item: T, max = 0): Array<T> {\n const newItems = [...items, item]\n return max && newItems.length > max ? newItems.slice(1) : newItems\n}\n\nexport function addToStart<T>(items: Array<T>, item: T, max = 0): Array<T> {\n const newItems = [item, ...items]\n return max && newItems.length > max ? newItems.slice(0, -1) : newItems\n}\n\nexport const skipToken = Symbol()\nexport type SkipToken = typeof skipToken\n\nexport function ensureQueryFn<\n TQueryFnData = unknown,\n TQueryKey extends QueryKey = QueryKey,\n>(\n options: {\n queryFn?: QueryFunction<TQueryFnData, TQueryKey> | SkipToken\n queryHash?: string\n },\n fetchOptions?: FetchOptions<TQueryFnData>,\n): QueryFunction<TQueryFnData, TQueryKey> {\n if (process.env.NODE_ENV !== 'production') {\n if (options.queryFn === skipToken) {\n console.error(\n `Attempted to invoke queryFn when set to skipToken. This is likely a configuration error. Query hash: '${options.queryHash}'`,\n )\n }\n }\n\n // if we attempt to retry a fetch that was triggered from an initialPromise\n // when we don't have a queryFn yet, we can't retry, so we just return the already rejected initialPromise\n // if an observer has already mounted, we will be able to retry with that queryFn\n if (!options.queryFn && fetchOptions?.initialPromise) {\n return () => fetchOptions.initialPromise!\n }\n\n if (!options.queryFn || options.queryFn === skipToken) {\n return () =>\n Promise.reject(new Error(`Missing queryFn: '${options.queryHash}'`))\n }\n\n return options.queryFn\n}\n"],"mappings":"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","names":[]}
|
package/build/modern/utils.js
CHANGED
|
@@ -179,11 +179,10 @@ function replaceData(prevData, data, options) {
|
|
|
179
179
|
} else if (options.structuralSharing !== false) {
|
|
180
180
|
if (process.env.NODE_ENV !== "production") {
|
|
181
181
|
try {
|
|
182
|
-
|
|
183
|
-
JSON.stringify(data);
|
|
182
|
+
return replaceEqualDeep(prevData, data);
|
|
184
183
|
} catch (error) {
|
|
185
184
|
console.error(
|
|
186
|
-
`
|
|
185
|
+
`Structural sharing requires data to be JSON serializable. To fix this, turn off structuralSharing or return JSON-serializable data from your queryFn. [${options.queryHash}]: ${error}`
|
|
187
186
|
);
|
|
188
187
|
}
|
|
189
188
|
}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../../src/utils.ts"],"sourcesContent":["import type {\n DefaultError,\n Enabled,\n FetchStatus,\n MutationKey,\n MutationStatus,\n QueryFunction,\n QueryKey,\n QueryOptions,\n StaleTime,\n} from './types'\nimport type { Mutation } from './mutation'\nimport type { FetchOptions, Query } from './query'\n\n// TYPES\n\nexport interface QueryFilters {\n /**\n * Filter to active queries, inactive queries or all queries\n */\n type?: QueryTypeFilter\n /**\n * Match query key exactly\n */\n exact?: boolean\n /**\n * Include queries matching this predicate function\n */\n predicate?: (query: Query) => boolean\n /**\n * Include queries matching this query key\n */\n queryKey?: QueryKey\n /**\n * Include or exclude stale queries\n */\n stale?: boolean\n /**\n * Include queries matching their fetchStatus\n */\n fetchStatus?: FetchStatus\n}\n\nexport interface MutationFilters {\n /**\n * Match mutation key exactly\n */\n exact?: boolean\n /**\n * Include mutations matching this predicate function\n */\n predicate?: (mutation: Mutation<any, any, any>) => boolean\n /**\n * Include mutations matching this mutation key\n */\n mutationKey?: MutationKey\n /**\n * Filter by mutation status\n */\n status?: MutationStatus\n}\n\nexport type Updater<TInput, TOutput> = TOutput | ((input: TInput) => TOutput)\n\nexport type QueryTypeFilter = 'all' | 'active' | 'inactive'\n\n// UTILS\n\nexport const isServer = typeof window === 'undefined' || 'Deno' in globalThis\n\nexport function noop(): undefined {\n return undefined\n}\n\nexport function functionalUpdate<TInput, TOutput>(\n updater: Updater<TInput, TOutput>,\n input: TInput,\n): TOutput {\n return typeof updater === 'function'\n ? (updater as (_: TInput) => TOutput)(input)\n : updater\n}\n\nexport function isValidTimeout(value: unknown): value is number {\n return typeof value === 'number' && value >= 0 && value !== Infinity\n}\n\nexport function timeUntilStale(updatedAt: number, staleTime?: number): number {\n return Math.max(updatedAt + (staleTime || 0) - Date.now(), 0)\n}\n\nexport function resolveStaleTime<\n TQueryFnData = unknown,\n TError = DefaultError,\n TData = TQueryFnData,\n TQueryKey extends QueryKey = QueryKey,\n>(\n staleTime: undefined | StaleTime<TQueryFnData, TError, TData, TQueryKey>,\n query: Query<TQueryFnData, TError, TData, TQueryKey>,\n): number | undefined {\n return typeof staleTime === 'function' ? staleTime(query) : staleTime\n}\n\nexport function resolveEnabled<\n TQueryFnData = unknown,\n TError = DefaultError,\n TData = TQueryFnData,\n TQueryKey extends QueryKey = QueryKey,\n>(\n enabled: undefined | Enabled<TQueryFnData, TError, TData, TQueryKey>,\n query: Query<TQueryFnData, TError, TData, TQueryKey>,\n): boolean | undefined {\n return typeof enabled === 'function' ? enabled(query) : enabled\n}\n\nexport function matchQuery(\n filters: QueryFilters,\n query: Query<any, any, any, any>,\n): boolean {\n const {\n type = 'all',\n exact,\n fetchStatus,\n predicate,\n queryKey,\n stale,\n } = filters\n\n if (queryKey) {\n if (exact) {\n if (query.queryHash !== hashQueryKeyByOptions(queryKey, query.options)) {\n return false\n }\n } else if (!partialMatchKey(query.queryKey, queryKey)) {\n return false\n }\n }\n\n if (type !== 'all') {\n const isActive = query.isActive()\n if (type === 'active' && !isActive) {\n return false\n }\n if (type === 'inactive' && isActive) {\n return false\n }\n }\n\n if (typeof stale === 'boolean' && query.isStale() !== stale) {\n return false\n }\n\n if (fetchStatus && fetchStatus !== query.state.fetchStatus) {\n return false\n }\n\n if (predicate && !predicate(query)) {\n return false\n }\n\n return true\n}\n\nexport function matchMutation(\n filters: MutationFilters,\n mutation: Mutation<any, any>,\n): boolean {\n const { exact, status, predicate, mutationKey } = filters\n if (mutationKey) {\n if (!mutation.options.mutationKey) {\n return false\n }\n if (exact) {\n if (hashKey(mutation.options.mutationKey) !== hashKey(mutationKey)) {\n return false\n }\n } else if (!partialMatchKey(mutation.options.mutationKey, mutationKey)) {\n return false\n }\n }\n\n if (status && mutation.state.status !== status) {\n return false\n }\n\n if (predicate && !predicate(mutation)) {\n return false\n }\n\n return true\n}\n\nexport function hashQueryKeyByOptions<TQueryKey extends QueryKey = QueryKey>(\n queryKey: TQueryKey,\n options?: Pick<QueryOptions<any, any, any, any>, 'queryKeyHashFn'>,\n): string {\n const hashFn = options?.queryKeyHashFn || hashKey\n return hashFn(queryKey)\n}\n\n/**\n * Default query & mutation keys hash function.\n * Hashes the value into a stable hash.\n */\nexport function hashKey(queryKey: QueryKey | MutationKey): string {\n return JSON.stringify(queryKey, (_, val) =>\n isPlainObject(val)\n ? Object.keys(val)\n .sort()\n .reduce((result, key) => {\n result[key] = val[key]\n return result\n }, {} as any)\n : val,\n )\n}\n\n/**\n * Checks if key `b` partially matches with key `a`.\n */\nexport function partialMatchKey(a: QueryKey, b: QueryKey): boolean\nexport function partialMatchKey(a: any, b: any): boolean {\n if (a === b) {\n return true\n }\n\n if (typeof a !== typeof b) {\n return false\n }\n\n if (a && b && typeof a === 'object' && typeof b === 'object') {\n return !Object.keys(b).some((key) => !partialMatchKey(a[key], b[key]))\n }\n\n return false\n}\n\n/**\n * This function returns `a` if `b` is deeply equal.\n * If not, it will replace any deeply equal children of `b` with those of `a`.\n * This can be used for structural sharing between JSON values for example.\n */\nexport function replaceEqualDeep<T>(a: unknown, b: T): T\nexport function replaceEqualDeep(a: any, b: any): any {\n if (a === b) {\n return a\n }\n\n const array = isPlainArray(a) && isPlainArray(b)\n\n if (array || (isPlainObject(a) && isPlainObject(b))) {\n const aItems = array ? a : Object.keys(a)\n const aSize = aItems.length\n const bItems = array ? b : Object.keys(b)\n const bSize = bItems.length\n const copy: any = array ? [] : {}\n\n let equalItems = 0\n\n for (let i = 0; i < bSize; i++) {\n const key = array ? i : bItems[i]\n if (\n ((!array && aItems.includes(key)) || array) &&\n a[key] === undefined &&\n b[key] === undefined\n ) {\n copy[key] = undefined\n equalItems++\n } else {\n copy[key] = replaceEqualDeep(a[key], b[key])\n if (copy[key] === a[key] && a[key] !== undefined) {\n equalItems++\n }\n }\n }\n\n return aSize === bSize && equalItems === aSize ? a : copy\n }\n\n return b\n}\n\n/**\n * Shallow compare objects.\n */\nexport function shallowEqualObjects<T extends Record<string, any>>(\n a: T,\n b: T | undefined,\n): boolean {\n if (!b || Object.keys(a).length !== Object.keys(b).length) {\n return false\n }\n\n for (const key in a) {\n if (a[key] !== b[key]) {\n return false\n }\n }\n\n return true\n}\n\nexport function isPlainArray(value: unknown) {\n return Array.isArray(value) && value.length === Object.keys(value).length\n}\n\n// Copied from: https://github.com/jonschlinkert/is-plain-object\n// eslint-disable-next-line @typescript-eslint/no-wrapper-object-types\nexport function isPlainObject(o: any): o is Object {\n if (!hasObjectPrototype(o)) {\n return false\n }\n\n // If has no constructor\n const ctor = o.constructor\n if (ctor === undefined) {\n return true\n }\n\n // If has modified prototype\n const prot = ctor.prototype\n if (!hasObjectPrototype(prot)) {\n return false\n }\n\n // If constructor does not have an Object-specific method\n if (!prot.hasOwnProperty('isPrototypeOf')) {\n return false\n }\n\n // Handles Objects created by Object.create(<arbitrary prototype>)\n if (Object.getPrototypeOf(o) !== Object.prototype) {\n return false\n }\n\n // Most likely a plain Object\n return true\n}\n\nfunction hasObjectPrototype(o: any): boolean {\n return Object.prototype.toString.call(o) === '[object Object]'\n}\n\nexport function sleep(timeout: number): Promise<void> {\n return new Promise((resolve) => {\n setTimeout(resolve, timeout)\n })\n}\n\nexport function replaceData<\n TData,\n TOptions extends QueryOptions<any, any, any, any>,\n>(prevData: TData | undefined, data: TData, options: TOptions): TData {\n if (typeof options.structuralSharing === 'function') {\n return options.structuralSharing(prevData, data) as TData\n } else if (options.structuralSharing !== false) {\n if (process.env.NODE_ENV !== 'production') {\n try {\n JSON.stringify(prevData)\n JSON.stringify(data)\n } catch (error) {\n console.error(\n `StructuralSharing requires data to be JSON serializable. To fix this, turn off structuralSharing or return JSON-serializable data from your queryFn. [${options.queryHash}]: ${error}`,\n )\n }\n }\n\n // Structurally share data between prev and new data if needed\n return replaceEqualDeep(prevData, data)\n }\n return data\n}\n\nexport function keepPreviousData<T>(\n previousData: T | undefined,\n): T | undefined {\n return previousData\n}\n\nexport function addToEnd<T>(items: Array<T>, item: T, max = 0): Array<T> {\n const newItems = [...items, item]\n return max && newItems.length > max ? newItems.slice(1) : newItems\n}\n\nexport function addToStart<T>(items: Array<T>, item: T, max = 0): Array<T> {\n const newItems = [item, ...items]\n return max && newItems.length > max ? newItems.slice(0, -1) : newItems\n}\n\nexport const skipToken = Symbol()\nexport type SkipToken = typeof skipToken\n\nexport function ensureQueryFn<\n TQueryFnData = unknown,\n TQueryKey extends QueryKey = QueryKey,\n>(\n options: {\n queryFn?: QueryFunction<TQueryFnData, TQueryKey> | SkipToken\n queryHash?: string\n },\n fetchOptions?: FetchOptions<TQueryFnData>,\n): QueryFunction<TQueryFnData, TQueryKey> {\n if (process.env.NODE_ENV !== 'production') {\n if (options.queryFn === skipToken) {\n console.error(\n `Attempted to invoke queryFn when set to skipToken. This is likely a configuration error. Query hash: '${options.queryHash}'`,\n )\n }\n }\n\n // if we attempt to retry a fetch that was triggered from an initialPromise\n // when we don't have a queryFn yet, we can't retry, so we just return the already rejected initialPromise\n // if an observer has already mounted, we will be able to retry with that queryFn\n if (!options.queryFn && fetchOptions?.initialPromise) {\n return () => fetchOptions.initialPromise!\n }\n\n if (!options.queryFn || options.queryFn === skipToken) {\n return () =>\n Promise.reject(new Error(`Missing queryFn: '${options.queryHash}'`))\n }\n\n return options.queryFn\n}\n"],"mappings":"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","names":[]}
|
|
1
|
+
{"version":3,"sources":["../../src/utils.ts"],"sourcesContent":["import type {\n DefaultError,\n Enabled,\n FetchStatus,\n MutationKey,\n MutationStatus,\n QueryFunction,\n QueryKey,\n QueryOptions,\n StaleTime,\n} from './types'\nimport type { Mutation } from './mutation'\nimport type { FetchOptions, Query } from './query'\n\n// TYPES\n\nexport interface QueryFilters {\n /**\n * Filter to active queries, inactive queries or all queries\n */\n type?: QueryTypeFilter\n /**\n * Match query key exactly\n */\n exact?: boolean\n /**\n * Include queries matching this predicate function\n */\n predicate?: (query: Query) => boolean\n /**\n * Include queries matching this query key\n */\n queryKey?: QueryKey\n /**\n * Include or exclude stale queries\n */\n stale?: boolean\n /**\n * Include queries matching their fetchStatus\n */\n fetchStatus?: FetchStatus\n}\n\nexport interface MutationFilters {\n /**\n * Match mutation key exactly\n */\n exact?: boolean\n /**\n * Include mutations matching this predicate function\n */\n predicate?: (mutation: Mutation<any, any, any>) => boolean\n /**\n * Include mutations matching this mutation key\n */\n mutationKey?: MutationKey\n /**\n * Filter by mutation status\n */\n status?: MutationStatus\n}\n\nexport type Updater<TInput, TOutput> = TOutput | ((input: TInput) => TOutput)\n\nexport type QueryTypeFilter = 'all' | 'active' | 'inactive'\n\n// UTILS\n\nexport const isServer = typeof window === 'undefined' || 'Deno' in globalThis\n\nexport function noop(): undefined {\n return undefined\n}\n\nexport function functionalUpdate<TInput, TOutput>(\n updater: Updater<TInput, TOutput>,\n input: TInput,\n): TOutput {\n return typeof updater === 'function'\n ? (updater as (_: TInput) => TOutput)(input)\n : updater\n}\n\nexport function isValidTimeout(value: unknown): value is number {\n return typeof value === 'number' && value >= 0 && value !== Infinity\n}\n\nexport function timeUntilStale(updatedAt: number, staleTime?: number): number {\n return Math.max(updatedAt + (staleTime || 0) - Date.now(), 0)\n}\n\nexport function resolveStaleTime<\n TQueryFnData = unknown,\n TError = DefaultError,\n TData = TQueryFnData,\n TQueryKey extends QueryKey = QueryKey,\n>(\n staleTime: undefined | StaleTime<TQueryFnData, TError, TData, TQueryKey>,\n query: Query<TQueryFnData, TError, TData, TQueryKey>,\n): number | undefined {\n return typeof staleTime === 'function' ? staleTime(query) : staleTime\n}\n\nexport function resolveEnabled<\n TQueryFnData = unknown,\n TError = DefaultError,\n TData = TQueryFnData,\n TQueryKey extends QueryKey = QueryKey,\n>(\n enabled: undefined | Enabled<TQueryFnData, TError, TData, TQueryKey>,\n query: Query<TQueryFnData, TError, TData, TQueryKey>,\n): boolean | undefined {\n return typeof enabled === 'function' ? enabled(query) : enabled\n}\n\nexport function matchQuery(\n filters: QueryFilters,\n query: Query<any, any, any, any>,\n): boolean {\n const {\n type = 'all',\n exact,\n fetchStatus,\n predicate,\n queryKey,\n stale,\n } = filters\n\n if (queryKey) {\n if (exact) {\n if (query.queryHash !== hashQueryKeyByOptions(queryKey, query.options)) {\n return false\n }\n } else if (!partialMatchKey(query.queryKey, queryKey)) {\n return false\n }\n }\n\n if (type !== 'all') {\n const isActive = query.isActive()\n if (type === 'active' && !isActive) {\n return false\n }\n if (type === 'inactive' && isActive) {\n return false\n }\n }\n\n if (typeof stale === 'boolean' && query.isStale() !== stale) {\n return false\n }\n\n if (fetchStatus && fetchStatus !== query.state.fetchStatus) {\n return false\n }\n\n if (predicate && !predicate(query)) {\n return false\n }\n\n return true\n}\n\nexport function matchMutation(\n filters: MutationFilters,\n mutation: Mutation<any, any>,\n): boolean {\n const { exact, status, predicate, mutationKey } = filters\n if (mutationKey) {\n if (!mutation.options.mutationKey) {\n return false\n }\n if (exact) {\n if (hashKey(mutation.options.mutationKey) !== hashKey(mutationKey)) {\n return false\n }\n } else if (!partialMatchKey(mutation.options.mutationKey, mutationKey)) {\n return false\n }\n }\n\n if (status && mutation.state.status !== status) {\n return false\n }\n\n if (predicate && !predicate(mutation)) {\n return false\n }\n\n return true\n}\n\nexport function hashQueryKeyByOptions<TQueryKey extends QueryKey = QueryKey>(\n queryKey: TQueryKey,\n options?: Pick<QueryOptions<any, any, any, any>, 'queryKeyHashFn'>,\n): string {\n const hashFn = options?.queryKeyHashFn || hashKey\n return hashFn(queryKey)\n}\n\n/**\n * Default query & mutation keys hash function.\n * Hashes the value into a stable hash.\n */\nexport function hashKey(queryKey: QueryKey | MutationKey): string {\n return JSON.stringify(queryKey, (_, val) =>\n isPlainObject(val)\n ? Object.keys(val)\n .sort()\n .reduce((result, key) => {\n result[key] = val[key]\n return result\n }, {} as any)\n : val,\n )\n}\n\n/**\n * Checks if key `b` partially matches with key `a`.\n */\nexport function partialMatchKey(a: QueryKey, b: QueryKey): boolean\nexport function partialMatchKey(a: any, b: any): boolean {\n if (a === b) {\n return true\n }\n\n if (typeof a !== typeof b) {\n return false\n }\n\n if (a && b && typeof a === 'object' && typeof b === 'object') {\n return !Object.keys(b).some((key) => !partialMatchKey(a[key], b[key]))\n }\n\n return false\n}\n\n/**\n * This function returns `a` if `b` is deeply equal.\n * If not, it will replace any deeply equal children of `b` with those of `a`.\n * This can be used for structural sharing between JSON values for example.\n */\nexport function replaceEqualDeep<T>(a: unknown, b: T): T\nexport function replaceEqualDeep(a: any, b: any): any {\n if (a === b) {\n return a\n }\n\n const array = isPlainArray(a) && isPlainArray(b)\n\n if (array || (isPlainObject(a) && isPlainObject(b))) {\n const aItems = array ? a : Object.keys(a)\n const aSize = aItems.length\n const bItems = array ? b : Object.keys(b)\n const bSize = bItems.length\n const copy: any = array ? [] : {}\n\n let equalItems = 0\n\n for (let i = 0; i < bSize; i++) {\n const key = array ? i : bItems[i]\n if (\n ((!array && aItems.includes(key)) || array) &&\n a[key] === undefined &&\n b[key] === undefined\n ) {\n copy[key] = undefined\n equalItems++\n } else {\n copy[key] = replaceEqualDeep(a[key], b[key])\n if (copy[key] === a[key] && a[key] !== undefined) {\n equalItems++\n }\n }\n }\n\n return aSize === bSize && equalItems === aSize ? a : copy\n }\n\n return b\n}\n\n/**\n * Shallow compare objects.\n */\nexport function shallowEqualObjects<T extends Record<string, any>>(\n a: T,\n b: T | undefined,\n): boolean {\n if (!b || Object.keys(a).length !== Object.keys(b).length) {\n return false\n }\n\n for (const key in a) {\n if (a[key] !== b[key]) {\n return false\n }\n }\n\n return true\n}\n\nexport function isPlainArray(value: unknown) {\n return Array.isArray(value) && value.length === Object.keys(value).length\n}\n\n// Copied from: https://github.com/jonschlinkert/is-plain-object\n// eslint-disable-next-line @typescript-eslint/no-wrapper-object-types\nexport function isPlainObject(o: any): o is Object {\n if (!hasObjectPrototype(o)) {\n return false\n }\n\n // If has no constructor\n const ctor = o.constructor\n if (ctor === undefined) {\n return true\n }\n\n // If has modified prototype\n const prot = ctor.prototype\n if (!hasObjectPrototype(prot)) {\n return false\n }\n\n // If constructor does not have an Object-specific method\n if (!prot.hasOwnProperty('isPrototypeOf')) {\n return false\n }\n\n // Handles Objects created by Object.create(<arbitrary prototype>)\n if (Object.getPrototypeOf(o) !== Object.prototype) {\n return false\n }\n\n // Most likely a plain Object\n return true\n}\n\nfunction hasObjectPrototype(o: any): boolean {\n return Object.prototype.toString.call(o) === '[object Object]'\n}\n\nexport function sleep(timeout: number): Promise<void> {\n return new Promise((resolve) => {\n setTimeout(resolve, timeout)\n })\n}\n\nexport function replaceData<\n TData,\n TOptions extends QueryOptions<any, any, any, any>,\n>(prevData: TData | undefined, data: TData, options: TOptions): TData {\n if (typeof options.structuralSharing === 'function') {\n return options.structuralSharing(prevData, data) as TData\n } else if (options.structuralSharing !== false) {\n if (process.env.NODE_ENV !== 'production') {\n try {\n return replaceEqualDeep(prevData, data)\n } catch (error) {\n console.error(\n `Structural sharing requires data to be JSON serializable. To fix this, turn off structuralSharing or return JSON-serializable data from your queryFn. [${options.queryHash}]: ${error}`,\n )\n }\n }\n // Structurally share data between prev and new data if needed\n return replaceEqualDeep(prevData, data)\n }\n return data\n}\n\nexport function keepPreviousData<T>(\n previousData: T | undefined,\n): T | undefined {\n return previousData\n}\n\nexport function addToEnd<T>(items: Array<T>, item: T, max = 0): Array<T> {\n const newItems = [...items, item]\n return max && newItems.length > max ? newItems.slice(1) : newItems\n}\n\nexport function addToStart<T>(items: Array<T>, item: T, max = 0): Array<T> {\n const newItems = [item, ...items]\n return max && newItems.length > max ? newItems.slice(0, -1) : newItems\n}\n\nexport const skipToken = Symbol()\nexport type SkipToken = typeof skipToken\n\nexport function ensureQueryFn<\n TQueryFnData = unknown,\n TQueryKey extends QueryKey = QueryKey,\n>(\n options: {\n queryFn?: QueryFunction<TQueryFnData, TQueryKey> | SkipToken\n queryHash?: string\n },\n fetchOptions?: FetchOptions<TQueryFnData>,\n): QueryFunction<TQueryFnData, TQueryKey> {\n if (process.env.NODE_ENV !== 'production') {\n if (options.queryFn === skipToken) {\n console.error(\n `Attempted to invoke queryFn when set to skipToken. This is likely a configuration error. Query hash: '${options.queryHash}'`,\n )\n }\n }\n\n // if we attempt to retry a fetch that was triggered from an initialPromise\n // when we don't have a queryFn yet, we can't retry, so we just return the already rejected initialPromise\n // if an observer has already mounted, we will be able to retry with that queryFn\n if (!options.queryFn && fetchOptions?.initialPromise) {\n return () => fetchOptions.initialPromise!\n }\n\n if (!options.queryFn || options.queryFn === skipToken) {\n return () =>\n Promise.reject(new Error(`Missing queryFn: '${options.queryHash}'`))\n }\n\n return options.queryFn\n}\n"],"mappings":"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","names":[]}
|
package/package.json
CHANGED
|
@@ -975,36 +975,46 @@ describe('query', () => {
|
|
|
975
975
|
|
|
976
976
|
const queryFn = vi.fn()
|
|
977
977
|
|
|
978
|
+
const data: Array<{
|
|
979
|
+
id: number
|
|
980
|
+
name: string
|
|
981
|
+
link: null | { id: number; name: string; link: unknown }
|
|
982
|
+
}> = Array.from({ length: 5 })
|
|
983
|
+
.fill(null)
|
|
984
|
+
.map((_, index) => ({
|
|
985
|
+
id: index,
|
|
986
|
+
name: `name-${index}`,
|
|
987
|
+
link: null,
|
|
988
|
+
}))
|
|
989
|
+
|
|
990
|
+
if (data[0] && data[1]) {
|
|
991
|
+
data[0].link = data[1]
|
|
992
|
+
data[1].link = data[0]
|
|
993
|
+
}
|
|
994
|
+
|
|
978
995
|
queryFn.mockImplementation(async () => {
|
|
979
996
|
await sleep(10)
|
|
980
|
-
|
|
981
|
-
const data: Array<{
|
|
982
|
-
id: number
|
|
983
|
-
name: string
|
|
984
|
-
link: null | { id: number; name: string; link: unknown }
|
|
985
|
-
}> = Array.from({ length: 5 })
|
|
986
|
-
.fill(null)
|
|
987
|
-
.map((_, index) => ({
|
|
988
|
-
id: index,
|
|
989
|
-
name: `name-${index}`,
|
|
990
|
-
link: null,
|
|
991
|
-
}))
|
|
992
|
-
|
|
993
|
-
if (data[0] && data[1]) {
|
|
994
|
-
data[0].link = data[1]
|
|
995
|
-
data[1].link = data[0]
|
|
996
|
-
}
|
|
997
|
-
|
|
998
997
|
return data
|
|
999
998
|
})
|
|
1000
999
|
|
|
1001
|
-
await queryClient.prefetchQuery({
|
|
1000
|
+
await queryClient.prefetchQuery({
|
|
1001
|
+
queryKey: key,
|
|
1002
|
+
queryFn,
|
|
1003
|
+
initialData: structuredClone(data),
|
|
1004
|
+
})
|
|
1005
|
+
|
|
1006
|
+
const query = queryCache.find({ queryKey: key })!
|
|
1002
1007
|
|
|
1003
1008
|
expect(queryFn).toHaveBeenCalledTimes(1)
|
|
1004
1009
|
|
|
1010
|
+
expect(query.state.status).toBe('error')
|
|
1011
|
+
expect(
|
|
1012
|
+
query.state.error?.message.includes('Maximum call stack size exceeded'),
|
|
1013
|
+
).toBeTruthy()
|
|
1014
|
+
|
|
1005
1015
|
expect(consoleMock).toHaveBeenCalledWith(
|
|
1006
1016
|
expect.stringContaining(
|
|
1007
|
-
'
|
|
1017
|
+
'Structural sharing requires data to be JSON serializable',
|
|
1008
1018
|
),
|
|
1009
1019
|
)
|
|
1010
1020
|
|
package/src/notifyManager.ts
CHANGED
|
@@ -21,24 +21,6 @@ export function createNotifyManager() {
|
|
|
21
21
|
}
|
|
22
22
|
let scheduleFn: ScheduleFunction = (cb) => setTimeout(cb, 0)
|
|
23
23
|
|
|
24
|
-
const setScheduler = (fn: ScheduleFunction) => {
|
|
25
|
-
scheduleFn = fn
|
|
26
|
-
}
|
|
27
|
-
|
|
28
|
-
const batch = <T>(callback: () => T): T => {
|
|
29
|
-
let result
|
|
30
|
-
transactions++
|
|
31
|
-
try {
|
|
32
|
-
result = callback()
|
|
33
|
-
} finally {
|
|
34
|
-
transactions--
|
|
35
|
-
if (!transactions) {
|
|
36
|
-
flush()
|
|
37
|
-
}
|
|
38
|
-
}
|
|
39
|
-
return result
|
|
40
|
-
}
|
|
41
|
-
|
|
42
24
|
const schedule = (callback: NotifyCallback): void => {
|
|
43
25
|
if (transactions) {
|
|
44
26
|
queue.push(callback)
|
|
@@ -48,20 +30,6 @@ export function createNotifyManager() {
|
|
|
48
30
|
})
|
|
49
31
|
}
|
|
50
32
|
}
|
|
51
|
-
|
|
52
|
-
/**
|
|
53
|
-
* All calls to the wrapped function will be batched.
|
|
54
|
-
*/
|
|
55
|
-
const batchCalls = <T extends Array<unknown>>(
|
|
56
|
-
callback: BatchCallsCallback<T>,
|
|
57
|
-
): BatchCallsCallback<T> => {
|
|
58
|
-
return (...args) => {
|
|
59
|
-
schedule(() => {
|
|
60
|
-
callback(...args)
|
|
61
|
-
})
|
|
62
|
-
}
|
|
63
|
-
}
|
|
64
|
-
|
|
65
33
|
const flush = (): void => {
|
|
66
34
|
const originalQueue = queue
|
|
67
35
|
queue = []
|
|
@@ -76,29 +44,50 @@ export function createNotifyManager() {
|
|
|
76
44
|
}
|
|
77
45
|
}
|
|
78
46
|
|
|
79
|
-
/**
|
|
80
|
-
* Use this method to set a custom notify function.
|
|
81
|
-
* This can be used to for example wrap notifications with `React.act` while running tests.
|
|
82
|
-
*/
|
|
83
|
-
const setNotifyFunction = (fn: NotifyFunction) => {
|
|
84
|
-
notifyFn = fn
|
|
85
|
-
}
|
|
86
|
-
|
|
87
|
-
/**
|
|
88
|
-
* Use this method to set a custom function to batch notifications together into a single tick.
|
|
89
|
-
* By default React Query will use the batch function provided by ReactDOM or React Native.
|
|
90
|
-
*/
|
|
91
|
-
const setBatchNotifyFunction = (fn: BatchNotifyFunction) => {
|
|
92
|
-
batchNotifyFn = fn
|
|
93
|
-
}
|
|
94
|
-
|
|
95
47
|
return {
|
|
96
|
-
batch
|
|
97
|
-
|
|
48
|
+
batch: <T>(callback: () => T): T => {
|
|
49
|
+
let result
|
|
50
|
+
transactions++
|
|
51
|
+
try {
|
|
52
|
+
result = callback()
|
|
53
|
+
} finally {
|
|
54
|
+
transactions--
|
|
55
|
+
if (!transactions) {
|
|
56
|
+
flush()
|
|
57
|
+
}
|
|
58
|
+
}
|
|
59
|
+
return result
|
|
60
|
+
},
|
|
61
|
+
/**
|
|
62
|
+
* All calls to the wrapped function will be batched.
|
|
63
|
+
*/
|
|
64
|
+
batchCalls: <T extends Array<unknown>>(
|
|
65
|
+
callback: BatchCallsCallback<T>,
|
|
66
|
+
): BatchCallsCallback<T> => {
|
|
67
|
+
return (...args) => {
|
|
68
|
+
schedule(() => {
|
|
69
|
+
callback(...args)
|
|
70
|
+
})
|
|
71
|
+
}
|
|
72
|
+
},
|
|
98
73
|
schedule,
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
74
|
+
/**
|
|
75
|
+
* Use this method to set a custom notify function.
|
|
76
|
+
* This can be used to for example wrap notifications with `React.act` while running tests.
|
|
77
|
+
*/
|
|
78
|
+
setNotifyFunction: (fn: NotifyFunction) => {
|
|
79
|
+
notifyFn = fn
|
|
80
|
+
},
|
|
81
|
+
/**
|
|
82
|
+
* Use this method to set a custom function to batch notifications together into a single tick.
|
|
83
|
+
* By default React Query will use the batch function provided by ReactDOM or React Native.
|
|
84
|
+
*/
|
|
85
|
+
setBatchNotifyFunction: (fn: BatchNotifyFunction) => {
|
|
86
|
+
batchNotifyFn = fn
|
|
87
|
+
},
|
|
88
|
+
setScheduler: (fn: ScheduleFunction) => {
|
|
89
|
+
scheduleFn = fn
|
|
90
|
+
},
|
|
102
91
|
} as const
|
|
103
92
|
}
|
|
104
93
|
|
package/src/utils.ts
CHANGED
|
@@ -356,15 +356,13 @@ export function replaceData<
|
|
|
356
356
|
} else if (options.structuralSharing !== false) {
|
|
357
357
|
if (process.env.NODE_ENV !== 'production') {
|
|
358
358
|
try {
|
|
359
|
-
|
|
360
|
-
JSON.stringify(data)
|
|
359
|
+
return replaceEqualDeep(prevData, data)
|
|
361
360
|
} catch (error) {
|
|
362
361
|
console.error(
|
|
363
|
-
`
|
|
362
|
+
`Structural sharing requires data to be JSON serializable. To fix this, turn off structuralSharing or return JSON-serializable data from your queryFn. [${options.queryHash}]: ${error}`,
|
|
364
363
|
)
|
|
365
364
|
}
|
|
366
365
|
}
|
|
367
|
-
|
|
368
366
|
// Structurally share data between prev and new data if needed
|
|
369
367
|
return replaceEqualDeep(prevData, data)
|
|
370
368
|
}
|