Neoheurist
Neoheurist

Reputation: 3474

TypeScript typing files are not being created/copied

When I run tsc from the command line my .js, .map, and .d.ts files are created:

C:\Users\{user}\Documents\My Projects\BEPS\angular2-soap>tsc -version
Version 1.8.10

...but when I invoke the following Gulp function everything works except that the .d.ts files are not created/copied to the ./app/ directory:

gulp.task('compile-typescript', function () {
    var sourcemaps = require('gulp-sourcemaps');
    var typescript = require('gulp-typescript');
    var typescriptCompiler = typescript({typescript: require('typescript')});
    var typescriptProject = typescript(typescript.createProject('tsconfig.json'));

    var tsResults = gulp.src(['!./src/**/spec*.ts', './src/**/*.ts'])
        .pipe(typescriptProject)
        .pipe(sourcemaps.init())
        .pipe(sourcemaps.write('../map/'))
        .pipe(gulp.dest('./app/'))
        .pipe(typescriptCompiler).dts.pipe(gulp.dest('./app/'));

    return tsResults;
});

snippet from my package.json file:

"devDependencies": {
   "autoprefixer": "6.3.6",
   "concurrently": "2.0.0",
   "cssnano": "3.5.2",
   "del": "2.2.0",
   "gulp": "3.9.1",
   "gulp-ext-replace": "0.3.0",
   "gulp-imagemin": "2.4.0",
   "gulp-postcss": "6.1.0",
   "gulp-sourcemaps": "1.6.0",
   "gulp-typescript": "2.13.0",
   "http-server": "0.9.0",
   "jasmine-core": "2.4.1",
   "karma": "0.13.22",
   "karma-chrome-launcher": "0.2.3",
   "karma-jasmine": "0.3.8",
   "karma-spec-reporter": "0.0.26",
   "lite-server": "2.2.0",
   "postcss": "5.0.19",
   "postcss-scss": "0.1.7",
   "precss": "^1.3.0",
   "run-sequence": "1.1.5",
   "systemjs": "0.19.26",
   "typescript": "latest",
   "typings": "0.8.1"
 },

my tsconfig.json file:

{
  "compileOnSave": true,
  "compilerOptions": {
    "target": "ES5",
    "module": "System",
    "moduleResolution": "node",
    "emitDecoratorMetadata": true,
    "experimentalDecorators": true,
    "removeComments": true,
    "noImplicitAny": true,
    "declaration": true,
    "sourceMap": true,
    "mapRoot": "map/",
    "diagnostics": true
  },
  "exclude": [
    "node_modules",
    "typings"
  ]
}

I thought that all I needed to do was to use the dts pipe to send the typing files to ./app/

What am I missing/doing incorrectly? Thanks!


Attempting to apply the suggestion from t34t5:

gulp.task('compile-typescript', function () {
    var sourcemaps = require('gulp-sourcemaps');
    var typescript = require('gulp-typescript');
    var project = typescript.createProject('tsconfig.json', {declaration: true});
    var merge = require('merge2');

    var tsResults = gulp.src(['!./src/**/spec*.ts', './src/**/*.ts'])
        .pipe(sourcemaps.init())
        .pipe(typescript(project))
        .pipe(sourcemaps.write('../map/'));

    return merge([
        tsResults.dts.pipe(gulp.dest('./app/')),
        tsResults.js.pipe(gulp.dest('./app/'))
    ]);
});

I get an error accessing tsResults.dts:

TypeError: Cannot read property 'pipe' of undefined

My guess is that the sourcemaps stream is what is being used (not the typescript stream)... does this make sense? if so, what can I do to fix it?


The following generates both the .js and .d.ts files - because it's not trying to also generate .map files:

gulp.task('compile-typescript', function () {
    var typescript = require('gulp-typescript');
    var project = typescript.createProject('tsconfig.json', {declaration: true});
    var merge = require('merge2');

    var tsResults = gulp.src(['!./src/**/spec*.ts', './src/**/*.ts'])
        .pipe(typescript(project));

    return merge([
        tsResults.dts.pipe(gulp.dest('./app/')),
        tsResults.js.pipe(gulp.dest('./app/'))
    ]);
});

Upvotes: 2

Views: 1962

Answers (4)

Jason Leach
Jason Leach

Reputation: 4229

I think you can do this in one step without merge. This works for me and produces all .js, .d.ts and js.map files:

const tsp = ts.createProject("tsconfig.json");

gulp.task('transpile-src', () =>
  tsp
    .src()
    .pipe(sourcemaps.init())
    .pipe(tsp())
    .pipe(
      sourcemaps.write('.', {
        includeContent: false,
        sourceRoot: file => {
          return file.cwd + '/src';
        },
      })
    )
    .pipe(gulp.dest('dist/src'))
);

Upvotes: 0

ryano.mcc13
ryano.mcc13

Reputation: 474

I think you would need to use something such as merge to write both the js files and type definition files. I may be wrong but I believe the stream closes after your first gulp.dest() so nothing gets sent through the dts pipe. Take a look at the readme file for gulp typescript. Under the basic usage section.

UPDATE: I was able to get the following to work using your tsconfig file. I was only using a single typescript source file though. This generated the .js, .d.ts, and .map files.

gulp.task('compile-typescript', function () {
    var typescript = require('gulp-typescript');
    var project = typescript.createProject('tsconfig.json', {declaration: true});
    var merge = require('merge2');

    var tsResults = gulp.src(['!./src/**/spec*.ts', './src/**/*.ts'])
        .pipe(sourcemaps.init())
        .pipe(typescript(project);

    return merge([
        tsResults.dts.pipe(gulp.dest('./app/')),
        tsResults.js.pipe(sourcemaps.write('./app/')).pipe(gulp.dest('./app/'))
    ]);


});

Upvotes: 1

Neoheurist
Neoheurist

Reputation: 3474

The following achieves the effect that I am seeking - but it requires the .ts source files to be compiled twice (once to generate the .js and .map files and once to generate the .d.ts files)

gulp.task('compile-typescript', function () {
    var sourcemaps = require('gulp-sourcemaps');
    var typescript = require('gulp-typescript');
    var merge = require('merge2');

    var src = gulp.src(['!./src/**/spec*.ts', './src/**/*.ts']);
    var dst = gulp.dest('./app/');

    var jsMap = src.pipe(typescript(typescript.createProject('tsconfig.json')))
                   .pipe(sourcemaps.init())
                   .pipe(sourcemaps.write('../map/'));

    var dts = src.pipe(typescript(typescript.createProject('tsconfig.json')));

    return merge([
        jsMap.pipe(dst),   // writes .js and .map files
        dts.dts.pipe(dst)  // writes .d.ts files
    ]);
});

I'm dissatisfied with this approach due to the redundancy - optimization suggestions are welcome.

Upvotes: 1

Louay Alakkad
Louay Alakkad

Reputation: 7408

You should have one typescript compiler, not two.

var typescriptProject = typescript.createProject('tsconfig.json', {
  typescript: require('typescript'), 
  declaration: true,
});

var tsResults = gulp.src(['!./src/**/spec*.ts', './src/**/*.ts'])
    .pipe(sourcemaps.init())
    .pipe(typescript(typescriptProject))
    .pipe(sourcemaps.write('../map/'))
    .pipe(gulp.dest('./app/'));

Upvotes: 0

Related Questions