wechat-miniprogram/api-typings

API 泛型添加

Opened this issue · 4 comments

希望能够为所有返回 any 的api添加泛型,如:

        getStorageSync(
            /** 本地缓存中指定的 key */
            key: string
        ): any

改为

        getStorageSync<T = any>(
            /** 本地缓存中指定的 key */
            key: string
        ): T

再如:

    interface RequestOption {
        ...
        /** 请求的参数 */
        data?: string | IAnyObject | ArrayBuffer
        ...
        /** 设置请求的 header,header 中不能设置 Referer。
         *
         * `content-type` 默认为 `application/json` */
        header?: IAnyObject
        ...
    }

    request(option: RequestOption): RequestTask

改为

    interface RequestOption<DataOption = string | IAnyObject | ArrayBuffer, HeaderOption extends IAnyObject> {
        ...
        /** 请求的参数 */
        data?: DataOption
        ...
        /** 设置请求的 header,header 中不能设置 Referer。
         *
         * `content-type` 默认为 `application/json` */
        header?: HeaderOption 
        ...
    }

    request<DataOption = string | IAnyObject | ArrayBuffer, HeaderOption extends IAnyObject>(option: RequestOption<DataOption, HeaderOption>): RequestTask

我个人是非常抵制 any 在 typescript 的使用的,遍地 any 约等于没用 typescript。
image

而满地 as 显然不够优雅:

// 判断是否已经显示过
const cache = wx.getStorageSync("add-tip") as numebr;

所以希望最好能够支持

```ts
// 判断是否已经显示过
const cache = wx.getStorageSync<number>("add-tip");
SgLy commented

getStorageSyncrequest 的这两个是比较好的提议,由于现在 api 定义和文档是同一个数据源,不太能支持泛型,改这两个可能需要一点时间;不过将所有的 any 全部改成泛型这点有待商榷,后续整理一下现况再看是不是要这样改

SgLy commented

已在 3.3.0 中支持了 getStorage, getStorageSyncrequest 的泛型

如果一个接口同时支持 Promisify 和泛型(比如 wx.getStorage),这几个用例应该通过

// 回调风格
const res = wx.getStorage<string>({
  key: 'key',
  success(res) {
    expectType<string>(res.data)
  }
})
expectType<void>(res)  // failing
wx.getStorage({
  key: 'key',
  success(res) {
    expectType<any>(res.data)
    expectNotType<string>(res.data)
  }
})

// Promise 风格
wx.getStorage<string>({ key: 'key' })
  .then((res) => {
    expectType<string>(res.data)
  })
wx.getStorage({ key: 'key' })
  .then((res) => {
    expectType<any>(res.data)
    expectNotType<string>(res.data)
  })

现在的类型实现其实是有问题的,现在的类型是:

declare function getStorage<
  T = any,
  U extends GetStorageOption<T> = GetStorageOption<T>
>(option: U): PromisifySuccessResult<U, GetStorageOption<T>>;

这个定义在上面标注 failing 的一句是跑不过的(会返回 Promise),不过至少能保证两种用法正常使用,所以先发了

这个 issue 暂时先不关闭,一是用来跟进其他可以使用泛型的接口,二是看看有没有更好的定义方式

wx.cloud那边我记得应该有不少可以完善完善,回头我看一下列出来。

另外我觉得这个通过函数重载的方式应该可以解决吧,稍后我也试一下。

类似这种接口声明个人感觉加了范型会更好用(指的是根据选择器的不同,返回的默认 value 的类型

/**
     * value 改变时触发 change 事件
     *
     * event.detail = {value}
     *
     * 当 mode = region 时 (最低基础库: 1.4.0)
     *
     * value 改变时触发 change 事件,event.detail = {value, code, postcode},其中字段 code 是统计用区划代码,postcode 是邮政编码
     */
    type PickerChange<
        Mark extends IAnyObject = IAnyObject,
        TargetDataset extends IAnyObject = IAnyObject
    > = CustomEvent<
        {
            /**
             * 当 mode = selector 时, 返回当前选择的 value
             *
             * 当 mode = multiSelector 时, 返回一个索引数组
             *
             * 当 mode = time | date 时, 返回 `"12:01"` | `"2016-09-01"`
             *
             * 当 mode = region 时, 返回 `["广东省", "广州市", "海珠区"]`
             */
            value: string | number[] | [string, string, string]
            /** 统计用区划代码 当 mode = region 时有效 (最低基础库: 1.4.0) */
            code: [string, string, string]
            /** 邮政编码 当 mode = region 时有效 (最低基础库: 1.4.0) */
            postcode: string
        },
        Mark,
        TargetDataset
    >