构建共享类型包:如何合并多份TS Interface文件到index.d.ts?
问题描述
我正尝试创建一个共享类型包,希望按领域(如菜单、餐厅等)拆分类型文件,再将它们合并到单个index.d.ts文件中。
当前文件结构如下:
project │ index.d.ts │ └───types │ restaurant.d.ts │ menus.d.ts
我尝试在index.d.ts中导入这些文件并将其加入同一个命名空间,代码如下:
import Restaurant from './types/restaurant'; import Menus from './types/menus'; export = MyTypes; export as namespace MyTypes; declare namespace MyTypes { type Restaurant = Restaurant.Restaurant; type Menus = Menus.Menus; }
我的Menus命名空间定义如下:
export = Menus; export as namespace Menus declare module Menus { export interface Menus { id: string; name: string; } }
但此时出现报错:
'Menus' refers to a UMD global, but the current file is a module. Consider adding an import instead.ts(2686)
请问我是否应该在此处使用declare module和export?如何正确定义Menus类型并在index.d.ts中导入?使用rollup这类工具是否更合适?
解决方案
1. 调整子类型文件的定义方式
不需要在子类型文件里用declare module,直接用ES模块导出类型即可,这样能避免UMD全局的冲突问题,也符合TypeScript现代模块规范。
修改types/menus.d.ts:
export interface Menus { id: string; name: string; }
types/restaurant.d.ts同理,改成直接导出类型:
export interface Restaurant { id: string; name: string; address: string; }
2. 重构index.d.ts整合类型
现在可以直接在index.d.ts中导入子类型,两种整合方式可选:
方式一:用命名空间整合(匹配你的原有思路)
import * as RestaurantTypes from './types/restaurant'; import * as MenuTypes from './types/menus'; export as namespace MyTypes; export = MyTypes; declare namespace MyTypes { export type Restaurant = RestaurantTypes.Restaurant; export type Menus = MenuTypes.Menus; }
方式二:直接作为ES模块导出(更推荐)
如果你的包供ES模块使用,完全可以不用命名空间,直接聚合导出:
export type { Restaurant } from './types/restaurant'; export type { Menus } from './types/menus';
用户使用时可直接按需导入:import { Restaurant, Menus } from 'your-package',更灵活。
3. 关于Rollup这类工具的必要性
如果只是单纯的类型包(只有.d.ts文件),完全不需要用Rollup。TypeScript本身可通过tsconfig.json配置来整合类型文件:
- 在
tsconfig.json中设置"declaration": true,可选配置"declarationDir": "./dist"指定类型输出目录 - 把
index.d.ts作为入口,TS会自动处理依赖的类型文件,用户安装包后可直接读取类型。
如果你的包包含JS代码+类型,Rollup可用来打包JS代码,但类型文件依然靠TS自身处理即可。
内容的提问来源于stack exchange,提问作者Stretch0
相关产品推荐
相关产品推荐

