@kirill.konshin/utils 0.0.19 → 0.0.20

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.
Files changed (352) hide show
  1. package/.ctirc +19 -10
  2. package/.storybook/main.ts +1 -20
  3. package/.storybook/preview.ts +1 -16
  4. package/.turbo/turbo-build.log +9 -66
  5. package/CHANGELOG.md +21 -0
  6. package/README.md +6 -0
  7. package/dist/bootstrap/index.d.ts +1 -12
  8. package/dist/bootstrap/index.d.ts.map +1 -1
  9. package/dist/browser/index.d.ts +2 -0
  10. package/dist/browser/index.d.ts.map +1 -0
  11. package/dist/core/index.d.ts +1 -9
  12. package/dist/core/index.d.ts.map +1 -1
  13. package/dist/electron/index.d.ts +1 -2
  14. package/dist/electron/index.d.ts.map +1 -1
  15. package/dist/electron-builder/index.d.ts +1 -2
  16. package/dist/electron-builder/index.d.ts.map +1 -1
  17. package/dist/index.d.ts +13 -0
  18. package/dist/index.d.ts.map +1 -0
  19. package/dist/index.js +27 -0
  20. package/dist/mui/index.d.ts +1 -4
  21. package/dist/mui/index.d.ts.map +1 -1
  22. package/dist/next/index.d.ts +1 -5
  23. package/dist/next/index.d.ts.map +1 -1
  24. package/dist/node/index.d.ts +2 -0
  25. package/dist/node/index.d.ts.map +1 -0
  26. package/dist/react/index.d.ts +1 -5
  27. package/dist/react/index.d.ts.map +1 -1
  28. package/dist/react-native/index.d.ts +1 -3
  29. package/dist/react-native/index.d.ts.map +1 -1
  30. package/dist/tailwind/index.d.ts +1 -2
  31. package/dist/tailwind/index.d.ts.map +1 -1
  32. package/dist/worker/index.d.ts +2 -0
  33. package/dist/worker/index.d.ts.map +1 -0
  34. package/package.json +41 -99
  35. package/src/bootstrap/index.ts +2 -12
  36. package/src/browser/index.ts +2 -0
  37. package/src/core/index.ts +2 -9
  38. package/src/electron/index.ts +2 -2
  39. package/src/electron-builder/index.ts +2 -2
  40. package/src/index.ts +12 -0
  41. package/src/mui/index.ts +2 -4
  42. package/src/next/index.ts +2 -5
  43. package/src/node/index.ts +2 -0
  44. package/src/react/index.ts +2 -5
  45. package/src/react-native/index.ts +2 -3
  46. package/src/tailwind/index.ts +2 -2
  47. package/src/worker/index.ts +2 -0
  48. package/tsconfig.json +2 -15
  49. package/vite.config.ts +2 -56
  50. package/.turbo/turbo-test.log +0 -171
  51. package/builders/.swcrc +0 -18
  52. package/builders/build.config.ts +0 -11
  53. package/builders/bun.build.js +0 -23
  54. package/builders/package.json +0 -209
  55. package/builders/perf.mjs +0 -63
  56. package/builders/rollup.config.mjs +0 -50
  57. package/builders/rslib.config.ts +0 -26
  58. package/builders/tsconfig.json +0 -21
  59. package/builders/tsup.config.ts +0 -20
  60. package/builders/turbo.json +0 -24
  61. package/builders/vite.config.ts +0 -37
  62. package/demo/worker-demo.ts +0 -73
  63. package/dist/bootstrap/adaptiveContainer.d.ts +0 -4
  64. package/dist/bootstrap/adaptiveContainer.d.ts.map +0 -1
  65. package/dist/bootstrap/adaptiveContainer.js +0 -11
  66. package/dist/bootstrap/adaptiveContainer.js.map +0 -1
  67. package/dist/bootstrap/controls.d.ts +0 -38
  68. package/dist/bootstrap/controls.d.ts.map +0 -1
  69. package/dist/bootstrap/controls.js +0 -78
  70. package/dist/bootstrap/controls.js.map +0 -1
  71. package/dist/bootstrap/controls.stories.d.ts +0 -9
  72. package/dist/bootstrap/controls.stories.d.ts.map +0 -1
  73. package/dist/bootstrap/error.d.ts +0 -9
  74. package/dist/bootstrap/error.d.ts.map +0 -1
  75. package/dist/bootstrap/error.js +0 -27
  76. package/dist/bootstrap/error.js.map +0 -1
  77. package/dist/bootstrap/error.stories.d.ts +0 -8
  78. package/dist/bootstrap/error.stories.d.ts.map +0 -1
  79. package/dist/bootstrap/field.d.ts +0 -11
  80. package/dist/bootstrap/field.d.ts.map +0 -1
  81. package/dist/bootstrap/field.js +0 -29
  82. package/dist/bootstrap/field.js.map +0 -1
  83. package/dist/bootstrap/field.stories.d.ts +0 -8
  84. package/dist/bootstrap/field.stories.d.ts.map +0 -1
  85. package/dist/bootstrap/footer.d.ts +0 -10
  86. package/dist/bootstrap/footer.d.ts.map +0 -1
  87. package/dist/bootstrap/footer.js +0 -45
  88. package/dist/bootstrap/footer.js.map +0 -1
  89. package/dist/bootstrap/globalLoading.d.ts +0 -6
  90. package/dist/bootstrap/globalLoading.d.ts.map +0 -1
  91. package/dist/bootstrap/globalLoading.js +0 -10
  92. package/dist/bootstrap/globalLoading.js.map +0 -1
  93. package/dist/bootstrap/globalLoading.stories.d.ts +0 -7
  94. package/dist/bootstrap/globalLoading.stories.d.ts.map +0 -1
  95. package/dist/bootstrap/index.js +0 -35
  96. package/dist/bootstrap/loading.d.ts +0 -10
  97. package/dist/bootstrap/loading.d.ts.map +0 -1
  98. package/dist/bootstrap/loading.js +0 -19
  99. package/dist/bootstrap/loading.js.map +0 -1
  100. package/dist/bootstrap/loading.stories.d.ts +0 -9
  101. package/dist/bootstrap/loading.stories.d.ts.map +0 -1
  102. package/dist/bootstrap/responsiveHelper.d.ts +0 -8
  103. package/dist/bootstrap/responsiveHelper.d.ts.map +0 -1
  104. package/dist/bootstrap/responsiveHelper.js +0 -46
  105. package/dist/bootstrap/responsiveHelper.js.map +0 -1
  106. package/dist/bootstrap/screen.d.ts +0 -22
  107. package/dist/bootstrap/screen.d.ts.map +0 -1
  108. package/dist/bootstrap/screen.js +0 -80
  109. package/dist/bootstrap/screen.js.map +0 -1
  110. package/dist/bootstrap/screen.stories.d.ts +0 -14
  111. package/dist/bootstrap/screen.stories.d.ts.map +0 -1
  112. package/dist/bootstrap/toaster.d.ts +0 -11
  113. package/dist/bootstrap/toaster.d.ts.map +0 -1
  114. package/dist/bootstrap/toaster.js +0 -34
  115. package/dist/bootstrap/toaster.js.map +0 -1
  116. package/dist/bootstrap/toaster.stories.d.ts +0 -8
  117. package/dist/bootstrap/toaster.stories.d.ts.map +0 -1
  118. package/dist/bootstrap/useModal.d.ts +0 -23
  119. package/dist/bootstrap/useModal.d.ts.map +0 -1
  120. package/dist/bootstrap/useModal.js +0 -50
  121. package/dist/bootstrap/useModal.js.map +0 -1
  122. package/dist/bootstrap/useModal.stories.d.ts +0 -9
  123. package/dist/bootstrap/useModal.stories.d.ts.map +0 -1
  124. package/dist/bootstrap/useWrappedForm.d.ts +0 -14
  125. package/dist/bootstrap/useWrappedForm.d.ts.map +0 -1
  126. package/dist/bootstrap/useWrappedForm.js +0 -32
  127. package/dist/bootstrap/useWrappedForm.js.map +0 -1
  128. package/dist/core/cache.d.ts +0 -120
  129. package/dist/core/cache.d.ts.map +0 -1
  130. package/dist/core/cache.js +0 -107
  131. package/dist/core/cache.js.map +0 -1
  132. package/dist/core/cache.test.d.ts +0 -2
  133. package/dist/core/cache.test.d.ts.map +0 -1
  134. package/dist/core/errors.d.ts +0 -2
  135. package/dist/core/errors.d.ts.map +0 -1
  136. package/dist/core/errors.js +0 -15
  137. package/dist/core/errors.js.map +0 -1
  138. package/dist/core/files.d.ts +0 -4
  139. package/dist/core/files.d.ts.map +0 -1
  140. package/dist/core/files.js +0 -31
  141. package/dist/core/files.js.map +0 -1
  142. package/dist/core/index.js +0 -35
  143. package/dist/core/index.js.map +0 -1
  144. package/dist/core/ls.d.ts +0 -6
  145. package/dist/core/ls.d.ts.map +0 -1
  146. package/dist/core/ls.js +0 -12
  147. package/dist/core/ls.js.map +0 -1
  148. package/dist/core/measure.d.ts +0 -35
  149. package/dist/core/measure.d.ts.map +0 -1
  150. package/dist/core/measure.js +0 -60
  151. package/dist/core/measure.js.map +0 -1
  152. package/dist/core/mutex.d.ts +0 -6
  153. package/dist/core/mutex.d.ts.map +0 -1
  154. package/dist/core/mutex.js +0 -26
  155. package/dist/core/mutex.js.map +0 -1
  156. package/dist/core/worker.d.ts +0 -98
  157. package/dist/core/worker.d.ts.map +0 -1
  158. package/dist/core/worker.js +0 -240
  159. package/dist/core/worker.js.map +0 -1
  160. package/dist/core/worker.test.d.ts +0 -2
  161. package/dist/core/worker.test.d.ts.map +0 -1
  162. package/dist/core/workerUtils.d.ts +0 -3
  163. package/dist/core/workerUtils.d.ts.map +0 -1
  164. package/dist/core/workerUtils.js +0 -31
  165. package/dist/core/workerUtils.js.map +0 -1
  166. package/dist/core/wrpc.d.ts +0 -45
  167. package/dist/core/wrpc.d.ts.map +0 -1
  168. package/dist/core/wrpc.fixture.d.ts +0 -26
  169. package/dist/core/wrpc.fixture.d.ts.map +0 -1
  170. package/dist/core/wrpc.js +0 -242
  171. package/dist/core/wrpc.js.map +0 -1
  172. package/dist/core/wrpc.test.d.ts +0 -1
  173. package/dist/core/wrpc.test.d.ts.map +0 -1
  174. package/dist/electron/createWindow.d.ts +0 -23
  175. package/dist/electron/createWindow.d.ts.map +0 -1
  176. package/dist/electron/createWindow.js +0 -160
  177. package/dist/electron/createWindow.js.map +0 -1
  178. package/dist/electron/index.js +0 -9
  179. package/dist/electron/index.js.map +0 -1
  180. package/dist/electron/updater.d.ts +0 -2
  181. package/dist/electron/updater.d.ts.map +0 -1
  182. package/dist/electron/updater.js +0 -47
  183. package/dist/electron/updater.js.map +0 -1
  184. package/dist/electron-builder/builder.d.ts +0 -8
  185. package/dist/electron-builder/builder.d.ts.map +0 -1
  186. package/dist/electron-builder/builder.js +0 -130
  187. package/dist/electron-builder/builder.js.map +0 -1
  188. package/dist/electron-builder/images.d.ts +0 -7
  189. package/dist/electron-builder/images.d.ts.map +0 -1
  190. package/dist/electron-builder/images.js +0 -25
  191. package/dist/electron-builder/images.js.map +0 -1
  192. package/dist/electron-builder/index.js +0 -7
  193. package/dist/electron-builder/index.js.map +0 -1
  194. package/dist/mui/formControlFieldset.d.ts +0 -5
  195. package/dist/mui/formControlFieldset.d.ts.map +0 -1
  196. package/dist/mui/formControlFieldset.js +0 -28
  197. package/dist/mui/formControlFieldset.js.map +0 -1
  198. package/dist/mui/formControlFieldset.stories.d.ts +0 -7
  199. package/dist/mui/formControlFieldset.stories.d.ts.map +0 -1
  200. package/dist/mui/formLabelLegend.d.ts +0 -4
  201. package/dist/mui/formLabelLegend.d.ts.map +0 -1
  202. package/dist/mui/formLabelLegend.js +0 -12
  203. package/dist/mui/formLabelLegend.js.map +0 -1
  204. package/dist/mui/genericControl.d.ts +0 -7
  205. package/dist/mui/genericControl.d.ts.map +0 -1
  206. package/dist/mui/genericControl.js +0 -21
  207. package/dist/mui/genericControl.js.map +0 -1
  208. package/dist/mui/index.js +0 -11
  209. package/dist/mui/index.js.map +0 -1
  210. package/dist/mui/readOnly.d.ts +0 -6
  211. package/dist/mui/readOnly.d.ts.map +0 -1
  212. package/dist/mui/readOnly.js +0 -7
  213. package/dist/mui/readOnly.js.map +0 -1
  214. package/dist/next/appLink.d.ts +0 -8
  215. package/dist/next/appLink.d.ts.map +0 -1
  216. package/dist/next/appLink.js +0 -34
  217. package/dist/next/appLink.js.map +0 -1
  218. package/dist/next/index.js +0 -15
  219. package/dist/next/index.js.map +0 -1
  220. package/dist/next/measure.d.ts +0 -15
  221. package/dist/next/measure.d.ts.map +0 -1
  222. package/dist/next/measure.js +0 -9
  223. package/dist/next/measure.js.map +0 -1
  224. package/dist/next/noSSR.d.ts +0 -29
  225. package/dist/next/noSSR.d.ts.map +0 -1
  226. package/dist/next/noSSR.js +0 -13
  227. package/dist/next/noSSR.js.map +0 -1
  228. package/dist/next/redirect.d.ts +0 -6
  229. package/dist/next/redirect.d.ts.map +0 -1
  230. package/dist/next/useIsInner.d.ts +0 -3
  231. package/dist/next/useIsInner.d.ts.map +0 -1
  232. package/dist/next/useIsInner.js +0 -15
  233. package/dist/next/useIsInner.js.map +0 -1
  234. package/dist/react/apiCall.d.ts +0 -6
  235. package/dist/react/apiCall.d.ts.map +0 -1
  236. package/dist/react/apiCall.js +0 -24
  237. package/dist/react/apiCall.js.map +0 -1
  238. package/dist/react/form/client.d.ts +0 -7
  239. package/dist/react/form/client.d.ts.map +0 -1
  240. package/dist/react/form/client.js +0 -46
  241. package/dist/react/form/client.js.map +0 -1
  242. package/dist/react/form/form.d.ts +0 -59
  243. package/dist/react/form/form.d.ts.map +0 -1
  244. package/dist/react/form/form.js +0 -89
  245. package/dist/react/form/form.js.map +0 -1
  246. package/dist/react/form/index.d.ts +0 -3
  247. package/dist/react/form/index.d.ts.map +0 -1
  248. package/dist/react/index.js +0 -26
  249. package/dist/react/index.js.map +0 -1
  250. package/dist/react/keyboard.d.ts +0 -10
  251. package/dist/react/keyboard.d.ts.map +0 -1
  252. package/dist/react/keyboard.js +0 -38
  253. package/dist/react/keyboard.js.map +0 -1
  254. package/dist/react/useFetch.d.ts +0 -2
  255. package/dist/react/useFetch.d.ts.map +0 -1
  256. package/dist/react/useFetch.js +0 -20
  257. package/dist/react/useFetch.js.map +0 -1
  258. package/dist/react/useFetcher.d.ts +0 -10
  259. package/dist/react/useFetcher.d.ts.map +0 -1
  260. package/dist/react/useFetcher.js +0 -43
  261. package/dist/react/useFetcher.js.map +0 -1
  262. package/dist/react-native/index.js +0 -9
  263. package/dist/react-native/index.js.map +0 -1
  264. package/dist/react-native/share.d.ts +0 -9
  265. package/dist/react-native/share.d.ts.map +0 -1
  266. package/dist/react-native/share.js +0 -23
  267. package/dist/react-native/share.js.map +0 -1
  268. package/dist/react-native/update.d.ts +0 -3
  269. package/dist/react-native/update.d.ts.map +0 -1
  270. package/dist/react-native/update.js +0 -40
  271. package/dist/react-native/update.js.map +0 -1
  272. package/dist/react-native/useAppState.d.ts +0 -2
  273. package/dist/react-native/useAppState.d.ts.map +0 -1
  274. package/dist/react-native/useAppState.js +0 -18
  275. package/dist/react-native/useAppState.js.map +0 -1
  276. package/dist/tailwind/fullpage.d.ts +0 -3
  277. package/dist/tailwind/fullpage.d.ts.map +0 -1
  278. package/dist/tailwind/fullpage.js +0 -14
  279. package/dist/tailwind/fullpage.js.map +0 -1
  280. package/dist/tailwind/index.js +0 -7
  281. package/dist/tailwind/index.js.map +0 -1
  282. package/dist/tailwind/responsiveHelper.d.ts +0 -3
  283. package/dist/tailwind/responsiveHelper.d.ts.map +0 -1
  284. package/dist/tailwind/responsiveHelper.js +0 -16
  285. package/dist/tailwind/responsiveHelper.js.map +0 -1
  286. package/src/bootstrap/adaptiveContainer.tsx +0 -12
  287. package/src/bootstrap/controls.stories.tsx +0 -62
  288. package/src/bootstrap/controls.tsx +0 -119
  289. package/src/bootstrap/error.stories.tsx +0 -34
  290. package/src/bootstrap/error.tsx +0 -37
  291. package/src/bootstrap/field.stories.tsx +0 -42
  292. package/src/bootstrap/field.tsx +0 -37
  293. package/src/bootstrap/footer.tsx +0 -61
  294. package/src/bootstrap/globalLoading.stories.tsx +0 -25
  295. package/src/bootstrap/globalLoading.tsx +0 -19
  296. package/src/bootstrap/loading.stories.tsx +0 -35
  297. package/src/bootstrap/loading.tsx +0 -24
  298. package/src/bootstrap/main.scss +0 -86
  299. package/src/bootstrap/responsiveHelper.tsx +0 -55
  300. package/src/bootstrap/screen.stories.tsx +0 -160
  301. package/src/bootstrap/screen.tsx +0 -146
  302. package/src/bootstrap/toaster.stories.tsx +0 -32
  303. package/src/bootstrap/toaster.tsx +0 -40
  304. package/src/bootstrap/useModal.stories.tsx +0 -51
  305. package/src/bootstrap/useModal.tsx +0 -93
  306. package/src/bootstrap/useWrappedForm.ts +0 -42
  307. package/src/core/README.md +0 -91
  308. package/src/core/cache.test.ts +0 -121
  309. package/src/core/cache.ts +0 -246
  310. package/src/core/errors.ts +0 -17
  311. package/src/core/files.ts +0 -29
  312. package/src/core/ls.ts +0 -15
  313. package/src/core/measure.ts +0 -109
  314. package/src/core/mutex.ts +0 -22
  315. package/src/core/worker.test.ts +0 -197
  316. package/src/core/worker.ts +0 -347
  317. package/src/core/workerUtils.ts +0 -32
  318. package/src/core/wrpc.fixture.ts +0 -106
  319. package/src/core/wrpc.test.ts +0 -225
  320. package/src/core/wrpc.ts +0 -377
  321. package/src/electron/README.md +0 -13
  322. package/src/electron/createWindow.ts +0 -234
  323. package/src/electron/updater.ts +0 -54
  324. package/src/electron-builder/builder.ts +0 -150
  325. package/src/electron-builder/images.ts +0 -33
  326. package/src/mui/README.md +0 -3
  327. package/src/mui/formControlFieldset.stories.tsx +0 -71
  328. package/src/mui/formControlFieldset.tsx +0 -26
  329. package/src/mui/formLabelLegend.tsx +0 -11
  330. package/src/mui/genericControl.tsx +0 -20
  331. package/src/mui/readOnly.tsx +0 -6
  332. package/src/next/appLink.tsx +0 -40
  333. package/src/next/measure.ts +0 -24
  334. package/src/next/noSSR.tsx +0 -36
  335. package/src/next/redirect.tsx +0 -13
  336. package/src/next/useIsInner.ts +0 -13
  337. package/src/react/apiCall.ts +0 -25
  338. package/src/react/form/client.tsx +0 -73
  339. package/src/react/form/form.tsx +0 -178
  340. package/src/react/form/index.ts +0 -2
  341. package/src/react/keyboard.tsx +0 -54
  342. package/src/react/useFetch.ts +0 -29
  343. package/src/react/useFetcher.ts +0 -54
  344. package/src/react-native/share.ts +0 -31
  345. package/src/react-native/update.tsx +0 -40
  346. package/src/react-native/useAppState.ts +0 -18
  347. package/src/tailwind/README.md +0 -8
  348. package/src/tailwind/fullpage.tsx +0 -11
  349. package/src/tailwind/responsiveHelper.tsx +0 -16
  350. package/src-todo/auth0.tsx +0 -177
  351. package/vite.exports.ts +0 -121
  352. /package/dist/{bootstrap/index.js.map → index.js.map} +0 -0
@@ -1,91 +0,0 @@
1
- # WRPC
2
-
3
- TODO
4
-
5
- - [ ] Add to readme https://stackoverflow.com/questions/77727664/how-to-get-returned-value-from-async-generator-when-using-for-await
6
- - [ ] Value passed to next are ignored https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/AsyncGenerator/next#sending_values_to_the_generator
7
-
8
- ```mermaid
9
- sequenceDiagram
10
- box Main
11
- participant Code
12
- participant Caller
13
- end
14
- box Worker
15
- participant Worker
16
- participant Resolver
17
- end
18
-
19
- %% autonumber
20
-
21
- Code->>Caller: caller.generator(payload)
22
-
23
- Caller-->>Code: iterator & promise
24
-
25
- Code->>Code: Start main CONSUMER loop
26
-
27
- Code->>Caller: iterator[Symbol]()
28
-
29
- Caller->>Caller: Start replica GENERATOR loop
30
-
31
- Code->>Caller: iterator.next()
32
-
33
- Caller->>Worker: postMessage(payload)
34
-
35
- Worker->>Resolver: resolver(payload)
36
-
37
- Resolver-->>Worker: iterator
38
-
39
- Worker->>Worker: Start replica CONSUMER loop
40
-
41
- Worker->>Resolver: iterator[Symbol]()
42
-
43
- Resolver->>Resolver: Start GENERATOR loop
44
-
45
- rect rgb(232, 244, 248)
46
-
47
- loop Synchronized iteration
48
- Worker->>+Resolver: iterator.next(payload)
49
-
50
- Resolver-->>-Worker: yield value
51
-
52
- Worker-->>Caller: postMessage(value, done=false)
53
-
54
- Note over Worker: Wait for ACK or ABORT
55
-
56
- Caller-->>Code: yield value
57
-
58
- Code->>Caller: iterator.next(nextPayload)
59
-
60
- Caller->>Worker: postMessage(ack, nextPayload)
61
- end
62
-
63
- end
64
-
65
- break Break or AbortSignal (maybe)
66
- Code-->>Code: Loop exits
67
- Code->>Caller: signal.abort()
68
-
69
- Caller-->>Caller: Loop exits
70
-
71
- Caller->>Worker: postMessage(abort)
72
-
73
- Worker-->>Worker: Loop exits via Break
74
-
75
- Resolver-->>Resolver: Loop exits
76
- end
77
-
78
- opt Occurs on Error
79
- Resolver-->>Worker: throw Error
80
-
81
- Worker-->>Caller: postMessage(error, done=true)
82
-
83
- Caller-->>Code: throw Error
84
- end
85
-
86
- Resolver-->>Worker: return value
87
-
88
- Worker-->>Caller: postMessage(value, done=true)
89
-
90
- Caller-->>Code: return value
91
- ```
@@ -1,121 +0,0 @@
1
- import { expect, describe, test, vi } from 'vitest';
2
- import { ANY, MaybePromise, memo, TransformerMap } from './cache';
3
-
4
- describe('memo', async () => {
5
- test('simple', async () => {
6
- const random = vi.fn(() => Math.random());
7
- const memoized = memo(random);
8
-
9
- const first = await memoized();
10
- const second = await memoized();
11
-
12
- expect(first.hit).toBeFalsy();
13
- expect(second.hit).toBeTruthy();
14
- expect(first.value).toBe(second.value);
15
- expect(memoized.size()).toBe(1);
16
-
17
- memoized.clear();
18
- expect(memoized.size()).toBe(0);
19
-
20
- const third = await memoized();
21
- expect(third.hit).toBeFalsy();
22
- });
23
-
24
- test('with key', async () => {
25
- const random = vi.fn((arg) => arg + Math.random().toString());
26
- const memoized = memo(random);
27
-
28
- const first = await memoized(1);
29
- const second = await memoized(2);
30
-
31
- expect(first.hit).toBeFalsy();
32
- expect(second.hit).toBeFalsy();
33
- expect(first.value).not.toBe(second.value);
34
- expect(memoized.size()).toBe(2);
35
-
36
- const first2 = await memoized(1);
37
- const second2 = await memoized(2);
38
-
39
- expect(first2.hit).toBeTruthy();
40
- expect(first.value).toBe(first2.value);
41
- expect(second2.hit).toBeTruthy();
42
- expect(second.value).toBe(second2.value);
43
-
44
- memoized.clear(1);
45
- expect(memoized.size()).toBe(1);
46
- memoized.clear(ANY);
47
- expect(memoized.size()).toBe(0);
48
- });
49
- });
50
-
51
- describe('TransformerMap', async () => {
52
- test('simple', async () => {
53
- const dispose = vi.fn();
54
-
55
- class Cache extends TransformerMap<number, any> {
56
- write(key, value, oldValue) {
57
- value.cached = true;
58
- value.read = 0;
59
- return value;
60
- }
61
- read(value, key) {
62
- value.read++;
63
- return value;
64
- }
65
- dispose(value, key) {
66
- dispose(value, key);
67
- }
68
- }
69
-
70
- const cache = new Cache('test');
71
-
72
- const obj = { a: 1 };
73
-
74
- const x1 = await cache.memo(1, obj);
75
- expect(x1).toStrictEqual({ a: 1, cached: true, read: 0 });
76
-
77
- const x2 = await cache.memo(1, obj);
78
- expect(x2).toStrictEqual({ a: 1, cached: true, read: 1 });
79
-
80
- const x3 = await cache.memo(1, { a: 2 });
81
- expect(x3).toStrictEqual({ a: 2, cached: true, read: 0 });
82
- expect(cache.size).toEqual(1);
83
- expect(dispose).toBeCalledTimes(1);
84
- expect(dispose).toBeCalledWith({ a: 1, cached: true, read: 1 }, 1);
85
-
86
- const x4 = await cache.memo(2, { a: 20 });
87
-
88
- expect(x4).toStrictEqual({ a: 20, cached: true, read: 0 });
89
- expect(cache.size).toEqual(2);
90
- expect(dispose).toBeCalledTimes(1);
91
- });
92
-
93
- test('key transform', async () => {
94
- const dispose = vi.fn();
95
-
96
- class Cache extends TransformerMap<number, any> {
97
- write(key, value, oldValue) {
98
- return { key, read: 0 };
99
- }
100
- read(value, key) {
101
- value.read++;
102
- return value;
103
- }
104
- dispose(value, key) {
105
- dispose(value, key);
106
- }
107
- }
108
-
109
- const cache = new Cache('test');
110
-
111
- const x1 = await cache.memo(1);
112
- expect(x1).toStrictEqual({ key: 1, read: 0 });
113
-
114
- const x2 = await cache.memo(1);
115
- expect(x2).toStrictEqual({ key: 1, read: 1 });
116
-
117
- cache.clear();
118
- expect(dispose).toBeCalledTimes(1);
119
- expect(dispose).toBeCalledWith({ key: 1, read: 1 }, 1);
120
- });
121
- });
package/src/core/cache.ts DELETED
@@ -1,246 +0,0 @@
1
- import ManyKeysMap from 'many-keys-map';
2
-
3
- export type MaybePromise<T> = T | Promise<T>;
4
-
5
- export const shallowCompare = (prev: any, next: any): boolean =>
6
- Array.from(new Set([...Object.keys(prev), ...Object.keys(next)])).every((key) => prev[key] === next[key]);
7
-
8
- export const equal = (prev: any, next: any): boolean => prev === next;
9
-
10
- const UNUSED = Symbol('UNUSED');
11
- export const ANY: unique symbol = Symbol('*');
12
-
13
- export function createTracker<Dep = any>(whenDifferent: (next: Dep, prev?: Dep) => any, shallow = false) {
14
- let lastDependency: Dep = UNUSED as any;
15
-
16
- const comparator = shallow ? shallowCompare : equal;
17
-
18
- return function tracker(dependency: Dep): Dep | false {
19
- // console.log('Tracker', lastDependency, dependency);
20
-
21
- if (lastDependency !== UNUSED && comparator(lastDependency, dependency)) {
22
- // console.log('RETAINED cache', { lastDependency, dependency });
23
- return false;
24
- }
25
-
26
- // console.log('INVALIDATED cache', {lastDependency, dependency});
27
-
28
- const res = whenDifferent(dependency, lastDependency === UNUSED ? undefined : lastDependency) || true;
29
-
30
- lastDependency = dependency;
31
-
32
- return res;
33
- };
34
- }
35
-
36
- /**
37
- * https://github.com/futpib/deep-weak-map
38
- * https://github.com/fregante/many-keys-map
39
- * https://github.com/fregante/many-keys-weakmap
40
- * https://github.com/sindresorhus/memoize?tab=readme-ov-file#example-multiple-non-serializable-arguments
41
- *
42
- * ```ts
43
- * const memoized = memo(
44
- * (file, options, ...args) => { ... },
45
- * {
46
- * key: (file, options, ...args) => [file, JSON.stringify(options), ...args],
47
- * invalidate: (bitmap) => !bitmap.width,
48
- * dispose: (bitmap) => bitmap.close(),
49
- * }
50
- * );
51
- * ```
52
- */
53
- export function memo<Key extends any[], Val, SerializedKey extends any[] = Key>(
54
- fn: (...args: Key) => MaybePromise<Val>,
55
- {
56
- key = (...k: Key) => k as never as SerializedKey,
57
- invalidate,
58
- dispose,
59
- }: {
60
- key?: (...key: Key) => SerializedKey;
61
- invalidate?: (prev: Val, ...key: SerializedKey) => boolean;
62
- dispose?: (prev: Val, ...key: SerializedKey) => void;
63
- } = {},
64
- ): {
65
- (...args: Key): Promise<{
66
- value?: Val;
67
- hit: boolean;
68
- }>;
69
- clear: (...condition: Key | any[]) => void;
70
- size: () => number;
71
- } {
72
- const map = new ManyKeysMap<SerializedKey, Val>();
73
-
74
- //TODO Extend ManyKeysMap
75
- const clear = (...condition: Key | any[]) => {
76
- if (!condition?.length) {
77
- map.forEach((value, serializedKey) => {
78
- dispose?.(value, ...serializedKey);
79
- });
80
- map.clear();
81
- return;
82
- }
83
-
84
- const keyToClear = key(...(condition as any));
85
-
86
- map.forEach((value, serializedKey) => {
87
- if (!serializedKey.every((kk, i) => keyToClear[i] === ANY || kk === keyToClear[i])) return;
88
- dispose?.(value, ...serializedKey);
89
- map.delete(serializedKey);
90
- });
91
- };
92
-
93
- const size = () => map.size;
94
-
95
- async function memoized(...args: Key) {
96
- const k = key(...args);
97
-
98
- const has = map.has(k);
99
- const old = map.get(k);
100
-
101
- if (has && !invalidate?.(old as never as Val, ...k)) {
102
- return { value: map.get(k), hit: true };
103
- }
104
-
105
- const value = await fn(...args);
106
-
107
- map.set(k, value);
108
-
109
- return { hit: false, value };
110
- }
111
-
112
- memoized.clear = clear;
113
- memoized.size = size;
114
-
115
- //TODO return mimic-function(memorized, fn);
116
-
117
- return memoized;
118
- }
119
-
120
- /**
121
- * Allows to memoize values by key and invalidate them based on the previous value.
122
- *
123
- * This makes possible to implement various one-off and subsequent transformations.
124
- *
125
- * 1. `write`: Transform value BEFORE writing to cache, called only once if cache IS NOT present or IS NOT valid
126
- * 2. `read`: Transform value AFTER it's read from cache, always called if cache IS valid, keep in mind this transform is applied on top of BEFORE
127
- *
128
- * Both should return same type or null.
129
- *
130
- * If `newValue` is null, old is returned, and no cache is set.
131
- *
132
- * ```ts
133
- * class InputCache extends TypedCache<string, ImageBitmap> {
134
- * dispose(bitmap: ImageBitmap, key: string) {
135
- * bitmap.close();
136
- * }
137
- * }
138
- *
139
- * const cache = new InputCache('input');
140
- *
141
- * // Cache provided OffscreenCanvas by name and create context once per canvas
142
- *
143
- * class CanvasCache extends TypedCache<string, OffscreenCanvas> {
144
- * protected write(key: string, canvas: OffscreenCanvas): OffscreenCanvas {
145
- * const canvas = newValue.getContext('2d');
146
- * canvas.ctx = canvas;
147
- * return canvas;
148
- * }
149
- * }
150
- *
151
- * // Transfer control to offscreen canvas and track removal of original
152
- * // When called again, always return null, because canvas is handed to worker, and never returned to main
153
- *
154
- * class CanvasCache extends TypedCache<HTMLCanvasElement, OffscreenCanvas> {
155
- *
156
- * protected write(canvas: HTMLCanvasElement): OffscreenCanvas {
157
- * let l;
158
- * canvas.addEventListener(
159
- * 'remove',
160
- * (l = () => {
161
- * console.log('Removing canvas from cache', key);
162
- * this.delete(canvas);
163
- * key.removeEventListener('remove', l);
164
- * }),
165
- * );
166
- * return canvas.transferControlToOffscreen();
167
- * }
168
- *
169
- * protected read() {
170
- * return null;
171
- * }
172
- * }
173
- *
174
- * // Create bitmap from file and check if was used, return null if used
175
- * // Since bitmaps are also cached in worker, used bitmaps are not sent
176
- *
177
- * class BitmapCache extends TypedCache<File, ImageBitmap, File> {
178
- * protected async write(file: File): Promise<ImageBitmap> {
179
- * return await createImageBitmap(file);
180
- * }
181
- *
182
- * protected read(bitmap: ImageBitmap): Promise<ImageBitmap> | ImageBitmap {
183
- * if (!bitmap.width) return null;
184
- * return bitmap;
185
- * }
186
- * }
187
- *
188
- * ```
189
- */
190
- export abstract class TransformerMap<Key, Val = Key> extends Map<Key, Val> {
191
- constructor(protected readonly name: string) {
192
- // console.warn('CREATE cache', name);
193
- super();
194
- }
195
-
196
- protected write(key: Key, newValue?: Val, oldValue?: Val): MaybePromise<Val> {
197
- return newValue as Val;
198
- }
199
-
200
- protected read(oldValue: Val, key: Key): MaybePromise<Val> {
201
- return oldValue;
202
- }
203
-
204
- delete(key: Key): boolean {
205
- const val = this.get(key);
206
- const has = typeof val !== 'undefined';
207
- if (has) this.dispose(val, key);
208
- super.delete(key);
209
- return has;
210
- }
211
-
212
- /**
213
- * Do something with the value and key before removing it from cache
214
- * For example, close a file or a bitmap
215
- */
216
- protected dispose(value: Val, key: Key): void {}
217
-
218
- clear(): void {
219
- console.log('CLEAR cache', this.name);
220
- this.forEach(this.dispose);
221
- super.clear();
222
- }
223
-
224
- set(key: Key, value: Val): this {
225
- throw new Error('Use memo() method instead');
226
- }
227
-
228
- async memo(key: Key, newValue?: Val): Promise<Val> {
229
- const oldValue = this.get(key);
230
-
231
- if (!!oldValue && (!newValue || newValue === oldValue)) {
232
- // console.log('FROM cache', this.name, key, 'old value', oldValue);
233
- return this.read?.(oldValue, key);
234
- }
235
-
236
- if (this.has(key)) this.delete(key);
237
-
238
- const value = await this.write(key, newValue, oldValue);
239
-
240
- super.set(key, value);
241
-
242
- // console.log('INVALIDATED KEY cache', this.name, key, 'has', has, 'invalidate', invalidate, 'new value', value);
243
-
244
- return value;
245
- }
246
- }
@@ -1,17 +0,0 @@
1
- // @see https://www.youtube.com/watch?v=AdmGHwvgaVs
2
- export function catchErrors<T, E extends Error = Error>(
3
- promise: Promise<T>,
4
- errors?: E[],
5
- ): Promise<any[] | (T | undefined)[]> {
6
- return promise
7
- .then((data) => [undefined, data])
8
- .catch((error) => {
9
- if (!errors?.length) {
10
- return [error];
11
- }
12
- if (errors.some((e) => e instanceof error)) {
13
- return [error];
14
- }
15
- throw error;
16
- });
17
- }
package/src/core/files.ts DELETED
@@ -1,29 +0,0 @@
1
- export const downloadFile = async (file: File): Promise<void> => {
2
- //FIXME https://github.com/eligrey/FileSaver.js/issues/471
3
- const { saveAs } = require('file-saver');
4
-
5
- //FIXME https://github.com/eligrey/FileSaver.js/issues/731
6
- return saveAs(file, file.name);
7
- };
8
-
9
- export const createFile = async (text: any, filename = 'file.json', type = 'application/json'): Promise<File> => {
10
- return new File([new Blob([text], { type })], filename);
11
- };
12
-
13
- export const openFile = (): Promise<string> =>
14
- new Promise((res, rej) => {
15
- const input = document.createElement('input');
16
- input.type = 'file';
17
- input.addEventListener('change', function readFile(e) {
18
- input.removeEventListener('change', readFile);
19
- // @ts-expect-error file is always there
20
- const [file] = e.target.files;
21
- if (!file) return;
22
- const reader = new FileReader();
23
- reader.onload = (e) => res(e.target?.result as string);
24
- reader.onerror = rej;
25
- reader.onabort = rej;
26
- reader.readAsText(file);
27
- });
28
- input.click();
29
- });
package/src/core/ls.ts DELETED
@@ -1,15 +0,0 @@
1
- export function getStorage(pref: string): {
2
- read: (key: string) => null | any;
3
- write: (key: string, value: any) => void;
4
- remove: (key: string) => void;
5
- } {
6
- const prefix = (key) => `${pref}-${key}`;
7
-
8
- const ls = (typeof window !== 'undefined' ? localStorage : null) as Storage;
9
-
10
- const read = (key: string): any => JSON.parse(ls?.getItem(prefix(key)) || 'null');
11
- const write = (key: string, value: any): void => ls?.setItem(prefix(key), JSON.stringify(value));
12
- const remove = (key: string): void => ls?.removeItem(prefix(key));
13
-
14
- return { read, write, remove };
15
- }
@@ -1,109 +0,0 @@
1
- import { bold, magenta, cyan, yellow, red, green } from 'colors/safe';
2
-
3
- export const colored: {
4
- important: typeof bold;
5
- subject: typeof magenta;
6
- arg: typeof cyan;
7
- sup: typeof yellow;
8
- err: typeof red;
9
- ok: typeof green;
10
- } = {
11
- important: bold,
12
- subject: magenta,
13
- arg: cyan,
14
- sup: yellow,
15
- err: red,
16
- ok: green,
17
- };
18
-
19
- const noColor = (str) => str;
20
-
21
- export const uncolored: {
22
- important: (str: any) => any;
23
- subject: (str: any) => any;
24
- arg: (str: any) => any;
25
- sup: (str: any) => any;
26
- err: (str: any) => any;
27
- ok: (str: any) => any;
28
- } = {
29
- important: noColor,
30
- subject: noColor,
31
- arg: noColor,
32
- sup: noColor,
33
- err: noColor,
34
- ok: noColor,
35
- };
36
-
37
- export function createMeasurer({
38
- colors = true,
39
- prepend = 'LOG',
40
- padding = 10,
41
- }: {
42
- colors?: boolean;
43
- prepend?: string;
44
- padding?: number;
45
- }): {
46
- measure: (
47
- what: string,
48
- step: string,
49
- supplemental?: string,
50
- ...args: any[]
51
- ) => {
52
- done: (result?: string, ...args2: any[]) => void;
53
- fail: (result?: string, ...args2: any[]) => void;
54
- log: (...args2: any[]) => void;
55
- };
56
- important: (str: any) => any;
57
- subject: (str: any) => any;
58
- arg: (str: any) => any;
59
- sup: (str: any) => any;
60
- ok: (str: any) => any;
61
- err: (str: any) => any;
62
- } {
63
- const { important, subject, arg, sup, ok, err } = colors ? colored : uncolored;
64
-
65
- function measure(
66
- what: string,
67
- step: string,
68
- supplemental: string = '',
69
- ...args: any[]
70
- ): {
71
- done: (result?: string, ...args2: any[]) => void;
72
- fail: (result?: string, ...args2: any[]) => void;
73
- log: (...args2: any[]) => void;
74
- } {
75
- const time = performance.now();
76
-
77
- const prefix = [
78
- prepend,
79
- important(subject(what.substring(0, padding).padStart(padding, ' '))),
80
- arg(step),
81
- sup(supplemental),
82
- ...args,
83
- ];
84
-
85
- const done = (result: string = ok('DONE'), ...args2: any[]): void => {
86
- console.log(
87
- ...[
88
- ...prefix,
89
- important(result),
90
- ...args2,
91
- 'in',
92
- important((performance.now() - time).toFixed(0)),
93
- 'ms',
94
- ].filter(Boolean),
95
- );
96
- console.groupEnd();
97
- };
98
-
99
- const fail = (result: string = err('FAIL'), ...args2: any[]): void => done(result, ...args2);
100
-
101
- const log = (...args2: any[]): void => {
102
- console.log(...prefix, ...args2);
103
- };
104
-
105
- return { done, fail, log };
106
- }
107
-
108
- return { measure, important, subject, arg, sup, ok, err };
109
- }
package/src/core/mutex.ts DELETED
@@ -1,22 +0,0 @@
1
- //TODO Implement queue with ranking & sorting
2
- //TODO https://github.com/sindresorhus/p-queue
3
- export class Mutex {
4
- private promise = Promise.resolve();
5
-
6
- public exec(fn: (...args: any) => any): ReturnType<typeof fn> {
7
- return new Promise((resolve, reject) => {
8
- // wrap in always successful function
9
- this.promise = this.promise.then(async () => {
10
- try {
11
- resolve(await fn());
12
- } catch (e) {
13
- reject(e);
14
- }
15
- });
16
- });
17
- }
18
-
19
- public wrap(fn: (...args: any) => any): ReturnType<typeof fn> {
20
- return (...args: any) => this.exec(() => fn(...args));
21
- }
22
- }