将参数传递给 Gulp 任务
Pass Parameter to Gulp Task
通常我们可以 运行 gulp 通过类似 gulp mytask
的方式从控制台执行任务。无论如何,我可以将参数传递给 gulp 任务吗?如果可能,请举例说明如何完成。
这是一个功能程序离不开的东西。你可以试试 yargs.
npm install --save-dev yargs
你可以这样使用它:
gulp mytask --production --test 1234
在代码中,例如:
var argv = require('yargs').argv;
var isProduction = (argv.production === undefined) ? false : true;
供您理解:
> gulp watch
console.log(argv.production === undefined); <-- true
console.log(argv.test === undefined); <-- true
> gulp watch --production
console.log(argv.production === undefined); <-- false
console.log(argv.production); <-- true
console.log(argv.test === undefined); <-- true
console.log(argv.test); <-- undefined
> gulp watch --production --test 1234
console.log(argv.production === undefined); <-- false
console.log(argv.production); <-- true
console.log(argv.test === undefined); <-- false
console.log(argv.test); <-- 1234
希望你能从这里开始。
您可以使用另一个插件,minimist。还有另一个 post,其中有 yargs 和 minimist 的很好的例子:(Is it possible to pass a flag to Gulp to have it run tasks in different ways?)
@Ethan 的回答完全有效。根据我的经验,更多节点的方式是使用环境变量。这是配置部署在托管平台(例如 Heroku 或 Dokku)上的程序的标准方法。
要从命令行传递参数,请这样做:
发展:
gulp dev
制作:
NODE_ENV=production gulp dev
语法不同,但很Unix,兼容Heroku、Dokku等
您可以在代码中访问变量 process.env.NODE_ENV
MYAPP=something_else gulp dev
会设置
process.env.MYAPP === 'something_else'
This answer 可能会给你一些其他的想法。
这是我的使用示例。对于 css/less 任务。所有人都可以申请。
var cssTask = function (options) {
var minifyCSS = require('gulp-minify-css'),
less = require('gulp-less'),
src = cssDependencies;
src.push(codePath + '**/*.less');
var run = function () {
var start = Date.now();
console.log('Start building CSS/LESS bundle');
gulp.src(src)
.pipe(gulpif(options.devBuild, plumber({
errorHandler: onError
})))
.pipe(concat('main.css'))
.pipe(less())
.pipe(gulpif(options.minify, minifyCSS()))
.pipe(gulp.dest(buildPath + 'css'))
.pipe(gulpif(options.devBuild, browserSync.reload({stream:true})))
.pipe(notify(function () {
console.log('END CSS/LESS built in ' + (Date.now() - start) + 'ms');
}));
};
run();
if (options.watch) {
gulp.watch(src, run);
}
};
gulp.task('dev', function () {
var options = {
devBuild: true,
minify: false,
watch: false
};
cssTask (options);
});
有官方的 gulp 食谱,使用 minimist。
https://github.com/gulpjs/gulp/blob/master/docs/recipes/pass-arguments-from-cli.md
基础知识是使用 minimist 来分离 cli 参数并将它们与已知选项组合:
var options = minimist(process.argv.slice(2), knownOptions);
这会解析类似
的内容
$ gulp scripts --env development
食谱中有更完整的信息。
只需将其加载到进程中的新对象中.. process.gulp = {}
并让任务在那里查看。
如果您想避免添加额外的依赖项,我发现节点的 process.argv
很有用:
gulp.task('mytask', function() {
console.log(process.argv);
});
所以如下:
gulp mytask --option 123
应该显示:
[ 'node', 'path/to/gulp.js', 'mytask', '--option', '123']
如果您确定所需参数位于正确位置,则不需要标志。**只需使用(在本例中):
var option = process.argv[4]; //set to '123'
但是:由于选项可能未设置,或者可能处于不同的位置,我觉得更好的主意是:
var option, i = process.argv.indexOf("--option");
if(i>-1) {
option = process.argv[i+1];
}
这样,您就可以处理多个选项的变化,例如:
//task should still find 'option' variable in all cases
gulp mytask --newoption somestuff --option 123
gulp mytask --option 123 --newoption somestuff
gulp mytask --flag --option 123
** 编辑:对于节点脚本是正确的,但是 gulp 将没有前导“--”的任何内容解释为另一个任务名称。所以使用 gulp mytask 123
会失败,因为 gulp 找不到名为“123”的任务。
如果你想使用环境参数和其他工具,比如日志,你可以使用gulp-util
/*
$npm install gulp-util --save-dev
$gulp --varName 123
*/
var util = require('gulp-util');
util.log(util.env.varName);
更新
gulp-util 现已弃用。您可以改用 minimist。
var argv = require('minimist')(process.argv.slice(2));
console.dir(argv);
将参数传递给 gulp 可能意味着以下几点:
- 从命令行到 gulp文件(已在此处举例说明)。
- 从 gulpfile.js 脚本主体到 gulp 任务。
- 从一个 gulp 任务到另一个 gulp 任务。
这是一种将参数从主 gulp 文件传递到 gulp 任务的方法。通过将需要参数的任务移动到它自己的模块并将其包装在函数中(因此可以传递参数)。:
// ./gulp-tasks/my-neat-task.js file
module.exports = function(opts){
opts.gulp.task('my-neat-task', function(){
console.log( 'the value is ' + opts.value );
});
};
//main gulpfile.js file
//...do some work to figure out a value called val...
var val = 'some value';
//pass that value as a parameter to the 'my-neat-task' gulp task
require('./gulp-tasks/my-neat-task.js')({ gulp: gulp, value: val});
如果您有很多 gulp 任务并想向它们传递一些方便的环境配置,这会派上用场。我不确定它是否可以在一个任务和另一个任务之间工作。
如果将 gulp 与 yargs 一起使用, 请注意以下事项:
如果您有任务 'customer' 并且不想使用 yargs build in Parameter checking for required commands:
.command("customer <place> [language]","Create a customer directory")
调用它:
gulp customer --customer Bob --place Chicago --language english
yargs 总是会抛出一个错误,即没有足够的命令分配给调用,即使您有!! —
尝试一下,只在命令中添加一个数字(使其不等于 gulp-任务名称)...它会起作用:
.command("customer1 <place> [language]","Create a customer directory")
这是因为 gulp 似乎在 yargs 能够检查此必需参数之前触发任务。弄清楚这一点花了我几个小时。
希望这对你有帮助..
这是另一种没有额外模块的方法:
我需要根据任务名称猜测环境,我有一个 'dev' 任务和一个 'prod' 任务。
当我运行 gulp prod
应该设置为生产环境。
当我 运行 gulp dev
或其他任何东西时,它应该设置为开发环境。
为此,我只检查 运行ning 任务名称:
devEnv = process.argv[process.argv.length-1] !== 'prod';
我知道我回答这个问题来晚了,但我想补充一些内容来回答@Ethan,这是投票最高和被接受的答案。
我们可以使用 yargs
来获取命令行参数,并且我们还可以为一些参数添加我们自己的别名,如下所示。
var args = require('yargs')
.alias('r', 'release')
.alias('d', 'develop')
.default('release', false)
.argv;
请参阅此 link 了解更多详情。
https://github.com/yargs/yargs/blob/HEAD/docs/api.md
以下是 yargs
文档中给出的别名的使用。我们还可以在那里找到更多 yargs
功能,可以使命令行传递体验更好。
.alias(key, alias)
Set key names as equivalent such that updates to a key will propagate
to aliases and vice-versa.
Optionally .alias() can take an object that maps keys to aliases. Each
key of this object should be the canonical version of the option, and
each value should be a string or an array of strings.
肯定有更短的表示法,但那是我的方法:
gulp.task('check_env', function () {
return new Promise(function (resolve, reject) {
// gulp --dev
var env = process.argv[3], isDev;
if (env) {
if (env == "--dev") {
log.info("Dev Mode on");
isDev = true;
} else {
log.info("Dev Mode off");
isDev = false;
}
} else {
if (variables.settings.isDev == true) {
isDev = true;
} else {
isDev = false;
}
}
resolve();
});
});
如果要根据实际 Git 分支 (master/develop) 设置环境:
gulp.task('set_env', function (cb) {
exec('git rev-parse --abbrev-ref HEAD', function (err, stdout, stderr) {
const git__branch = stdout.replace(/(\r\n|\n|\r)/gm, ""),
regex__feature = new RegExp('feature/feature-*');
if (git__branch == "develop") {
log.info("Develop Branch");
isCompressing = false;
} else if (git__branch == "master") {
log.info("Master Branch");
isCompressing = true;
} else if (regex__feature.test(git__branch) === true){
log.info("✨Feature Branch");
isCompressing = true;
}else{
//TODO: check for other branch
log.warn("Unknown " + git__branch + ", maybe hotfix?");
//isCompressing = variables.settings.isCompressing;
}
log.info(stderr);
cb(err);
});
return;
})
P.s。对于日志,我添加了以下内容:
var log = require('fancy-log');
如果你需要它,那是我的默认任务:
gulp.task('default',
gulp.series('set_env', gulp.parallel('build_scss', 'minify_js', 'minify_ts', 'minify_html', 'browser_sync_func', 'watch'),
function () {
}));
欢迎提出优化建议。
通常我们可以 运行 gulp 通过类似 gulp mytask
的方式从控制台执行任务。无论如何,我可以将参数传递给 gulp 任务吗?如果可能,请举例说明如何完成。
这是一个功能程序离不开的东西。你可以试试 yargs.
npm install --save-dev yargs
你可以这样使用它:
gulp mytask --production --test 1234
在代码中,例如:
var argv = require('yargs').argv;
var isProduction = (argv.production === undefined) ? false : true;
供您理解:
> gulp watch
console.log(argv.production === undefined); <-- true
console.log(argv.test === undefined); <-- true
> gulp watch --production
console.log(argv.production === undefined); <-- false
console.log(argv.production); <-- true
console.log(argv.test === undefined); <-- true
console.log(argv.test); <-- undefined
> gulp watch --production --test 1234
console.log(argv.production === undefined); <-- false
console.log(argv.production); <-- true
console.log(argv.test === undefined); <-- false
console.log(argv.test); <-- 1234
希望你能从这里开始。
您可以使用另一个插件,minimist。还有另一个 post,其中有 yargs 和 minimist 的很好的例子:(Is it possible to pass a flag to Gulp to have it run tasks in different ways?)
@Ethan 的回答完全有效。根据我的经验,更多节点的方式是使用环境变量。这是配置部署在托管平台(例如 Heroku 或 Dokku)上的程序的标准方法。
要从命令行传递参数,请这样做:
发展:
gulp dev
制作:
NODE_ENV=production gulp dev
语法不同,但很Unix,兼容Heroku、Dokku等
您可以在代码中访问变量 process.env.NODE_ENV
MYAPP=something_else gulp dev
会设置
process.env.MYAPP === 'something_else'
This answer 可能会给你一些其他的想法。
这是我的使用示例。对于 css/less 任务。所有人都可以申请。
var cssTask = function (options) {
var minifyCSS = require('gulp-minify-css'),
less = require('gulp-less'),
src = cssDependencies;
src.push(codePath + '**/*.less');
var run = function () {
var start = Date.now();
console.log('Start building CSS/LESS bundle');
gulp.src(src)
.pipe(gulpif(options.devBuild, plumber({
errorHandler: onError
})))
.pipe(concat('main.css'))
.pipe(less())
.pipe(gulpif(options.minify, minifyCSS()))
.pipe(gulp.dest(buildPath + 'css'))
.pipe(gulpif(options.devBuild, browserSync.reload({stream:true})))
.pipe(notify(function () {
console.log('END CSS/LESS built in ' + (Date.now() - start) + 'ms');
}));
};
run();
if (options.watch) {
gulp.watch(src, run);
}
};
gulp.task('dev', function () {
var options = {
devBuild: true,
minify: false,
watch: false
};
cssTask (options);
});
有官方的 gulp 食谱,使用 minimist。
https://github.com/gulpjs/gulp/blob/master/docs/recipes/pass-arguments-from-cli.md
基础知识是使用 minimist 来分离 cli 参数并将它们与已知选项组合:
var options = minimist(process.argv.slice(2), knownOptions);
这会解析类似
的内容$ gulp scripts --env development
食谱中有更完整的信息。
只需将其加载到进程中的新对象中.. process.gulp = {}
并让任务在那里查看。
如果您想避免添加额外的依赖项,我发现节点的 process.argv
很有用:
gulp.task('mytask', function() {
console.log(process.argv);
});
所以如下:
gulp mytask --option 123
应该显示:
[ 'node', 'path/to/gulp.js', 'mytask', '--option', '123']
如果您确定所需参数位于正确位置,则不需要标志。**只需使用(在本例中):
var option = process.argv[4]; //set to '123'
但是:由于选项可能未设置,或者可能处于不同的位置,我觉得更好的主意是:
var option, i = process.argv.indexOf("--option");
if(i>-1) {
option = process.argv[i+1];
}
这样,您就可以处理多个选项的变化,例如:
//task should still find 'option' variable in all cases
gulp mytask --newoption somestuff --option 123
gulp mytask --option 123 --newoption somestuff
gulp mytask --flag --option 123
** 编辑:对于节点脚本是正确的,但是 gulp 将没有前导“--”的任何内容解释为另一个任务名称。所以使用 gulp mytask 123
会失败,因为 gulp 找不到名为“123”的任务。
如果你想使用环境参数和其他工具,比如日志,你可以使用gulp-util
/*
$npm install gulp-util --save-dev
$gulp --varName 123
*/
var util = require('gulp-util');
util.log(util.env.varName);
更新
gulp-util 现已弃用。您可以改用 minimist。
var argv = require('minimist')(process.argv.slice(2));
console.dir(argv);
将参数传递给 gulp 可能意味着以下几点:
- 从命令行到 gulp文件(已在此处举例说明)。
- 从 gulpfile.js 脚本主体到 gulp 任务。
- 从一个 gulp 任务到另一个 gulp 任务。
这是一种将参数从主 gulp 文件传递到 gulp 任务的方法。通过将需要参数的任务移动到它自己的模块并将其包装在函数中(因此可以传递参数)。:
// ./gulp-tasks/my-neat-task.js file
module.exports = function(opts){
opts.gulp.task('my-neat-task', function(){
console.log( 'the value is ' + opts.value );
});
};
//main gulpfile.js file
//...do some work to figure out a value called val...
var val = 'some value';
//pass that value as a parameter to the 'my-neat-task' gulp task
require('./gulp-tasks/my-neat-task.js')({ gulp: gulp, value: val});
如果您有很多 gulp 任务并想向它们传递一些方便的环境配置,这会派上用场。我不确定它是否可以在一个任务和另一个任务之间工作。
如果将 gulp 与 yargs 一起使用, 请注意以下事项:
如果您有任务 'customer' 并且不想使用 yargs build in Parameter checking for required commands:
.command("customer <place> [language]","Create a customer directory")
调用它:
gulp customer --customer Bob --place Chicago --language english
yargs 总是会抛出一个错误,即没有足够的命令分配给调用,即使您有!! —
尝试一下,只在命令中添加一个数字(使其不等于 gulp-任务名称)...它会起作用:
.command("customer1 <place> [language]","Create a customer directory")
这是因为 gulp 似乎在 yargs 能够检查此必需参数之前触发任务。弄清楚这一点花了我几个小时。
希望这对你有帮助..
这是另一种没有额外模块的方法:
我需要根据任务名称猜测环境,我有一个 'dev' 任务和一个 'prod' 任务。
当我运行 gulp prod
应该设置为生产环境。
当我 运行 gulp dev
或其他任何东西时,它应该设置为开发环境。
为此,我只检查 运行ning 任务名称:
devEnv = process.argv[process.argv.length-1] !== 'prod';
我知道我回答这个问题来晚了,但我想补充一些内容来回答@Ethan,这是投票最高和被接受的答案。
我们可以使用 yargs
来获取命令行参数,并且我们还可以为一些参数添加我们自己的别名,如下所示。
var args = require('yargs')
.alias('r', 'release')
.alias('d', 'develop')
.default('release', false)
.argv;
请参阅此 link 了解更多详情。 https://github.com/yargs/yargs/blob/HEAD/docs/api.md
以下是 yargs
文档中给出的别名的使用。我们还可以在那里找到更多 yargs
功能,可以使命令行传递体验更好。
.alias(key, alias)
Set key names as equivalent such that updates to a key will propagate to aliases and vice-versa.
Optionally .alias() can take an object that maps keys to aliases. Each key of this object should be the canonical version of the option, and each value should be a string or an array of strings.
肯定有更短的表示法,但那是我的方法:
gulp.task('check_env', function () {
return new Promise(function (resolve, reject) {
// gulp --dev
var env = process.argv[3], isDev;
if (env) {
if (env == "--dev") {
log.info("Dev Mode on");
isDev = true;
} else {
log.info("Dev Mode off");
isDev = false;
}
} else {
if (variables.settings.isDev == true) {
isDev = true;
} else {
isDev = false;
}
}
resolve();
});
});
如果要根据实际 Git 分支 (master/develop) 设置环境:
gulp.task('set_env', function (cb) {
exec('git rev-parse --abbrev-ref HEAD', function (err, stdout, stderr) {
const git__branch = stdout.replace(/(\r\n|\n|\r)/gm, ""),
regex__feature = new RegExp('feature/feature-*');
if (git__branch == "develop") {
log.info("Develop Branch");
isCompressing = false;
} else if (git__branch == "master") {
log.info("Master Branch");
isCompressing = true;
} else if (regex__feature.test(git__branch) === true){
log.info("✨Feature Branch");
isCompressing = true;
}else{
//TODO: check for other branch
log.warn("Unknown " + git__branch + ", maybe hotfix?");
//isCompressing = variables.settings.isCompressing;
}
log.info(stderr);
cb(err);
});
return;
})
P.s。对于日志,我添加了以下内容:
var log = require('fancy-log');
如果你需要它,那是我的默认任务:
gulp.task('default',
gulp.series('set_env', gulp.parallel('build_scss', 'minify_js', 'minify_ts', 'minify_html', 'browser_sync_func', 'watch'),
function () {
}));
欢迎提出优化建议。