嗯,通过 openapi-typescript 生成 swagger 的类型定义(类型定义文件内容如下)
export interface paths {
"/api/cusfood/create": {
post: operations["controller-cusfood-create"];
};
}
export interface definitions {
cusfoodRequest: {
ch?: number;
energy: number;
fat?: number;
protein?: number;
};
cusfoodResponse: {
/** 状态码 */
code: number;
/** 具体数据 */
data: definitions["cusfoodbody"];
/** 是否成功 */
success?: boolean;
};
}
export interface operations {
"controller-cusfood-create": {
parameters: {
body: {
/** ( post 对应 body 请求,请求值设定为用户习惯信息 )。 */
body: definitions["cusfoodRequest"];
};
};
responses: {
/** ( 响应 )。 */
200: {
schema: definitions["cusfoodResponse"];
};
};
};
}
然后我想写个方便的泛型函数,来约束入参类型,以及方便编辑器提示出参类型
const xFetch = <
Path extends keyof paths,
OpName extends keyof paths[Path],
Query extends ???,
Body extends ???,
Resp extends ???
>
(path: Path, opName: OpName, query: Query, body: Body): Promise<Resp> => {
// 由于 path + OpName 具有唯一性
// 那么应该可以利用 typescript 里面的 可辨识联合 来推导出 Query, Body, Resp 的类型
}
求助
谢谢
1
Sparetire 2021-03-18 01:45:33 +08:00 via Android
Body extends Pick<Pick<Pick<operations, keyof operations>, 'parameters'>, 'body'>
手机打字没测试。。不一定对 Resp 类似 Query type Key = string; type Value = string; type QS = '${Key}=${Value}'; Query extends QS |
2
ruandao OP @Sparetire 不大对,你这个方式 Pick 和 operations["xxx"] 能够得到一样的类型,但是这里想要的是 从 url 那边开始推导出类型,operations["xxx"] 得到的类型 无法关联到具体的类型
|
3
RaminZhong 2021-03-18 22:18:54 +08:00
不太清楚你要的是哪种效果,试着写了下
const xFetch = < Path extends keyof paths, OpName extends keyof paths[Path], Parameters extends paths[Path][OpName] extends { parameters: { query?: any; body?: any } } ? paths[Path][OpName]["parameters"] : { query: any; body: any } >( path: Path, opName: OpName, query: Parameters["query"]["query"], body: Parameters["body"]["body"] ): Promise< paths[Path][OpName] extends { responses: { [key: number]: { schema: any } } } ? paths[Path][OpName]["responses"][keyof paths[Path][OpName]["responses"]] extends { schema: any } ? paths[Path][OpName]["responses"][keyof paths[Path][OpName]["responses"]]["schema"] : any : any > => { return {} as any; }; 冗余地方有点多,你可以自行优化下 |