UNPKG

@flopflip/react-redux

Version:

A feature toggle wrapper to use LaunchDarkly with React Redux

368 lines (367 loc) 14.7 kB
Object.defineProperty(exports, Symbol.toStringTag, { value: "Module" }); //#region \0rolldown/runtime.js var __create = Object.create; var __defProp = Object.defineProperty; var __getOwnPropDesc = Object.getOwnPropertyDescriptor; var __getOwnPropNames = Object.getOwnPropertyNames; var __getProtoOf = Object.getPrototypeOf; var __hasOwnProp = Object.prototype.hasOwnProperty; var __copyProps = (to, from, except, desc) => { if (from && typeof from === "object" || typeof from === "function") for (var keys = __getOwnPropNames(from), i = 0, n = keys.length, key; i < n; i++) { key = keys[i]; if (!__hasOwnProp.call(to, key) && key !== except) __defProp(to, key, { get: ((k) => from[k]).bind(null, key), enumerable: !(desc = __getOwnPropDesc(from, key)) || desc.enumerable }); } return to; }; var __toESM = (mod, isNodeMode, target) => (target = mod != null ? __create(__getProtoOf(mod)) : {}, __copyProps(isNodeMode || !mod || !mod.__esModule ? __defProp(target, "default", { value: mod, enumerable: true }) : target, mod)); //#endregion let react = require("react"); react = __toESM(react, 1); let _flopflip_react = require("@flopflip/react"); let react_redux = require("react-redux"); let _reduxjs_toolkit = require("@reduxjs/toolkit"); let _flopflip_types = require("@flopflip/types"); //#region src/constants.ts const STATE_SLICE = "@flopflip"; //#endregion //#region \0@oxc-project+runtime@0.134.0/helpers/esm/typeof.js function _typeof(o) { "@babel/helpers - typeof"; return _typeof = "function" == typeof Symbol && "symbol" == typeof Symbol.iterator ? function(o) { return typeof o; } : function(o) { return o && "function" == typeof Symbol && o.constructor === Symbol && o !== Symbol.prototype ? "symbol" : typeof o; }, _typeof(o); } //#endregion //#region \0@oxc-project+runtime@0.134.0/helpers/esm/toPrimitive.js function toPrimitive(t, r) { if ("object" != _typeof(t) || !t) return t; var e = t[Symbol.toPrimitive]; if (void 0 !== e) { var i = e.call(t, r || "default"); if ("object" != _typeof(i)) return i; throw new TypeError("@@toPrimitive must return a primitive value."); } return ("string" === r ? String : Number)(t); } //#endregion //#region \0@oxc-project+runtime@0.134.0/helpers/esm/toPropertyKey.js function toPropertyKey(t) { var i = toPrimitive(t, "string"); return "symbol" == _typeof(i) ? i : i + ""; } //#endregion //#region \0@oxc-project+runtime@0.134.0/helpers/esm/defineProperty.js function _defineProperty(e, r, t) { return (r = toPropertyKey(r)) in e ? Object.defineProperty(e, r, { value: t, enumerable: !0, configurable: !0, writable: !0 }) : e[r] = t, e; } //#endregion //#region \0@oxc-project+runtime@0.134.0/helpers/esm/objectSpread2.js function ownKeys(e, r) { var t = Object.keys(e); if (Object.getOwnPropertySymbols) { var o = Object.getOwnPropertySymbols(e); r && (o = o.filter(function(r) { return Object.getOwnPropertyDescriptor(e, r).enumerable; })), t.push.apply(t, o); } return t; } function _objectSpread2(e) { for (var r = 1; r < arguments.length; r++) { var t = null != arguments[r] ? arguments[r] : {}; r % 2 ? ownKeys(Object(t), !0).forEach(function(r) { _defineProperty(e, r, t[r]); }) : Object.getOwnPropertyDescriptors ? Object.defineProperties(e, Object.getOwnPropertyDescriptors(t)) : ownKeys(Object(t)).forEach(function(r) { Object.defineProperty(e, r, Object.getOwnPropertyDescriptor(t, r)); }); } return e; } //#endregion //#region src/ducks/flags.ts const initialState = { memory: {} }; const flagsSlice = (0, _reduxjs_toolkit.createSlice)({ name: "flags", initialState, reducers: { updateFlags: { reducer(state, action) { if (action.payload.id) { state[action.payload.id] = _objectSpread2(_objectSpread2({}, state[action.payload.id]), action.payload.flags); return; } for (const adapterId of action.payload.adapterIdentifiers) state[adapterId] = _objectSpread2(_objectSpread2({}, state[adapterId]), action.payload.flags); }, prepare(flagsChange, adapterIdentifiers) { return { payload: _objectSpread2(_objectSpread2({}, flagsChange), {}, { adapterIdentifiers }) }; } } } }); const { updateFlags } = flagsSlice.actions; const reducer$1 = flagsSlice.reducer; const createReducer = (preloadedState = initialState) => { return (state = preloadedState, action) => reducer$1(state, action); }; const selectFlags = () => (state) => { var _state$STATE_SLICE$fl; return (_state$STATE_SLICE$fl = state["@flopflip"].flags) !== null && _state$STATE_SLICE$fl !== void 0 ? _state$STATE_SLICE$fl : {}; }; const selectFlag = (flagName, adapterIdentifiers) => (state) => { const allFlags = selectFlags()(state); let foundFlagVariation = false; for (const adapterId of adapterIdentifiers) { var _allFlags$adapterId; const flagValue = (_allFlags$adapterId = allFlags[adapterId]) === null || _allFlags$adapterId === void 0 ? void 0 : _allFlags$adapterId[flagName]; if (!(0, _flopflip_react.isNil)(flagValue)) foundFlagVariation = flagValue; } return foundFlagVariation; }; //#endregion //#region src/use-feature-toggle.ts function useFeatureToggle(flagName, flagVariation = true) { const adapterContext = (0, _flopflip_react.useAdapterContext)(); const isFeatureEnabled = (0, _flopflip_react.getIsFeatureEnabled)((0, react_redux.useSelector)(selectFlags()), adapterContext.adapterEffectIdentifiers, flagName, flagVariation); (0, react.useDebugValue)({ flagName, flagVariation, isEnabled: isFeatureEnabled }); return isFeatureEnabled; } //#endregion //#region src/branch-on-feature-toggle.tsx function branchOnFeatureToggle({ flag: flagName, variation: flagVariation }, UntoggledComponent) { return (ToggledComponent) => { function WrappedToggledComponent(ownProps) { if (useFeatureToggle(flagName, flagVariation)) return /* @__PURE__ */ react.default.createElement(ToggledComponent, ownProps); if (UntoggledComponent) return /* @__PURE__ */ react.default.createElement(UntoggledComponent, ownProps); return null; } return WrappedToggledComponent; }; } //#endregion //#region src/use-update-flags.ts const useUpdateFlags = ({ adapterIdentifiers }) => { const dispatch = (0, react_redux.useDispatch)(); return (0, react.useCallback)((flagsChange) => dispatch(updateFlags(flagsChange, adapterIdentifiers)), [dispatch, adapterIdentifiers]); }; //#endregion //#region src/ducks/status.ts const statusSlice = (0, _reduxjs_toolkit.createSlice)({ name: "status", initialState: {}, reducers: { updateStatus: { reducer(state, action) { if (action.payload.id) { state[action.payload.id] = _objectSpread2(_objectSpread2({}, state[action.payload.id]), action.payload.status); return; } for (const adapterInterfaceIdentifier of action.payload.adapterIdentifiers) state[adapterInterfaceIdentifier] = _objectSpread2(_objectSpread2({}, state[adapterInterfaceIdentifier]), action.payload.status); }, prepare(statusChange, adapterIdentifiers) { return { payload: _objectSpread2(_objectSpread2({}, statusChange), {}, { adapterIdentifiers }) }; } } } }); const { updateStatus } = statusSlice.actions; const reducer = statusSlice.reducer; const selectStatus = ({ adapterIdentifiers } = {}) => (state) => { const { status } = state[STATE_SLICE]; return (0, _flopflip_react.selectAdapterConfigurationStatus)(status, adapterIdentifiers); }; //#endregion //#region src/use-update-status.ts const useUpdateStatus = () => { const dispatch = (0, react_redux.useDispatch)(); return (0, react.useCallback)((statusChange) => dispatch(updateStatus(statusChange, Object.keys(_flopflip_types.adapterIdentifiers))), [dispatch]); }; //#endregion //#region src/configure.tsx function Configure({ adapter, adapterArgs, children, defaultFlags = {}, shouldDeferAdapterConfiguration = false }) { const handleUpdateFlags = useUpdateFlags({ adapterIdentifiers: [adapter.id] }); const handleUpdateStatus = useUpdateStatus(); (0, _flopflip_react.useAdapterSubscription)(adapter); return /* @__PURE__ */ react.default.createElement(_flopflip_react.ConfigureAdapter, { adapter, adapterArgs, defaultFlags, shouldDeferAdapterConfiguration, onFlagsStateChange: handleUpdateFlags, onStatusStateChange: handleUpdateStatus }, children); } Configure.displayName = "ConfigureFlopflip"; //#endregion //#region src/ducks/index.ts const flopflipReducer = (0, _reduxjs_toolkit.combineReducers)({ flags: reducer$1, status: reducer }); const createFlopflipReducer = (preloadedState = { memory: {} }) => (0, _reduxjs_toolkit.combineReducers)({ flags: createReducer(preloadedState), status: reducer }); //#endregion //#region src/enhancer.ts const configureAdapter = (0, _reduxjs_toolkit.createAction)("flopflip/configureAdapter"); function createFlopFlipEnhancer(adapter, adapterArgs) { return (next) => (...args) => { const store = next(...args); store.dispatch(configureAdapter({ adapter, adapterArgs })); adapter.configure(adapterArgs, { onFlagsStateChange: (flagsChange) => { store.dispatch(updateFlags(flagsChange, [adapter.id])); }, onStatusStateChange: (statusChange) => { store.dispatch(updateStatus(statusChange, Object.keys(_flopflip_types.adapterIdentifiers))); } }); return store; }; } //#endregion //#region src/use-flag-variations.ts function useFlagVariations(flagNames) { const adapterContext = (0, _flopflip_react.useAdapterContext)(); const allFlags = (0, react_redux.useSelector)(selectFlags()); return flagNames.map((requestedVariation) => (0, _flopflip_react.getFlagVariation)(allFlags, adapterContext.adapterEffectIdentifiers, requestedVariation)); } //#endregion //#region src/inject-feature-toggle.tsx const injectFeatureToggle = (flagName, propKey = _flopflip_react.DEFAULT_FLAG_PROP_KEY) => (Component) => { function WrappedComponent(ownProps) { const [flagVariation] = useFlagVariations([flagName]); const props = _objectSpread2(_objectSpread2({}, ownProps), {}, { [propKey]: flagVariation }); return /* @__PURE__ */ react.default.createElement(Component, props); } (0, _flopflip_react.setDisplayName)((0, _flopflip_react.wrapDisplayName)(WrappedComponent, "injectFeatureToggle")); return WrappedComponent; }; //#endregion //#region src/inject-feature-toggles.tsx const injectFeatureToggles = (flagNames, propKey = _flopflip_react.DEFAULT_FLAGS_PROP_KEY) => (Component) => { function WrappedComponent(ownProps) { const flagVariations = useFlagVariations(flagNames); const flags = Object.fromEntries(flagNames.map((flagName, indexOfFlagName) => [flagName, flagVariations[indexOfFlagName]])); const props = _objectSpread2(_objectSpread2({}, ownProps), {}, { [propKey]: flags }); return /* @__PURE__ */ react.default.createElement(Component, props); } (0, _flopflip_react.setDisplayName)((0, _flopflip_react.wrapDisplayName)(WrappedComponent, "injectFeatureToggles")); return WrappedComponent; }; //#endregion //#region \0@oxc-project+runtime@0.134.0/helpers/esm/objectWithoutPropertiesLoose.js function _objectWithoutPropertiesLoose(r, e) { if (null == r) return {}; var t = {}; for (var n in r) if ({}.hasOwnProperty.call(r, n)) { if (e.includes(n)) continue; t[n] = r[n]; } return t; } //#endregion //#region \0@oxc-project+runtime@0.134.0/helpers/esm/objectWithoutProperties.js function _objectWithoutProperties(e, t) { if (null == e) return {}; var o, r, i = _objectWithoutPropertiesLoose(e, t); if (Object.getOwnPropertySymbols) { var s = Object.getOwnPropertySymbols(e); for (r = 0; r < s.length; r++) o = s[r], t.includes(o) || {}.propertyIsEnumerable.call(e, o) && (i[o] = e[o]); } return i; } //#endregion //#region src/toggle-feature.tsx const _excluded = ["flag", "variation"]; function ToggleFeature(_ref) { let { flag, variation } = _ref, remainingProps = _objectWithoutProperties(_ref, _excluded); const isFeatureEnabled = useFeatureToggle(flag, variation); return /* @__PURE__ */ react.default.createElement(_flopflip_react.ToggleFeature, _objectSpread2(_objectSpread2({ flag, variation }, remainingProps), {}, { isFeatureEnabled })); } ToggleFeature.displayName = "ToggleFeature"; //#endregion //#region src/use-adapter-status.ts function useAdapterStatus({ adapterIdentifiers } = {}) { const adapterStatus = (0, react_redux.useSelector)(selectStatus({ adapterIdentifiers })); (0, react.useDebugValue)({ adapterStatus }); return adapterStatus; } //#endregion //#region src/use-all-feature-toggles.ts function useAllFeatureToggles() { const adapterContext = (0, _flopflip_react.useAdapterContext)(); const allFlags = (0, react_redux.useSelector)(selectFlags()); return [...adapterContext.adapterEffectIdentifiers].toReversed().reduce((_allFlags, adapterIdentifier) => _objectSpread2(_objectSpread2({}, _allFlags), allFlags[adapterIdentifier]), {}); } //#endregion //#region src/use-feature-toggles.ts function useFeatureToggles(flags) { const allFlags = (0, react_redux.useSelector)(selectFlags()); const adapterContext = (0, _flopflip_react.useAdapterContext)(); return Object.entries(flags).reduce((previousFlags, [flagName, flagVariation]) => { const isFeatureEnabled = (0, _flopflip_react.getIsFeatureEnabled)(allFlags, adapterContext.adapterEffectIdentifiers, flagName, flagVariation); previousFlags.push(isFeatureEnabled); return previousFlags; }, []); } //#endregion //#region src/use-flag-variation.ts function useFlagVariation(flagName) { const [flagVariation] = useFlagVariations([flagName]); return flagVariation; } //#endregion //#region src/index.ts const version = "__@FLOPFLIP/VERSION_OF_RELEASE__"; //#endregion exports.ConfigureFlopFlip = Configure; exports.FLOPFLIP_STATE_SLICE = STATE_SLICE; Object.defineProperty(exports, "ReconfigureFlopFlip", { enumerable: true, get: function() { return _flopflip_react.ReconfigureAdapter; } }); exports.ToggleFeature = ToggleFeature; exports.branchOnFeatureToggle = branchOnFeatureToggle; exports.createFlopFlipEnhancer = createFlopFlipEnhancer; exports.createFlopflipReducer = createFlopflipReducer; exports.flopflipReducer = flopflipReducer; exports.injectFeatureToggle = injectFeatureToggle; exports.injectFeatureToggles = injectFeatureToggles; exports.selectFeatureFlag = selectFlag; exports.selectFeatureFlags = selectFlags; Object.defineProperty(exports, "useAdapterReconfiguration", { enumerable: true, get: function() { return _flopflip_react.useAdapterReconfiguration; } }); exports.useAdapterStatus = useAdapterStatus; exports.useAllFeatureToggles = useAllFeatureToggles; exports.useFeatureToggle = useFeatureToggle; exports.useFeatureToggles = useFeatureToggles; exports.useFlagVariation = useFlagVariation; exports.useFlagVariations = useFlagVariations; exports.version = version; //# sourceMappingURL=index.cjs.map