repluggable-core 0.0.0-pr280.413 → 0.0.0-pr282.418
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/__tests__/spec-setup.js +3 -0
- package/dist/es/{API.d.ts → src/API.d.ts} +31 -10
- package/dist/es/src/API.d.ts.map +1 -0
- package/dist/es/src/API.js +2 -0
- package/dist/es/src/API.js.map +1 -0
- package/dist/es/src/IterableWeakMap.d.ts +20 -0
- package/dist/es/src/IterableWeakMap.d.ts.map +1 -0
- package/dist/es/src/IterableWeakMap.js +92 -0
- package/dist/es/src/IterableWeakMap.js.map +1 -0
- package/dist/es/src/appHost.d.ts +7 -0
- package/dist/es/src/appHost.d.ts.map +1 -0
- package/dist/es/src/appHost.js +848 -0
- package/dist/es/src/appHost.js.map +1 -0
- package/dist/es/src/appHostServices.d.ts +12 -0
- package/dist/es/src/appHostServices.d.ts.map +1 -0
- package/dist/es/src/appHostServices.js +25 -0
- package/dist/es/src/appHostServices.js.map +1 -0
- package/dist/es/src/appHostUtils.d.ts +4 -0
- package/dist/es/src/appHostUtils.d.ts.map +1 -0
- package/dist/es/src/appHostUtils.js +8 -0
- package/dist/es/src/appHostUtils.js.map +1 -0
- package/dist/es/src/extensionSlot.d.ts +8 -0
- package/dist/es/src/extensionSlot.d.ts.map +1 -0
- package/dist/es/src/extensionSlot.js +59 -0
- package/dist/es/src/extensionSlot.js.map +1 -0
- package/dist/es/src/hot.d.ts +14 -0
- package/dist/es/src/hot.d.ts.map +1 -0
- package/dist/es/src/hot.js +52 -0
- package/dist/es/src/hot.js.map +1 -0
- package/dist/es/src/index.d.ts +11 -0
- package/dist/es/src/index.d.ts.map +1 -0
- package/dist/es/src/index.js +10 -0
- package/dist/es/src/index.js.map +1 -0
- package/dist/es/src/installedShellsState.d.ts +19 -0
- package/dist/es/src/installedShellsState.d.ts.map +1 -0
- package/dist/es/src/installedShellsState.js +30 -0
- package/dist/es/src/installedShellsState.js.map +1 -0
- package/dist/es/src/interceptAnyObject.d.ts +7 -0
- package/dist/es/src/interceptAnyObject.d.ts.map +1 -0
- package/dist/es/src/interceptAnyObject.js +21 -0
- package/dist/es/src/interceptAnyObject.js.map +1 -0
- package/dist/es/src/interceptEntryPoints.d.ts +6 -0
- package/dist/es/src/interceptEntryPoints.d.ts.map +1 -0
- package/dist/es/src/interceptEntryPoints.js +22 -0
- package/dist/es/src/interceptEntryPoints.js.map +1 -0
- package/dist/es/src/invokeSlotCallbacks.d.ts +3 -0
- package/dist/es/src/invokeSlotCallbacks.d.ts.map +1 -0
- package/dist/es/src/invokeSlotCallbacks.js +20 -0
- package/dist/es/src/invokeSlotCallbacks.js.map +1 -0
- package/dist/es/src/loggers.d.ts +4 -0
- package/dist/es/src/loggers.d.ts.map +1 -0
- package/dist/es/src/loggers.js +100 -0
- package/dist/es/src/loggers.js.map +1 -0
- package/dist/es/src/monitorAPI.d.ts +3 -0
- package/dist/es/src/monitorAPI.d.ts.map +1 -0
- package/dist/es/src/monitorAPI.js +53 -0
- package/dist/es/src/monitorAPI.js.map +1 -0
- package/dist/es/src/repluggableAppDebug/index.d.ts +2 -0
- package/dist/es/src/repluggableAppDebug/index.d.ts.map +1 -0
- package/dist/es/src/repluggableAppDebug/index.js +2 -0
- package/dist/es/src/repluggableAppDebug/index.js.map +1 -0
- package/dist/es/src/repluggableAppDebug/performanceDebugInfo.d.ts +15 -0
- package/dist/es/src/repluggableAppDebug/performanceDebugInfo.d.ts.map +1 -0
- package/dist/es/src/repluggableAppDebug/performanceDebugInfo.js +94 -0
- package/dist/es/src/repluggableAppDebug/performanceDebugInfo.js.map +1 -0
- package/dist/es/src/repluggableAppDebug/repluggableAppDebug.d.ts +24 -0
- package/dist/es/src/repluggableAppDebug/repluggableAppDebug.d.ts.map +1 -0
- package/dist/es/src/repluggableAppDebug/repluggableAppDebug.js +132 -0
- package/dist/es/src/repluggableAppDebug/repluggableAppDebug.js.map +1 -0
- package/dist/es/src/tarjanGraph.d.ts +27 -0
- package/dist/es/src/tarjanGraph.d.ts.map +1 -0
- package/dist/es/src/tarjanGraph.js +94 -0
- package/dist/es/src/tarjanGraph.js.map +1 -0
- package/dist/es/src/throttledStore.d.ts +32 -0
- package/dist/es/src/throttledStore.d.ts.map +1 -0
- package/dist/es/src/throttledStore.js +240 -0
- package/dist/es/src/throttledStore.js.map +1 -0
- package/dist/es/test/IterableWeakMap.spec.d.ts +2 -0
- package/dist/es/test/IterableWeakMap.spec.d.ts.map +1 -0
- package/dist/es/test/IterableWeakMap.spec.js +218 -0
- package/dist/es/test/IterableWeakMap.spec.js.map +1 -0
- package/dist/es/test/appHost.mock.d.ts +4 -0
- package/dist/es/test/appHost.mock.d.ts.map +1 -0
- package/dist/es/test/appHost.mock.js +54 -0
- package/dist/es/test/appHost.mock.js.map +1 -0
- package/dist/es/test/appHost.spec.d.ts +2 -0
- package/dist/es/test/appHost.spec.d.ts.map +1 -0
- package/dist/es/test/appHost.spec.js +1323 -0
- package/dist/es/test/appHost.spec.js.map +1 -0
- package/dist/es/test/customExtensionSlot.spec.d.ts +2 -0
- package/dist/es/test/customExtensionSlot.spec.d.ts.map +1 -0
- package/dist/es/test/customExtensionSlot.spec.js +112 -0
- package/dist/es/test/customExtensionSlot.spec.js.map +1 -0
- package/dist/es/test/extensionSlot.spec.d.ts +2 -0
- package/dist/es/test/extensionSlot.spec.d.ts.map +1 -0
- package/dist/es/test/extensionSlot.spec.js +73 -0
- package/dist/es/test/extensionSlot.spec.js.map +1 -0
- package/dist/es/test/installedShellsState.spec.d.ts +2 -0
- package/dist/es/test/installedShellsState.spec.d.ts.map +1 -0
- package/dist/es/test/installedShellsState.spec.js +28 -0
- package/dist/es/test/installedShellsState.spec.js.map +1 -0
- package/dist/es/test/interceptAnyObject.spec.d.ts +2 -0
- package/dist/es/test/interceptAnyObject.spec.d.ts.map +1 -0
- package/dist/es/test/interceptAnyObject.spec.js +166 -0
- package/dist/es/test/interceptAnyObject.spec.js.map +1 -0
- package/dist/es/test/interceptEntryPoints.spec.d.ts +2 -0
- package/dist/es/test/interceptEntryPoints.spec.d.ts.map +1 -0
- package/dist/es/test/interceptEntryPoints.spec.js +244 -0
- package/dist/es/test/interceptEntryPoints.spec.js.map +1 -0
- package/dist/es/test/loggers.spec.d.ts +2 -0
- package/dist/es/test/loggers.spec.d.ts.map +1 -0
- package/dist/es/test/loggers.spec.js +218 -0
- package/dist/es/test/loggers.spec.js.map +1 -0
- package/dist/es/test/repluggableAppDebug.spec.d.ts +2 -0
- package/dist/es/test/repluggableAppDebug.spec.d.ts.map +1 -0
- package/dist/es/test/repluggableAppDebug.spec.js +107 -0
- package/dist/es/test/repluggableAppDebug.spec.js.map +1 -0
- package/dist/es/test/testKit.spec.d.ts +2 -0
- package/dist/es/test/testKit.spec.d.ts.map +1 -0
- package/dist/es/test/testKit.spec.js +129 -0
- package/dist/es/test/testKit.spec.js.map +1 -0
- package/dist/es/testKit/emptyLoggerOptions.d.ts +3 -0
- package/dist/es/testKit/emptyLoggerOptions.d.ts.map +1 -0
- package/dist/es/testKit/emptyLoggerOptions.js +15 -0
- package/dist/es/testKit/emptyLoggerOptions.js.map +1 -0
- package/dist/es/testKit/index.d.ts +25 -0
- package/dist/es/testKit/index.d.ts.map +1 -0
- package/dist/es/testKit/index.js +130 -0
- package/dist/es/testKit/index.js.map +1 -0
- package/dist/es/testKit/mockPackage.d.ts +21 -0
- package/dist/es/testKit/mockPackage.d.ts.map +1 -0
- package/dist/es/testKit/mockPackage.js +85 -0
- package/dist/es/testKit/mockPackage.js.map +1 -0
- package/dist/es/testKit/withConsoleErrors.d.ts +2 -0
- package/dist/es/testKit/withConsoleErrors.d.ts.map +1 -0
- package/dist/es/testKit/withConsoleErrors.js +12 -0
- package/dist/es/testKit/withConsoleErrors.js.map +1 -0
- package/dist/es/testKit/withThrowOnError.d.ts +3 -0
- package/dist/es/testKit/withThrowOnError.d.ts.map +1 -0
- package/dist/es/testKit/withThrowOnError.js +27 -0
- package/dist/es/testKit/withThrowOnError.js.map +1 -0
- package/dist/src/API.d.ts +31 -10
- package/dist/src/API.d.ts.map +1 -1
- package/dist/src/API.js +3 -0
- package/dist/src/API.js.map +1 -1
- package/dist/src/IterableWeakMap.d.ts +20 -0
- package/dist/src/IterableWeakMap.d.ts.map +1 -0
- package/dist/src/IterableWeakMap.js +96 -0
- package/dist/src/IterableWeakMap.js.map +1 -0
- package/dist/src/appHost.d.ts +7 -0
- package/dist/src/appHost.d.ts.map +1 -0
- package/dist/src/appHost.js +856 -0
- package/dist/src/appHost.js.map +1 -0
- package/dist/src/appHostServices.d.ts +12 -0
- package/dist/src/appHostServices.d.ts.map +1 -0
- package/dist/src/appHostServices.js +29 -0
- package/dist/src/appHostServices.js.map +1 -0
- package/dist/src/appHostUtils.d.ts +4 -0
- package/dist/src/appHostUtils.d.ts.map +1 -0
- package/dist/src/appHostUtils.js +16 -0
- package/dist/src/appHostUtils.js.map +1 -0
- package/dist/src/extensionSlot.d.ts +8 -0
- package/dist/src/extensionSlot.d.ts.map +1 -0
- package/dist/src/extensionSlot.js +67 -0
- package/dist/src/extensionSlot.js.map +1 -0
- package/dist/src/hot.d.ts +14 -0
- package/dist/src/hot.d.ts.map +1 -0
- package/dist/src/hot.js +56 -0
- package/dist/src/hot.js.map +1 -0
- package/dist/src/index.d.ts +10 -1
- package/dist/src/index.d.ts.map +1 -1
- package/dist/src/index.js +23 -0
- package/dist/src/index.js.map +1 -1
- package/dist/src/installedShellsState.d.ts +19 -0
- package/dist/src/installedShellsState.d.ts.map +1 -0
- package/dist/src/installedShellsState.js +38 -0
- package/dist/src/installedShellsState.js.map +1 -0
- package/dist/src/interceptAnyObject.d.ts +7 -0
- package/dist/src/interceptAnyObject.d.ts.map +1 -0
- package/dist/src/interceptAnyObject.js +28 -0
- package/dist/src/interceptAnyObject.js.map +1 -0
- package/dist/src/interceptEntryPoints.d.ts +6 -0
- package/dist/src/interceptEntryPoints.d.ts.map +1 -0
- package/dist/src/interceptEntryPoints.js +30 -0
- package/dist/src/interceptEntryPoints.js.map +1 -0
- package/dist/src/invokeSlotCallbacks.d.ts +3 -0
- package/dist/src/invokeSlotCallbacks.d.ts.map +1 -0
- package/dist/src/invokeSlotCallbacks.js +24 -0
- package/dist/src/invokeSlotCallbacks.js.map +1 -0
- package/dist/src/loggers.d.ts +4 -0
- package/dist/src/loggers.d.ts.map +1 -0
- package/dist/src/loggers.js +104 -0
- package/dist/src/loggers.js.map +1 -0
- package/dist/src/monitorAPI.d.ts +3 -0
- package/dist/src/monitorAPI.d.ts.map +1 -0
- package/dist/src/monitorAPI.js +57 -0
- package/dist/src/monitorAPI.js.map +1 -0
- package/dist/src/repluggableAppDebug/index.d.ts +2 -0
- package/dist/src/repluggableAppDebug/index.d.ts.map +1 -0
- package/dist/src/repluggableAppDebug/index.js +6 -0
- package/dist/src/repluggableAppDebug/index.js.map +1 -0
- package/dist/src/repluggableAppDebug/performanceDebugInfo.d.ts +15 -0
- package/dist/src/repluggableAppDebug/performanceDebugInfo.d.ts.map +1 -0
- package/dist/src/repluggableAppDebug/performanceDebugInfo.js +101 -0
- package/dist/src/repluggableAppDebug/performanceDebugInfo.js.map +1 -0
- package/dist/src/repluggableAppDebug/repluggableAppDebug.d.ts +24 -0
- package/dist/src/repluggableAppDebug/repluggableAppDebug.d.ts.map +1 -0
- package/dist/src/repluggableAppDebug/repluggableAppDebug.js +139 -0
- package/dist/src/repluggableAppDebug/repluggableAppDebug.js.map +1 -0
- package/dist/src/tarjanGraph.d.ts +27 -0
- package/dist/src/tarjanGraph.d.ts.map +1 -0
- package/dist/src/tarjanGraph.js +100 -0
- package/dist/src/tarjanGraph.js.map +1 -0
- package/dist/src/throttledStore.d.ts +32 -0
- package/dist/src/throttledStore.d.ts.map +1 -0
- package/dist/src/throttledStore.js +249 -0
- package/dist/src/throttledStore.js.map +1 -0
- package/dist/test/IterableWeakMap.spec.d.ts +2 -0
- package/dist/test/IterableWeakMap.spec.d.ts.map +1 -0
- package/dist/test/IterableWeakMap.spec.js +220 -0
- package/dist/test/IterableWeakMap.spec.js.map +1 -0
- package/dist/test/appHost.mock.d.ts +4 -0
- package/dist/test/appHost.mock.d.ts.map +1 -0
- package/dist/test/appHost.mock.js +59 -0
- package/dist/test/appHost.mock.js.map +1 -0
- package/dist/test/appHost.spec.d.ts +2 -0
- package/dist/test/appHost.spec.d.ts.map +1 -0
- package/dist/test/appHost.spec.js +1328 -0
- package/dist/test/appHost.spec.js.map +1 -0
- package/dist/test/customExtensionSlot.spec.d.ts +2 -0
- package/dist/test/customExtensionSlot.spec.d.ts.map +1 -0
- package/dist/test/customExtensionSlot.spec.js +117 -0
- package/dist/test/customExtensionSlot.spec.js.map +1 -0
- package/dist/test/extensionSlot.spec.d.ts +2 -0
- package/dist/test/extensionSlot.spec.d.ts.map +1 -0
- package/dist/test/extensionSlot.spec.js +75 -0
- package/dist/test/extensionSlot.spec.js.map +1 -0
- package/dist/test/installedShellsState.spec.d.ts +2 -0
- package/dist/test/installedShellsState.spec.d.ts.map +1 -0
- package/dist/test/installedShellsState.spec.js +30 -0
- package/dist/test/installedShellsState.spec.js.map +1 -0
- package/dist/test/interceptAnyObject.spec.d.ts +2 -0
- package/dist/test/interceptAnyObject.spec.d.ts.map +1 -0
- package/dist/test/interceptAnyObject.spec.js +171 -0
- package/dist/test/interceptAnyObject.spec.js.map +1 -0
- package/dist/test/interceptEntryPoints.spec.d.ts +2 -0
- package/dist/test/interceptEntryPoints.spec.d.ts.map +1 -0
- package/dist/test/interceptEntryPoints.spec.js +249 -0
- package/dist/test/interceptEntryPoints.spec.js.map +1 -0
- package/dist/test/loggers.spec.d.ts +2 -0
- package/dist/test/loggers.spec.d.ts.map +1 -0
- package/dist/test/loggers.spec.js +220 -0
- package/dist/test/loggers.spec.js.map +1 -0
- package/dist/test/repluggableAppDebug.spec.d.ts +2 -0
- package/dist/test/repluggableAppDebug.spec.d.ts.map +1 -0
- package/dist/test/repluggableAppDebug.spec.js +109 -0
- package/dist/test/repluggableAppDebug.spec.js.map +1 -0
- package/dist/test/testKit.spec.d.ts +2 -0
- package/dist/test/testKit.spec.d.ts.map +1 -0
- package/dist/test/testKit.spec.js +134 -0
- package/dist/test/testKit.spec.js.map +1 -0
- package/dist/testKit/emptyLoggerOptions.d.ts +3 -0
- package/dist/testKit/emptyLoggerOptions.d.ts.map +1 -0
- package/dist/testKit/emptyLoggerOptions.js +18 -0
- package/dist/testKit/emptyLoggerOptions.js.map +1 -0
- package/dist/testKit/index.d.ts +25 -0
- package/dist/testKit/index.d.ts.map +1 -0
- package/dist/testKit/index.js +158 -0
- package/dist/testKit/index.js.map +1 -0
- package/dist/testKit/mockPackage.d.ts +21 -0
- package/dist/testKit/mockPackage.d.ts.map +1 -0
- package/dist/testKit/mockPackage.js +91 -0
- package/dist/testKit/mockPackage.js.map +1 -0
- package/dist/testKit/withConsoleErrors.d.ts +2 -0
- package/dist/testKit/withConsoleErrors.d.ts.map +1 -0
- package/dist/testKit/withConsoleErrors.js +16 -0
- package/dist/testKit/withConsoleErrors.js.map +1 -0
- package/dist/testKit/withThrowOnError.d.ts +3 -0
- package/dist/testKit/withThrowOnError.d.ts.map +1 -0
- package/dist/testKit/withThrowOnError.js +31 -0
- package/dist/testKit/withThrowOnError.js.map +1 -0
- package/jest.config.js +16 -0
- package/package.json +5 -3
- package/src/API.ts +474 -378
- package/src/IterableWeakMap.ts +121 -0
- package/src/appHost.ts +1383 -0
- package/src/appHostServices.ts +42 -0
- package/src/appHostUtils.ts +11 -0
- package/src/extensionSlot.ts +96 -0
- package/src/hot.ts +53 -0
- package/src/index.ts +55 -3
- package/src/installedShellsState.ts +54 -0
- package/src/interceptAnyObject.ts +39 -0
- package/src/interceptEntryPoints.ts +25 -0
- package/src/invokeSlotCallbacks.ts +20 -0
- package/src/loggers.ts +112 -0
- package/src/monitorAPI.ts +71 -0
- package/src/repluggableAppDebug/debug.d.ts +37 -0
- package/src/repluggableAppDebug/index.ts +1 -0
- package/src/repluggableAppDebug/performanceDebugInfo.ts +96 -0
- package/src/repluggableAppDebug/repluggableAppDebug.ts +192 -0
- package/src/tarjanGraph.ts +96 -0
- package/src/throttledStore.ts +355 -0
- package/test/IterableWeakMap.spec.ts +284 -0
- package/test/appHost.mock.ts +58 -0
- package/test/appHost.spec.ts +1629 -0
- package/test/customExtensionSlot.spec.ts +153 -0
- package/test/extensionSlot.spec.ts +94 -0
- package/test/installedShellsState.spec.ts +39 -0
- package/test/interceptAnyObject.spec.ts +217 -0
- package/test/interceptEntryPoints.spec.ts +291 -0
- package/test/loggers.spec.ts +288 -0
- package/test/repluggableAppDebug.spec.ts +118 -0
- package/test/testKit.spec.tsx +153 -0
- package/testKit/emptyLoggerOptions.ts +16 -0
- package/testKit/index.ts +172 -0
- package/testKit/mockPackage.ts +99 -0
- package/testKit/package.json +3 -0
- package/testKit/withConsoleErrors.ts +12 -0
- package/testKit/withThrowOnError.ts +34 -0
- package/tsconfig.json +11 -1
- package/dist/es/API.d.ts.map +0 -1
- package/dist/es/API.js +0 -2
- package/dist/es/API.js.map +0 -1
- package/dist/es/index.d.ts +0 -2
- package/dist/es/index.d.ts.map +0 -1
- package/dist/es/index.js +0 -2
- package/dist/es/index.js.map +0 -1
|
@@ -0,0 +1,355 @@
|
|
|
1
|
+
import _ from 'lodash'
|
|
2
|
+
import { Action, AnyAction, Dispatch, Reducer, ReducersMapObject, Store, Unsubscribe, combineReducers, createStore } from 'redux'
|
|
3
|
+
import { devToolsEnhancer } from 'redux-devtools-extension'
|
|
4
|
+
import { AppHost, ExtensionSlot, ObservableState, ReducersMapObjectContributor, Shell, SlotKey, StateObserver } from './API'
|
|
5
|
+
import { AppHostServicesProvider } from './appHostServices'
|
|
6
|
+
import { contributeInstalledShellsState } from './installedShellsState'
|
|
7
|
+
import { interceptAnyObject } from './interceptAnyObject'
|
|
8
|
+
import { invokeSlotCallbacks } from './invokeSlotCallbacks'
|
|
9
|
+
|
|
10
|
+
type ReducerNotificationScope = 'broadcasting' | 'observable'
|
|
11
|
+
interface ShellsReducersMap {
|
|
12
|
+
[shellName: string]: ReducersMapObject
|
|
13
|
+
}
|
|
14
|
+
|
|
15
|
+
interface AnyShellAction extends AnyAction {
|
|
16
|
+
__shellName?: string
|
|
17
|
+
}
|
|
18
|
+
|
|
19
|
+
|
|
20
|
+
function createTimeOutPublisher ( notify: () => void) {
|
|
21
|
+
let id : null | NodeJS.Timeout = null
|
|
22
|
+
return () => {
|
|
23
|
+
if (id === null) {
|
|
24
|
+
id = setTimeout(() => {
|
|
25
|
+
id = null
|
|
26
|
+
notify()
|
|
27
|
+
},0)
|
|
28
|
+
}
|
|
29
|
+
return () => {
|
|
30
|
+
if(id === null) {
|
|
31
|
+
return
|
|
32
|
+
}
|
|
33
|
+
clearTimeout(id)
|
|
34
|
+
id = null
|
|
35
|
+
}
|
|
36
|
+
}
|
|
37
|
+
}
|
|
38
|
+
|
|
39
|
+
function createAnimationFramePublisher ( notify: () => void) {
|
|
40
|
+
let id : null | number = null
|
|
41
|
+
return () => {
|
|
42
|
+
if (id === null) {
|
|
43
|
+
id = requestAnimationFrame(() => {
|
|
44
|
+
id = null
|
|
45
|
+
notify()
|
|
46
|
+
})
|
|
47
|
+
}
|
|
48
|
+
return () => {
|
|
49
|
+
if(id === null) {
|
|
50
|
+
return
|
|
51
|
+
}
|
|
52
|
+
cancelAnimationFrame(id)
|
|
53
|
+
id = null
|
|
54
|
+
}
|
|
55
|
+
}
|
|
56
|
+
}
|
|
57
|
+
|
|
58
|
+
|
|
59
|
+
|
|
60
|
+
|
|
61
|
+
type Subscriber = () => void
|
|
62
|
+
|
|
63
|
+
export interface StateContribution<TState = {}, TAction extends AnyAction = AnyAction> {
|
|
64
|
+
reducerFactory: ReducersMapObjectContributor<TState, TAction>
|
|
65
|
+
notificationScope: ReducerNotificationScope
|
|
66
|
+
observable?: AnyPrivateObservableState
|
|
67
|
+
}
|
|
68
|
+
|
|
69
|
+
export interface ThrottledStore<T = any> extends Store<T> {
|
|
70
|
+
hasPendingSubscribers(): boolean
|
|
71
|
+
flush(config?: { excecutionType: 'scheduled' | 'immediate' | 'default' }): void
|
|
72
|
+
deferSubscriberNotifications<K>(action: () => K | Promise<K>, shouldDispatchClearCache?: boolean): Promise<K>
|
|
73
|
+
}
|
|
74
|
+
|
|
75
|
+
export interface PrivateThrottledStore<T = any> extends ThrottledStore<T> {
|
|
76
|
+
broadcastNotify(): void
|
|
77
|
+
observableNotify(observer: AnyPrivateObservableState): void
|
|
78
|
+
resetPendingNotifications(): void
|
|
79
|
+
syncSubscribe(listener: () => void): Unsubscribe
|
|
80
|
+
dispatchWithShell(shell: Shell): Dispatch
|
|
81
|
+
}
|
|
82
|
+
|
|
83
|
+
export interface PrivateObservableState<TState, TSelector> extends ObservableState<TSelector> {
|
|
84
|
+
notify(): void
|
|
85
|
+
}
|
|
86
|
+
|
|
87
|
+
export type AnyPrivateObservableState = PrivateObservableState<any, any>
|
|
88
|
+
|
|
89
|
+
const buildStoreReducer = (
|
|
90
|
+
contributedState: ExtensionSlot<StateContribution>,
|
|
91
|
+
broadcastNotify: PrivateThrottledStore['broadcastNotify'],
|
|
92
|
+
observableNotify: PrivateThrottledStore['observableNotify'],
|
|
93
|
+
shouldScopeReducers?: boolean
|
|
94
|
+
): Reducer => {
|
|
95
|
+
function withNotifyAction(
|
|
96
|
+
originalReducersMap: ReducersMapObject,
|
|
97
|
+
notifyAction: () => void,
|
|
98
|
+
storeShellName?: string
|
|
99
|
+
): ReducersMapObject {
|
|
100
|
+
const decorateReducer = (originalReducer: Reducer): Reducer => {
|
|
101
|
+
return (state0, action: AnyShellAction) => {
|
|
102
|
+
if (shouldScopeReducers && state0 && storeShellName && action.__shellName && storeShellName !== action.__shellName) {
|
|
103
|
+
return state0
|
|
104
|
+
}
|
|
105
|
+
const state1 = originalReducer(state0, action)
|
|
106
|
+
if (state1 !== state0) {
|
|
107
|
+
notifyAction()
|
|
108
|
+
}
|
|
109
|
+
return state1
|
|
110
|
+
}
|
|
111
|
+
}
|
|
112
|
+
const wrapper = interceptAnyObject(originalReducersMap, (name, func) => {
|
|
113
|
+
const originalReducer = func as Reducer
|
|
114
|
+
return decorateReducer(originalReducer)
|
|
115
|
+
})
|
|
116
|
+
return wrapper
|
|
117
|
+
}
|
|
118
|
+
|
|
119
|
+
function withBroadcastOrObservableNotify(
|
|
120
|
+
{ notificationScope, reducerFactory, observable }: StateContribution,
|
|
121
|
+
storeShellName: string
|
|
122
|
+
): ReducersMapObject {
|
|
123
|
+
const originalReducersMap = reducerFactory()
|
|
124
|
+
if (notificationScope === 'broadcasting') {
|
|
125
|
+
return withNotifyAction(originalReducersMap, broadcastNotify, storeShellName)
|
|
126
|
+
}
|
|
127
|
+
if (!observable) {
|
|
128
|
+
// should never happen; would be an internal bug
|
|
129
|
+
throw new Error(
|
|
130
|
+
`getPerShellReducersMapObject: notificationScope=observable but 'observable' is falsy, in shell '${storeShellName}'`
|
|
131
|
+
)
|
|
132
|
+
}
|
|
133
|
+
return withNotifyAction(originalReducersMap, () => observableNotify(observable))
|
|
134
|
+
}
|
|
135
|
+
|
|
136
|
+
function getPerShellReducersMapObject(): ShellsReducersMap {
|
|
137
|
+
return contributedState.getItems().reduce((map: ShellsReducersMap, item) => {
|
|
138
|
+
const shellName = item.shell.name
|
|
139
|
+
map[shellName] = {
|
|
140
|
+
...map[shellName],
|
|
141
|
+
...withBroadcastOrObservableNotify(item.contribution, shellName)
|
|
142
|
+
}
|
|
143
|
+
return map
|
|
144
|
+
}, {})
|
|
145
|
+
}
|
|
146
|
+
|
|
147
|
+
function getCombinedShellReducers(): ReducersMapObject {
|
|
148
|
+
const shellsReducerMaps = getPerShellReducersMapObject()
|
|
149
|
+
const combinedReducersMap = _.mapValues(shellsReducerMaps, singleMap => combineReducers(singleMap))
|
|
150
|
+
return combinedReducersMap
|
|
151
|
+
}
|
|
152
|
+
|
|
153
|
+
function buildReducersMapObject(): ReducersMapObject {
|
|
154
|
+
// TODO: get rid of builtInReducersMaps
|
|
155
|
+
const builtInReducersMaps: ReducersMapObject = {
|
|
156
|
+
...contributeInstalledShellsState()
|
|
157
|
+
}
|
|
158
|
+
return { ...builtInReducersMaps, ...getCombinedShellReducers() }
|
|
159
|
+
}
|
|
160
|
+
|
|
161
|
+
const reducersMap = buildReducersMapObject()
|
|
162
|
+
const combinedReducer = combineReducers(reducersMap)
|
|
163
|
+
return combinedReducer
|
|
164
|
+
}
|
|
165
|
+
|
|
166
|
+
export const updateThrottledStore = (
|
|
167
|
+
host: AppHost & AppHostServicesProvider,
|
|
168
|
+
store: PrivateThrottledStore,
|
|
169
|
+
contributedState: ExtensionSlot<StateContribution>
|
|
170
|
+
): void => {
|
|
171
|
+
const newReducer = buildStoreReducer(contributedState, store.broadcastNotify, store.observableNotify, host.options.shouldScopeReducers)
|
|
172
|
+
store.replaceReducer(newReducer)
|
|
173
|
+
store.resetPendingNotifications()
|
|
174
|
+
}
|
|
175
|
+
|
|
176
|
+
export const createThrottledStore = (
|
|
177
|
+
host: AppHost & AppHostServicesProvider,
|
|
178
|
+
contributedState: ExtensionSlot<StateContribution>,
|
|
179
|
+
updateIsSubscriptionNotifyInProgress: (isSubscriptionNotifyInProgress: boolean) => void,
|
|
180
|
+
updateIsObserversNotifyInProgress: (isObserversNotifyInProgress: boolean) => void,
|
|
181
|
+
updateShouldFlushMemoizationSync: (shouldFlushMemoizationSync: boolean) => void
|
|
182
|
+
): PrivateThrottledStore => {
|
|
183
|
+
let pendingBroadcastNotification = false
|
|
184
|
+
let pendingObservableNotifications: Set<AnyPrivateObservableState> | undefined
|
|
185
|
+
let isDeferrringNotifications = false
|
|
186
|
+
let pendingFlush = false
|
|
187
|
+
|
|
188
|
+
const onBroadcastNotify = () => {
|
|
189
|
+
pendingBroadcastNotification = true
|
|
190
|
+
}
|
|
191
|
+
|
|
192
|
+
const onObservableNotify = (observable: AnyPrivateObservableState) => {
|
|
193
|
+
if (!pendingObservableNotifications) {
|
|
194
|
+
pendingObservableNotifications = new Set<AnyPrivateObservableState>()
|
|
195
|
+
}
|
|
196
|
+
pendingObservableNotifications.add(observable)
|
|
197
|
+
}
|
|
198
|
+
|
|
199
|
+
const resetAllPendingNotifications = () => {
|
|
200
|
+
pendingBroadcastNotification = false
|
|
201
|
+
pendingObservableNotifications = undefined
|
|
202
|
+
}
|
|
203
|
+
|
|
204
|
+
const reducer = buildStoreReducer(contributedState, onBroadcastNotify, onObservableNotify, host.options.shouldScopeReducers)
|
|
205
|
+
const store: Store = host.options.enableReduxDevtoolsExtension
|
|
206
|
+
? createStore(reducer, devToolsEnhancer({ name: 'repluggable' }))
|
|
207
|
+
: createStore(reducer)
|
|
208
|
+
const invoke = (f: Subscriber) => f()
|
|
209
|
+
|
|
210
|
+
let broadcastSubscribers: Subscriber[] = []
|
|
211
|
+
|
|
212
|
+
const subscribe = (subscriber: Subscriber) => {
|
|
213
|
+
broadcastSubscribers = _.concat(broadcastSubscribers, subscriber)
|
|
214
|
+
return () => {
|
|
215
|
+
broadcastSubscribers = _.without(broadcastSubscribers, subscriber)
|
|
216
|
+
}
|
|
217
|
+
}
|
|
218
|
+
|
|
219
|
+
const notifySubscribers = () => {
|
|
220
|
+
if (pendingBroadcastNotification || !pendingObservableNotifications) {
|
|
221
|
+
host.getAppHostServicesShell().log.monitor('ThrottledStore.notifySubscribers', {}, () =>
|
|
222
|
+
_.forEach(broadcastSubscribers, invoke)
|
|
223
|
+
)
|
|
224
|
+
}
|
|
225
|
+
}
|
|
226
|
+
|
|
227
|
+
const notifyObservers = () => {
|
|
228
|
+
if (pendingObservableNotifications) {
|
|
229
|
+
pendingObservableNotifications.forEach(observable => {
|
|
230
|
+
observable.notify()
|
|
231
|
+
})
|
|
232
|
+
}
|
|
233
|
+
}
|
|
234
|
+
|
|
235
|
+
const notifyAll = () => {
|
|
236
|
+
try {
|
|
237
|
+
updateIsObserversNotifyInProgress(true)
|
|
238
|
+
notifyObservers()
|
|
239
|
+
updateIsSubscriptionNotifyInProgress(true)
|
|
240
|
+
notifySubscribers()
|
|
241
|
+
} finally {
|
|
242
|
+
resetAllPendingNotifications()
|
|
243
|
+
updateIsSubscriptionNotifyInProgress(false)
|
|
244
|
+
updateIsObserversNotifyInProgress(false)
|
|
245
|
+
}
|
|
246
|
+
}
|
|
247
|
+
|
|
248
|
+
const scheduledNotifyAll = () => {
|
|
249
|
+
if (isDeferrringNotifications) {
|
|
250
|
+
return
|
|
251
|
+
}
|
|
252
|
+
notifyAll()
|
|
253
|
+
}
|
|
254
|
+
|
|
255
|
+
|
|
256
|
+
|
|
257
|
+
|
|
258
|
+
const notifyAllOnPublish = typeof window === 'undefined' ? createTimeOutPublisher(scheduledNotifyAll) : createAnimationFramePublisher(scheduledNotifyAll)
|
|
259
|
+
|
|
260
|
+
let cancelRender = _.noop
|
|
261
|
+
|
|
262
|
+
store.subscribe(() => {
|
|
263
|
+
cancelRender = notifyAllOnPublish()
|
|
264
|
+
})
|
|
265
|
+
|
|
266
|
+
const flush = (config = { excecutionType: 'default' }) => {
|
|
267
|
+
if (isDeferrringNotifications && config.excecutionType !== 'immediate') {
|
|
268
|
+
pendingFlush = true
|
|
269
|
+
return
|
|
270
|
+
}
|
|
271
|
+
if (config.excecutionType !== 'scheduled') {
|
|
272
|
+
cancelRender()
|
|
273
|
+
}
|
|
274
|
+
notifyAll()
|
|
275
|
+
}
|
|
276
|
+
|
|
277
|
+
const dispatch: Dispatch<AnyAction> = action => {
|
|
278
|
+
return store.dispatch(action)
|
|
279
|
+
}
|
|
280
|
+
|
|
281
|
+
const toShellAction = <T extends Action>(shell: Shell, action: T): T => ({
|
|
282
|
+
...action,
|
|
283
|
+
__shellName: shell.name
|
|
284
|
+
})
|
|
285
|
+
|
|
286
|
+
const executePendingActions = () => {
|
|
287
|
+
if (pendingFlush) {
|
|
288
|
+
pendingFlush = false
|
|
289
|
+
flush()
|
|
290
|
+
} else if (pendingBroadcastNotification || pendingObservableNotifications) {
|
|
291
|
+
notifyAll()
|
|
292
|
+
}
|
|
293
|
+
}
|
|
294
|
+
|
|
295
|
+
const result: PrivateThrottledStore = {
|
|
296
|
+
...store,
|
|
297
|
+
subscribe,
|
|
298
|
+
syncSubscribe: store.subscribe,
|
|
299
|
+
dispatch,
|
|
300
|
+
dispatchWithShell: shell => action => dispatch(toShellAction(shell, action)),
|
|
301
|
+
flush,
|
|
302
|
+
broadcastNotify: onBroadcastNotify,
|
|
303
|
+
observableNotify: onObservableNotify,
|
|
304
|
+
resetPendingNotifications: resetAllPendingNotifications,
|
|
305
|
+
hasPendingSubscribers: () => pendingBroadcastNotification,
|
|
306
|
+
deferSubscriberNotifications: async (action, shouldDispatchClearCache) => {
|
|
307
|
+
if (isDeferrringNotifications) {
|
|
308
|
+
return action()
|
|
309
|
+
}
|
|
310
|
+
try {
|
|
311
|
+
executePendingActions()
|
|
312
|
+
isDeferrringNotifications = true
|
|
313
|
+
shouldDispatchClearCache && updateShouldFlushMemoizationSync(isDeferrringNotifications)
|
|
314
|
+
const functionResult = await action()
|
|
315
|
+
return functionResult
|
|
316
|
+
} finally {
|
|
317
|
+
isDeferrringNotifications = false
|
|
318
|
+
shouldDispatchClearCache && updateShouldFlushMemoizationSync(isDeferrringNotifications)
|
|
319
|
+
executePendingActions()
|
|
320
|
+
}
|
|
321
|
+
}
|
|
322
|
+
}
|
|
323
|
+
|
|
324
|
+
resetAllPendingNotifications()
|
|
325
|
+
return result
|
|
326
|
+
}
|
|
327
|
+
|
|
328
|
+
export const createObservable = <TState, TSelector>(
|
|
329
|
+
shell: Shell,
|
|
330
|
+
uniqueName: string,
|
|
331
|
+
selectorFactory: (state: TState) => TSelector
|
|
332
|
+
): PrivateObservableState<TState, TSelector> => {
|
|
333
|
+
const subscribersSlotKey: SlotKey<StateObserver<TSelector>> = {
|
|
334
|
+
name: uniqueName
|
|
335
|
+
}
|
|
336
|
+
const observersSlot = shell.declareSlot(subscribersSlotKey)
|
|
337
|
+
|
|
338
|
+
const createSelector = (): TSelector => {
|
|
339
|
+
return selectorFactory(shell.getStore<TState>().getState())
|
|
340
|
+
}
|
|
341
|
+
|
|
342
|
+
return {
|
|
343
|
+
subscribe(fromShell, callback) {
|
|
344
|
+
observersSlot.contribute(fromShell, callback)
|
|
345
|
+
return () => {
|
|
346
|
+
observersSlot.discardBy(item => item.contribution === callback)
|
|
347
|
+
}
|
|
348
|
+
},
|
|
349
|
+
notify() {
|
|
350
|
+
const newSelector = createSelector()
|
|
351
|
+
invokeSlotCallbacks(observersSlot, newSelector)
|
|
352
|
+
},
|
|
353
|
+
current: createSelector
|
|
354
|
+
}
|
|
355
|
+
}
|
|
@@ -0,0 +1,284 @@
|
|
|
1
|
+
import { IterableWeakMap } from "../src/IterableWeakMap";
|
|
2
|
+
|
|
3
|
+
describe("IterableWeakMap", () => {
|
|
4
|
+
function runCommonTests() {
|
|
5
|
+
describe("#constructor", () => {
|
|
6
|
+
it("should add initial values to Map", function () {
|
|
7
|
+
const ref = {};
|
|
8
|
+
const value = {};
|
|
9
|
+
const iwm = new IterableWeakMap([[ref, value]]);
|
|
10
|
+
|
|
11
|
+
const entries = Array.from(iwm.entries());
|
|
12
|
+
expect(entries).toEqual([[ref, value]]);
|
|
13
|
+
});
|
|
14
|
+
});
|
|
15
|
+
|
|
16
|
+
describe("#set", () => {
|
|
17
|
+
it("should add new value", function () {
|
|
18
|
+
const iwm = new IterableWeakMap();
|
|
19
|
+
const ref = {};
|
|
20
|
+
const value = {};
|
|
21
|
+
|
|
22
|
+
iwm.set(ref, value);
|
|
23
|
+
|
|
24
|
+
const entries = Array.from(iwm.entries());
|
|
25
|
+
expect(entries).toEqual([[ref, value]]);
|
|
26
|
+
});
|
|
27
|
+
});
|
|
28
|
+
|
|
29
|
+
describe("#get", () => {
|
|
30
|
+
it("should return value if ref exists in Map", function () {
|
|
31
|
+
const iwm = new IterableWeakMap();
|
|
32
|
+
const ref = {};
|
|
33
|
+
const value = {};
|
|
34
|
+
|
|
35
|
+
iwm.set(ref, value);
|
|
36
|
+
|
|
37
|
+
const getValue = iwm.get(ref);
|
|
38
|
+
expect(getValue).toEqual(value);
|
|
39
|
+
});
|
|
40
|
+
|
|
41
|
+
it("should return undefined if ref doesn't exist in Map", function () {
|
|
42
|
+
const iwm = new IterableWeakMap();
|
|
43
|
+
const ref = {};
|
|
44
|
+
const value = {};
|
|
45
|
+
const ref2 = {};
|
|
46
|
+
|
|
47
|
+
iwm.set(ref, value);
|
|
48
|
+
|
|
49
|
+
const getValue = iwm.get(ref2);
|
|
50
|
+
expect(getValue).toBeUndefined();
|
|
51
|
+
});
|
|
52
|
+
});
|
|
53
|
+
|
|
54
|
+
describe("#delete", () => {
|
|
55
|
+
it("should delete value from Map and return true", function () {
|
|
56
|
+
const iwm = new IterableWeakMap();
|
|
57
|
+
const ref = {};
|
|
58
|
+
const value = {};
|
|
59
|
+
|
|
60
|
+
iwm.set(ref, value);
|
|
61
|
+
|
|
62
|
+
const res = iwm.delete(ref);
|
|
63
|
+
|
|
64
|
+
expect(iwm.size).toBe(0);
|
|
65
|
+
expect(res).toBeTruthy();
|
|
66
|
+
});
|
|
67
|
+
|
|
68
|
+
it("should return false if there is no ref in Map", function () {
|
|
69
|
+
const iwm = new IterableWeakMap();
|
|
70
|
+
const ref = {};
|
|
71
|
+
const value = {};
|
|
72
|
+
const refToDelete = {};
|
|
73
|
+
|
|
74
|
+
iwm.set(ref, value);
|
|
75
|
+
|
|
76
|
+
const res = iwm.delete(refToDelete);
|
|
77
|
+
|
|
78
|
+
expect(iwm.size).toBe(1);
|
|
79
|
+
expect(res).toBeFalsy();
|
|
80
|
+
});
|
|
81
|
+
});
|
|
82
|
+
|
|
83
|
+
describe("#size", () => {
|
|
84
|
+
it("should return size of Map", function () {
|
|
85
|
+
const iwm = new IterableWeakMap();
|
|
86
|
+
const ref = {};
|
|
87
|
+
const value = {};
|
|
88
|
+
const ref2 = {};
|
|
89
|
+
const value2 = {};
|
|
90
|
+
|
|
91
|
+
iwm.set(ref, value);
|
|
92
|
+
iwm.set(ref2, value2);
|
|
93
|
+
|
|
94
|
+
expect(iwm.size).toBe(2);
|
|
95
|
+
});
|
|
96
|
+
});
|
|
97
|
+
|
|
98
|
+
describe("#has", () => {
|
|
99
|
+
it("should return true if map has ref", function () {
|
|
100
|
+
const iwm = new IterableWeakMap();
|
|
101
|
+
const ref = {};
|
|
102
|
+
const value = {};
|
|
103
|
+
|
|
104
|
+
iwm.set(ref, value);
|
|
105
|
+
|
|
106
|
+
expect(iwm.has(ref)).toBe(true);
|
|
107
|
+
});
|
|
108
|
+
|
|
109
|
+
it("should return false if map doesn't have ref", function () {
|
|
110
|
+
const iwm = new IterableWeakMap();
|
|
111
|
+
const ref = {};
|
|
112
|
+
const value = {};
|
|
113
|
+
const ref2 = {};
|
|
114
|
+
|
|
115
|
+
iwm.set(ref, value);
|
|
116
|
+
|
|
117
|
+
expect(iwm.has(ref2)).toBe(false);
|
|
118
|
+
});
|
|
119
|
+
});
|
|
120
|
+
|
|
121
|
+
describe("#clear", () => {
|
|
122
|
+
it("should delete all refs from Map", function () {
|
|
123
|
+
const iwm = new IterableWeakMap();
|
|
124
|
+
const ref = {};
|
|
125
|
+
const value = {};
|
|
126
|
+
const ref2 = {};
|
|
127
|
+
const value2 = {};
|
|
128
|
+
|
|
129
|
+
iwm.set(ref, value);
|
|
130
|
+
iwm.set(ref2, value2);
|
|
131
|
+
|
|
132
|
+
expect(iwm.size).toBe(2);
|
|
133
|
+
|
|
134
|
+
iwm.clear();
|
|
135
|
+
|
|
136
|
+
expect(iwm.size).toBe(0);
|
|
137
|
+
});
|
|
138
|
+
});
|
|
139
|
+
|
|
140
|
+
describe("#forEach", () => {
|
|
141
|
+
it("should iterate over all entries in Map", function () {
|
|
142
|
+
const iwm = new IterableWeakMap();
|
|
143
|
+
const ref = {};
|
|
144
|
+
const value = {};
|
|
145
|
+
const ref2 = {};
|
|
146
|
+
const value2 = {};
|
|
147
|
+
|
|
148
|
+
iwm.set(ref, value);
|
|
149
|
+
iwm.set(ref2, value2);
|
|
150
|
+
|
|
151
|
+
const res: [object, object, IterableWeakMap<any, any>][] = [];
|
|
152
|
+
|
|
153
|
+
iwm.forEach((v, k, map) => {
|
|
154
|
+
res.push([v, k, map]);
|
|
155
|
+
});
|
|
156
|
+
|
|
157
|
+
expect(res).toEqual([
|
|
158
|
+
[ref, value, iwm],
|
|
159
|
+
[ref2, value2, iwm],
|
|
160
|
+
]);
|
|
161
|
+
});
|
|
162
|
+
});
|
|
163
|
+
|
|
164
|
+
describe("#keys", () => {
|
|
165
|
+
it("should return all keys in Map", function () {
|
|
166
|
+
const iwm = new IterableWeakMap();
|
|
167
|
+
const ref = {};
|
|
168
|
+
const value = {};
|
|
169
|
+
const ref2 = {};
|
|
170
|
+
const value2 = {};
|
|
171
|
+
|
|
172
|
+
iwm.set(ref, value);
|
|
173
|
+
iwm.set(ref2, value2);
|
|
174
|
+
|
|
175
|
+
const res = Array.from(iwm.keys());
|
|
176
|
+
|
|
177
|
+
expect(res).toEqual([ref, ref2]);
|
|
178
|
+
});
|
|
179
|
+
});
|
|
180
|
+
|
|
181
|
+
describe("#valeus", () => {
|
|
182
|
+
it("should return all values in Map", function () {
|
|
183
|
+
const iwm = new IterableWeakMap();
|
|
184
|
+
const ref = {};
|
|
185
|
+
const value = {};
|
|
186
|
+
const ref2 = {};
|
|
187
|
+
const value2 = {};
|
|
188
|
+
|
|
189
|
+
iwm.set(ref, value);
|
|
190
|
+
iwm.set(ref2, value2);
|
|
191
|
+
|
|
192
|
+
const res = Array.from(iwm.values());
|
|
193
|
+
|
|
194
|
+
expect(res).toEqual([value, value2]);
|
|
195
|
+
});
|
|
196
|
+
});
|
|
197
|
+
}
|
|
198
|
+
|
|
199
|
+
describe("environment supports WeakRef and FinalizationRegistry", () => {
|
|
200
|
+
runCommonTests();
|
|
201
|
+
|
|
202
|
+
describe("memory", () => {
|
|
203
|
+
let originalFinalizationRegistry: FinalizationRegistry<any>;
|
|
204
|
+
let cleanupMemory = (ref: any) => {};
|
|
205
|
+
|
|
206
|
+
beforeEach(() => {
|
|
207
|
+
originalFinalizationRegistry = FinalizationRegistry as any;
|
|
208
|
+
globalThis.FinalizationRegistry = function (
|
|
209
|
+
cleanupCb: (heldValue: any) => void
|
|
210
|
+
) {
|
|
211
|
+
const heldValueSet = new Map();
|
|
212
|
+
|
|
213
|
+
cleanupMemory = (ref) => {
|
|
214
|
+
const heldValue = heldValueSet.get(ref);
|
|
215
|
+
|
|
216
|
+
cleanupCb(heldValue);
|
|
217
|
+
};
|
|
218
|
+
|
|
219
|
+
return {
|
|
220
|
+
register(target: object, heldValue: any, unregisterToken?: object) {
|
|
221
|
+
heldValueSet.set(target, heldValue);
|
|
222
|
+
},
|
|
223
|
+
unregister() {},
|
|
224
|
+
} as unknown as FinalizationRegistry<any>;
|
|
225
|
+
} as any;
|
|
226
|
+
});
|
|
227
|
+
|
|
228
|
+
afterEach(() => {
|
|
229
|
+
globalThis.FinalizationRegistry = originalFinalizationRegistry as any;
|
|
230
|
+
});
|
|
231
|
+
|
|
232
|
+
it("should be auto cleaned when ref in Map is freeing in program", function () {
|
|
233
|
+
const iwm = new IterableWeakMap();
|
|
234
|
+
const ref = {};
|
|
235
|
+
const value = {};
|
|
236
|
+
const ref2 = {};
|
|
237
|
+
const value2 = {};
|
|
238
|
+
|
|
239
|
+
iwm.set(ref, value);
|
|
240
|
+
iwm.set(ref2, value2);
|
|
241
|
+
|
|
242
|
+
expect(iwm.size).toBe(2);
|
|
243
|
+
expect(Array.from(iwm.entries())).toEqual([
|
|
244
|
+
[ref, value],
|
|
245
|
+
[ref2, value2],
|
|
246
|
+
]);
|
|
247
|
+
|
|
248
|
+
// emulate freeing "ref" in memory
|
|
249
|
+
cleanupMemory(ref);
|
|
250
|
+
|
|
251
|
+
expect(iwm.size).toBe(1);
|
|
252
|
+
expect(Array.from(iwm.entries())).toEqual([[ref2, value2]]);
|
|
253
|
+
});
|
|
254
|
+
});
|
|
255
|
+
});
|
|
256
|
+
|
|
257
|
+
describe("environment doesn't support WeakRef and FinalizationRegistry", () => {
|
|
258
|
+
let originalWeakRef: WeakRefConstructor | undefined;
|
|
259
|
+
let originalFinalizationRegistry:
|
|
260
|
+
| FinalizationRegistryConstructor
|
|
261
|
+
| undefined;
|
|
262
|
+
|
|
263
|
+
beforeAll(() => {
|
|
264
|
+
originalWeakRef = global.WeakRef;
|
|
265
|
+
// @ts-ignore
|
|
266
|
+
delete global.WeakRef;
|
|
267
|
+
originalFinalizationRegistry = global.FinalizationRegistry;
|
|
268
|
+
// @ts-ignore
|
|
269
|
+
delete global.FinalizationRegistry;
|
|
270
|
+
});
|
|
271
|
+
|
|
272
|
+
afterAll(() => {
|
|
273
|
+
if (originalWeakRef && originalFinalizationRegistry) {
|
|
274
|
+
global.WeakRef = originalWeakRef;
|
|
275
|
+
originalWeakRef = undefined;
|
|
276
|
+
|
|
277
|
+
global.FinalizationRegistry = originalFinalizationRegistry;
|
|
278
|
+
originalFinalizationRegistry = undefined;
|
|
279
|
+
}
|
|
280
|
+
});
|
|
281
|
+
|
|
282
|
+
runCommonTests();
|
|
283
|
+
});
|
|
284
|
+
});
|
|
@@ -0,0 +1,58 @@
|
|
|
1
|
+
import { EntryPoint, SlotKey } from '../src/API'
|
|
2
|
+
|
|
3
|
+
export const createCircularEntryPoints = (usePublicAPIKeys: boolean = false): EntryPoint[] => {
|
|
4
|
+
const MockAPI1: SlotKey<{}> = { name: 'Mock-API-1', public: usePublicAPIKeys }
|
|
5
|
+
const MockAPI2: SlotKey<{}> = { name: 'Mock-API-2', public: usePublicAPIKeys }
|
|
6
|
+
const MockAPI3: SlotKey<{}> = { name: 'Mock-API-3', public: usePublicAPIKeys }
|
|
7
|
+
const MockAPI4: SlotKey<{}> = { name: 'Mock-API-4', public: usePublicAPIKeys }
|
|
8
|
+
|
|
9
|
+
const ep1Deps = usePublicAPIKeys
|
|
10
|
+
? [
|
|
11
|
+
{ name: 'Mock-API-2', public: true },
|
|
12
|
+
{ name: 'Mock-API-3', public: true }
|
|
13
|
+
]
|
|
14
|
+
: [MockAPI2, MockAPI3]
|
|
15
|
+
const ep2Deps = usePublicAPIKeys ? [{ name: 'Mock-API-4', public: true }] : [MockAPI4]
|
|
16
|
+
const ep3Deps = usePublicAPIKeys ? [{ name: 'Mock-API-4', public: true }] : [MockAPI4]
|
|
17
|
+
const ep4Deps = usePublicAPIKeys ? [{ name: 'Mock-API-1', public: true }] : [MockAPI1]
|
|
18
|
+
|
|
19
|
+
return [
|
|
20
|
+
{
|
|
21
|
+
name: 'MOCK_ENTRY_POINT_1',
|
|
22
|
+
getDependencyAPIs: () => ep1Deps,
|
|
23
|
+
declareAPIs: () => [MockAPI1]
|
|
24
|
+
},
|
|
25
|
+
{
|
|
26
|
+
name: 'MOCK_ENTRY_POINT_2',
|
|
27
|
+
getDependencyAPIs: () => ep2Deps,
|
|
28
|
+
declareAPIs: () => [MockAPI2]
|
|
29
|
+
},
|
|
30
|
+
{
|
|
31
|
+
name: 'MOCK_ENTRY_POINT_3',
|
|
32
|
+
getDependencyAPIs: () => ep3Deps,
|
|
33
|
+
declareAPIs: () => [MockAPI3]
|
|
34
|
+
},
|
|
35
|
+
{
|
|
36
|
+
name: 'MOCK_ENTRY_POINT_4',
|
|
37
|
+
getDependencyAPIs: () => ep4Deps,
|
|
38
|
+
declareAPIs: () => [MockAPI4]
|
|
39
|
+
}
|
|
40
|
+
]
|
|
41
|
+
}
|
|
42
|
+
|
|
43
|
+
export const createDirectCircularEntryPoints = (usePublicAPIKeys: boolean = false): EntryPoint[] => {
|
|
44
|
+
const MockAPI1: SlotKey<{}> = { name: 'Mock-API-1', public: usePublicAPIKeys }
|
|
45
|
+
const MockAPI2: SlotKey<{}> = { name: 'Mock-API-2', public: usePublicAPIKeys }
|
|
46
|
+
return [
|
|
47
|
+
{
|
|
48
|
+
name: 'MOCK_ENTRY_POINT_1',
|
|
49
|
+
getDependencyAPIs: () => [usePublicAPIKeys ? { name: 'Mock-API-2', public: true } : MockAPI2],
|
|
50
|
+
declareAPIs: () => [MockAPI1]
|
|
51
|
+
},
|
|
52
|
+
{
|
|
53
|
+
name: 'MOCK_ENTRY_POINT_2',
|
|
54
|
+
getDependencyAPIs: () => [usePublicAPIKeys ? { name: 'Mock-API-1', public: true } : MockAPI1],
|
|
55
|
+
declareAPIs: () => [MockAPI2]
|
|
56
|
+
}
|
|
57
|
+
]
|
|
58
|
+
}
|