簡體   English   中英

如何在 Typescript 中指定我想要的重載函數?

[英]How to specify which overloaded function I want in Typescript?

我試圖承諾標准節點 fs.writeFile。 我有 node 和 bluebird 的類型,這是我在這里選擇的 Promise 庫:

const f = Promise.promisify(fs.writeFile)
return f(file, content); // Should be a promise

這不起作用,因為:

[ts] 提供的參數與調用目標的任何簽名都不匹配。 const f: (arg1: string) => Promise<{}>

所以我選擇了錯誤的重載方法,因為對 promisify 的調用無法真正知道我猜是哪個。 或者甚至不是那個,而是帶有可選參數的東西,因為這些是三個重載的 writeFile:

export function writeFile(filename: string, data: any, callback?: (err: NodeJS.ErrnoException) => void): void;
export function writeFile(filename: string, data: any, options: { encoding?: string; mode?: number; flag?: string; }, callback?: (err: NodeJS.ErrnoException) => void): void;
export function writeFile(filename: string, data: any, options: { encoding?: string; mode?: string; flag?: string; }, callback?: (err: NodeJS.ErrnoException) => void): void;

promisify 對 # of args 有很多重載,如下所示:

/**
 * Returns a function that will wrap the given `nodeFunction`. Instead of taking a callback, the returned function will return a promise whose fate is decided by the callback behavior of the given node function. The node function should conform to node.js convention of accepting a callback as last argument and calling that callback with error as the first argument and success value on the second argument.
 *
 * If the `nodeFunction` calls its callback with multiple success values, the fulfillment value will be an array of them.
 *
 * If you pass a `receiver`, the `nodeFunction` will be called as a method on the `receiver`.
 */
static promisify<T>(func: (callback: (err:any, result: T) => void) => void, receiver?: any): () => Promise<T>;
static promisify<T, A1>(func: (arg1: A1, callback: (err: any, result: T) => void) => void, receiver?: any): (arg1: A1) => Promise<T>;
static promisify<T, A1, A2>(func: (arg1: A1, arg2: A2, callback: (err: any, result: T) => void) => void, receiver?: any): (arg1: A1, arg2: A2) => Promise<T>;
static promisify<T, A1, A2, A3>(func: (arg1: A1, arg2: A2, arg3: A3, callback: (err: any, result: T) => void) => void, receiver?: any): (arg1: A1, arg2: A2, arg3: A3) => Promise<T>;
static promisify<T, A1, A2, A3, A4>(func: (arg1: A1, arg2: A2, arg3: A3, arg4: A4, callback: (err: any, result: T) => void) => void, receiver?: any): (arg1: A1, arg2: A2, arg3: A3, arg4: A4) => Promise<T>;
static promisify<T, A1, A2, A3, A4, A5>(func: (arg1: A1, arg2: A2, arg3: A3, arg4: A4, arg5: A5, callback: (err: any, result: T) => void) => void, receiver?: any): (arg1: A1, arg2: A2, arg3: A3, arg4: A4, arg5: A5) => Promise<T>;
static promisify(nodeFunction: Function, receiver?: any): Function;

因此,似乎正在使用錯誤的promisify。 有什么更干凈的方法可以讓我實現我想要的嗎? 目前我必須解決這個問題:

const writeFile : (filename: string, data: any, callback: (err: NodeJS.ErrnoException) => void) => void = fs.writeFile
const f = Promise.promisify(writeFile)
return f(file, content); 

我覺得這很丑陋和冗長......

我無法設置一個好的簡單的工作示例,但以下類型斷言將允許您提示和您期望的內容:

const f = <(file: string, content: string) => void> Promise.promisify(fs.writeFile)

您可以修改<(file: string, content: string) => void>以更好地描述您期望可用的內容,或者使用更廣泛的類型<Function>或使用<any>動態化。

第一個選項需要更多的工作,但允許在稍后調用f時推斷返回類型(在這種情況下為void - 但您可以想象這種返回類型將被更積極地使用的情況)。

根據您的評論,我猜您需要...

const f = <(file: string, content: string) => Promise<any>> Promise.promisify(fs.writeFile)

你也可以在地方使用的聯合類型any在這個例子中,如果你知道了兩種可能的結果,即Promise<any>可以是:

Promise<ErrnoException | MySuccessfulType>

這將允許返回類型為Promise<ErrnoException>或返回類型為Promise<MySuccessfulType>

你可以使用__promisify__fs.writeFile命名空間:

fs.writeFile.__promisify__(file, content)

否則,您必須明確提及泛型類型以選擇相應的重載:

  • Node內置的util包有一個promisify()函數
const f = util.promisify<PathLike, string, void>(fs.writeFile)
f(file, content)

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM