23

How to run a npm script command from inside a gulp task?

package.json

"scripts": 
{
    "tsc": "tsc -w"
}

gulpfile.js

gulp.task('compile:app', function(){
  return gulp.src('src/**/*.ts')
    .pipe(/*npm run tsc*/)
    .pipe(gulp.dest('./dist'))
    .pipe(connect.reload());
});

I want to do this because running npm run tsc does not give me any error but if I use gulp-typescript to compile .ts then I get bunch of errors.

lbrahim
  • 3,710
  • 12
  • 57
  • 95

3 Answers3

14

You can get the equivalent using gulp-typescript

var gulp = require('gulp');
var ts = require('gulp-typescript');

gulp.task('default', function () {
  var tsProject = ts.createProject('tsconfig.json');

  var result = tsProject.src().pipe(ts(tsProject));

  return result.js.pipe(gulp.dest('release'));
});

gulp.task('watch', ['default'], function() {
  gulp.watch('src/*.ts', ['default']);
});

Then on your package.json

"scripts": {
  "gulp": "gulp",
  "gulp-watch": "gulp watch"
}

Then run

npm run gulp-watch

Alternatively using shell

var gulp = require('gulp');
var shell = require('gulp-shell');

gulp.task('default', function () {
  return gulp.src('src/**/*.ts')
    .pipe(shell('npm run tsc'))
    .pipe(gulp.dest('./dist'))
    .pipe(connect.reload());
});

gulp-shell has been blacklisted you can see why here

Another alternative would be setting up webpack.

BrunoLM
  • 97,872
  • 84
  • 296
  • 452
  • How can i run gulp watch along with npm start. I tried but on npm start the scss is not getting compiled to css as it should be. Here is the code in package.json: "start": "concurrently \"npm run tsc:w\" \"npm run lite\" \"gulp\" ", – Peter Nov 04 '16 at 18:02
  • Running the command from the command line works fine. Using this I get `ReferenceError: connect is not defined` but even after installing `gulp-connect`, I got events.js:141 throw er; // Unhandled 'error' event ^ Error: spawn npm run buildng ENOENT at exports._errnoException (util.js:907:11) at Process.ChildProcess._handle.onexit (internal/child_process.js:178:32) at onErrorNT (internal/child_process.js:344:16) at nextTickCallbackWith2Args (node.js:442:9) at process._tickCallback (node.js:356:17) Process terminated with code 1. – Serj Sagan May 04 '17 at 03:03
  • Note that `gulp-shell` has been blacklisted by `gulp`. Use `child_process.exec` or `child_process.spawn` instead. See https://stackoverflow.com/questions/29511491/running-a-shell-command-from-gulp – 4Z4T4R Oct 04 '17 at 21:47
14

Wasted about 1 hour on this simple thing, looking for a ~complete answer, so adding another here:

If you question is only on typescript (tsc), see https://stackoverflow.com/a/36633318/984471
Else, see below for a generic answer.

The question title is generic, so a generic example is given below first, then the answer.

Generic example:

  1. Install nodejs, if you haven't, preferably LTS version, from here: https://nodejs.org/

  2. Install below:

    npm install --save-dev gulp gulp-run

  3. File package.json has below contents (other contents can be there):

{
      "name": "myproject",
      "scripts": {
          "cmd1": "echo \"yay! cmd1 command is run.\" && exit 1",
      }
}
  1. Create a file gulpfile.js with below contents:
var gulp = require('gulp');
var run = require('gulp-run');

gulp.task('mywatchtask1', function () {
    // watch for javascript file (*.js) changes, in current directory (./)
    gulp.watch('./*.js', function () {

        // run an npm command called `test`, when above js file changes
        return run('npm run cmd1').exec();

        // uncomment below, and comment above, if you have problems
        // return run('echo Hello World').exec();
    });
});
  1. Run the task mywatchtask1 using gulp?

    gulp mywatchtask1

Now, gulp is its watching for js file changes in the current directory
if any changes happen then the npm command cmd1 is run, it will print yay! cmd1 command is run. everytime the one of the js file changes.

For this question: as another example:

a) package.json will have

"tsc": "tsc -w",

instead of the below:

"cmd1": "echo \"yay! cmd1 command is run.\" && exit 1",

b) and, gulpfile.js will have:

return run('npm run tsc').exec();

instead of below:

return run('npm run cmd1').exec();

Hope that helps.

Fabian Lauer
  • 8,891
  • 4
  • 26
  • 35
Manohar Reddy Poreddy
  • 25,399
  • 9
  • 157
  • 140
7

You can try to implement it using childprecess node package or

use https://www.npmjs.com/package/gulp-run

var run = require('gulp-run');
gulp.task('compile:app', function(){
  return gulp.src(['src/**/*.js','src/**/*.map'])
    .pipe(run('npm run tsc'))
    .pipe(gulp.dest('./dist'))
    .pipe(connect.reload());

});
LazyDeveloper
  • 599
  • 3
  • 8