使用ng-packagr打包Angular的方法示例
写在前面
为了让Angular类库应用范围更自由,Angular提出一套打包格式建议名曰:AngularPackageFormat,包括FESM2015、FESM5、UMD、ESM2015、ESM5、ES2015格式,不同格式可以在不同的环境(AngularCli、Webpack、SystemJS等)中使用。
传统方式需要对这些格式逐一打包,一个示例打包脚本写法。这种写法只能针对不同项目的配置,而且除非你了解这些格式的本质否则很难维护;后来社区根据APF规范实现了类库ng-packagr,通过简单的配置可以将你的类库打包成APF规范格式。
至V6以后AngularCli也基于ng-packagr实现了另一个@angular-devkit/build-ng-packagr应用构建器。
如何使用
既然ng-packagr被AngularCli内置,这让我们进一步简化了生产一个APF规范格式的类库的成本。在AngualrCli里使用ngglibrary来创建一个类库模板,例如在一个新的Angular应用里执行:
ngglibrary
而打包,则:
ngbuild
最终,将生成的dist/
配置说明
由AngularCli生成的类库模板大部分内容同Angular应用一样,只是多了一个ng-package.json的配置文件(对于生产环境是ng-package.prod.json),它是专门针对ng-packagr的一个配置文件,如同angular.json一般也是基于JSONSchema格式,因此可以通过访问ng-package.schema.json了解所有细节,以下描述一些重点项。
whitelistedNonPeerDependencies
ng-packagr默认会根据package.json的peerDependencies节点清单来决定类库所需要第三方依赖包,这些依赖包是不会被打包至类库。
然而,所依赖包不存在peerDependencies节点里时(当然建议需要依赖的项应该在里面),就需要该属性的配置。
lib/entryFile
指定入口文件。
lib/umdModuleIds
UMD格式采用rollup打包,当类库需要引用一些无法猜出正确UMD标识符时,就需要你手动映射这些类库的标识。
"umdModuleIds":{ "lodash":"_" }
angular.json
AngularCli配置文件angular.json内会增加一个以
"builder":"@angular-devkit/build-ng-packagr:build"
次级入口
有时候一个类库可能会包含着多个二次入口,就像@angular/core类库包含着一个@angular/core/testing模块,它只是运用于测试,因此并不希望在项目中引入@angular/core时也包含测试代码,但同时二者又是同一个功能性时,这种次级导入显得非常重要。
另一种像ngx-bootstrap、@angular/cdk/ally等都提供次级模块的导入,可以更好的优化体积。
不论出于何种目的,都可以通过AngularCli简单的文件组织进一步打包出主、次级分明的类库。
ngglibrary生成的结构大概如下:
├──src |├──public_api.ts |└──lib/*.ts ├──ng-package.json ├──ng-package.prod.json ├──package.json ├──tsconfig.lib.json └──tsconfig.spec.json
当根目录下包含README.md、LICENSE时会自动被复制到dist目录中,Npm规定必须包含README.md文件,否则访问已发布类库页时会有未找到描述文件错误提示。
若想创建一个
├──src |├──public_api.ts |└──lib/*.ts ├──ng-package.json ├──ng-package.prod.json ├──package.json ├──tsconfig.lib.json ├──tsconfig.spec.json └──testing ├──src |├──public_api.ts |└──*.ts └──package.json
核心是需要提供一个package.json文件,而且内容简单到姥姥家。
{ "ngPackage":{} }
最后,依然使用ngbuild
小结
至此,基本上利用AngularCli可以快速的构建一个可发布于NpmAngular类库,更复杂的可以构建像ngx-bootstrap、@angular/cdk/*类库。
自定义构建
AngularCli虽然提供非常便利的环境,但是对于一些复杂环境像Delon类库(ng-alain基建系列类库)包含着多个类库、类库又包含多个次级导入时,AngularCli会显得有点啰嗦,特别是对每个类库的angular.json配置。其实@angular-devkit/build-ng-packagr非常简单,如果将取进一步简化,整个实现差不多相当于:
constpath=require('path'); constngPackage=require('ng-packagr'); consttarget=path.resolve(__dirname,'./projects/'); ngPackage .ngPackagr() .forProject(path.resolve(target,`ng-package.prod.json`)) .withTsConfig(path.resolve(target,'tsconfig.lib.json')) .build() .then(()=>{ //构建完成后干点事 });
将上面的代码放到./build.js,执行:
nodescripts/build.js
其结果完成是等价。
build()返回的是一个Promise对象,意味着可以确保构建开始前和结束后做一点额外的事。
总结
ng-packagr极大简化Angular类库被打包出一个APF规范建议,虽然它以ng-开头,但本质上并不一定非要在Angular中运用,也可以使用在React、VUE。
以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持毛票票。