基于字符串参数的打字稿条件返回类型

Jør*_*edt 3 generics typescript

当使用字符串文字的联合作为输入参数时,删除强制转换并将类型放入函数头中需要什么

const get = <T extends "barcode" | "mqtt">(s: T) =>
    s === "barcode" ?
        <T extends "barcode" ? {scan: () => string} : {pan: () => string}>{scan: () => "we are scanning"} :
        <T extends "barcode" ? {scan: () => string} : {pan: () => string}>{pan: () => "we are panning"}

get("barcode").scan() // OK
get("mqtt").pan()     // OK
get("barcode").pan() // Error
Run Code Online (Sandbox Code Playgroud)

我遇到了这个试图回答别人的问题:https : //stackoverflow.com/a/55059318/2684980

Tit*_*mir 6

最干净的解决方案是在这种情况下(尽管没有比类型断言更安全的类型)是使用重载来代替。您可以在公共签名中使用条件类型,并在实现签名中使用简单的联合。您将需要切换到函数声明,因为函数表达式(箭头或正则)不容易支持重载:

function get<T extends "barcode" | "mqtt">(s: T): T extends "barcode" ? { scan: () => string } : { pan: () => string }
function get(s: "barcode" | "mqtt"): { scan: () => string } | { pan: () => string } {
    return s === "barcode" ?
        { scan: () => "we are scanning" } :
        { pan: () => "we are panning" }
}

get("barcode").scan() // OK
get("mqtt").pan()     // OK
get("barcode").pan() // Error
Run Code Online (Sandbox Code Playgroud)