CommonJS环境下如何导出异步初始化的Client对象?
实现无需提前await的异步初始化Client导出
核心思路是用Proxy代理包装异步初始化的Promise,让代理对象在被调用方法时自动等待Client初始化完成,从而实现导入后直接await client.getPets()的效果。
解决方案代码
首先缓存Client初始化的Promise(避免重复执行初始化逻辑),再用Proxy拦截属性访问:
async function get_client() { const api = new OpenAPIClientAxios({ definition: 'http://localhost/api/openapi.json', axiosConfigDefaults: { headers: { "Authorization": `Bearer ${get_bearer()}`, "Content-Type": "application/json", }, }, }); api.init(); api.withServer({ url: "http://localhost/" }); return await api.getClient(); } // 缓存初始化Promise,确保只执行一次Client初始化 const clientPromise = get_client(); // 创建代理对象,拦截所有属性/方法访问 const client = new Proxy({}, { get: async (_, prop) => { // 等待Client初始化完成 const realClient = await clientPromise; // 返回真实Client对应的属性或方法 return realClient[prop as keyof typeof realClient]; }, }) as unknown as ClientType; export { client };
原理说明
- 代理对象本身是一个空对象,但通过
get陷阱拦截了所有属性访问请求 - 当你调用
client.getPets()时,Proxy会先等待clientPromiseresolve拿到真实的Client实例,再返回实例上的getPets方法 - 因为
clientPromise是缓存的,所以第一次调用后后续请求都会直接使用已初始化完成的Client,不会重复执行初始化逻辑
使用方式
导入后直接调用方法并await即可:
import { client } from './api'; // 无需提前await client,直接await方法调用 console.log(await client.getPets());
注意事项
- 如果Client初始化失败,调用方法时会抛出初始化时的错误,建议在调用处添加try/catch处理
- 第一次调用方法会等待初始化完成,存在一定的延迟,后续调用则无额外开销
内容的提问来源于stack exchange,提问作者Paul Sender
相关产品推荐
相关产品推荐

