Gulp

Gulp

本快速入门指南将教你如何打造打字稿gulp,然后添加BrowserifyuglifyWatchify到吞气管道。本指南还使用Babelify添加了Babel功能。

我们假设你已经在使用Node.js的NPM

最小的项目

让我们开始一个新的目录。我们proj现在就为它命名,但你可以将它改为任何你想要的。

mkdir proj cd proj

首先,我们将按照以下方式构建我们的项目:

proj/ ├─ src/ └─ dist/

TypeScript文件将从您的src文件夹开始,通过TypeScript编译器运行并结束dist

让我们支撑这一点:

mkdir src mkdir dist

初始化该项目

现在我们将把这个文件夹变成一个npm包。

npm init

你会得到一系列提示。您可以使用除入口点之外的默认值。对于你的入口点,使用./dist/main.js。您可以随时返回并在package.json为您生成的文件中进行更改。

安装我们的依赖关系

现在我们可以使用npm install安装软件包了。首先gulp-cli全局安装(如果您使用的是Unix系统,则可能需要npm install在本指南中使用前缀命令sudo)。

npm install -g gulp-cli

然后安装typescriptgulpgulp-typescript在您的项目的开发依赖。Gulp- typescript是Typescript的一个插件。

npm install --save-dev typescript gulp gulp-typescript

写一个简单的例子

我们来写一个Hello World程序。在src,创建文件main.ts

function hello(compiler: string) { console.log(`Hello from ${compiler}` } hello("TypeScript"

在项目根目录下proj,创建文件tsconfig.json

{ "files": [ "src/main.ts" ], "compilerOptions": { "noImplicitAny": true, "target": "es5" } }

创建一个 gulpfile.js

在项目根目录下,创建文件gulpfile.js

var gulp = require("gulp" var ts = require("gulp-typescript" var tsProject = ts.createProject("tsconfig.json" gulp.task("default", function () { return tsProject.src() .pipe(tsProject()) .js.pipe(gulp.dest("dist") }

测试最终的应用程序

gulp node dist/main.js

该程序应打印“来自TypeScript的Hello!”。

将代码添加到模块中

在我们开始使用Browserify之前,让我们构建代码并将模块添加到组合中。这是您更可能用于真实应用程序的结构。

创建一个名为src/greet.ts

export function sayHello(name: string) { return `Hello from ${name}`; }

现在更改代码src/main.tssayHellogreet.ts以下位置导入:

import { sayHello } from "./greet"; console.log(sayHello("TypeScript")

最后,添加src/greet.tstsconfig.json

{ "files": [ "src/main.ts", "src/greet.ts" ], "compilerOptions": { "noImplicitAny": true, "target": "es5" } }

确保模块通过运行gulp然后在Node中测试来工作:

gulp node dist/main.js

请注意,即使我们使用ES2015模块语法,TypeScript也会发出节点使用的CommonJS模块。在本教程中,我们将坚持使用CommonJS,但您可以module在options对象中设置以更改此选项。

Browserify

现在让我们把这个项目从Node移到浏览器。为此,我们希望将我们所有的模块打包成一个JavaScript文件。幸运的是,这正是Browserify所做的。更好的是,它让我们使用由Node使用的CommonJS模块系统,这是默认的TypeScript方式。这意味着我们的TypeScript和Node设置将基本不变地传输到浏览器。

首先,安装browserifytsifyvinyl-source-stream。tsify是一个Browserify插件,与gulp-typescript一样,可以访问TypeScript编译器。vinyl-source-stream让我们可以将Browserify的文件输出重新转换为一种可以称之为vinyl的格式。

npm install --save-dev browserify tsify vinyl-source-stream

创建一个页面

srcnamed中创建一个文件index.html

<!DOCTYPE html> <html> <head> <meta charset="UTF-8" /> <title>Hello World!</title> </head> <body> <p id="greeting">Loading ...</p> <script src="bundle.js"></script> </body> </html>

现在main.ts转到更新页面:

import { sayHello } from "./greet"; function showHello(divName: string, name: string) { const elt = document.getElementById(divName elt.innerText = sayHello(name } showHello("greeting", "TypeScript"

调用showHello调用sayHello以更改段落的文本。现在将您的gulp文件更改为以下内容:

var gulp = require("gulp" var browserify = require("browserify" var source = require('vinyl-source-stream' var tsify = require("tsify" var paths = { pages: ['src/*.html'] }; gulp.task("copy-html", function () { return gulp.src(paths.pages) .pipe(gulp.dest("dist") } gulp.task("default", ["copy-html"], function () { return browserify{ basedir: '.', debug: true, entries: ['src/main.ts'], cache: {}, packageCache: {} }) .plugin(tsify) .bundle() .pipe(source('bundle.js')) .pipe(gulp.dest("dist") }

这添加了该copy-html任务并将其添加为依赖项default。这意味着任何时候都要default运行,copy-html必须先运行。我们也改变default了使用tsify插件而不是gulp-typescript来调用Browserify。方便的是,它们都允许我们将相同的选项对象传递给TypeScript编译器。

调用bundle我们使用source(我们的乙烯来源流的别名)来命名我们的输出包bundle.js

通过运行gulp然后dist/index.html在浏览器中打开来测试页面。您应该在页面上看到“来自TypeScript的Hello”。

注意我们指定debug: true给Browserify。这会导致tsify在绑定的JavaScript文件中发出源映射。源地图让您可以在浏览器中调试原始的TypeScript代码,而不是捆绑的JavaScript。您可以通过打开浏览器的调试器并在其中放置断点来测试源映射的工作方式main.ts。刷新页面时,断点应暂停页面并让您进行调试greet.ts

Watchify,Babel和Uglify

现在我们将我们的代码与Browserify和tsify捆绑在一起,我们可以使用browserify插件为我们的构建添加各种功能。

  • Watchify开始使用gulp并保持运行,每当您保存文件时都会逐步编译。这可以让您在浏览器中保持编辑 - 保存刷新周期。

  • Babel是一款非常灵活的编译器,可将ES2015及以后的版本转换为ES5和ES3。这使您可以添加TypeScript不支持的广泛的自定义转换。

  • 下载我们将从Watchify开始提供后台编译:npm install --save-dev watchify gulp-utilNow将您的gulp文件更改为以下内容:var gulp = require(“gulp” ); var browserify = require(“browserify”); var source = require('vinyl-source-stream'); var watchify = require(“watchify”); var tsify = require(“tsify”); var gutil = require(“gulp-util”); var paths = {pages:['src / *。html']}; var watchedBrowserify = watchify(browserify({basedir:'。',debug:true,entries:['src / main.ts'],cache:{},packageCache:{}})。plugin(tsify)); gulp.task(“copy-html”,function(){return gulp.src(paths.pages).pipe(gulp.dest(“dist”));}); 函数bundle(){return watchedBrowserify .bundle().pipe(source('bundle.js')).pipe(gulp.dest(“dist”)); } gulp.task(“default”,[“copy-html”],bundle); watchedBrowserify.on(“更新”,捆绑); watchedBrowserify.on(“log”,gutil.log);这里基本上有三个变化,但它们需要你重构你的代码。

  • 我们将browserify实例包装在一个调用中watchify,然后保持结果。

  • 我们调用了watchedBrowserify.on("update", bundle这个选项,以便bundle每次您的TypeScript文件发生更改时,Browserify都会运行该函数。

  • 我们调用watchedBrowserify.on("log", gutil.log登录到控制台。

一起(1)和(2)意味着我们必须将我们的呼叫转移browserifydefault任务。default由于Watchify和Gulp都需要这个名称,所以我们必须给这个函数起个名字。使用(3)添加日志记录是可选的,但对调试设置非常有用。

现在,当你运行Gulp时,它应该开始并保持运行。试着改变代码showHellomain.ts并保存。你应该看到如下所示的输出:

proj$ gulp [10:34:20] Using gulpfile ~/src/proj/gulpfile.js [10:34:20] Starting 'copy-html'... [10:34:20] Finished 'copy-html' after 26 ms [10:34:20] Starting 'default'... [10:34:21] 2824 bytes written (0.13 seconds) [10:34:21] Finished 'default' after 1.36 s [10:35:22] 2261 bytes written (0.02 seconds) [10:35:24] 2808 bytes written (0.05 seconds)

Uglify

首先安装Uglify。由于Uglify的意义在于破坏你的代码,我们还需要安装vinyl-buffer和gulp-sourcemaps来保持源代码的工作。

npm install --save-dev gulp-uglify vinyl-buffer gulp-sourcemaps

现在将您的gulp文件更改为以下内容:

var gulp = require("gulp" var browserify = require("browserify" var source = require('vinyl-source-stream' var tsify = require("tsify" var uglify = require('gulp-uglify' var sourcemaps = require('gulp-sourcemaps' var buffer = require('vinyl-buffer' var paths = { pages: ['src/*.html'] }; gulp.task("copy-html", function () { return gulp.src(paths.pages) .pipe(gulp.dest("dist") } gulp.task("default", ["copy-html"], function () { return browserify{ basedir: '.', debug: true, entries: ['src/main.ts'], cache: {}, packageCache: {} }) .plugin(tsify) .bundle() .pipe(source('bundle.js')) .pipe(buffer()) .pipe(sourcemaps.init{loadMaps: true})) .pipe(uglify()) .pipe(sourcemaps.write('./')) .pipe(gulp.dest("dist") }

注意,uglify它本身只有一个调用 - 调用buffersourcemaps存在以确保源映射保持正常工作。这些调用为我们提供了一个单独的源代码文件,而不像以前那样使用内联源代码。现在你可以运行Gulp并检查它bundle.js是否被缩小到一个不可读的混乱:

gulp cat dist/bundle.js

Babel

首先安装ES1515的Babelify和Babel预设。像Uglify一样,Babelify破坏代码,所以我们需要乙烯缓冲区和gulp源代码。默认情况下,Babelify将只与扩展处理文件.js.es.es6.jsx因此我们需要将添加.ts扩展作为一个选项,以Babelify。

npm install --save-dev babelify babel-preset-es2015 vinyl-buffer gulp-sourcemaps

现在将您的gulp文件更改为以下内容:

var gulp = require('gulp' var browserify = require('browserify' var source = require('vinyl-source-stream' var tsify = require('tsify' var sourcemaps = require('gulp-sourcemaps' var buffer = require('vinyl-buffer' var paths = { pages: ['src/*.html'] }; gulp.task('copyHtml', function () { return gulp.src(paths.pages) .pipe(gulp.dest('dist') } gulp.task('default', ['copyHtml'], function () { return browserify{ basedir: '.', debug: true, entries: ['src/main.ts'], cache: {}, packageCache: {} }) .plugin(tsify) .transform('babelify', { presets: ['es2015'], extensions: ['.ts'] }) .bundle() .pipe(source('bundle.js')) .pipe(buffer()) .pipe(sourcemaps.init{loadMaps: true})) .pipe(sourcemaps.write('./')) .pipe(gulp.dest('dist') }

我们还需要使用TypeScript目标ES2015。然后Babel将根据TypeScript发出的ES2015代码生成ES5。让我们修改tsconfig.json

{ "files": [ "src/main.ts" ], "compilerOptions": { "noImplicitAny": true, "target": "es2015" } }

对于如此简单的脚本,Babel的ES5输出应该与TypeScript的输出非常相似。