I'm trying to write a gulp task to execute a program and to wait for any key to be pressed to exit the program.
So far I have this:
gulp.task('runDevelopment', function (done) {
console.log('\n\n---\nPress any key to exit\n---\n');
var api = spawn('node', ['node_modules/api-gateway-server/server.js', 'etc/swagger.yaml']);
api.stdout.on('data', function (data) {
console.log(data.toString());
});
api.stderr.on('data', function (data) {
console.log(data.toString());
});
process.stdin.on('data', function () {
api.kill('SIGKILL');
done();
});
});
This runs the program, and kills it as expected but gulp never quits. I see this in the console:
20:04 $ gulp
[20:06:54] Using gulpfile ~/Development/swiki/gulpfile.js
[20:06:54] Starting 'documentCopy'...
[20:06:54] Starting 'documentZip'...
[20:06:54] Starting 'runDevelopment'...
---
Press any key to exit
---
[20:06:54] Finished 'documentCopy' after 52 ms
[20:06:54] Finished 'documentZip' after 41 ms
[20:06:54] Starting 'package'...
[20:06:54] Finished 'package' after 4.9 μs
API Gateway server listening on port 7111
[20:06:57] Finished 'runDevelopment' after 3.06 s
[20:06:57] Starting 'run'...
[20:06:57] Finished 'run' after 2.72 μs
[20:06:57] Starting 'default'...
[20:06:57] Finished 'default' after 1.16 μs
Terminated: 15
✘-TERM ~/Development/swiki [master|…6]
20:07 $
gulp gives me the Terminated: 15 only after I killall gulp in another terminal.
How can I get this to work properly?
The problem is that you're successfully terminating the child process by sending SIGKILL, but you're still listening for incoming data on process.stdin of the parent process. As long as you are doing that the parent process won't exit.
You have to explicitly tell process.stdin to no longer emit 'data' events by calling stream.pause():
process.stdin.on('data', function () {
process.stdin.pause();
api.kill('SIGKILL');
done();
});
If all else fails you can also call process.exit() as a last resort:
process.stdin.on('data', function () {
api.kill('SIGKILL');
done();
process.exit(0);
});
Related
I'm new to Gulp. I wrote a function to parse the version in my package.json file like this
// Get the semver part of the version, e.g.,
// version = 1.4.31-p2, should return 1.4.31
function getSemVer(cb) {
var semVer = pkg.version;
if (semVer.includes("-")) {
semVer = semVer.split("-")[0];
}
console.log(semVer);
cb();
}
exports.getSemVer = getSemver
But when I run this I get an error
$ gulp getSemver -f gulpfiles/version.js
[22:56:58] Working directory changed to /path/gulpfiles
[22:56:59] Using gulpfile /path/gulpfiles/version.js
[22:56:59] Starting 'getSemVer'...
[22:56:59] 'getSemVer' errored after 1.53 ms
[22:56:59] TypeError: semVer.includes is not a function
at getSemVer (/path/gulpfiles/version.js:27:14)
at taskWrapper (/path/node_modules/undertaker/lib/set-task.js:13:15)
at bound (node:domain:416:15)
at runBound (node:domain:427:12)
at asyncRunner (/path/node_modules/async-done/index.js:55:18)
at processTicksAndRejections (node:internal/process/task_queues:78:11)
I thought includes() a valid JavaScript function, shown in JavaScript String includes(). What gives?
When I edit theme .yml files in my themes source folder, I get this error. This does not happen when I edit scss or template .yml files from the template folder, only in the main folder. Others that had this error use things like webpack what I don't have. The gulp task for copy_theme_files is the same as other tasks with the difference that it has no return because I didn't know how to return there with two gulp.src functions.
gulp.task('copy_theme_files', function() {
console.log('[copy_theme_files] Console Log: copy '+paths.themeSrc+' to '+paths.themeDest);
gulp.src(paths.themeSrc)
.pipe(gulp.dest(paths.themeDest));
gulp.src(paths.root + '/*.{png,ico,svg}')
.pipe(paths.themeDest);
});
Full gulpfile.js https://pastebin.com/NWt2uMwV
Error Output:
[00:37:58] Using gulpfile /var/www/themes.src/mytheme.src/gulpfile.js
[00:37:58] Starting 'watch'...
[00:38:20] Starting 'copy_theme_files'...
[copy_theme_files] Console Log: copy *.{yml,theme,php,png,jpg,gif,svg,ico},.gitkeep to build
[00:38:20] 'copy_theme_files' errored after 23 ms
[00:38:20] TypeError: dest.on is not a function
at DestroyableTransform.Readable.pipe (/var/www/themes.src/mytheme.src/node_modules/readable-stream/lib/_stream_readable.js:564:8)
at /var/www/themes.src/mytheme.src/gulpfile.js:122:10
at taskWrapper (/var/www/themes.src/mytheme.src/node_modules/undertaker/lib/set-task.js:13:15)
at bound (domain.js:395:14)
at runBound (domain.js:408:12)
at asyncRunner (/var/www/themes.src/mytheme.src/node_modules/async-done/index.js:55:18)
at process._tickCallback (internal/process/next_tick.js:61:11)
[00:38:20] Starting 'copy_includes'...
[copy_includes] Console Log: copy includes/**/*.*,includes/**/.gitkeep to build/includes
[00:38:20] Finished 'copy_includes' after 7.41 ms
[00:38:20] Starting 'copy_build'...
[copy_build] Console Log: copy build/**/*.*,build/**/.gitkeep to ../../web/themes/local/mytheme
[00:38:20] Finished 'copy_build' after 60 ms
Other tasks run fine
[00:41:06] Starting 'copy_templates'...
[copy_templates] Console Log: copy templates/**/*.twig,templates/**/.gitkeep to build/templates
[00:41:08] Finished 'copy_templates' after 1.86 s
[00:41:08] Starting 'copy_build'...
[copy_build] Console Log: copy build/**/*.*,build/**/.gitkeep to ../../web/themes/local/mytheme
[00:41:09] Finished 'copy_build' after 326 ms
You have this line in your task:
.pipe(paths.themeDest);
You probably mean:
.pipe(gulp.dest(paths.themeDest));
For your other question look at merging two gulp.src streams for how to return:
var merge = require('merge-stream');
gulp.task('copy_theme_files', function() {
console.log('[copy_theme_files] Console Log: copy '+paths.themeSrc+' to '+paths.themeDest);
const themesStream = gulp.src(paths.themeSrc)
.pipe(gulp.dest(paths.themeDest));
const imagesStream = gulp.src(paths.root + '/*.{png,ico,svg}')
.pipe(paths.themeDest);
return merge(themesStream , imagesStream );
});
I was following the answer (the one chosen by op) here to change directory in my gulpfile.js. To test whether the directory was changed, I added another task that prints the current directory. When run, both tasks are executed without any errors. However, console.log prints the address
of the parent directory instead of the directory that was navigated into in the previous task.
Here's how I setup my directory, gulpfile.js and package.json.
directory tree
-- auth
---- gulpfile.js
---- package.json
---- other js scripts
---- <dest_folder>
gulpfile.js
/// TASKS
gulp.task('directory-changer', changeDirectory);
gulp.task('directory-printer', printCD);
gulp.task('default', gulp.series('directory-changer', 'directory-printer'));
/// TASKS
function changeDirectory(done) {
process.chdir(path.resolve(__dirname, 'dest'));
gulp.src()
done();
}
function printCD(done) {
console.log(__dirname);
done();
}
pacakge.json
{ // other properties
"scripts": {
"test": "echo \"Error: no test specified\" && exit 1",
"run-gulp": "node ./node_modules/gulp/bin/gulp.js"
},
// other fields
The output generated:
npm run run-gulp
> auth#1.0.0 run-gulp <PROJECT_PATH>/
> node ./node_modules/gulp/bin/gulp.js
[13:42:48] Using gulpfile <PROJECT_PATH>/gulpfile.js
[13:42:48] Starting 'default'...
[13:42:48] Starting 'directory-changer'...
[13:42:48] Finished 'directory-changer' after 1.14 ms
[13:42:48] Starting 'directory-printer'...
<PROJECT_PATH>/
[13:42:48] Finished 'directory-printer' after 387 μs
[13:42:48] Finished 'default' after 4.81 ms
Now my I think that it maybe because the __dirname is printing the execution path of the script rather than the changed directory. Is that the case or is there something else going on?
I am trying to run the gulp build task for the dev environment on the server but its failing. However, The same gulp build is working on my local machine. The function and error are given below.
Function:
// S3 Upload for dev
gulp.task('s3sync:dev', function () {
var config = {
accessKeyId: "-Key-",
secretAccessKey: "-Key-"
};
var s3 = require('gulp-s3-upload')(config);
return gulp.src("./dist/**")
.pipe(s3({
Bucket: 'example',
ACL: 'public-read'
}, {
maxRetries: 5
}))
});
Command:
Gulp build:development
Error:
[09:01:04] Starting 's3sync:dev'...
events.js:160
throw er; // Unhandled 'error' event
^
Error: EISDIR: illegal operation on a directory, read
at Error (native)
Any idea?
Finally, This problem has been solved by removing a system symlink which was created after the deployment from the capistrano which is also running below npm commands.
npm run clean && npm run build
After removing the system file. I have run the below command and it works fine.
gulp build:development
I am trying to get browserSync to work with a watch task for a Polymer app. Here is my gulp file:
function source() {
return project.splitSource()
.pipe(gulpif('**/*.html', html.lint())).on('end', log('Linted HTML'))
.pipe(gulpif('**/*.html', html.minify())).on('end', log('Minified HTML'))
.pipe(gulpif('**/*.js', javascript.minify())).on('end', log('Minified Javascript'))
.pipe(gulpif('**/*.js', javascript.babelify())).on('end', log('Transpiled Javascript'))
.pipe(gulpif('**/*.{gif,jpg,svg}', images.minify())).on('end', log('Minified Images'))
.pipe(project.rejoin()); // Call rejoin when you're finished
}
function dependencies() {
return project.splitDependencies()
.pipe(project.rejoin());
}
gulp.task('default', gulp.series([
clean.build,
project.merge(source, dependencies),
project.serviceWorker
]));
gulp.task('reload', function(){
browserSync.reload();
} );
gulp.task('dev', gulp.series(
project.merge(source, dependencies)
));
gulp.task('browser-sync', function(){
return new Promise(function(resolve){
resolve( browserSync({
port: 5000,
notify: false,
logPrefix: 'PSK',
snippetOptions: {
rule: {
match: '<span id="browser-sync-binding"></span>',
fn: function(snippet) {
return snippet;
}
}
},
server: {
baseDir: ['./'],
}
})
)
});
})
gulp.task('watch', function(){
gulp.watch(['**/*.html'], gulp.series('dev','reload'));
gulp.watch(['**/*.js'], gulp.series('dev', 'reload'));
});
gulp.task('serve',
gulp.series(
'dev',
gulp.parallel('browser-sync','watch')), function(){
return gulp.src('**/*.html', {passthrough:true})
}
);
The project.splitSource is a polymer starter kit specific function that splits web components into seperate html , css, js entities so you can perform whatever tasks you need on them.
When I run 'gulp serve' , the tasks complete and my app is served.
As soon as I change the contents of a file, the watch runs the 'dev' task and attempts to run the reload task, and thats where it crashes. Here is the command line messages for this entire process :
→ gulp serve
[08:53:43] Using gulpfile ~/Documents/Projects/unicef/etools-dashboard/gulpfile.js
[08:53:43] Starting 'serve'...
[08:53:43] Starting 'dev'...
[08:53:43] Starting 'output'...
[08:55:20] Linted HTML
[08:55:20] Minified HTML
[08:55:20] Minified CSS
[08:55:20] Minified Javascript
[08:55:20] Transpiled Javascript
[08:55:20] gulp-imagemin: Minified 511 images (saved 212 kB - 3.1%)
[08:55:20] Minified Images
[08:55:29] Finished 'output' after 1.75 min
[08:55:29] Finished 'dev' after 1.75 min
[08:55:29] Starting 'browser-sync'...
[08:55:29] Starting 'watch'...
[08:55:30] Finished 'browser-sync' after 551 ms
[PSK] Access URLs:
--------------------------------------
Local: http://localhost:5000
External: http://192.168.0.102:5000
--------------------------------------
UI: http://localhost:3001
UI External: http://192.168.0.102:3001
--------------------------------------
[PSK] Serving files from: ./
[08:56:20] Starting 'dev'...
[08:56:20] Starting 'output'...
[08:56:20] Finished 'output' after 288 ms
[08:56:20] Finished 'dev' after 290 ms
[08:56:20] Starting 'reload'...
[PSK] Reloading Browsers...
Error: write after end
at writeAfterEnd (_stream_writable.js:159:12)
at StreamAnalyzer.Writable.write (_stream_writable.js:204:5)
at PassThrough.ondata (/Users/Marko1/Documents/Projects/unicef/etools-dashboard/node_modules/merge-stream/node_modules/readable-stream/lib/_stream_readable.js:546:20)
at emitOne (events.js:77:13)
at PassThrough.emit (events.js:169:7)
at readableAddChunk (/Users/Marko1/Documents/Projects/unicef/etools-dashboard/node_modules/merge-stream/node_modules/readable-stream/lib/_stream_readable.js:217:18)
at PassThrough.Readable.push (/Users/Marko1/Documents/Projects/unicef/etools-dashboard/node_modules/merge-stream/node_modules/readable-stream/lib/_stream_readable.js:176:10)
at PassThrough.Transform.push (/Users/Marko1/Documents/Projects/unicef/etools-dashboard/node_modules/merge-stream/node_modules/readable-stream/lib/_stream_transform.js:123:32)
at afterTransform (/Users/Marko1/Documents/Projects/unicef/etools-dashboard/node_modules/merge-stream/node_modules/readable-stream/lib/_stream_transform.js:79:51)
at TransformState.afterTransform (/Users/Marko1/Documents/Projects/unicef/etools-dashboard/node_modules/merge-stream/node_modules/readable-stream/lib/_stream_transform.js:58:12)
[08:56:21] The following tasks did not complete: serve, <parallel>, watch, <series>, reload
[08:56:21] Did you forget to signal async completion?
Any idea why the reload causes this to crash? I've googled this "write after end" and seems like the stream needs to be returned or async actions need an explicit done cb, but I'm not sure how to do that with gulp 4. Any advice would be of great help.