zustand-duck
Version:
Simple reducer writing and cross-process state sharing.
57 lines • 2 kB
JavaScript
const rawDuck = (options) => (set, get, api) => {
const { actionRewrite, initialize, reducers, state } = options;
const listeners = [];
const originActions = { reset: () => set({ ...state }, true) };
const actions = { ...originActions };
let readyResolve = (value) => { };
const readyPromise = new Promise(resolve => {
readyResolve = resolve;
});
Object.keys(reducers).forEach(action => {
originActions[action] = (...args) => {
set((state) => reducers[action](state, ...args), true);
listeners.forEach(item => {
if (action === item.action) {
item.listener(...args);
}
});
return args;
};
});
Object.keys(originActions).forEach(action => {
actions[action] = actionRewrite
? (...payload) => actionRewrite({ action, payload }, originActions[action])
: originActions[action];
});
const newAPI = api;
newAPI.actions = actions;
newAPI.originActions = originActions;
newAPI.ready = () => readyPromise;
newAPI.wait = async (condition) => {
await readyPromise;
return new Promise(resolve => {
if (condition(newAPI.getState())) {
resolve(newAPI);
return;
}
const unsubscribe = newAPI.subscribe((state) => {
if (condition(state)) {
unsubscribe();
resolve(newAPI);
}
});
});
};
newAPI.onAction = (action, listener) => {
const data = { action, listener };
listeners.push(data);
return () => {
const index = listeners.findIndex(item => item === data);
listeners.splice(index, 1);
};
};
initialize ? initialize(newAPI, readyResolve) : readyResolve(newAPI);
return { ...state };
};
export const duck = rawDuck;
//# sourceMappingURL=duck.js.map