From 42ab8ae8583745d48ce09c44741bbc0a77b9bca4 Mon Sep 17 00:00:00 2001 From: Joyee Cheung Date: Tue, 7 Feb 2023 01:37:17 +0100 Subject: [PATCH] cli: implement --run --- lib/internal/main/run.js | 45 ++++++++++++++++++++++++++++++++++++++++ src/node.cc | 4 ++++ src/node_file.cc | 1 + src/node_options.cc | 3 +++ src/node_options.h | 1 + 5 files changed, 54 insertions(+) create mode 100644 lib/internal/main/run.js diff --git a/lib/internal/main/run.js b/lib/internal/main/run.js new file mode 100644 index 00000000000000..129e4c8f4bf312 --- /dev/null +++ b/lib/internal/main/run.js @@ -0,0 +1,45 @@ +'use strict'; + +const { + JSONParse, + ObjectKeys +} = primordials; + +const { + prepareMainThreadExecution, + markBootstrapComplete +} = require('internal/process/pre_execution'); +const { internalModuleReadJSON } = internalBinding('fs'); +const { execSync } = require('child_process'); +const { getOptionValue } = require('internal/options'); +const { log, error } = console; + +prepareMainThreadExecution(false, false); + +markBootstrapComplete(); + +const result = internalModuleReadJSON('package.json'); +if (result.length === 0) { + error(`Can't read package.json`); + process.exit(1); +} + +const json = JSONParse(result[0]); +const id = getOptionValue('--run'); +const command = json.scripts[id]; + +if (!command) { + error(`Missing script: "${id}"`); + error('Available scripts are:\n'); + for (const script of ObjectKeys(json.scripts)) { + error(` ${script}: ${json.scripts[script]}`); + } + process.exit(1); +} + +log(''); +log('>', id); +log('>', command); +log(''); + +execSync(command, { stdio: 'inherit' }); diff --git a/src/node.cc b/src/node.cc index f92be4b089db87..b3c7b4383d298a 100644 --- a/src/node.cc +++ b/src/node.cc @@ -344,6 +344,10 @@ MaybeLocal StartExecution(Environment* env, StartExecutionCallback cb) { return StartExecution(env, "internal/main/watch_mode"); } + if (!env->options()->run.empty()) { + return StartExecution(env, "internal/main/run"); + } + if (!first_argv.empty() && first_argv != "-") { return StartExecution(env, "internal/main/run_main_module"); } diff --git a/src/node_file.cc b/src/node_file.cc index 49ed96eca05416..d2f733f02d4aba 100644 --- a/src/node_file.cc +++ b/src/node_file.cc @@ -1079,6 +1079,7 @@ static void InternalModuleReadJSON(const FunctionCallbackInfo& args) { } else if (n == 7) { if (0 == memcmp(s, "exports", 7)) break; if (0 == memcmp(s, "imports", 7)) break; + if (0 == memcmp(s, "scripts", 7)) break; } } diff --git a/src/node_options.cc b/src/node_options.cc index c1f97a5d9207eb..f9a13bdad73b66 100644 --- a/src/node_options.cc +++ b/src/node_options.cc @@ -506,6 +506,9 @@ EnvironmentOptionsParser::EnvironmentOptionsParser() { AddOption("--prof-process", "process V8 profiler output generated using --prof", &EnvironmentOptions::prof_process); + AddOption("--run", + "Run a script specified in package.json", + &EnvironmentOptions::run); // Options after --prof-process are passed through to the prof processor. AddAlias("--prof-process", { "--prof-process", "--" }); #if HAVE_INSPECTOR diff --git a/src/node_options.h b/src/node_options.h index 07ec47d861c77f..d2ba9e2a3dde3a 100644 --- a/src/node_options.h +++ b/src/node_options.h @@ -178,6 +178,7 @@ class EnvironmentOptions : public Options { false; #endif // DEBUG + std::string run; bool watch_mode = false; bool watch_mode_report_to_parent = false; bool watch_mode_preserve_output = false;