@depup/react-redux 9.3.0-depup.53

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 (48) hide show
  1. package/LICENSE.md +21 -0
  2. package/README.md +32 -0
  3. package/changes.json +14 -0
  4. package/dist/cjs/index.js +6 -0
  5. package/dist/cjs/react-redux.development.cjs +1119 -0
  6. package/dist/cjs/react-redux.development.cjs.map +1 -0
  7. package/dist/cjs/react-redux.production.min.cjs +6 -0
  8. package/dist/cjs/react-redux.production.min.cjs.map +1 -0
  9. package/dist/react-redux.browser.mjs +6 -0
  10. package/dist/react-redux.browser.mjs.map +1 -0
  11. package/dist/react-redux.d.ts +587 -0
  12. package/dist/react-redux.legacy-esm.js +1105 -0
  13. package/dist/react-redux.legacy-esm.js.map +1 -0
  14. package/dist/react-redux.mjs +1071 -0
  15. package/dist/react-redux.mjs.map +1 -0
  16. package/dist/rsc.mjs +46 -0
  17. package/dist/rsc.mjs.map +1 -0
  18. package/package.json +124 -0
  19. package/src/components/Context.ts +50 -0
  20. package/src/components/Provider.tsx +105 -0
  21. package/src/components/connect.tsx +845 -0
  22. package/src/connect/invalidArgFactory.ts +14 -0
  23. package/src/connect/mapDispatchToProps.ts +25 -0
  24. package/src/connect/mapStateToProps.ts +14 -0
  25. package/src/connect/mergeProps.ts +78 -0
  26. package/src/connect/selectorFactory.ts +242 -0
  27. package/src/connect/verifySubselectors.ts +26 -0
  28. package/src/connect/wrapMapToProps.ts +110 -0
  29. package/src/exports.ts +51 -0
  30. package/src/hooks/useDispatch.ts +104 -0
  31. package/src/hooks/useReduxContext.ts +42 -0
  32. package/src/hooks/useSelector.ts +286 -0
  33. package/src/hooks/useStore.ts +123 -0
  34. package/src/index-rsc.ts +35 -0
  35. package/src/index.ts +1 -0
  36. package/src/types.ts +180 -0
  37. package/src/utils/Subscription.ts +183 -0
  38. package/src/utils/batch.ts +4 -0
  39. package/src/utils/bindActionCreators.ts +16 -0
  40. package/src/utils/hoistStatics.ts +139 -0
  41. package/src/utils/isPlainObject.ts +17 -0
  42. package/src/utils/react-is.ts +97 -0
  43. package/src/utils/react.ts +3 -0
  44. package/src/utils/shallowEqual.ts +36 -0
  45. package/src/utils/useIsomorphicLayoutEffect.ts +40 -0
  46. package/src/utils/useSyncExternalStore.ts +9 -0
  47. package/src/utils/verifyPlainObject.ts +14 -0
  48. package/src/utils/warning.ts +21 -0
@@ -0,0 +1,42 @@
1
+ import { React } from '../utils/react'
2
+ import { ReactReduxContext } from '../components/Context'
3
+ import type { ReactReduxContextValue } from '../components/Context'
4
+
5
+ /**
6
+ * Hook factory, which creates a `useReduxContext` hook bound to a given context. This is a low-level
7
+ * hook that you should usually not need to call directly.
8
+ *
9
+ * @param {React.Context} [context=ReactReduxContext] Context passed to your `<Provider>`.
10
+ * @returns {Function} A `useReduxContext` hook bound to the specified context.
11
+ */
12
+ export function createReduxContextHook(context = ReactReduxContext) {
13
+ return function useReduxContext(): ReactReduxContextValue {
14
+ const contextValue = React.useContext(context)
15
+
16
+ if (process.env.NODE_ENV !== 'production' && !contextValue) {
17
+ throw new Error(
18
+ 'could not find react-redux context value; please ensure the component is wrapped in a <Provider>',
19
+ )
20
+ }
21
+
22
+ return contextValue!
23
+ }
24
+ }
25
+
26
+ /**
27
+ * A hook to access the value of the `ReactReduxContext`. This is a low-level
28
+ * hook that you should usually not need to call directly.
29
+ *
30
+ * @returns {any} the value of the `ReactReduxContext`
31
+ *
32
+ * @example
33
+ *
34
+ * import React from 'react'
35
+ * import { useReduxContext } from 'react-redux'
36
+ *
37
+ * export const CounterComponent = () => {
38
+ * const { store } = useReduxContext()
39
+ * return <div>{store.getState()}</div>
40
+ * }
41
+ */
42
+ export const useReduxContext = /*#__PURE__*/ createReduxContextHook()
@@ -0,0 +1,286 @@
1
+ //import * as React from 'react'
2
+ import { React } from '../utils/react'
3
+ import { useSyncExternalStoreWithSelector } from 'use-sync-external-store/with-selector.js'
4
+ import type { ReactReduxContextValue } from '../components/Context'
5
+ import { ReactReduxContext } from '../components/Context'
6
+ import type { EqualityFn, NoInfer } from '../types'
7
+ import {
8
+ createReduxContextHook,
9
+ useReduxContext as useDefaultReduxContext,
10
+ } from './useReduxContext'
11
+
12
+ /**
13
+ * The frequency of development mode checks.
14
+ *
15
+ * @since 8.1.0
16
+ * @internal
17
+ */
18
+ export type DevModeCheckFrequency = 'never' | 'once' | 'always'
19
+
20
+ /**
21
+ * Represents the configuration for development mode checks.
22
+ *
23
+ * @since 9.0.0
24
+ * @internal
25
+ */
26
+ export interface DevModeChecks {
27
+ /**
28
+ * Overrides the global stability check for the selector.
29
+ * - `once` - Run only the first time the selector is called.
30
+ * - `always` - Run every time the selector is called.
31
+ * - `never` - Never run the stability check.
32
+ *
33
+ * @default 'once'
34
+ *
35
+ * @since 8.1.0
36
+ */
37
+ stabilityCheck: DevModeCheckFrequency
38
+
39
+ /**
40
+ * Overrides the global identity function check for the selector.
41
+ * - `once` - Run only the first time the selector is called.
42
+ * - `always` - Run every time the selector is called.
43
+ * - `never` - Never run the identity function check.
44
+ *
45
+ * **Note**: Previously referred to as `noopCheck`.
46
+ *
47
+ * @default 'once'
48
+ *
49
+ * @since 9.0.0
50
+ */
51
+ identityFunctionCheck: DevModeCheckFrequency
52
+ }
53
+
54
+ export interface UseSelectorOptions<Selected = unknown> {
55
+ equalityFn?: EqualityFn<Selected>
56
+
57
+ /**
58
+ * `useSelector` performs additional checks in development mode to help
59
+ * identify and warn about potential issues in selector behavior. This
60
+ * option allows you to customize the behavior of these checks per selector.
61
+ *
62
+ * @since 9.0.0
63
+ */
64
+ devModeChecks?: Partial<DevModeChecks>
65
+ }
66
+
67
+ /**
68
+ * Represents a custom hook that allows you to extract data from the
69
+ * Redux store state, using a selector function. The selector function
70
+ * takes the current state as an argument and returns a part of the state
71
+ * or some derived data. The hook also supports an optional equality
72
+ * function or options object to customize its behavior.
73
+ *
74
+ * @template StateType - The specific type of state this hook operates on.
75
+ *
76
+ * @public
77
+ */
78
+ export interface UseSelector<StateType = unknown> {
79
+ /**
80
+ * A function that takes a selector function as its first argument.
81
+ * The selector function is responsible for selecting a part of
82
+ * the Redux store's state or computing derived data.
83
+ *
84
+ * @param selector - A function that receives the current state and returns a part of the state or some derived data.
85
+ * @param equalityFnOrOptions - An optional equality function or options object for customizing the behavior of the selector.
86
+ * @returns The selected part of the state or derived data.
87
+ *
88
+ * @template TState - The specific type of state this hook operates on.
89
+ * @template Selected - The type of the value that the selector function will return.
90
+ */
91
+ <TState extends StateType = StateType, Selected = unknown>(
92
+ selector: (state: TState) => Selected,
93
+ equalityFnOrOptions?: EqualityFn<Selected> | UseSelectorOptions<Selected>,
94
+ ): Selected
95
+
96
+ /**
97
+ * Creates a "pre-typed" version of {@linkcode useSelector useSelector}
98
+ * where the `state` type is predefined.
99
+ *
100
+ * This allows you to set the `state` type once, eliminating the need to
101
+ * specify it with every {@linkcode useSelector useSelector} call.
102
+ *
103
+ * @returns A pre-typed `useSelector` with the state type already defined.
104
+ *
105
+ * @example
106
+ * ```ts
107
+ * export const useAppSelector = useSelector.withTypes<RootState>()
108
+ * ```
109
+ *
110
+ * @template OverrideStateType - The specific type of state this hook operates on.
111
+ *
112
+ * @since 9.1.0
113
+ */
114
+ withTypes: <
115
+ OverrideStateType extends StateType,
116
+ >() => UseSelector<OverrideStateType>
117
+ }
118
+
119
+ const refEquality: EqualityFn<any> = (a, b) => a === b
120
+
121
+ /**
122
+ * Hook factory, which creates a `useSelector` hook bound to a given context.
123
+ *
124
+ * @param {React.Context} [context=ReactReduxContext] Context passed to your `<Provider>`.
125
+ * @returns {Function} A `useSelector` hook bound to the specified context.
126
+ */
127
+ export function createSelectorHook(
128
+ context: React.Context<ReactReduxContextValue<
129
+ any,
130
+ any
131
+ > | null> = ReactReduxContext,
132
+ ): UseSelector {
133
+ const useReduxContext =
134
+ context === ReactReduxContext
135
+ ? useDefaultReduxContext
136
+ : createReduxContextHook(context)
137
+
138
+ const useSelector = <TState, Selected>(
139
+ selector: (state: TState) => Selected,
140
+ equalityFnOrOptions:
141
+ | EqualityFn<NoInfer<Selected>>
142
+ | UseSelectorOptions<NoInfer<Selected>> = {},
143
+ ): Selected => {
144
+ const { equalityFn = refEquality } =
145
+ typeof equalityFnOrOptions === 'function'
146
+ ? { equalityFn: equalityFnOrOptions }
147
+ : equalityFnOrOptions
148
+ if (process.env.NODE_ENV !== 'production') {
149
+ if (!selector) {
150
+ throw new Error(`You must pass a selector to useSelector`)
151
+ }
152
+ if (typeof selector !== 'function') {
153
+ throw new Error(`You must pass a function as a selector to useSelector`)
154
+ }
155
+ if (typeof equalityFn !== 'function') {
156
+ throw new Error(
157
+ `You must pass a function as an equality function to useSelector`,
158
+ )
159
+ }
160
+ }
161
+
162
+ const reduxContext = useReduxContext()
163
+
164
+ const { store, subscription, getServerState } = reduxContext
165
+
166
+ const firstRun = React.useRef(true)
167
+
168
+ const wrappedSelector = React.useCallback<typeof selector>(
169
+ {
170
+ [selector.name](state: TState) {
171
+ const selected = selector(state)
172
+ if (process.env.NODE_ENV !== 'production') {
173
+ const { devModeChecks = {} } =
174
+ typeof equalityFnOrOptions === 'function'
175
+ ? {}
176
+ : equalityFnOrOptions
177
+ const { identityFunctionCheck, stabilityCheck } = reduxContext
178
+ const {
179
+ identityFunctionCheck: finalIdentityFunctionCheck,
180
+ stabilityCheck: finalStabilityCheck,
181
+ } = {
182
+ stabilityCheck,
183
+ identityFunctionCheck,
184
+ ...devModeChecks,
185
+ }
186
+ if (
187
+ finalStabilityCheck === 'always' ||
188
+ (finalStabilityCheck === 'once' && firstRun.current)
189
+ ) {
190
+ const toCompare = selector(state)
191
+ if (!equalityFn(selected, toCompare)) {
192
+ let stack: string | undefined = undefined
193
+ try {
194
+ throw new Error()
195
+ } catch (e) {
196
+ // eslint-disable-next-line no-extra-semi
197
+ ;({ stack } = e as Error)
198
+ }
199
+ console.warn(
200
+ 'Selector ' +
201
+ (selector.name || 'unknown') +
202
+ ' returned a different result when called with the same parameters. This can lead to unnecessary rerenders.' +
203
+ '\nSelectors that return a new reference (such as an object or an array) should be memoized: https://redux.js.org/usage/deriving-data-selectors#optimizing-selectors-with-memoization',
204
+ {
205
+ state,
206
+ selected,
207
+ selected2: toCompare,
208
+ stack,
209
+ },
210
+ )
211
+ }
212
+ }
213
+ if (
214
+ finalIdentityFunctionCheck === 'always' ||
215
+ (finalIdentityFunctionCheck === 'once' && firstRun.current)
216
+ ) {
217
+ // @ts-ignore
218
+ if (selected === state) {
219
+ let stack: string | undefined = undefined
220
+ try {
221
+ throw new Error()
222
+ } catch (e) {
223
+ // eslint-disable-next-line no-extra-semi
224
+ ;({ stack } = e as Error)
225
+ }
226
+ console.warn(
227
+ 'Selector ' +
228
+ (selector.name || 'unknown') +
229
+ ' returned the root state when called. This can lead to unnecessary rerenders.' +
230
+ '\nSelectors that return the entire state are almost certainly a mistake, as they will cause a rerender whenever *anything* in state changes.',
231
+ { stack },
232
+ )
233
+ }
234
+ }
235
+ if (firstRun.current) firstRun.current = false
236
+ }
237
+ return selected
238
+ },
239
+ }[selector.name],
240
+ [selector],
241
+ )
242
+
243
+ const selectedState = useSyncExternalStoreWithSelector(
244
+ subscription.addNestedSub,
245
+ store.getState,
246
+ getServerState || store.getState,
247
+ wrappedSelector,
248
+ equalityFn,
249
+ )
250
+
251
+ React.useDebugValue(selectedState)
252
+
253
+ return selectedState
254
+ }
255
+
256
+ Object.assign(useSelector, {
257
+ withTypes: () => useSelector,
258
+ })
259
+
260
+ return useSelector as UseSelector
261
+ }
262
+
263
+ /**
264
+ * A hook to access the redux store's state. This hook takes a selector function
265
+ * as an argument. The selector is called with the store state.
266
+ *
267
+ * This hook takes an optional equality comparison function as the second parameter
268
+ * that allows you to customize the way the selected state is compared to determine
269
+ * whether the component needs to be re-rendered.
270
+ *
271
+ * @param {Function} selector the selector function
272
+ * @param {Function=} equalityFn the function that will be used to determine equality
273
+ *
274
+ * @returns {any} the selected state
275
+ *
276
+ * @example
277
+ *
278
+ * import React from 'react'
279
+ * import { useSelector } from 'react-redux'
280
+ *
281
+ * export const CounterComponent = () => {
282
+ * const counter = useSelector(state => state.counter)
283
+ * return <div>{counter}</div>
284
+ * }
285
+ */
286
+ export const useSelector = /*#__PURE__*/ createSelectorHook()
@@ -0,0 +1,123 @@
1
+ import type { Context } from 'react'
2
+ import type { Action, Store } from 'redux'
3
+ import type { ReactReduxContextValue } from '../components/Context'
4
+ import { ReactReduxContext } from '../components/Context'
5
+ import {
6
+ createReduxContextHook,
7
+ useReduxContext as useDefaultReduxContext,
8
+ } from './useReduxContext'
9
+
10
+ /**
11
+ * Represents a type that extracts the action type from a given Redux store.
12
+ *
13
+ * @template StoreType - The specific type of the Redux store.
14
+ *
15
+ * @since 9.1.0
16
+ * @internal
17
+ */
18
+ export type ExtractStoreActionType<StoreType extends Store> =
19
+ StoreType extends Store<any, infer ActionType> ? ActionType : never
20
+
21
+ /**
22
+ * Represents a custom hook that provides access to the Redux store.
23
+ *
24
+ * @template StoreType - The specific type of the Redux store that gets returned.
25
+ *
26
+ * @since 9.1.0
27
+ * @public
28
+ */
29
+ export interface UseStore<StoreType extends Store> {
30
+ /**
31
+ * Returns the Redux store instance.
32
+ *
33
+ * @returns The Redux store instance.
34
+ */
35
+ (): StoreType
36
+
37
+ /**
38
+ * Returns the Redux store instance with specific state and action types.
39
+ *
40
+ * @returns The Redux store with the specified state and action types.
41
+ *
42
+ * @template StateType - The specific type of the state used in the store.
43
+ * @template ActionType - The specific type of the actions used in the store.
44
+ */
45
+ <
46
+ StateType extends ReturnType<StoreType['getState']> = ReturnType<
47
+ StoreType['getState']
48
+ >,
49
+ ActionType extends Action = ExtractStoreActionType<Store>,
50
+ >(): Store<StateType, ActionType>
51
+
52
+ /**
53
+ * Creates a "pre-typed" version of {@linkcode useStore useStore}
54
+ * where the type of the Redux `store` is predefined.
55
+ *
56
+ * This allows you to set the `store` type once, eliminating the need to
57
+ * specify it with every {@linkcode useStore useStore} call.
58
+ *
59
+ * @returns A pre-typed `useStore` with the store type already defined.
60
+ *
61
+ * @example
62
+ * ```ts
63
+ * export const useAppStore = useStore.withTypes<AppStore>()
64
+ * ```
65
+ *
66
+ * @template OverrideStoreType - The specific type of the Redux store that gets returned.
67
+ *
68
+ * @since 9.1.0
69
+ */
70
+ withTypes: <
71
+ OverrideStoreType extends StoreType,
72
+ >() => UseStore<OverrideStoreType>
73
+ }
74
+
75
+ /**
76
+ * Hook factory, which creates a `useStore` hook bound to a given context.
77
+ *
78
+ * @param {React.Context} [context=ReactReduxContext] Context passed to your `<Provider>`.
79
+ * @returns {Function} A `useStore` hook bound to the specified context.
80
+ */
81
+ export function createStoreHook<
82
+ StateType = unknown,
83
+ ActionType extends Action = Action,
84
+ >(
85
+ // @ts-ignore
86
+ context?: Context<ReactReduxContextValue<
87
+ StateType,
88
+ ActionType
89
+ > | null> = ReactReduxContext,
90
+ ) {
91
+ const useReduxContext =
92
+ context === ReactReduxContext
93
+ ? useDefaultReduxContext
94
+ : // @ts-ignore
95
+ createReduxContextHook(context)
96
+ const useStore = () => {
97
+ const { store } = useReduxContext()
98
+ return store
99
+ }
100
+
101
+ Object.assign(useStore, {
102
+ withTypes: () => useStore,
103
+ })
104
+
105
+ return useStore as UseStore<Store<StateType, ActionType>>
106
+ }
107
+
108
+ /**
109
+ * A hook to access the redux store.
110
+ *
111
+ * @returns {any} the redux store
112
+ *
113
+ * @example
114
+ *
115
+ * import React from 'react'
116
+ * import { useStore } from 'react-redux'
117
+ *
118
+ * export const ExampleComponent = () => {
119
+ * const store = useStore()
120
+ * return <div>{store.getState()}</div>
121
+ * }
122
+ */
123
+ export const useStore = /*#__PURE__*/ createStoreHook()
@@ -0,0 +1,35 @@
1
+ import type * as normal from './index'
2
+ import type * as rsc from './index-rsc'
3
+
4
+ // checks to make sure we didn't forgot to replicate any exports
5
+
6
+ // eslint-disable-next-line @typescript-eslint/no-unused-vars
7
+ const _check: typeof normal = {} as typeof rsc
8
+ // eslint-disable-next-line @typescript-eslint/no-unused-vars
9
+ const _check2: typeof rsc = {} as typeof normal
10
+
11
+ // -------------------------------------------------------------------------------------
12
+
13
+ const throwNotSupportedError = ((
14
+ // eslint-disable-next-line @typescript-eslint/no-unused-vars
15
+ ...args: any[]
16
+ ): any => {
17
+ throw new Error(
18
+ 'This function is not supported in React Server Components. Please only use this export in a Client Component.',
19
+ )
20
+ }) as any
21
+
22
+ export {
23
+ throwNotSupportedError as Provider,
24
+ throwNotSupportedError as batch,
25
+ throwNotSupportedError as connect,
26
+ throwNotSupportedError as legacy_connect,
27
+ throwNotSupportedError as createDispatchHook,
28
+ throwNotSupportedError as createSelectorHook,
29
+ throwNotSupportedError as createStoreHook,
30
+ throwNotSupportedError as useDispatch,
31
+ throwNotSupportedError as useSelector,
32
+ throwNotSupportedError as useStore,
33
+ }
34
+ export const ReactReduxContext = {} as any
35
+ export { default as shallowEqual } from './utils/shallowEqual'
package/src/index.ts ADDED
@@ -0,0 +1 @@
1
+ export * from './exports'
package/src/types.ts ADDED
@@ -0,0 +1,180 @@
1
+ import type {
2
+ ClassAttributes,
3
+ ComponentClass,
4
+ ComponentType,
5
+ FunctionComponent,
6
+ JSX,
7
+ } from 'react'
8
+
9
+ import type { Action, UnknownAction, Dispatch } from 'redux'
10
+
11
+ import type { NonReactStatics } from './utils/hoistStatics'
12
+
13
+ import type { ConnectProps } from './components/connect'
14
+
15
+ import type { UseSelectorOptions } from './hooks/useSelector'
16
+
17
+ export type FixTypeLater = any
18
+
19
+ export type EqualityFn<T> = (a: T, b: T) => boolean
20
+
21
+ export type ExtendedEqualityFn<T, P> = (a: T, b: T, c: P, d: P) => boolean
22
+
23
+ export type AnyIfEmpty<T extends object> = keyof T extends never ? any : T
24
+
25
+ export type DistributiveOmit<T, K extends keyof T> = T extends unknown
26
+ ? Omit<T, K>
27
+ : never
28
+
29
+ export interface DispatchProp<A extends Action<string> = UnknownAction> {
30
+ dispatch: Dispatch<A>
31
+ }
32
+
33
+ /**
34
+ * A property P will be present if:
35
+ * - it is present in DecorationTargetProps
36
+ *
37
+ * Its value will be dependent on the following conditions
38
+ * - if property P is present in InjectedProps and its definition extends the definition
39
+ * in DecorationTargetProps, then its definition will be that of DecorationTargetProps[P]
40
+ * - if property P is not present in InjectedProps then its definition will be that of
41
+ * DecorationTargetProps[P]
42
+ * - if property P is present in InjectedProps but does not extend the
43
+ * DecorationTargetProps[P] definition, its definition will be that of InjectedProps[P]
44
+ */
45
+ export type Matching<InjectedProps, DecorationTargetProps> = {
46
+ [P in keyof DecorationTargetProps]: P extends keyof InjectedProps
47
+ ? InjectedProps[P] extends DecorationTargetProps[P]
48
+ ? DecorationTargetProps[P]
49
+ : InjectedProps[P]
50
+ : DecorationTargetProps[P]
51
+ }
52
+
53
+ /**
54
+ * a property P will be present if :
55
+ * - it is present in both DecorationTargetProps and InjectedProps
56
+ * - InjectedProps[P] can satisfy DecorationTargetProps[P]
57
+ * ie: decorated component can accept more types than decorator is injecting
58
+ *
59
+ * For decoration, inject props or ownProps are all optionally
60
+ * required by the decorated (right hand side) component.
61
+ * But any property required by the decorated component must be satisfied by the injected property.
62
+ */
63
+ export type Shared<InjectedProps, DecorationTargetProps> = {
64
+ [P in Extract<
65
+ keyof InjectedProps,
66
+ keyof DecorationTargetProps
67
+ >]?: InjectedProps[P] extends DecorationTargetProps[P]
68
+ ? DecorationTargetProps[P]
69
+ : never
70
+ }
71
+
72
+ // Infers prop type from component C
73
+ export type GetProps<C> =
74
+ C extends ComponentType<infer P>
75
+ ? C extends ComponentClass<P>
76
+ ? ClassAttributes<InstanceType<C>> & P
77
+ : P
78
+ : never
79
+
80
+ // Applies LibraryManagedAttributes (proper handling of defaultProps
81
+ // and propTypes).
82
+ export type GetLibraryManagedProps<C> = JSX.LibraryManagedAttributes<
83
+ C,
84
+ GetProps<C>
85
+ >
86
+
87
+ // Applies LibraryManagedAttributes (proper handling of defaultProps
88
+ // and propTypes), as well as defines WrappedComponent.
89
+ export type ConnectedComponent<
90
+ C extends ComponentType<any>,
91
+ P,
92
+ > = FunctionComponent<P> &
93
+ NonReactStatics<C> & {
94
+ WrappedComponent: C
95
+ }
96
+
97
+ export type ConnectPropsMaybeWithoutContext<TActualOwnProps> =
98
+ TActualOwnProps extends { context: any }
99
+ ? Omit<ConnectProps, 'context'>
100
+ : ConnectProps
101
+
102
+ type Identity<T> = T
103
+ export type Mapped<T> = Identity<{ [k in keyof T]: T[k] }>
104
+
105
+ // Injects props and removes them from the prop requirements.
106
+ // Will not pass through the injected props if they are passed in during
107
+ // render. Also adds new prop requirements from TNeedsProps.
108
+ // Uses distributive omit to preserve discriminated unions part of original prop type.
109
+ // Note> Most of the time TNeedsProps is empty, because the overloads in `Connect`
110
+ // just pass in `{}`. The real props we need come from the component.
111
+ export type InferableComponentEnhancerWithProps<TInjectedProps, TNeedsProps> = <
112
+ C extends ComponentType<Matching<TInjectedProps, GetProps<C>>>,
113
+ >(
114
+ component: C,
115
+ ) => ConnectedComponent<
116
+ C,
117
+ Mapped<
118
+ DistributiveOmit<
119
+ GetLibraryManagedProps<C>,
120
+ keyof Shared<TInjectedProps, GetLibraryManagedProps<C>>
121
+ > &
122
+ TNeedsProps &
123
+ ConnectPropsMaybeWithoutContext<TNeedsProps & GetProps<C>>
124
+ >
125
+ >
126
+
127
+ // Injects props and removes them from the prop requirements.
128
+ // Will not pass through the injected props if they are passed in during
129
+ // render.
130
+ export type InferableComponentEnhancer<TInjectedProps> =
131
+ InferableComponentEnhancerWithProps<TInjectedProps, {}>
132
+
133
+ export type InferThunkActionCreatorType<
134
+ TActionCreator extends (...args: any[]) => any,
135
+ > = TActionCreator extends (
136
+ ...args: infer TParams
137
+ ) => (...args: any[]) => infer TReturn
138
+ ? (...args: TParams) => TReturn
139
+ : TActionCreator
140
+
141
+ export type HandleThunkActionCreator<TActionCreator> = TActionCreator extends (
142
+ ...args: any[]
143
+ ) => any
144
+ ? InferThunkActionCreatorType<TActionCreator>
145
+ : TActionCreator
146
+
147
+ // redux-thunk middleware returns thunk's return value from dispatch call
148
+ // https://github.com/reduxjs/redux-thunk#composition
149
+ export type ResolveThunks<TDispatchProps> = TDispatchProps extends {
150
+ [key: string]: any
151
+ }
152
+ ? {
153
+ [C in keyof TDispatchProps]: HandleThunkActionCreator<TDispatchProps[C]>
154
+ }
155
+ : TDispatchProps
156
+
157
+ /**
158
+ * This interface allows you to easily create a hook that is properly typed for your
159
+ * store's root state.
160
+ *
161
+ * @example
162
+ *
163
+ * interface RootState {
164
+ * property: string;
165
+ * }
166
+ *
167
+ * const useTypedSelector: TypedUseSelectorHook<RootState> = useSelector;
168
+ */
169
+ export interface TypedUseSelectorHook<TState> {
170
+ <TSelected>(
171
+ selector: (state: TState) => TSelected,
172
+ equalityFn?: EqualityFn<NoInfer<TSelected>>,
173
+ ): TSelected
174
+ <Selected = unknown>(
175
+ selector: (state: TState) => Selected,
176
+ options?: UseSelectorOptions<Selected>,
177
+ ): Selected
178
+ }
179
+
180
+ export type NoInfer<T> = [T][T extends any ? 0 : never]