create-wdio 9.32.0 → 10.0.0-alpha.149

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -262,6 +262,13 @@ export declare const QUESTIONNAIRE: ({
262
262
  default: (answers: Questionnair) => Promise<string>;
263
263
  when: (answers: Questionnair) => boolean | undefined;
264
264
  choices?: undefined;
265
+ } | {
266
+ type: string;
267
+ name: string;
268
+ message: string;
269
+ default: boolean;
270
+ choices?: undefined;
271
+ when?: undefined;
265
272
  } | {
266
273
  type: string;
267
274
  name: string;
@@ -1 +1 @@
1
- {"version":3,"file":"constants.d.ts","sourceRoot":"","sources":["../src/constants.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"constants.d.ts","sourceRoot":"","sources":["../src/constants.ts"],"names":[],"mappings":"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"}
@@ -1 +1 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAeA,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,YAAY,CAAA;AAK7C,wBAAsB,GAAG,CAAC,SAAS,2BAAoB,iBAkCtD;AAkBD,wBAAsB,iBAAiB,CAAC,IAAI,EAAE,WAAW,iBAqCxD"}
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAkBA,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,YAAY,CAAA;AAK7C,wBAAsB,GAAG,CAAC,SAAS,2BAAoB,iBAuDtD;AAkBD,wBAAsB,iBAAiB,CAAC,IAAI,EAAE,WAAW,iBAmDxD"}
package/build/index.js CHANGED
@@ -5,7 +5,7 @@ import { pathToFileURL } from "node:url";
5
5
  import { execSync as execSync2 } from "node:child_process";
6
6
  import chalk3 from "chalk";
7
7
  import semver from "semver";
8
- import { Command } from "commander";
8
+ import { Command, Option } from "commander";
9
9
  import { resolve } from "import-meta-resolve";
10
10
 
11
11
  // src/utils.ts
@@ -14,7 +14,6 @@ import path2 from "node:path";
14
14
  import util, { promisify } from "node:util";
15
15
  import fs2 from "node:fs/promises";
16
16
  import { execSync } from "node:child_process";
17
- import readDir from "recursive-readdir";
18
17
  import { $ } from "execa";
19
18
  import { readPackageUp } from "read-pkg-up";
20
19
  import inquirer from "inquirer";
@@ -24,7 +23,7 @@ import spawn from "cross-spawn";
24
23
  // package.json
25
24
  var package_default = {
26
25
  name: "create-wdio",
27
- version: "9.31.6",
26
+ version: "9.32.0",
28
27
  description: "Install and setup a WebdriverIO project with all its dependencies in a single run",
29
28
  author: "WebdriverIO Team <mail@webdriver.io>",
30
29
  homepage: "https://github.com/webdriverio/webdriverio/tree/main/packages/create-wdio",
@@ -53,9 +52,9 @@ var package_default = {
53
52
  }
54
53
  },
55
54
  types: "./build/index.d.ts",
56
- typeScriptVersion: "3.8.3",
55
+ typeScriptVersion: "6.0.3",
57
56
  engines: {
58
- node: ">=18.20.0"
57
+ node: ">=22.19.0"
59
58
  },
60
59
  repository: {
61
60
  type: "git",
@@ -85,10 +84,9 @@ var package_default = {
85
84
  inquirer: "^12.7.0",
86
85
  "normalize-package-data": "^7.0.0",
87
86
  "read-pkg-up": "^10.1.0",
88
- "recursive-readdir": "^2.2.3",
89
87
  semver: "^7.6.3",
90
88
  "type-fest": "^4.41.0",
91
- yargs: "^17.7.2"
89
+ yargs: "^18.2.0"
92
90
  },
93
91
  devDependencies: {
94
92
  "@types/cross-spawn": "^6.0.6",
@@ -158,7 +156,7 @@ var PROGRAM_TITLE = `
158
156
  `;
159
157
  var UNSUPPORTED_NODE_VERSION = `\u26A0\uFE0F Unsupported Node.js Version Error \u26A0\uFE0F
160
158
  You are using Node.js ${process.version} which is too old to be used with WebdriverIO.
161
- Please update to Node.js v20 to continue.
159
+ Please update to Node.js v22.19.0 to continue.
162
160
  `;
163
161
  var INSTALL_COMMAND = {
164
162
  npm: "install",
@@ -233,6 +231,7 @@ var SUPPORTED_PACKAGES = {
233
231
  service: [
234
232
  // internal or community driver services
235
233
  { name: "visual", value: "@wdio/visual-service$--$visual" },
234
+ { name: "ai", value: "@wdio/ai-service$--$ai" },
236
235
  { name: "vite", value: "wdio-vite-service$--$vite" },
237
236
  { name: "nuxt", value: "wdio-nuxt-service$--$nuxt" },
238
237
  { name: "firefox-profile", value: "@wdio/firefox-profile-service$--$firefox-profile" },
@@ -824,6 +823,11 @@ var QUESTIONNAIRE = [{
824
823
  /* istanbul ignore next */
825
824
  (answers) => answers.generateTestFiles && usesSerenity(answers)
826
825
  )
826
+ }, {
827
+ type: "confirm",
828
+ name: "agentSupport",
829
+ message: "Set up coding agent support (AGENTS.md section and wdio-session skill)?",
830
+ default: true
827
831
  }, {
828
832
  type: "checkbox",
829
833
  name: "reporters",
@@ -954,17 +958,352 @@ import chalk2 from "chalk";
954
958
  // src/install.ts
955
959
  import { execa } from "execa";
956
960
 
961
+ // src/answerFlags.ts
962
+ var AnswerFlagError = class extends Error {
963
+ name = "AnswerFlagError";
964
+ };
965
+ var HASH = "$--$";
966
+ function packageChoices(packages, key = (short) => short) {
967
+ return () => Object.fromEntries(packages().map(({ value }) => {
968
+ const [pkg, short, purpose] = value.split(HASH);
969
+ return [key(short, purpose, pkg), value];
970
+ }));
971
+ }
972
+ var ANSWER_FLAGS = [{
973
+ name: "runner",
974
+ answer: "runner",
975
+ type: "string",
976
+ desc: "Type of testing",
977
+ choices: packageChoices(() => SUPPORTED_PACKAGES.runner, (_, purpose) => purpose)
978
+ }, {
979
+ name: "preset",
980
+ answer: "preset",
981
+ type: "string",
982
+ desc: "UI framework of your components (with --runner component)",
983
+ choices: () => Object.fromEntries(SUPPORTED_BROWSER_RUNNER_PRESETS.map(({ name, value }) => [
984
+ value === null ? "other" : value.split(HASH)[1] || name.split(" ")[0].toLowerCase(),
985
+ value
986
+ ]))
987
+ }, {
988
+ name: "testingLibrary",
989
+ answer: "installTestingLibrary",
990
+ type: "boolean",
991
+ desc: "Install Testing Library (with --preset vue, svelte, solid, react or preact)"
992
+ }, {
993
+ name: "desktopFramework",
994
+ answer: "desktopFramework",
995
+ type: "string",
996
+ desc: "Desktop app framework (with --runner desktop)",
997
+ choices: () => ({
998
+ electron: "Electron (https://www.electronjs.org/)" /* Electron */,
999
+ tauri: "Tauri (https://tauri.app/)" /* Tauri */,
1000
+ dioxus: "Dioxus (https://dioxuslabs.com/)" /* Dioxus */,
1001
+ macos: "Native macOS app" /* MacOS */
1002
+ })
1003
+ }, {
1004
+ name: "electronBuildTool",
1005
+ answer: "electronBuildTool",
1006
+ type: "string",
1007
+ desc: "Tool that builds your Electron app (with --desktop-framework electron)",
1008
+ choices: () => ({
1009
+ forge: "Electron Forge (https://www.electronforge.io/)" /* ElectronForge */,
1010
+ builder: "electron-builder (https://www.electron.build/)" /* ElectronBuilder */,
1011
+ other: "Something else" /* SomethingElse */
1012
+ })
1013
+ }, {
1014
+ name: "electronAppBinaryPath",
1015
+ answer: "electronAppBinaryPath",
1016
+ type: "string",
1017
+ desc: "Path to the built Electron app (with --electron-build-tool other)"
1018
+ }, {
1019
+ name: "tauriDriverProvider",
1020
+ answer: "tauriDriverProvider",
1021
+ type: "string",
1022
+ desc: "WebDriver provider for Tauri (with --desktop-framework tauri)",
1023
+ choices: () => ({
1024
+ official: "Official tauri-driver (cross-platform, Cargo-installed)" /* Official */,
1025
+ crabnebula: "CrabNebula tauri-driver (managed cloud / drop-in)" /* CrabNebula */,
1026
+ embedded: "Embedded driver via tauri-plugin-wdio-webdriver crate" /* Embedded */
1027
+ })
1028
+ }, {
1029
+ name: "tauriFrontendPlugin",
1030
+ answer: "tauriUseFrontendPlugin",
1031
+ type: "boolean",
1032
+ desc: "Install @wdio/tauri-plugin (with --desktop-framework tauri)"
1033
+ }, {
1034
+ name: "tauriAppBinaryPath",
1035
+ answer: "tauriAppBinaryPath",
1036
+ type: "string",
1037
+ desc: "Path to the built Tauri binary (with --desktop-framework tauri)"
1038
+ }, {
1039
+ name: "dioxusDriverProvider",
1040
+ answer: "dioxusDriverProvider",
1041
+ type: "string",
1042
+ desc: "WebDriver provider for Dioxus (with --desktop-framework dioxus)",
1043
+ choices: () => ({
1044
+ embedded: "Embedded in-process driver (recommended \u2014 no external driver, all platforms)" /* Embedded */,
1045
+ external: "External driver via wdio-dioxus-driver (Windows only)" /* External */
1046
+ })
1047
+ }, {
1048
+ name: "dioxusAppBinaryPath",
1049
+ answer: "dioxusAppBinaryPath",
1050
+ type: "string",
1051
+ desc: "Path to the Dioxus debug binary (with --desktop-framework dioxus)"
1052
+ }, {
1053
+ name: "backend",
1054
+ answer: "backend",
1055
+ type: "string",
1056
+ desc: "Where the automation backend runs (with --runner e2e)",
1057
+ choices: () => ({
1058
+ local: "On my local machine" /* Local */,
1059
+ experitest: "In the cloud using Experitest" /* Experitest */,
1060
+ saucelabs: "In the cloud using Sauce Labs" /* Saucelabs */,
1061
+ browserstack: "In the cloud using BrowserStack" /* Browserstack */,
1062
+ other: "In the cloud using Testingbot or LambdaTest or a different service" /* OtherVendors */,
1063
+ grid: "I have my own Selenium cloud" /* Grid */
1064
+ })
1065
+ }, {
1066
+ name: "environment",
1067
+ answer: "e2eEnvironment",
1068
+ type: "string",
1069
+ desc: "What to automate (with --runner e2e). Implied by --browsers or --mobile-environment",
1070
+ choices: () => ({ web: "web", mobile: "mobile" })
1071
+ }, {
1072
+ name: "mobileEnvironment",
1073
+ answer: "mobileEnvironment",
1074
+ type: "string",
1075
+ desc: "Mobile platform (with --environment mobile)",
1076
+ choices: () => ({ android: "android", ios: "ios" })
1077
+ }, {
1078
+ name: "browsers",
1079
+ answer: "browserEnvironment",
1080
+ type: "array",
1081
+ desc: "Comma-separated browsers to start with (with --environment web)",
1082
+ choices: () => ({ chrome: "chrome", firefox: "firefox", safari: "safari", edge: "MicrosoftEdge" })
1083
+ }, {
1084
+ name: "hostname",
1085
+ answer: "hostname",
1086
+ type: "string",
1087
+ desc: "Host of the cloud service or Selenium server (with --backend other or grid)"
1088
+ }, {
1089
+ name: "port",
1090
+ answer: "port",
1091
+ type: "string",
1092
+ desc: "Port of the cloud service or Selenium server (with --backend other or grid)"
1093
+ }, {
1094
+ name: "path",
1095
+ answer: "path",
1096
+ type: "string",
1097
+ desc: "Path of the Selenium server (with --backend grid)"
1098
+ }, {
1099
+ name: "envUser",
1100
+ answer: "env_user",
1101
+ type: "string",
1102
+ desc: "Environment variable for the cloud username (with --backend saucelabs or browserstack, or other with a lambdatest.com --hostname)"
1103
+ }, {
1104
+ name: "envKey",
1105
+ answer: "env_key",
1106
+ type: "string",
1107
+ desc: "Environment variable for the cloud access key (with --backend saucelabs or browserstack, or other with a lambdatest.com --hostname)"
1108
+ }, {
1109
+ name: "region",
1110
+ answer: "region",
1111
+ type: "string",
1112
+ desc: "Sauce Labs region (with --backend saucelabs)",
1113
+ choices: () => Object.fromEntries(Object.values(RegionOptions).map((region) => [region, region]))
1114
+ }, {
1115
+ name: "sauceConnect",
1116
+ answer: "useSauceConnect",
1117
+ type: "boolean",
1118
+ desc: "Set up Sauce Connect for a local app (with --backend saucelabs)"
1119
+ }, {
1120
+ name: "expAccessKey",
1121
+ answer: "expEnvAccessKey",
1122
+ type: "string",
1123
+ desc: "Experitest access key (with --backend experitest)"
1124
+ }, {
1125
+ name: "expHostname",
1126
+ answer: "expEnvHostname",
1127
+ type: "string",
1128
+ desc: "Experitest cloud host (with --backend experitest)"
1129
+ }, {
1130
+ name: "expPort",
1131
+ answer: "expEnvPort",
1132
+ type: "string",
1133
+ desc: "Experitest cloud port (with --backend experitest)"
1134
+ }, {
1135
+ name: "expProtocol",
1136
+ answer: "expEnvProtocol",
1137
+ type: "string",
1138
+ desc: "Experitest protocol (with --backend experitest and a port other than 80 or 443)",
1139
+ choices: () => ({ http: "http", https: "https" })
1140
+ }, {
1141
+ name: "framework",
1142
+ answer: "framework",
1143
+ type: "string",
1144
+ desc: "Test framework",
1145
+ choices: packageChoices(() => SUPPORTED_PACKAGES.framework, (short, purpose, pkg) => pkg.startsWith("@serenity-js") ? `serenity-${purpose}` : short)
1146
+ }, {
1147
+ name: "typescript",
1148
+ answer: "isUsingTypeScript",
1149
+ type: "boolean",
1150
+ desc: "Write tests in TypeScript"
1151
+ }, {
1152
+ name: "generateTestFiles",
1153
+ answer: "generateTestFiles",
1154
+ type: "boolean",
1155
+ desc: "Generate example test files"
1156
+ }, {
1157
+ name: "specs",
1158
+ answer: "specs",
1159
+ type: "string",
1160
+ desc: "Location of spec or feature files (with --generate-test-files)"
1161
+ }, {
1162
+ name: "stepDefinitions",
1163
+ answer: "stepDefinitions",
1164
+ type: "string",
1165
+ desc: "Location of step definitions (with --framework cucumber)"
1166
+ }, {
1167
+ name: "pageObjects",
1168
+ answer: "usePageObjects",
1169
+ type: "boolean",
1170
+ desc: "Generate page objects (with --runner e2e and --generate-test-files)"
1171
+ }, {
1172
+ name: "pages",
1173
+ answer: "pages",
1174
+ type: "string",
1175
+ desc: "Location of page objects (with --page-objects)"
1176
+ }, {
1177
+ name: "serenityLibPath",
1178
+ answer: "serenityLibPath",
1179
+ type: "string",
1180
+ desc: "Location of the Serenity/JS Screenplay library (with --framework serenity-*)"
1181
+ }, {
1182
+ name: "agentSupport",
1183
+ answer: "agentSupport",
1184
+ type: "boolean",
1185
+ desc: "Write the AGENTS.md section and the wdio-session skill"
1186
+ }, {
1187
+ name: "reporters",
1188
+ answer: "reporters",
1189
+ type: "array",
1190
+ desc: "Comma-separated reporters",
1191
+ choices: packageChoices(() => SUPPORTED_PACKAGES.reporter)
1192
+ }, {
1193
+ name: "plugins",
1194
+ answer: "plugins",
1195
+ type: "array",
1196
+ desc: "Comma-separated plugins",
1197
+ choices: packageChoices(() => SUPPORTED_PACKAGES.plugin)
1198
+ }, {
1199
+ name: "visualTesting",
1200
+ answer: "includeVisualTesting",
1201
+ type: "boolean",
1202
+ desc: "Add visual testing (with --runner e2e or component)"
1203
+ }, {
1204
+ name: "services",
1205
+ answer: "services",
1206
+ type: "array",
1207
+ desc: "Comma-separated services, replaces the ones the wizard picks for your setup",
1208
+ choices: packageChoices(() => SUPPORTED_PACKAGES.service)
1209
+ }, {
1210
+ name: "npmInstall",
1211
+ answer: "npmInstall",
1212
+ type: "boolean",
1213
+ desc: "Install the dependencies"
1214
+ }];
1215
+ function toKebabCase(name) {
1216
+ return name.replace(/[A-Z]/g, (char) => `-${char.toLowerCase()}`);
1217
+ }
1218
+ function describeChoices(flag) {
1219
+ return Object.keys(flag.choices()).join(", ");
1220
+ }
1221
+ function describeAnswerFlag(flag) {
1222
+ return flag.choices ? `${flag.desc}: ${describeChoices(flag)}` : flag.desc;
1223
+ }
1224
+ var ANSWER_FLAGS_HELP = [
1225
+ "Every wizard question has a flag. A flag answers its question and the wizard",
1226
+ "asks the rest, or uses the defaults for the rest with --yes. Boolean flags",
1227
+ "take a --no- prefix, e.g. --no-typescript. A flag for a question the wizard",
1228
+ "does not ask for your setup is an error, and so is a value it does not offer."
1229
+ ].join("\n");
1230
+ function answerFlagUsage(flag) {
1231
+ const kebab = toKebabCase(flag.name);
1232
+ return flag.type === "boolean" ? `--${kebab}` : `--${kebab} <${flag.type === "array" ? "list" : "value"}>`;
1233
+ }
1234
+ function lastValue(raw) {
1235
+ return Array.isArray(raw) ? raw[raw.length - 1] : raw;
1236
+ }
1237
+ function toAnswerValue(flag, value) {
1238
+ if (!flag.choices) {
1239
+ return value;
1240
+ }
1241
+ const choices = flag.choices();
1242
+ const key = value.toLowerCase();
1243
+ if (!Object.prototype.hasOwnProperty.call(choices, key)) {
1244
+ throw new AnswerFlagError(
1245
+ `Invalid value "${value}" for --${toKebabCase(flag.name)}. Use one of: ${describeChoices(flag)}`
1246
+ );
1247
+ }
1248
+ return choices[key];
1249
+ }
1250
+ function parseAnswerFlags(argv) {
1251
+ const answers = {};
1252
+ for (const flag of ANSWER_FLAGS) {
1253
+ const raw = argv[flag.name];
1254
+ if (typeof raw === "undefined") {
1255
+ continue;
1256
+ }
1257
+ if (flag.type === "boolean") {
1258
+ answers[flag.answer] = raw === true || raw === "true";
1259
+ } else if (flag.type === "array") {
1260
+ const values = [raw].flat().flatMap((value) => String(value).split(",")).map((value) => value.trim()).filter(Boolean).map((value) => toAnswerValue(flag, value));
1261
+ answers[flag.answer] = [...new Set(values)];
1262
+ } else {
1263
+ answers[flag.answer] = toAnswerValue(flag, String(lastValue(raw)));
1264
+ }
1265
+ }
1266
+ if (!answers.e2eEnvironment) {
1267
+ if (answers.mobileEnvironment) {
1268
+ answers.e2eEnvironment = "mobile";
1269
+ } else if (answers.browserEnvironment) {
1270
+ answers.e2eEnvironment = "web";
1271
+ }
1272
+ }
1273
+ return answers;
1274
+ }
1275
+ function answerFlagsToArgs(argv) {
1276
+ const args = [];
1277
+ for (const flag of ANSWER_FLAGS) {
1278
+ const raw = argv[flag.name];
1279
+ if (typeof raw === "undefined") {
1280
+ continue;
1281
+ }
1282
+ const kebab = toKebabCase(flag.name);
1283
+ if (flag.type === "boolean") {
1284
+ args.push(raw === true || raw === "true" ? `--${kebab}` : `--no-${kebab}`);
1285
+ } else {
1286
+ args.push(`--${kebab}`, [raw].flat().join(","));
1287
+ }
1288
+ }
1289
+ return args;
1290
+ }
1291
+
957
1292
  // src/utils.ts
958
1293
  var NPM_COMMAND = /^win/.test(process.platform) ? "npm.cmd" : "npm";
959
1294
  var __dirname = path2.dirname(url.fileURLToPath(import.meta.url));
960
1295
  process.on("SIGINT", () => printAndExit(void 0, "SIGINT"));
961
1296
  var TEMPLATE_ROOT_DIR = process.env.WDIO_UNIT_TESTS ? path2.join(__dirname, "templates", "exampleFiles") : path2.join(__dirname, "..", "templates", "exampleFiles");
962
- function runProgram(command, args, options) {
1297
+ function runProgram(command, args, options, passUsageError = false) {
963
1298
  const child = spawn(command, args, { stdio: "inherit", ...options });
964
1299
  return new Promise((resolve2, rejects) => {
965
1300
  let error;
966
1301
  child.on("error", (e) => error = e);
967
1302
  child.on("close", (code, signal) => {
1303
+ if (passUsageError && code === 2) {
1304
+ process.exit(2);
1305
+ return rejects(`Usage error calling: ${command} ${args.join(" ")}`);
1306
+ }
968
1307
  if (code !== 0) {
969
1308
  const errorMessage = error && error.message || `Error calling: ${command} ${args.join(" ")}`;
970
1309
  printAndExit(errorMessage, signal);
@@ -1056,12 +1395,29 @@ async function run(operation = createWebdriverIO) {
1056
1395
  if (!(process.argv.includes("--version") || process.argv.includes("-v"))) {
1057
1396
  console.log(ASCII_ROBOT, PROGRAM_TITLE);
1058
1397
  }
1059
- const unsupportedNodeVersion = !semver.satisfies(process.version, ">=18.18.0");
1398
+ const unsupportedNodeVersion = !semver.satisfies(process.version, ">=22.19.0");
1060
1399
  if (unsupportedNodeVersion) {
1061
1400
  console.log(chalk3.yellow(UNSUPPORTED_NODE_VERSION));
1062
1401
  return;
1063
1402
  }
1064
- const program = new Command(WDIO_COMMAND).version(version, "-v, --version").arguments("[project-path]").usage(`${chalk3.green("[project-path]")} [options]`).action((name) => projectDir = name).option("-t, --npm-tag <tag>", "Which NPM version you like to install, e.g. @next", DEFAULT_NPM_TAG).option("-y, --yes", "will fill in all config defaults without prompting", false).option("-d, --dev", "Install all packages as into devDependencies", true).allowUnknownOption().on("--help", () => console.log()).parse(process.argv);
1403
+ const program = new Command(WDIO_COMMAND).version(version, "-v, --version").arguments("[project-path]").usage(`${chalk3.green("[project-path]")} [options]`).action((name) => projectDir = name).option("-t, --npm-tag <tag>", "Which NPM version you like to install, e.g. @next", DEFAULT_NPM_TAG).option("-y, --yes", "will fill in all config defaults without prompting", false).option("-d, --dev", "Install all packages as into devDependencies", true);
1404
+ for (const flag of ANSWER_FLAGS) {
1405
+ program.option(answerFlagUsage(flag), describeAnswerFlag(flag));
1406
+ if (flag.type === "boolean") {
1407
+ program.addOption(new Option(answerFlagUsage(flag).replace("--", "--no-")).hideHelp());
1408
+ }
1409
+ }
1410
+ program.allowUnknownOption().addHelpText("after", [
1411
+ "",
1412
+ ANSWER_FLAGS_HELP,
1413
+ "",
1414
+ "Examples:",
1415
+ " npm init wdio@latest . -- --yes",
1416
+ " npm init wdio@latest ./e2e -- --yes --framework cucumber --no-typescript",
1417
+ " npm init wdio@latest . -- --yes --environment mobile --mobile-environment android",
1418
+ " npm init wdio@latest . -- --runner component --preset react",
1419
+ ""
1420
+ ].join("\n")).parse(process.argv);
1065
1421
  return operation(program.opts());
1066
1422
  }
1067
1423
  function detectPackageManager2() {
@@ -1073,6 +1429,16 @@ function detectPackageManager2() {
1073
1429
  return matchedPM || "npm";
1074
1430
  }
1075
1431
  async function createWebdriverIO(opts) {
1432
+ try {
1433
+ parseAnswerFlags(opts);
1434
+ } catch (err) {
1435
+ if (!(err instanceof AnswerFlagError)) {
1436
+ throw err;
1437
+ }
1438
+ console.error(`Error: ${err.message}
1439
+ Run "npm init wdio -- --help" for all flags.`);
1440
+ return process.exit(2);
1441
+ }
1076
1442
  const npmTag = opts.npmTag.startsWith("@") ? opts.npmTag : `@${opts.npmTag}`;
1077
1443
  const root = path3.resolve(process.cwd(), projectDir || "");
1078
1444
  const pm = detectPackageManager2();
@@ -1101,8 +1467,9 @@ Installing ${chalk3.bold("@wdio/cli")} to initialize project...`);
1101
1467
  WDIO_COMMAND,
1102
1468
  "config",
1103
1469
  ...opts.yes ? ["--yes"] : [],
1104
- ...opts.npmTag ? ["--npm-tag", opts.npmTag] : []
1105
- ].filter((i) => !!i), { cwd: root });
1470
+ ...opts.npmTag ? ["--npm-tag", opts.npmTag] : [],
1471
+ ...answerFlagsToArgs(opts)
1472
+ ].filter((i) => !!i), { cwd: root }, true);
1106
1473
  }
1107
1474
  async function isCLIInstalled(path4) {
1108
1475
  try {