Skip to content

Commit

Permalink
Regression fix - properly handle mute state per specific epic, make s…
Browse files Browse the repository at this point in the history
…ure that if at least one plugin intended to register epic and such plugin is on the page - epic will not be muted.
  • Loading branch information
alexander-fedorenko committed Aug 19, 2022
1 parent d606efe commit 9ebe144
Show file tree
Hide file tree
Showing 2 changed files with 47 additions and 20 deletions.
15 changes: 8 additions & 7 deletions web/client/hooks/useModulePlugins.js
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@
*/

import {useEffect, useMemo, useState} from 'react';
import {createPlugin, getPlugins, isMapStorePlugin} from '../utils/PluginsUtils';
import {createPlugin, getPlugins, isMapStorePlugin, normalizeName} from '../utils/PluginsUtils';
import {getStore} from '../utils/StateUtils';
import join from 'lodash/join';
import {size} from "lodash";
Expand Down Expand Up @@ -41,13 +41,14 @@ function useModulePlugins({
}) {
const [plugins, setPlugins] = useState(storedPlugins);
const [pending, setPending] = useState(true);

const normalizedEntries = useMemo(
() => Object.keys(pluginsEntries).reduce((prev, current) => ({...prev, [normalizeName(current)]: pluginsEntries[current]}), {}),
[pluginsEntries]
);
const pluginsKeys = useMemo(() => pluginsConfig.reduce((prev, curr) => {
const key = curr?.name ?? curr;
if (pluginsEntries[key]) {
const key = normalizeName(curr?.name ?? curr);
if (normalizedEntries[key]) {
return [ ...prev, key];
} else if (pluginsEntries[key + 'Plugin']) {
return [ ...prev, key + 'Plugin'];
}
return prev;
}, []),
Expand All @@ -61,7 +62,7 @@ function useModulePlugins({
setPending(true);
const loadPlugins = filteredPluginsKeys
.map(pluginName => {
return pluginsEntries[pluginName]().then((mod) => {
return normalizedEntries[pluginName]().then((mod) => {
return mod.default;
});
});
Expand Down
52 changes: 39 additions & 13 deletions web/client/utils/StateUtils.js
Original file line number Diff line number Diff line change
Expand Up @@ -130,6 +130,10 @@ export const createStoreManager = (initialReducers, initialEpics) => {
// Create an object which maps keys to reducers
const reducers = {...initialReducers};
const epics = {...initialEpics};
const addedEpics = {};
const epicsListenedBy = {};
const epicRegistrations = {};
const groupedByModule = {};

// Create the initial combinedReducer
let combinedReducer = combineReducers(reducers);
Expand All @@ -144,6 +148,12 @@ export const createStoreManager = (initialReducers, initialEpics) => {

let muteState = {};

const addToRegistry = (module, epicName) => {
epicRegistrations[epicName] = [...(epicRegistrations[epicName] ?? []), module];
groupedByModule[module] = [...(groupedByModule[module] ?? []), epicName];
epicsListenedBy[epicName] = [...(epicsListenedBy[epicName] ?? []), module];
};

return {
getReducerMap: () => reducers,

Expand Down Expand Up @@ -196,30 +206,46 @@ export const createStoreManager = (initialReducers, initialEpics) => {
addEpics: (key, epicsList) => {
if (Object.keys(epicsList).length) {
const epicsToAdd = Object.keys(epicsList).reduce((prev, current) => {
if (!epics[current]) {
epics[current] = epicsList[current];
if (!addedEpics[current]) {
addedEpics[current] = key;
addToRegistry(key, current);
return ({...prev, [current]: epicsList[current]});
}
addToRegistry(key, current);
return prev;
}, {});
const normalizedName = normalizeName(key);
muteState[normalizedName] = new Subject();
const isolatedEpics = isolateEpics(epicsToAdd, muteState[normalizedName].asObservable());
const isolatedEpics = isolateEpics(epicsToAdd, muteState);
wrapEpics(isolatedEpics).forEach(epic => epic$.next(epic));
}
},
// Mute epics set with a specified key
muteEpics: (key) => {
const normalizedName = normalizeName(key);
if (typeof muteState[normalizedName] !== 'undefined') {
muteState[normalizedName].next(false);
}
const moduleEpicRegistrations = groupedByModule[key];
// try to mute everything registered by module. If epic is shared, remove current module from epicsListenedBy
moduleEpicRegistrations && moduleEpicRegistrations.forEach(epicName => {
const indexOf = epicsListenedBy[epicName].indexOf(key);
if (indexOf >= 0) {
delete epicsListenedBy[epicName][indexOf];
}
// check if epic is still listened by anything. If not - mute it
if (!epicsListenedBy[epicName].length) {
muteState[epicName].next(false);
}
});
},
unmuteEpics: (key) => {
const normalizedName = normalizeName(key);
if (typeof muteState[normalizedName] !== 'undefined') {
muteState[normalizedName].next(true);
}
const moduleEpicRegistrations = groupedByModule[key];
// unmute epics if exactly one plugin wants to register specific epic
moduleEpicRegistrations && moduleEpicRegistrations.forEach(epicName => {
const indexOf = epicsListenedBy[epicName].indexOf(key);
if (indexOf === -1) {
epicsListenedBy[epicName].push(key);
}
// now if epic intended to be registered by first listener plugin - unmute it
if (epicsListenedBy[epicName].length === 1) {
muteState[epicName].next(true);
}
});
},
rootEpic: (...args) => epic$.mergeMap(e => e(...args))
};
Expand Down

0 comments on commit 9ebe144

Please sign in to comment.