让我们考虑一下getUser
的实现,客户端上的用法就像那样
const user = await getUser(http, { id: '1' })
工作但不是非常类型安全的实现
// ./api.ts - shared interfaces
const endpoint = '/users'
interface Arg { id: string }
interface Resp { name: string }
// ./client-api.ts - client side
import { endpoint, Arg, Resp } from './api.ts'
function getUser(http: HttpClient, arg: Arg): Promise<Resp> {
return http.get(endpoint, arg)
}
// ./server-api.ts - server side
import { endpoint, Arg, Resp } from './api.ts'
function getUser(db: Db, arg: Arg): Promise<Resp> {
return db.findById(arg.id)
}
// Additionally it needs to be registered
httpServer.on(endpoint, (params) => getUser(db, params))
问题:样板太多,可能会使Arg
与另一个方法Resp
不匹配,或者不匹配endpoint
,或忘记在服务器上注册端点
可能的更好的实施可能就像下面的代码一样。虽然它也没有强制执行端点,但忘记注册服务器端处理程序是可能的:
// ./api.ts
interface GetUser {
endpoint: '/users',
arg: { id: string },
resp: { name: string }
}
type ClientFn<Command> = no idea how to do that, some TS magic
type ServerFn<Command> = no idea how to do that, some TS magic
// ./client-api.ts
const getUser: ClientFn<GetUser> = (http, arg) => http.get(endpoint, arg)
// ./server-api.ts
const getUser: ServerFn<GetUser> = (db, arg) => db.findById(arg.id)
httpServer.on(endpoint, (params) => getUser(db, params))
你知道更好的方式吗?或者也许是TypeScript中的代码生成库可以做到这一点?