From 067e6d0236ab0c69f5e782d4372ef3b299dbca9a Mon Sep 17 00:00:00 2001 From: Alexander Smith Date: Fri, 12 Jul 2019 16:17:18 -0700 Subject: [PATCH 1/2] Incorporate Flow types into source code --- .flowconfig | 11 ++++ flow-typed/npm/redux_v4.x.x.js | 100 +++++++++++++++++++++++++++++++++ package.json | 4 +- src/index.flow.js | 39 +++++++++++++ 4 files changed, 153 insertions(+), 1 deletion(-) create mode 100644 .flowconfig create mode 100644 flow-typed/npm/redux_v4.x.x.js create mode 100644 src/index.flow.js diff --git a/.flowconfig b/.flowconfig new file mode 100644 index 0000000..1fed445 --- /dev/null +++ b/.flowconfig @@ -0,0 +1,11 @@ +[ignore] + +[include] + +[libs] + +[lints] + +[options] + +[strict] diff --git a/flow-typed/npm/redux_v4.x.x.js b/flow-typed/npm/redux_v4.x.x.js new file mode 100644 index 0000000..2ba2c8b --- /dev/null +++ b/flow-typed/npm/redux_v4.x.x.js @@ -0,0 +1,100 @@ +// flow-typed signature: a49a6c96fe8a8bb3330cce2028588f4c +// flow-typed version: de5b3a01c6/redux_v4.x.x/flow_>=v0.89.x + +declare module 'redux' { + /* + + S = State + A = Action + D = Dispatch + + */ + + declare export type Action = { + type: T + } + + declare export type DispatchAPI = (action: A) => A; + + declare export type Dispatch = DispatchAPI; + + declare export type MiddlewareAPI> = { + dispatch: D, + getState(): S, + }; + + declare export type Store> = { + // rewrite MiddlewareAPI members in order to get nicer error messages (intersections produce long messages) + dispatch: D, + getState(): S, + subscribe(listener: () => void): () => void, + replaceReducer(nextReducer: Reducer): void, + }; + + declare export type Reducer = (state: S | void, action: A) => S; + + declare export type CombinedReducer = ( + state: ($Shape & {}) | void, + action: A + ) => S; + + declare export type Middleware> = ( + api: MiddlewareAPI + ) => (next: D) => D; + + declare export type StoreCreator> = { + (reducer: Reducer, enhancer?: StoreEnhancer): Store, + ( + reducer: Reducer, + preloadedState: S, + enhancer?: StoreEnhancer + ): Store, + }; + + declare export type StoreEnhancer> = ( + next: StoreCreator + ) => StoreCreator; + + declare export function createStore( + reducer: Reducer, + enhancer?: StoreEnhancer + ): Store; + declare export function createStore( + reducer: Reducer, + preloadedState?: S, + enhancer?: StoreEnhancer + ): Store; + + declare export function applyMiddleware( + ...middlewares: Array> + ): StoreEnhancer; + + declare export type ActionCreator = (...args: Array) => A; + declare export type ActionCreators = { + [key: K]: ActionCreator, + }; + + declare export function bindActionCreators< + A, + C: ActionCreator, + D: DispatchAPI + >( + actionCreator: C, + dispatch: D + ): C; + declare export function bindActionCreators< + A, + K, + C: ActionCreators, + D: DispatchAPI + >( + actionCreators: C, + dispatch: D + ): C; + + declare export function combineReducers( + reducers: O + ): CombinedReducer<$ObjMap(r: Reducer) => S>, A>; + + declare export var compose: $Compose; +} diff --git a/package.json b/package.json index 3a50148..929cf3d 100644 --- a/package.json +++ b/package.json @@ -14,13 +14,15 @@ "build-cjs": "rollup src/index.js --format cjs --output dist/index.cjs.js", "build-es": "rollup src/index.js --format es --output dist/index.es.js", "build": "npm run build-cjs && npm run build-es", + "flow": "flow check", "prepublishOnly": "npm run build" }, "author": "Giancarlo Anemone", "license": "MIT", "dependencies": {}, "devDependencies": { - "redux": "^3.6.0", + "flow-bin": "^0.102.0", + "redux": "^4.0.4", "rollup": "^0.41.6", "tape": "^4.6.3" } diff --git a/src/index.flow.js b/src/index.flow.js new file mode 100644 index 0000000..506033c --- /dev/null +++ b/src/index.flow.js @@ -0,0 +1,39 @@ +// @flow + +import type {StoreCreator, Action, Reducer} from 'redux'; + +type ReactorAction = {| + type: T, + payload?: mixed, + __REACTOR__?: Reducer>, +|}; + +export function reactorEnhancer< + S, + ActionType, + A: ReactorAction, + D +>(createStore: StoreCreator): StoreCreator { + return function storeCreator(reducer, ...remainingArgs) { + function wrappedReducer(state: S | void, action: A): S { + if (action.__REACTOR__) { + return action.__REACTOR__(state, action); + } + return reducer(state, action); + } + return createStore(wrappedReducer, ...remainingArgs); + }; +} + +export function createReactor( + type: T, + __REACTOR__: Reducer> +): (payload: mixed) => ReactorAction { + return function actionCreator(payload: mixed) { + return { + type: type, + payload: payload, + __REACTOR__: __REACTOR__, + }; + }; +} From e19137db49fee8d468112c99e1144d410c1b383d Mon Sep 17 00:00:00 2001 From: Alexander Smith Date: Mon, 15 Jul 2019 15:05:55 -0700 Subject: [PATCH 2/2] Signature changes to include Action + ReactActions --- src/index.flow.js | 13 +++++++------ 1 file changed, 7 insertions(+), 6 deletions(-) diff --git a/src/index.flow.js b/src/index.flow.js index 506033c..fd64b39 100644 --- a/src/index.flow.js +++ b/src/index.flow.js @@ -2,21 +2,22 @@ import type {StoreCreator, Action, Reducer} from 'redux'; -type ReactorAction = {| +export type ReactorAction = {| type: T, - payload?: mixed, - __REACTOR__?: Reducer>, + payload: mixed, + __REACTOR__: Reducer>, |}; export function reactorEnhancer< S, ActionType, - A: ReactorAction, + A: Action | ReactorAction, D >(createStore: StoreCreator): StoreCreator { return function storeCreator(reducer, ...remainingArgs) { function wrappedReducer(state: S | void, action: A): S { if (action.__REACTOR__) { + // $FlowFixMe return action.__REACTOR__(state, action); } return reducer(state, action); @@ -27,9 +28,9 @@ export function reactorEnhancer< export function createReactor( type: T, - __REACTOR__: Reducer> + __REACTOR__: Reducer> ): (payload: mixed) => ReactorAction { - return function actionCreator(payload: mixed) { + return function actionCreator(payload: mixed): ReactorAction { return { type: type, payload: payload,