[@types/combine-reducers] initial commit (#37090)

This commit is contained in:
Paul Marbach 2019-07-24 15:06:59 -05:00 committed by Wesley Wigham
parent f130553d6c
commit d4a4c4472d
4 changed files with 160 additions and 0 deletions

View File

@ -0,0 +1,36 @@
import combineReducers from 'combine-reducers';
function counter(state: number = 0, action: { type: string; payload?: any }): number {
if (action.type === 'increment_counter') {
return (state += 1);
} else if (action.type === 'decrement_counter') {
return (state -= 1);
}
return state;
}
function toggle(state: boolean = false, action: { type: string; payload?: any }): boolean {
if (action.type === 'toggle') {
return action.payload;
}
return state;
}
const reducer = combineReducers({
toggle,
counter,
});
// $ExpectError
combineReducers();
reducer({ toggle: false, counter: 4 }, { type: 'increment_counter' });
reducer({ toggle: false, counter: 4 }, { type: 'decrement_counter' });
reducer({ toggle: true, counter: 4 }, { type: 'toggle', payload: false });
// $ExpectError
reducer({ toggle: false, counter: 4, extra: false }, { type: 'decrement_counter' });
// $ExpectError
reducer({ toggle: false, counter: 4, extra: false });
// $ExpectError
reducer({ toggle: 3, counter: 4 }, { type: 'decrement_counter' });

100
types/combine-reducers/index.d.ts vendored Normal file
View File

@ -0,0 +1,100 @@
// Type definitions for combine-reducers 1.0
// Project: https://github.com/wesleytodd/combine-reducers#readme
// Definitions by: Paul Marbach <https://github.com/me>
// Definitions: https://github.com/DefinitelyTyped/DefinitelyTyped
// TypeScript Version: 2.3
/**
* these types are from the main redux type definitions:
* https://github.com/reduxjs/redux/blob/master/index.d.ts
*/
/**
* An *action* is a plain object that represents an intention to change the
* state. Actions are the only way to get data into the store. Any data,
* whether from UI events, network callbacks, or other sources such as
* WebSockets needs to eventually be dispatched as actions.
*
* Actions must have a `type` field that indicates the type of action being
* performed. Types can be defined as constants and imported from another
* module. It's better to use strings for `type` than Symbols because strings
* are serializable.
*
* Other than `type`, the structure of an action object is really up to you.
* If you're interested, check out Flux Standard Action for recommendations on
* how actions should be constructed.
*
* @template T the type of the action's `type` tag.
*/
export interface Action<T = any> {
type: T;
}
/**
* An Action type which accepts any other properties.
* This is mainly for the use of the `Reducer` type.
* This is not part of `Action` itself to prevent types that extend `Action` from
* having an index signature.
*/
export interface AnyAction extends Action {
// Allows any extra properties to be defined in an action.
[extraProps: string]: any;
}
/* reducers */
/**
* A *reducer* (also called a *reducing function*) is a function that accepts
* an accumulation and a value and returns a new accumulation. They are used
* to reduce a collection of values down to a single value
*
* Reducers are not unique to Reduxthey are a fundamental concept in
* functional programming. Even most non-functional languages, like
* JavaScript, have a built-in API for reducing. In JavaScript, it's
* `Array.prototype.reduce()`.
*
* In Redux, the accumulated value is the state object, and the values being
* accumulated are actions. Reducers calculate a new state given the previous
* state and an action. They must be *pure functions*functions that return
* the exact same output for given inputs. They should also be free of
* side-effects. This is what enables exciting features like hot reloading and
* time travel.
*
* Reducers are the most important concept in Redux.
*
* *Do not put API calls into reducers.*
*
* @template S The type of state consumed and produced by this reducer.
* @template A The type of actions the reducer can potentially respond to.
*/
export type Reducer<S = any, A extends Action = AnyAction> = (state: S | undefined, action: A) => S;
/**
* Object whose values correspond to different reducer functions.
*
* @template A The type of actions the reducers can potentially respond to.
*/
export type ReducersMapObject<S = any, A extends Action = Action> = {
[K in keyof S]: Reducer<S[K], A>;
};
/**
* Turns an object whose values are different reducer functions, into a single
* reducer function. It will call every child reducer, and gather their results
* into a single state object, whose keys correspond to the keys of the passed
* reducer functions.
*
* @template S Combined state object type.
*
* @param reducers An object whose values correspond to different reducer
* functions that need to be combined into one. One handy way to obtain it
* is to use ES6 `import * as reducers` syntax. The reducers may never
* return undefined for any action. Instead, they should return their
* initial state if the state passed to them was undefined, and the current
* state for any unrecognized action.
*
* @returns A reducer function that invokes every reducer inside the passed
* object, and builds a state object with the same shape.
*/
export default function combineReducers<S>(reducers: ReducersMapObject<S, any>): Reducer<S>;
export default function combineReducers<S, A extends Action = AnyAction>(reducers: ReducersMapObject<S, A>): Reducer<S, A>;

View File

@ -0,0 +1,23 @@
{
"compilerOptions": {
"module": "commonjs",
"lib": [
"es6"
],
"noImplicitAny": true,
"noImplicitThis": true,
"strictFunctionTypes": true,
"strictNullChecks": true,
"baseUrl": "../",
"typeRoots": [
"../"
],
"types": [],
"noEmit": true,
"forceConsistentCasingInFileNames": true
},
"files": [
"index.d.ts",
"combine-reducers-tests.ts"
]
}

View File

@ -0,0 +1 @@
{ "extends": "dtslint/dt.json" }