Angular 2 已经发布了 2.1.2 版本, 相信很多人已经在使用(试用)了, 相比 AngularJS 1.x , Angular 2 在性能上有了长足的进步, 同时 Angular 2 也变得非常的庞大, 动辄几兆的脚本, 如何部署到生产环境? 接下来就介绍如何为生产环境编译 Angular 2 应用, 在本文中, 我们将 Angular 2 官方文档中的 Hello Angular
应用编译到 50K 以下, 以用于生产环境。
未经优化的应用
根据 Angular2 官方的 QuickStart 快速创建一个 Hello Angular
应用, 在没有任何优化的情况下, 运行情况如下图所示:
从上图可以看出, 仅仅一个 Hello 应用, 就产生了 40 个请求, 加载了 1.8M 的脚本, 这个在生产环境下(特别是移动端)是无法接受的。
要看这一步的完整源代码, 请移步 GitHub 。
打包与压缩
传统的方式无非就是进行打包和压缩, 我使用 browserify 和 uglifyjs 来进行打包与压缩, 首先是安装这两个工具类库:
npm i -D browserify uglifyjs
在 package.json 文件中添加这两个 npm 命令:
{ "scripts": { "bundle": "browserify -s main app/main.js > dist/bundle.js", "minify": "uglifyjs dist/bundle.js --screw-ie8 --compress --mangle --output dist/bundle.min.js" } }
现在运行这两个命令, 看看会怎么样:
npm run bundle && npm run minify
经过一大堆 WARN 之后, 没有出现 ERROR , 也没有出现 npm-debug.log 文件, 证明没有错误, 现在来分析一下大小:
ls -hl dist -rw-r--r-- 1 zhang staff 1.4M Nov 14 14:08 bundle.js -rw-r--r-- 1 zhang staff 528K Nov 14 14:10 bundle.min.js
bundle.js 有 1.4M , 不过 bundle.min.js 被压缩到了 528K , 看起来还不错, 还可以再优化一下, 那就是 gzip 压缩, 通常在服务器上都会启用:
gzip dist/bundle.min.js -c > dist/bundle.min.js.gz && ls -hl dist -rw-r--r-- 1 zhang staff 1.4M Nov 14 14:08 bundle.js -rw-r--r-- 1 zhang staff 528K Nov 14 14:10 bundle.min.js -rw-r--r-- 1 zhang staff 129K Nov 14 14:15 bundle.min.js.gz
经过 gzip 之后, bundle.min.js.gz 有 129K , 似乎应该可以了吧? 但是我觉得还有优化的空间。
要看这一步的完整源代码, 请移步 GitHub 。
AOT 以及 Tree Shaking
ES2016 (ES6) 有一个很重要的特性, 那就是 Tree Shaking , 可以移除项目中不需要的部分, 接下来我们使用 rollup 进行 Tree Shaking 。
为了能够使用 Tree Shaking , 我们需要将项目中的 TypeScript 编译成 ES2015 脚本, 需要修改 TypeScript 配置, 新建一个 tsconfig-es2015.json
的配置文件, 内容如下:
{ "compilerOptions": { "target": "es2015", "module": "es2015", "moduleResolution": "node", "declaration": false, "removeComments": true, "noLib": false, "emitDecoratorMetadata": true, "experimentalDecorators": true, "lib": ["es6", "es2015", "dom"], "sourceMap": true, "pretty": true, "allowUnreachableCode": false, "allowUnusedLabels": false, "noImplicitAny": true, "noImplicitReturns": true, "noImplicitUseStrict": false, "noFallthroughCasesInSwitch": true, "typeRoots": [ "./node_modules/@types", "./node_modules" ], "types": [ ] }, "files": [ "app/main-aot.ts" ] }
在 Angular2 应用中, 包含了一个即时编辑器 (JIT) , 在预编译好的应用中不是必需的, 使用 Angular2 的 AOT 编译可以移除即时编译器 (JIT) , 因此需要先安装 Angular 的编译器:
npm i -D @angular/compiler-cli
为了使用 aot 编译出来的文件, main.ts 文件也要做相应的修改, 将 main.ts 文件另存为 main-aot.ts , 修改内容如下:
import { enableProdMode } from '@angular/core'; import { platformBrowser } from '@angular/platform-browser'; import { AppModuleNgFactory } from './app.module.ngfactory'; enableProdMode(); const platform = platformBrowser(); platform.bootstrapModuleFactory(AppModuleNgFactory);
不再使用 platform-browser-dynamic
, 改为使用 platform-browser
。
同时 index.html 也另存为 index-aot.html
, 也做相应的修改, 不在加载 system.js , 改为直接使用最终的 aot 脚本:
<!-- <script src="/UploadFiles/2021-04-02/system.src.js">接下来的整体的思路是:
1、使用 ngc 进行 aot 编译;
npm run ngc -- -p tsconfig-es2015.json这一步将会生成一系列
*.ngfactory.ts *.module.metadata.json
临时文件, 可以更新.gitignore
来忽略这些文件, 避免对代码库造成污染;2、将 typescript 文件编译成 es2015 (es6) 脚本;
npm run tsc -- -p tsconfig-es2015.json3、使用 rollup 进行 tree shaking , 移除项目不使用的功能;
rollup -f iife -c rollup.config.js -o dist/bundle-aot-es2015.js4、再次使用 typescript 将 tree shaking 之后的脚本编译成 es5 脚本;
tsc --target es5 --allowJs dist/bundle-aot-es2015.js -out dist/bundle-aot.js5、使用 uglifyjs 再次压缩上一部生成的 es5 脚本;
uglifyjs dist/bundle-aot.js --screw-ie8 --compress --mangle --output dist/bundle-aot.min.js这几个命令对应的 npm 脚本如下:
{ "scripts": { "ngc": "ngc", "rollup": "rollup -f iife -c rollup.config.js -o dist/bundle-aot-es2015.js", "es5": "tsc --target es5 --allowJs dist/bundle-aot-es2015.js -out dist/bundle-aot.js", "minify-aot": "uglifyjs dist/bundle-aot.js --screw-ie8 --compress --mangle --output dist/bundle-aot.min.js", "prod-aot": "npm run ngc -- -p tsconfig-es2015.json && npm run tsc -- -p tsconfig-es2015.json && rollup && npm run es5 && npm run minify-aot" } }最终只要运行一个命令即可:
npm run prod-aot最后来看一下最终的文件大小:
ls -hl -rw-r--r-- 1 zhang staff 595K Nov 14 15:59 bundle-aot-es2015.js -rw-r--r-- 1 zhang staff 669K Nov 14 16:01 bundle-aot.js -rw-r--r-- 1 zhang staff 194K Nov 14 16:01 bundle-aot.min.js -rw-r--r-- 1 zhang staff 46K Nov 14 16:02 bundle-aot.min.js.gz -rw-r--r-- 1 zhang staff 1.4M Nov 14 15:54 bundle.js -rw-r--r-- 1 zhang staff 528K Nov 14 15:54 bundle.min.js -rw-r--r-- 1 zhang staff 129K Nov 14 16:02 bundle.min.js.gz最终生成的 bundle-aot.min.js.gz 只有 46K , 比没有使用 aot 编译的最终文件 bundle.min.js.gz 少了将近 2/3 , 可以说 aot + tree shaking 效果非常的显著。
要看这一步的完整源代码, 请移步 GitHub 。
经过这样的终极编译优化编译之后, 应该可以放心的部署到生产环境了。
参考资料:
Angular Quick Start
AoT Compilation
Building an Angular 2 Application for Production
以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持。
免责声明:本站文章均来自网站采集或用户投稿,网站不提供任何软件下载或自行开发的软件! 如有用户或公司发现本站内容信息存在侵权行为,请邮件告知! 858582#qq.com
《魔兽世界》大逃杀!60人新游玩模式《强袭风暴》3月21日上线
暴雪近日发布了《魔兽世界》10.2.6 更新内容,新游玩模式《强袭风暴》即将于3月21 日在亚服上线,届时玩家将前往阿拉希高地展开一场 60 人大逃杀对战。
艾泽拉斯的冒险者已经征服了艾泽拉斯的大地及遥远的彼岸。他们在对抗世界上最致命的敌人时展现出过人的手腕,并且成功阻止终结宇宙等级的威胁。当他们在为即将于《魔兽世界》资料片《地心之战》中来袭的萨拉塔斯势力做战斗准备时,他们还需要在熟悉的阿拉希高地面对一个全新的敌人──那就是彼此。在《巨龙崛起》10.2.6 更新的《强袭风暴》中,玩家将会进入一个全新的海盗主题大逃杀式限时活动,其中包含极高的风险和史诗级的奖励。
《强袭风暴》不是普通的战场,作为一个独立于主游戏之外的活动,玩家可以用大逃杀的风格来体验《魔兽世界》,不分职业、不分装备(除了你在赛局中捡到的),光是技巧和战略的强弱之分就能决定出谁才是能坚持到最后的赢家。本次活动将会开放单人和双人模式,玩家在加入海盗主题的预赛大厅区域前,可以从强袭风暴角色画面新增好友。游玩游戏将可以累计名望轨迹,《巨龙崛起》和《魔兽世界:巫妖王之怒 经典版》的玩家都可以获得奖励。