From 2063ad467d082a28098da739c4b567adfff97238 Mon Sep 17 00:00:00 2001 From: Lyubomir Marinov Date: Fri, 3 Feb 2017 10:17:20 -0600 Subject: [PATCH] flow-typed --- .eslintignore | 1 + .jshintignore | 7 +- flow-typed/npm/flow-bin_v0.x.x.js | 6 ++ flow-typed/npm/react-redux_v5.x.x.js | 89 +++++++++++++++++++ flow-typed/npm/redux_v3.x.x.js | 56 ++++++++++++ package.json | 1 + react/.eslintrc.js | 8 +- .../features/base/redux/MiddlewareRegistry.js | 19 ++-- 8 files changed, 177 insertions(+), 10 deletions(-) create mode 100644 flow-typed/npm/flow-bin_v0.x.x.js create mode 100644 flow-typed/npm/react-redux_v5.x.x.js create mode 100644 flow-typed/npm/redux_v3.x.x.js diff --git a/.eslintignore b/.eslintignore index 2bd2bb7be304..85a31624d469 100644 --- a/.eslintignore +++ b/.eslintignore @@ -3,6 +3,7 @@ build/* # Third-party source code which we (1) do not want to modify or (2) try to # modify as little as possible. +flow-typed/* libs/* # ESLint will by default ignore its own configuration file. However, there does diff --git a/.jshintignore b/.jshintignore index 2d9530a6c55c..b0e2ed3b773d 100644 --- a/.jshintignore +++ b/.jshintignore @@ -1,7 +1,12 @@ +# The following do not need to be checked because they do not represent JS +# source code. build/ debian/ libs/ node_modules/ + +# The following are checked by ESLint which supersedes JSHint. +flow-typed/ react/ + analytics.js -webpack.config.babel.js diff --git a/flow-typed/npm/flow-bin_v0.x.x.js b/flow-typed/npm/flow-bin_v0.x.x.js new file mode 100644 index 000000000000..c538e2086f11 --- /dev/null +++ b/flow-typed/npm/flow-bin_v0.x.x.js @@ -0,0 +1,6 @@ +// flow-typed signature: 6a5610678d4b01e13bbfbbc62bdaf583 +// flow-typed version: 3817bc6980/flow-bin_v0.x.x/flow_>=v0.25.x + +declare module "flow-bin" { + declare module.exports: string; +} diff --git a/flow-typed/npm/react-redux_v5.x.x.js b/flow-typed/npm/react-redux_v5.x.x.js new file mode 100644 index 000000000000..8be01f19b1c5 --- /dev/null +++ b/flow-typed/npm/react-redux_v5.x.x.js @@ -0,0 +1,89 @@ +// flow-typed signature: 0ed284c5a2e97a9e3c0e87af3dedc09d +// flow-typed version: bdf1e66252/react-redux_v5.x.x/flow_>=v0.30.x + +import type { Dispatch, Store } from 'redux' + +declare module 'react-redux' { + + /* + + S = State + A = Action + OP = OwnProps + SP = StateProps + DP = DispatchProps + + */ + + declare type MapStateToProps = (state: S, ownProps: OP) => SP | MapStateToProps; + + declare type MapDispatchToProps = ((dispatch: Dispatch, ownProps: OP) => DP) | DP; + + declare type MergeProps = (stateProps: SP, dispatchProps: DP, ownProps: OP) => P; + + declare type StatelessComponent

= (props: P) => ?React$Element; + + declare class ConnectedComponent extends React$Component { + static WrappedComponent: Class>; + getWrappedInstance(): React$Component; + static defaultProps: void; + props: OP; + state: void; + } + + declare type ConnectedComponentClass = Class>; + + declare type Connector = { + (component: StatelessComponent

): ConnectedComponentClass; + (component: Class>): ConnectedComponentClass; + }; + + declare class Provider extends React$Component, children?: any }, void> { } + + declare type ConnectOptions = { + pure?: boolean, + withRef?: boolean + }; + + declare type Null = null | void; + + declare function connect( + ...rest: Array // <= workaround for https://github.com/facebook/flow/issues/2360 + ): Connector } & OP>>; + + declare function connect( + mapStateToProps: Null, + mapDispatchToProps: Null, + mergeProps: Null, + options: ConnectOptions + ): Connector } & OP>>; + + declare function connect( + mapStateToProps: MapStateToProps, + mapDispatchToProps: Null, + mergeProps: Null, + options?: ConnectOptions + ): Connector } & OP>>; + + declare function connect( + mapStateToProps: Null, + mapDispatchToProps: MapDispatchToProps, + mergeProps: Null, + options?: ConnectOptions + ): Connector>; + + declare function connect( + mapStateToProps: MapStateToProps, + mapDispatchToProps: MapDispatchToProps, + mergeProps: Null, + options?: ConnectOptions + ): Connector>; + + declare function connect( + mapStateToProps: MapStateToProps, + mapDispatchToProps: MapDispatchToProps, + mergeProps: MergeProps, + options?: ConnectOptions + ): Connector; + +} diff --git a/flow-typed/npm/redux_v3.x.x.js b/flow-typed/npm/redux_v3.x.x.js new file mode 100644 index 000000000000..0094abfa9986 --- /dev/null +++ b/flow-typed/npm/redux_v3.x.x.js @@ -0,0 +1,56 @@ +// flow-typed signature: ba132c96664f1a05288f3eb2272a3c35 +// flow-typed version: c4bbd91cfc/redux_v3.x.x/flow_>=v0.33.x + +declare module 'redux' { + + /* + + S = State + A = Action + + */ + + declare type Dispatch }> = (action: A) => A; + + declare type MiddlewareAPI = { + dispatch: Dispatch; + getState(): S; + }; + + declare type Store = { + // rewrite MiddlewareAPI members in order to get nicer error messages (intersections produce long messages) + dispatch: Dispatch; + getState(): S; + subscribe(listener: () => void): () => void; + replaceReducer(nextReducer: Reducer): void + }; + + declare type Reducer = (state: S, action: A) => S; + + declare type Middleware = + (api: MiddlewareAPI) => + (next: Dispatch) => Dispatch; + + declare type StoreCreator = { + (reducer: Reducer, enhancer?: StoreEnhancer): Store; + (reducer: Reducer, preloadedState: S, enhancer?: StoreEnhancer): Store; + }; + + declare type StoreEnhancer = (next: StoreCreator) => StoreCreator; + + declare function createStore(reducer: Reducer, enhancer?: StoreEnhancer): Store; + declare function createStore(reducer: Reducer, preloadedState: S, enhancer?: StoreEnhancer): Store; + + declare function applyMiddleware(...middlewares: Array>): StoreEnhancer; + + declare type ActionCreator = (...args: Array) => A; + declare type ActionCreators = { [key: K]: ActionCreator }; + + declare function bindActionCreators>(actionCreator: C, dispatch: Dispatch): C; + declare function bindActionCreators>(actionCreators: C, dispatch: Dispatch): C; + + declare function combineReducers(reducers: O): Reducer<$ObjMap(r: Reducer) => S>, A>; + + declare function compose(...fns: Array>): Function; + +} diff --git a/package.json b/package.json index 9cae42c11ead..dd9f61bf46a2 100644 --- a/package.json +++ b/package.json @@ -60,6 +60,7 @@ "clean-css": "^3.0.0", "css-loader": "*", "eslint": "^3.14.1", + "eslint-plugin-import": "^2.2.0", "eslint-plugin-jsdoc": "*", "eslint-plugin-react": "*", "eslint-plugin-react-native": "^2.2.1", diff --git a/react/.eslintrc.js b/react/.eslintrc.js index c50fc451b2aa..d18d4d7eb09c 100644 --- a/react/.eslintrc.js +++ b/react/.eslintrc.js @@ -6,6 +6,11 @@ module.exports = { } }, 'plugins': [ + + // ESLint's rule no-duplicate-imports does not understand Flow's import + // type. Fortunately, eslint-plugin-import understands Flow's import + // type. + 'import', 'jsdoc', 'react', 'react-native' @@ -273,7 +278,6 @@ module.exports = { 'no-confusing-arrow': 2, 'no-const-assign': 2, 'no-dupe-class-members': 2, - 'no-duplicate-imports': 2, 'no-new-symbol': 2, 'no-restricted-imports': 0, 'no-this-before-super': 2, @@ -298,6 +302,8 @@ module.exports = { 'template-curly-spacing': 2, 'yield-star-spacing': 2, + 'import/no-duplicates': 2, + // JsDoc plugin rules group. The following rules are in addition to // valid-jsdoc rule. 'jsdoc/check-param-names': 0, diff --git a/react/features/base/redux/MiddlewareRegistry.js b/react/features/base/redux/MiddlewareRegistry.js index 6ca51e09da6c..ca39c13b8cf7 100644 --- a/react/features/base/redux/MiddlewareRegistry.js +++ b/react/features/base/redux/MiddlewareRegistry.js @@ -1,15 +1,14 @@ /* @flow */ import { applyMiddleware } from 'redux'; - -type Middleware = Function; +import type { Middleware } from 'redux'; /** * A registry for Redux middleware, allowing features to register their * middleware without needing to create additional inter-feature dependencies. */ class MiddlewareRegistry { - _elements: Middleware[]; + _elements: Array>; /** * Creates a MiddlewareRegistry instance. @@ -19,7 +18,7 @@ class MiddlewareRegistry { * The set of registered middleware. * * @private - * @type {Route[]} + * @type {Middleware[]} */ this._elements = []; } @@ -32,11 +31,15 @@ class MiddlewareRegistry { * be included (such as middleware from third-party modules). * @returns {Middleware} */ - applyMiddleware(...additional: Middleware[]) { - return applyMiddleware( + applyMiddleware(...additional: Array>) { + // XXX The explicit definition of the local variable middlewares is to + // satisfy flow. + const middlewares = [ ...this._elements, ...additional - ); + ]; + + return applyMiddleware(...middlewares); } /** @@ -47,7 +50,7 @@ class MiddlewareRegistry { * @param {Middleware} middleware - A Redux middleware. * @returns {void} */ - register(middleware: Middleware) { + register(middleware: Middleware<*, *>) { this._elements.push(middleware); } }