A TypeScript Angular2 starter project walkthrough – integrating TypeScript

by
Tags: , , ,
Category:

Note – This blog entry is out of date and is being kept online for historical purposes. The repository is located at github.com/angular-seed-typescript.

Setting up the typescript compiler

Now it's time to configure TypeScript, the JavaScript uber-language
that is taking over from CoffeeScript as the darling of modern JavaScript
development. TypeScript is a strongly-typed, mostly ES6 language syntax
that can be transpiled down to ES5. We’ll set it up so that any files we
configure in the src/ directory ending in .ts
will be compiled by our Gulp compiler.

We'll start by defining tsconfig.json in the root of the project
(ignore the extra newlines at the end of the files section,
they just help the example fit in our blog article):

{
  "version": "1.6.0",
  "compilerOptions": {
    "rootDir": "src",
    "outDir": "web/js",
    "target": "es5",
    "module": "system",
    "declaration": false,
    "noImplicitAny": false,
    "removeComments": true,
    "noLib": false,
    "emitDecoratorMetadata": true,
    "experimentalDecorators": true,
    "sourceMap": true,
    "listFiles": true
  },
  "files": [
        "node_modules/angular2/bundles/typings
           /angular2/angular2.d.ts",
        "node_modules/angular2/bundles/typings
           /angular2/http.d.ts",
        "node_modules/angular2/bundles/typings
           /angular2/router.d.ts",
        "node_modules/@reactivex/rxjs/es6/R.d.ts",
        "src/hiya.ts"
  ]
}

The config file is used by several leading editors including Atom and Visual Studio Code, and allows them to call the TypeScript compiler during code edits. It also works well with the Gulp plugin gulp-typescript. This particular example does the following things:

  • Tells the compiler to generate ES5-compatable code

  • Uses the System.js module shim

  • emits decorators (annotations) and new, experimental ones
    (from Angular) that are not part of the standard listFiles

  • generates source maps

  • compiles certain files (in the files section only)

A weakness with this file

Currently, every single TypeScript file must be placed in the list of files in the files section (as of TypeScript 1.6.2).
However, some tools, such as Atom and gulp-typescript, honor the filesGlob section, which you can
write up like this to capture all TypeScript files, like this:

  "filesGlob": [
    "src/**/*.ts"
  ],

Finally, you’ll want to exclude any other node modules by default, so you add the exclude property to tsconfig.json:

  "exclude": [ "node_modules" ]

And make sure the file is closed properly with a final curly brace. The file should look like this when finished:

  "version": "1.6.0",
  "compilerOptions": {
    "rootDir": "src",
    "outDir": "web/js",
    "target": "es5",
    "module": "system",
    "declaration": false,
    "noImplicitAny": false,
    "removeComments": true,
    "noLib": false,
    "emitDecoratorMetadata": true,
    "experimentalDecorators": true,
    "sourceMap": true,
    "listFiles": true
  },
  "files": [
        "node_modules/angular2/bundles/typings
           /angular2/angular2.d.ts",
        "node_modules/angular2/bundles/typings
           /angular2/http.d.ts",
        "node_modules/angular2/bundles/typings
           /angular2/router.d.ts",
        "node_modules/@reactivex/rxjs/es6/R.d.ts",
        "src/hiya.ts"
  ],
  "filesGlob": [
    "src/**/*.ts"
  ],
  "exclude": [ "node_modules" ]
}

If you want to push the TypeScript compiler team to make this a native feature of the TypeScript
compiler’s tooling, feel free to cast a vote over at
the github issue – #1927.

Typescript components

TypeScript is installed using the following Node command:

npm install -g typescript@1.6.2

We’re using 1.6.2 as a more recent version of TypeScript. This may be able to be dropped at this point, but
it’s a force of habit for me at the moment.

This provides a command-line compiler, tsc, as well as an
API. Let's try using the compiler against a trivial test file:

Put the file hiya.ts in your src directory
using the following contents:

class Foo {
  constructor() {
    console.log('hiya');
  }
}

Run the tsc command again, and see if it compiles
your typescript to the web\js directory. Here is what
my TypeScript compiler emitted:

var Foo = (function () {
    function Foo() {
        console.log('hiya');
    }
    return Foo;
})();
//# sourceMappingURL=hiya.js.map

You'll note that TypeScript is generating safe ES5 code here –
converting the class definition into a simple constructor function.
It also makes a note about the source mapping as a cross-reference
comment.

Adding TypeScript compilation to the build

Now we'll install the gulp-typescript plugin to
execute TypeScript during our ts gulp task.

npm install --save-dev gulp-typescript

Let’s replace the ts function with the lines below. Note
the stand-alone line at the top – you can paste that toward the top of the
file and replace the task where you placed the original stub.

// add this line after the initial gulp require statement
var ts = require('gulp-typescript');
// replace the Gulp task for ts with this:
gulp.task('ts', function(done) {
  var tsResult = gulp.src([
      "node_modules/angular2/bundles/typings/angular2/angular2.d.ts",
      "node_modules/angular2/bundles/typings/angular2/http.d.ts",
      "node_modules/angular2/bundles/typings/angular2/router.d.ts",
      "node_modules/@reactivex/rxjs/dist/es6/Rx.d.ts",
      "src/**/*.ts"
    ])
    .pipe(ts(tsProject), undefined, ts.reporter.fullReporter());
  return tsResult.js.pipe(gulp.dest('web/js'));
});

(Ignore the line breaks in the paths, they are there so the sample fits in the blog article space).
Now, you should be able to use gulp ts to compile the typescript. Try it, and it should
do the exact same build as before, just using gulp instead of the
TypeScript command-line tool directly.

Next, we’ll install the web server, Express, and configure live reload. Then we’ll be all set to try out a simple application.