strip the types away

typescript
Yanick Champoux 2019-10-22 10:55:54 -04:00
parent 78696efcbb
commit 5c75b7ffdb
12 changed files with 24 additions and 110 deletions

View File

@ -1,16 +1,15 @@
import fp from 'lodash/fp';
import { ActionEffects, ActionCreator, ActionCreators, ActionMutations } from '../types';
function actionFor(type: string) {
function actionFor(type) {
return ( (payload = undefined, meta = undefined) =>
fp.pickBy(v => v !== null)({type, payload, meta})
) as ActionCreator;
);
}
export default function buildActions(
mutations : ActionMutations = {},
effects : ActionEffects = {},
subActions : ActionCreators = {},
mutations = {},
effects = {},
subActions = {},
) {
return { ...subActions,

View File

@ -12,6 +12,6 @@ export default function buildCreateStore( reducer, initial, middleware,
};
}
return store as any;
return store;
}
};

View File

@ -1,8 +1,8 @@
import fp from 'lodash/fp';
export default function buildInitial<S = any>(
initial: any = {},
export default function buildInitial(
initial= {},
subduxes = {},
): S {
) {
return fp.isPlainObject(initial) ? fp.mergeAll([subduxes, initial]) : initial;
}

View File

@ -1,6 +0,0 @@
// TypeScript Version: 3.4
import buildInitial from '.';
// $ExpectType any
const x = buildInitial();

View File

@ -1,14 +0,0 @@
import buildInitial from '.';
import {expectType} from 'tsd';
type MyState = {
foo: number,
bar: string,
};
const x = buildInitial<MyState>({
initial: {
glug: 3,
}
});
expectType<MyState>(x);

View File

@ -1,6 +0,0 @@
import buildMiddleware from '../buildMiddleware';
import {expectType} from 'tsd';
expectType<any>( buildMiddleware );

View File

@ -1,25 +1,23 @@
import fp from 'lodash/fp';
import u from 'updeep';
import { Mutation, Mutations } from '../types';
const composeMutations = (mutations:Mutation[]) =>
const composeMutations = (mutations) =>
mutations.reduce( (m1,m2) =>
(payload=null,action={}) => state => m2(payload,action)(
m1(payload,action)(state) ));
export default function buildMutations(mutations = {}, subduxes= {}) :Mutations{
export default function buildMutations(mutations = {}, subduxes= {}) {
// we have to differentiate the subduxes with '*' than those
// without, as the root '*' is not the same as any sub-'*'
const actions = fp.uniq( Object.keys(mutations).concat(
...Object.values( subduxes ).map( ({mutations = {}}:any) => Object.keys(mutations) )
...Object.values( subduxes ).map( ({mutations = {}}) => Object.keys(mutations) )
) );
let mergedMutations = {};
let [ globby, nonGlobby ] = fp.partition(
([_,{mutations={}}]:any) => mutations['*'],
([_,{mutations={}}]) => mutations['*'],
Object.entries(subduxes)
);
@ -32,16 +30,16 @@ export default function buildMutations(mutations = {}, subduxes= {}) :Mutations{
])(globby);
const globbyMutation = (payload,action) => u(
fp.mapValues( (mut:any) => mut(payload,action) )(globby)
fp.mapValues( (mut) => mut(payload,action) )(globby)
);
actions.forEach( action => {
mergedMutations[action] = [ globbyMutation ]
});
nonGlobby.forEach( ([slice, {mutations={},reducer={}}]:any) => {
nonGlobby.forEach( ([slice, {mutations={},reducer={}}]) => {
Object.entries(mutations).forEach(([type,mutation]) => {
const localized = (payload=null,action={}) => u.updateIn( slice )( (mutation as any)(payload,action) );
const localized = (payload=null,action={}) => u.updateIn( slice )( (mutation)(payload,action) );
mergedMutations[type].push(localized);
})
@ -51,5 +49,5 @@ export default function buildMutations(mutations = {}, subduxes= {}) :Mutations{
mergedMutations[type].push(mutation);
});
return fp.mapValues( composeMutations )(mergedMutations) as Mutations;
return fp.mapValues( composeMutations )(mergedMutations);
}

View File

@ -1,18 +1,15 @@
import fp from 'lodash/fp';
import {Mutations} from '../types';
type Upreducer = <S>(action:any) => (state:S) => S;
export default function buildUpreducer<S>(initial: S, mutations: Mutations): Upreducer {
return (action = {}) => (state:any) => {
export default function buildUpreducer(initial, mutations) {
return (action = {}) => (state) => {
if (state === null) state = initial;
const a =
mutations[(action as any).type] ||
mutations[(action).type] ||
mutations['*'];
if(!a) return state;
return a((action as any).payload, action)(state) as S;
return a((action).payload, action)(state);
};
}

View File

@ -1,7 +1,6 @@
import fp from 'lodash/fp';
import u from 'updeep';
export { Updux } from './updux';
import Updux from './updux';
export default function updux(config) {

View File

@ -1,5 +0,0 @@
import updux, {Updux } from '.';
import {expectType} from 'tsd';
const x = updux({});
expectType<Updux>(x);

View File

@ -1,23 +0,0 @@
export type Dictionary<T> = { [key: string]: T };
export type Mutation = (payload: any, action: any) => (state:any) => any;
export type Mutations = Dictionary<Mutation>;
export type ActionMutations = Dictionary<Mutation>;
export type Effect = (api:any) => (next: Function) => (action: any) => any;
export type ActionEffects = Dictionary<Effect>;
export type Action<T = string, P = any, M = any> = {
type: T,
payload: P,
meta: M,
}
export type ActionCreator = <P,M>(payload?: P, meta?: M ) => Action<string,P,M>;
export type ActionCreators = Dictionary<ActionCreator>;

View File

@ -3,42 +3,17 @@ import buildActions from './buildActions';
import buildInitial from './buildInitial';
import buildMutations from './buildMutations';
import { Dictionary, Mutation, ActionCreators } from './types';
import buildCreateStore from './buildCreateStore';
import buildMiddleware from './buildMiddleware';
import buildUpreducer from './buildUpreducer';
type UpduxConfig = {
initial?: any,
mutations?: any,
effects?: any,
subduxes?: {
[ slice: string ]: UpduxConfig | Updux
}
};
export class Updux {
actions: ActionCreators;
subduxes: Dictionary<Updux>;
initial: any;
mutations: Dictionary<Mutation>;
createStore: Function;
upreducer: (action:any)=>(state:any)=>any;
reducer: <S>(state:S,action:any) => S;
middleware: (api:any) => (next: Function) => (action: any) => any;
constructor(config: UpduxConfig) {
constructor(config) {
this.subduxes = fp.mapValues(
value => fp.isPlainObject(value) ? new Updux(value as UpduxConfig) : value )(fp.getOr({},'subduxes',config)
) as Dictionary<Updux>;
value => fp.isPlainObject(value) ? new Updux(value ) : value )(fp.getOr({},'subduxes',config)
);
this.actions = buildActions(