k6-cucumber-steps
Version:
Cucumber step definitions for running k6 performance tests.
179 lines (156 loc) • 5.87 kB
JavaScript
const path = require("path");
const fs = require("fs");
const { spawn } = require("child_process");
const { Command } = require("commander");
require("dotenv").config();
const { linkReports } = require("../scripts/linkReports");
console.log(`
-----------------------------------------
🚀 Starting k6-cucumber-steps execution...
-----------------------------------------
`);
const program = new Command();
program
.command("run")
.option("-f, --feature <path>", "Feature file path")
.option("-t, --tags <string>", "Cucumber tags")
.option("-c, --config <file>", "Custom config file")
.option("--saveK6Script", "Keep generated k6 script files", false)
.option("--overwrite", "Overwrite report files", false)
.option("--cleanReports", "Clean the reports folder before running", false)
.option("--reporter", "Enable report generation", false)
.option("--clean", "Alias for --cleanReports")
.option("-p, --payloadPath <dir>", "Directory for payload files")
// Add CLI options for all config options
.option("--script <file>", "k6 script file to run")
.option("--k6Config <file>", "k6 config file to use")
.action(async (argv) => {
// Load config file
const configFileInput =
argv.config || process.env.CUCUMBER_CONFIG_FILE || "cucumber.js";
const configFilePath = path.isAbsolute(configFileInput)
? configFileInput
: path.resolve(process.cwd(), configFileInput);
let configOptions = {};
if (fs.existsSync(configFilePath)) {
try {
const loadedConfig = require(configFilePath);
configOptions = loadedConfig.default || loadedConfig;
} catch (err) {
console.warn("⚠️ Could not load config file:", err.message);
}
}
// Build the cucumber-js command from config
const cucumberConfig = configOptions.default || configOptions;
let cliParts = [];
// Add paths
if (cucumberConfig.paths && Array.isArray(cucumberConfig.paths)) {
cliParts.push(...cucumberConfig.paths);
}
if (argv.feature) {
cliParts.push(argv.feature);
}
// Add require
if (cucumberConfig.require && Array.isArray(cucumberConfig.require)) {
cucumberConfig.require.forEach((req) => {
cliParts.push("--require", req);
});
}
// Add format
if (cucumberConfig.format && Array.isArray(cucumberConfig.format)) {
cucumberConfig.format.forEach((fmt) => {
cliParts.push("--format", fmt);
});
}
// Add tags
if (cucumberConfig.tags) {
cliParts.push("--tags", cucumberConfig.tags);
}
if (argv.tags) {
cliParts.push("--tags", argv.tags);
}
// Determine project root (where your main package.json is)
const projectRoot = process.cwd();
// Determine payload directory from CLI or config, always relative to project root
let payloadDirRaw =
argv.payloadPath ||
(cucumberConfig.worldParameters &&
cucumberConfig.worldParameters.payloadPath) ||
"payloads";
const payloadDir = path.resolve(projectRoot, payloadDirRaw);
console.log("📦 Resolved payload path:", payloadDir);
// Add --world-parameters to CLI args
const worldParams = {
...(cucumberConfig.worldParameters || {}),
payloadPath: payloadDir,
};
cliParts.push("--world-parameters", JSON.stringify(worldParams));
// Add CLI options for k6 script and config
if (argv.script) {
cliParts.push("--script", argv.script);
}
if (argv.k6Config) {
cliParts.push("--k6Config", argv.k6Config);
}
const finalCommand = ["npx", "cucumber-js", ...cliParts].join(" ");
console.log("▶️ Final arguments passed to cucumber-js:", finalCommand);
// Collect options to pass as env vars
const extraEnv = {
// Priority: cucumberConfig > CLI
SAVE_K6_SCRIPT:
cucumberConfig.saveK6Script === true || argv.saveK6Script === true
? "true"
: "false",
K6_CUCUMBER_OVERWRITE:
cucumberConfig.overwrite === true || argv.overwrite === true
? "true"
: "false",
CLEAN_REPORTS:
cucumberConfig.cleanReports === true ||
argv.cleanReports === true ||
argv.clean === true
? "true"
: "false",
K6_CUCUMBER_REPORTER:
cucumberConfig.reporter === true || argv.reporter === true
? "true"
: "false",
};
// Clean reports directory if requested
const shouldCleanReports =
argv.cleanReports || argv.clean || cucumberConfig.cleanReports;
if (shouldCleanReports) {
const reportsDir = path.join(projectRoot, "reports");
if (fs.existsSync(reportsDir)) {
fs.rmSync(reportsDir, { recursive: true, force: true });
fs.mkdirSync(reportsDir, { recursive: true });
}
}
// Now spawn the process
const cucumberProcess = spawn("npx", ["cucumber-js", ...cliParts], {
stdio: "inherit",
env: { ...process.env, ...extraEnv },
});
cucumberProcess.on("close", async (code) => {
if (code === 0) {
console.log("-----------------------------------------");
console.log("✅ k6-cucumber-steps execution completed successfully.");
try {
await linkReports();
console.log(
"🔗 Reports linked successfully with embedded Cucumber tab."
);
} catch (err) {
console.error("⚠️ Failed to link reports:", err.message);
}
console.log("-----------------------------------------");
} else {
console.error("-----------------------------------------");
console.error("❌ k6-cucumber-steps execution failed.");
console.error("-----------------------------------------");
}
process.exit(code);
});
});
program.parse(process.argv);