Тип метода аннотирования reflectPromise

голоса
0

Я пытался ввести annoate версию reflectметода обещания здесь - https://stackoverflow.com/a/31424853/1828637

function reflectPromise(p){
    return p.then(data => ({
                data,
                resolved: true
             }))
            .catch(error => ({
                error,
                rejected: true
             }));
}

Что она делает это берет обещание, и возвращает другое обещание, когда он разрешен или отвергнут.

То, что я пытаюсь сделать с псевдокодом:

  1. Заявляем , что dataявляетсяtypeof ResolveValue(p)
  2. Заявляем , что errorявляетсяtypeof RejectValue(p)
  3. Объявляет , что другие могут проверить const didReject = !!(await (reflectedPromise(somePromise)).rejected(что это будет делать для решенных обещаний, который возвращает { data: xxx, resolved:true }) в свою очередь undefinedк true. В настоящее время , когда я !!blah.rejectedмашинопись говорит мнеProperty 'rejected' does not exist on type

Это то, что я до сих пор:

function reflectPromise(p: Promise<any>): Promise<
        { data: any, resolved: boolean, rejected: void  } |
        { error: any, resolved: void, rejected: boolean }
    > {
    return p.then(data: any) => ({
                data,
                resolved: true
             }))
            .catch((error: any) => ({
                error,
                rejected: true
             }));
}
Задан 19/09/2018 в 21:29
источник пользователем
На других языках...                            


1 ответов

голоса
2

Вы должны использовать общий тип , чтобы иметь тип результата выведенного. Тип ошибки считается anyв машинописном и нет безопасности типа там. Кроме того, я напечатал бы rejectedи , resolvedкак undefinedне void(их значение будет определено в конце концов во время выполнения , так что это более Acurate) , и я бы их по желанию , если они не присутствуют.

Кроме того, когда resolveи rejectесть true, я бы ввести их в качестве булева буквального типа trueдля того , чтобы позволить типа охранникам работать лучше.

Собираю вместе это составляет (со строгими проверками нуля):

function reflectPromise<T>(p: Promise<T>): Promise<
        { data: T, resolved: boolean, rejected?: undefined  } |
        { error: any, resolved?: undefined, rejected: boolean }
    > {
    return p.then((data: any) => ({
                data,
                resolved: true
            }))
            .catch((error: any) => ({
                error,
                rejected: true
            }));
}


(async function (somePromise: Promise<number>) {
    const result = await (reflectPromise(somePromise));
    const didReject = !!result.rejected
    if (result.rejected) {
        result.error // result is { error: any, resolved?: undefined, rejected: true }
    } else {
        result.data // result { data: number, resolved: true, rejected?: undefined  } 
    }

    if (result.resolved) {
        result.data // result { data: number, resolved: true, rejected?: undefined  } 
    } else {
        result.error // result is { error: any, resolved?: undefined, rejected: true }
    }
})(Promise.resolve(1));

Кроме того , реализация reflectPromiseвыглядит лучше async/awaitна мой взгляд:

async function reflectPromise<T>(p: Promise<T>): Promise<
    { data: T, resolved: true, rejected?: undefined } |
    { error: any, resolved?: undefined, rejected: true }
> {
    try {
        return {
            data: await p,
            resolved: true
        }
    } catch (e) {
        return {
            error: e,
            rejected: true
        }
    }
}

Без строгого нулевых проверок, охранник типа будет частично работать , если нам нужно изменить типы немного, и установить как resolvedи rejectна обеих ветвях:

async function reflectPromise<T>(p: Promise<T>): Promise<
    { data: T, resolved: true, rejected: false } |
    { error: any, resolved: false, rejected: true }
> {
    try {
        return {
            data: await p,
            resolved: true,
            rejected: false,
        }
    } catch (e) {
        return {
            error: e,
            rejected: true,
            resolved: false
        }
    }
}

(async function (somePromise: Promise<number>) {
    const result = await (reflectPromise(somePromise));
    const didReject = !!result.rejected
    if (result.rejected) {
        result.error // result is { error: any, resolved?: undefined, rejected: true }
    } 

    if (result.resolved) {
        result.data // result { data: number, resolved: true, rejected?: undefined  } 
    }
})(Promise.resolve(1));
Ответил 19/09/2018 в 22:41
источник пользователем

Cookies help us deliver our services. By using our services, you agree to our use of cookies. Learn more