字符串文字类型作为默认参数值

时间:2017-06-01 19:09:45

标签: generics typescript types redux

我正在尝试使用from pyspark.sql import functions as f (sqlContext .table("myTempTable") .select(f.concat_ws(",", f.first(f.lit(date)), f.min("id"), f.max("id"))) .coalesce(1) .write.format("text").mode("append").save("/tmp/fooo")) 中的user-defined type guard阻止我的redux缩减器中的强制转换。我设法得到了一个可行的解决方案。

代码

这是我正在使用的辅助类型保护功能:

TypeScript

我在减速机中使用它是这样的:

export function isAction<A extends Action>(action: Action, type: A['type']): action is A {
    return action.type === type;
}

动作界面(上面的if (isAction<actions.LoginAction>(action, types.LOGIN)) { // access action.payload here } )定义如下:

actions.LoginAction

动作类型声明为:

export interface LoginAction
{
    type: typeof types.LOGIN,
    payload: {
        username: string,
        password: string;
    }
}

问题

如何重写export const LOGIN = "authentication/login"; 方法以防止必须两次指定操作类型(一次在操作界面内,一次在调用isAction中)。

我尝试了以下的许多变体,但没有任何东西可以编译。

isAction

编译器有信息,但我似乎无法表达我想要它做什么。

1 个答案:

答案 0 :(得分:1)

您可以在减速机内获得出色的型号支持,而无需进行用户定义的类型保护。我输入我的redux比特和碎片,而typescript编译器足够聪明,可以在switch语句的每个分支内找出正确的动作形状。希望这是有帮助的。在https://basarat.gitbooks.io/typescript/docs/types/literal-types.html有关于字符串文字类型的更多信息 - 它们是让redux输入为我工作的关键。

// Constants/Types
// This is a string literal type, meaning that no other string
// will pass type checking
export type LOGIN = 'LOGIN';
export const LOGIN = 'LOGIN';

// Generic action type, for typing actions themselves
// This is just to make typing actions quicker/easier, I 
// merge declare it on the redux module.
export interface TypedAction<T> extends Redux.Action {
    type: T;
}

// Which is used to create typed actions
// E.g. with a payload
export interface LoginAction extends TypedAction<LOGIN> {
    payload: {
        username: string;
        password: string;
    }
}

// Or without a payload
export type LogoutAction = TypedAction<LOGIN>;

// I typically then export a union type of all the actions that a
// reducer will be dealing with
export type HandledActions = LoginAction | LogoutAction;

// The reducer state is typed...
export interface StateShape {
    currentUser: string;
}

const initialState: StateShape = {
    currentUser: '';
}

// And the reducer action is typed using the union type from above
const reducer: Redux.Reducer<StateShape> = (state = initialState, action: HandledActions) => {
    // Within the switch statement the action will have the correct type
    switch(action.type) {
        case LOGIN:
            // Passes type checks, code autocomplete gives correct payload
            const { username } = action.payload;
            return { currentUser: username };
        case LOGOUT:
            // Code autocomplete gives no payload here
            return initialState;
        default:
             return state;
    }
}