@gatling.io/cli 3.11.2 → 3.11.3
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.
- package/README.md +15 -0
- package/package.json +3 -3
- package/target/bundle.d.ts +1 -1
- package/target/bundle.js +11 -2
- package/target/dependencies/coursier.d.ts +3 -0
- package/target/dependencies/coursier.js +68 -0
- package/target/dependencies/graalVm.d.ts +1 -0
- package/target/dependencies/graalVm.js +76 -0
- package/target/dependencies/index.d.ts +2 -4
- package/target/dependencies/index.js +20 -112
- package/target/dependencies/os.d.ts +2 -0
- package/target/dependencies/os.js +28 -0
- package/target/dependencies/versions.js +2 -2
- package/target/index.js +42 -18
- package/target/run.d.ts +10 -2
- package/target/run.js +45 -40
package/README.md
ADDED
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
# Gatling JS - CLI
|
|
2
|
+
|
|
3
|
+
Gatling JS is a JavaScript/TypeScript interface for the [Gatling load testing tool](https://gatling.io/).
|
|
4
|
+
|
|
5
|
+
This package contains a command-line utility for use with Gatling JS, to allow you to easily build and run you Gatling JS projects.
|
|
6
|
+
|
|
7
|
+
To get started with Gatling JS, see our [introduction to JavaScript scripting](https://docs.gatling.io/tutorials/scripting-intro-js); or simply have a look at [our demo projects](https://github.com/gatling/gatling-js-demo).
|
|
8
|
+
|
|
9
|
+
## Questions, help?
|
|
10
|
+
|
|
11
|
+
Read the [documentation](https://docs.gatling.io).
|
|
12
|
+
|
|
13
|
+
Join the [Gatling Community Forum](https://community.gatling.io).
|
|
14
|
+
|
|
15
|
+
Found a real bug? Raise an [issue](https://github.com/gatling/gatling/issues).
|
package/package.json
CHANGED
|
@@ -1,9 +1,9 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@gatling.io/cli",
|
|
3
|
-
"version": "3.11.
|
|
3
|
+
"version": "3.11.3",
|
|
4
4
|
"license": "Apache-2.0",
|
|
5
5
|
"bin": {
|
|
6
|
-
"gatling
|
|
6
|
+
"gatling": "target/index.js"
|
|
7
7
|
},
|
|
8
8
|
"main": "target/index.js",
|
|
9
9
|
"types": "target/index.d.ts",
|
|
@@ -22,7 +22,7 @@
|
|
|
22
22
|
"typescript": "5.4.5"
|
|
23
23
|
},
|
|
24
24
|
"scripts": {
|
|
25
|
-
"clean": "rimraf target
|
|
25
|
+
"clean": "rimraf target",
|
|
26
26
|
"format": "prettier --write '**/*.ts'",
|
|
27
27
|
"build": "tsc -p . && chmod +x ./target/index.js"
|
|
28
28
|
}
|
package/target/bundle.d.ts
CHANGED
package/target/bundle.js
CHANGED
|
@@ -29,14 +29,23 @@ Object.defineProperty(exports, "__esModule", { value: true });
|
|
|
29
29
|
exports.bundle = void 0;
|
|
30
30
|
const esbuild = __importStar(require("esbuild"));
|
|
31
31
|
const esbuild_plugin_tsc_1 = __importDefault(require("esbuild-plugin-tsc"));
|
|
32
|
+
const promises_1 = __importDefault(require("fs/promises"));
|
|
32
33
|
const log_1 = require("./log");
|
|
33
34
|
const bundle = async (options) => {
|
|
34
35
|
log_1.logger.info(`Packaging a Gatling simulation with options:
|
|
35
|
-
-
|
|
36
|
+
- sourcesFolder: ${options.sourcesFolder}
|
|
36
37
|
- bundleFile: ${options.bundleFile}`);
|
|
38
|
+
const children = await promises_1.default.readdir(options.sourcesFolder, { recursive: false });
|
|
39
|
+
const contents = children
|
|
40
|
+
.filter((f) => (options.typescript ? f.endsWith(".gatling.ts") : f.endsWith(".gatling.js")))
|
|
41
|
+
.map((f) => `export { default as "${f.slice(0, -11)}" } from "./${f}";`)
|
|
42
|
+
.join("\n");
|
|
37
43
|
const plugins = options.typescript ? [(0, esbuild_plugin_tsc_1.default)({ force: true })] : [];
|
|
38
44
|
await esbuild.build({
|
|
39
|
-
|
|
45
|
+
stdin: {
|
|
46
|
+
contents,
|
|
47
|
+
resolveDir: options.sourcesFolder
|
|
48
|
+
},
|
|
40
49
|
outfile: options.bundleFile,
|
|
41
50
|
bundle: true,
|
|
42
51
|
minify: false,
|
|
@@ -0,0 +1,3 @@
|
|
|
1
|
+
export declare const installCoursier: (gatlingHomeDir: string, downloadDir: string) => Promise<string>;
|
|
2
|
+
export declare const resolveGatlingJsDependencies: (coursierPath: string, javaHome: string) => Promise<string>;
|
|
3
|
+
export declare const resolveRecorderDependencies: (coursierPath: string, javaHome: string) => Promise<string>;
|
|
@@ -0,0 +1,68 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
3
|
+
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
4
|
+
};
|
|
5
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
6
|
+
exports.resolveRecorderDependencies = exports.resolveGatlingJsDependencies = exports.installCoursier = void 0;
|
|
7
|
+
const fs_1 = require("fs");
|
|
8
|
+
const promises_1 = __importDefault(require("fs/promises"));
|
|
9
|
+
const download_1 = require("./download");
|
|
10
|
+
const log_1 = require("../log");
|
|
11
|
+
const versions_1 = require("./versions");
|
|
12
|
+
const util_1 = require("util");
|
|
13
|
+
const child_process_1 = require("child_process");
|
|
14
|
+
const os_1 = require("./os");
|
|
15
|
+
const installCoursier = async (gatlingHomeDir, downloadDir) => {
|
|
16
|
+
const coursierRootPath = `${gatlingHomeDir}/coursier/${versions_1.versions.coursier}`;
|
|
17
|
+
const coursierPath = `${coursierRootPath}/cs`;
|
|
18
|
+
if (!(0, fs_1.existsSync)(coursierPath)) {
|
|
19
|
+
const jarUrl = `https://github.com/coursier/coursier/releases/download/v${versions_1.versions.coursier}/coursier`;
|
|
20
|
+
const windowsBatUrl = `https://github.com/coursier/launchers/raw/master/coursier.bat`;
|
|
21
|
+
const downloadPath = `${downloadDir}/cs`;
|
|
22
|
+
if ((0, fs_1.existsSync)(coursierRootPath)) {
|
|
23
|
+
await promises_1.default.rm(coursierRootPath, { recursive: true });
|
|
24
|
+
}
|
|
25
|
+
if ((0, fs_1.existsSync)(downloadPath)) {
|
|
26
|
+
await promises_1.default.rm(downloadPath);
|
|
27
|
+
}
|
|
28
|
+
await promises_1.default.mkdir(coursierRootPath, { recursive: true });
|
|
29
|
+
log_1.logger.info(`Downloading Coursier ${versions_1.versions.coursier} to ${downloadPath}`);
|
|
30
|
+
await (0, download_1.downloadFile)(jarUrl, downloadPath);
|
|
31
|
+
if (os_1.osType === "Windows_NT") {
|
|
32
|
+
await (0, download_1.downloadFile)(windowsBatUrl, `${downloadPath}.bat`);
|
|
33
|
+
}
|
|
34
|
+
else {
|
|
35
|
+
await promises_1.default.chmod(downloadPath, 0o744);
|
|
36
|
+
}
|
|
37
|
+
log_1.logger.info(`Installing Coursier to ${coursierPath}`);
|
|
38
|
+
await promises_1.default.rename(downloadPath, coursierPath);
|
|
39
|
+
if (os_1.osType === "Windows_NT") {
|
|
40
|
+
await promises_1.default.rename(`${downloadPath}.bat`, `${coursierPath}.bat`);
|
|
41
|
+
}
|
|
42
|
+
}
|
|
43
|
+
else {
|
|
44
|
+
log_1.logger.info(`Coursier ${versions_1.versions.coursier} already installed at ${coursierPath}`);
|
|
45
|
+
}
|
|
46
|
+
return coursierPath;
|
|
47
|
+
};
|
|
48
|
+
exports.installCoursier = installCoursier;
|
|
49
|
+
const resolveGatlingJsDependencies = async (coursierPath, javaHome) => {
|
|
50
|
+
const gatlingDep = `"io.gatling.highcharts:gatling-charts-highcharts:${versions_1.versions.gatling.core}"`;
|
|
51
|
+
const gatlingAdapterDep = `"io.gatling:gatling-jvm-to-js-adapter:${versions_1.versions.gatling.jsAdapter}"`;
|
|
52
|
+
const graalvmJsDep = `"org.graalvm.polyglot:js-community:${versions_1.versions.graalvm.js}"`;
|
|
53
|
+
return await resolveDependencies(coursierPath, javaHome, gatlingDep, gatlingAdapterDep, graalvmJsDep);
|
|
54
|
+
};
|
|
55
|
+
exports.resolveGatlingJsDependencies = resolveGatlingJsDependencies;
|
|
56
|
+
const resolveRecorderDependencies = async (coursierPath, javaHome) => {
|
|
57
|
+
const recorderDep = `io.gatling:gatling-recorder:${versions_1.versions.gatling.core}`;
|
|
58
|
+
return await resolveDependencies(coursierPath, javaHome, recorderDep);
|
|
59
|
+
};
|
|
60
|
+
exports.resolveRecorderDependencies = resolveRecorderDependencies;
|
|
61
|
+
const resolveDependencies = async (coursierPath, javaHome, ...dependencies) => {
|
|
62
|
+
const command = `"${coursierPath}" fetch --classpath ${dependencies.join(" ")}`;
|
|
63
|
+
// TODO could add a timeout
|
|
64
|
+
log_1.logger.info(`Resolving dependencies with Coursier`);
|
|
65
|
+
const { stdout } = await execAsync(command, { env: { ...process.env, JAVA_HOME: javaHome } });
|
|
66
|
+
return stdout;
|
|
67
|
+
};
|
|
68
|
+
const execAsync = (0, util_1.promisify)(child_process_1.exec);
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export declare const installGraalVm: (gatlingHomeDir: string, downloadDir: string) => Promise<string>;
|
|
@@ -0,0 +1,76 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
3
|
+
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
4
|
+
};
|
|
5
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
6
|
+
exports.installGraalVm = void 0;
|
|
7
|
+
const fs_1 = require("fs");
|
|
8
|
+
const promises_1 = __importDefault(require("fs/promises"));
|
|
9
|
+
const decompress_1 = __importDefault(require("decompress"));
|
|
10
|
+
const download_1 = require("./download");
|
|
11
|
+
const log_1 = require("../log");
|
|
12
|
+
const os_1 = require("./os");
|
|
13
|
+
const versions_1 = require("./versions");
|
|
14
|
+
const installGraalVm = async (gatlingHomeDir, downloadDir) => {
|
|
15
|
+
const { os, arch, extension, homePath, binPath } = graalVmPlatformParams();
|
|
16
|
+
const graalvmRootPath = `${gatlingHomeDir}/graalvm/${versions_1.versions.graalvm.jdk}`;
|
|
17
|
+
const graalvmHomePath = `${graalvmRootPath}${homePath}`;
|
|
18
|
+
const graalvmJavaPath = `${graalvmHomePath}${binPath}`;
|
|
19
|
+
if (!(0, fs_1.existsSync)(graalvmJavaPath)) {
|
|
20
|
+
const url = `https://github.com/graalvm/graalvm-ce-builds/releases/download/jdk-${versions_1.versions.graalvm.jdk}/graalvm-community-jdk-${versions_1.versions.graalvm.jdk}_${os}-${arch}_bin.${extension}`;
|
|
21
|
+
const downloadPath = `${downloadDir}/graalvm.${extension}`;
|
|
22
|
+
if ((0, fs_1.existsSync)(graalvmRootPath)) {
|
|
23
|
+
await promises_1.default.rm(graalvmRootPath, { recursive: true });
|
|
24
|
+
}
|
|
25
|
+
if ((0, fs_1.existsSync)(downloadPath)) {
|
|
26
|
+
await promises_1.default.rm(downloadPath);
|
|
27
|
+
}
|
|
28
|
+
await promises_1.default.mkdir(graalvmRootPath, { recursive: true });
|
|
29
|
+
log_1.logger.info(`Downloading GraalVM Community Edition ${versions_1.versions.graalvm.jdk} to ${downloadPath}`);
|
|
30
|
+
await (0, download_1.downloadFile)(url, downloadPath);
|
|
31
|
+
log_1.logger.info(`Unpacking GraalVM to ${graalvmRootPath}`);
|
|
32
|
+
await (0, decompress_1.default)(downloadPath, graalvmRootPath, {
|
|
33
|
+
map: (file) => {
|
|
34
|
+
// Remove first level of file name, because it already contains a root directory
|
|
35
|
+
file.path = file.path.split("/").slice(1).join("/");
|
|
36
|
+
return file;
|
|
37
|
+
}
|
|
38
|
+
});
|
|
39
|
+
await promises_1.default.rm(downloadPath);
|
|
40
|
+
}
|
|
41
|
+
else {
|
|
42
|
+
log_1.logger.info(`GraalVM Community Edition ${versions_1.versions.graalvm.jdk} already installed at ${graalvmRootPath}`);
|
|
43
|
+
}
|
|
44
|
+
return graalvmHomePath;
|
|
45
|
+
};
|
|
46
|
+
exports.installGraalVm = installGraalVm;
|
|
47
|
+
const graalVmPlatformParams = () => {
|
|
48
|
+
if (os_1.osType === "Linux") {
|
|
49
|
+
const os = "linux";
|
|
50
|
+
const extension = "tar.gz";
|
|
51
|
+
const homePath = "";
|
|
52
|
+
const binPath = "/bin/java";
|
|
53
|
+
if (os_1.osArch === "x64") {
|
|
54
|
+
return { os, arch: "x64", extension, homePath, binPath };
|
|
55
|
+
}
|
|
56
|
+
else if (os_1.osArch === "arm64") {
|
|
57
|
+
return { os, arch: "aarch64", extension, homePath, binPath };
|
|
58
|
+
}
|
|
59
|
+
}
|
|
60
|
+
else if (os_1.osType === "Darwin") {
|
|
61
|
+
const os = "macos";
|
|
62
|
+
const extension = "tar.gz";
|
|
63
|
+
const homePath = "/Contents/Home";
|
|
64
|
+
const binPath = "/bin/java";
|
|
65
|
+
if (os_1.osArch === "x64") {
|
|
66
|
+
return { os, arch: "x64", extension, homePath, binPath };
|
|
67
|
+
}
|
|
68
|
+
else if (os_1.osArch === "arm64") {
|
|
69
|
+
return { os, arch: "aarch64", extension, homePath, binPath };
|
|
70
|
+
}
|
|
71
|
+
}
|
|
72
|
+
else if (os_1.osType === "Windows_NT" && os_1.osArch === "x64") {
|
|
73
|
+
return { os: "windows", arch: "x64", extension: "zip", homePath: "", binPath: "/bin/java.exe" };
|
|
74
|
+
}
|
|
75
|
+
throw Error(`Operating system type '${os_1.osType}' with architecture '${os_1.osArch}' is not currently supported.`);
|
|
76
|
+
};
|
|
@@ -1,6 +1,3 @@
|
|
|
1
|
-
/// <reference types="node" />
|
|
2
|
-
import { exec } from "child_process";
|
|
3
|
-
export declare const execAsync: typeof exec.__promisify__;
|
|
4
1
|
export interface DependenciesOptions {
|
|
5
2
|
gatlingHome: string;
|
|
6
3
|
}
|
|
@@ -9,4 +6,5 @@ export interface ResolvedDependencies {
|
|
|
9
6
|
coursierBinary: string;
|
|
10
7
|
jvmClasspath: string;
|
|
11
8
|
}
|
|
12
|
-
export declare const
|
|
9
|
+
export declare const installGatlingJs: (options: DependenciesOptions) => Promise<ResolvedDependencies>;
|
|
10
|
+
export declare const installRecorder: (options: DependenciesOptions) => Promise<ResolvedDependencies>;
|
|
@@ -3,125 +3,33 @@ var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
|
3
3
|
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
4
4
|
};
|
|
5
5
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
6
|
-
exports.
|
|
7
|
-
const child_process_1 = require("child_process");
|
|
8
|
-
const decompress_1 = __importDefault(require("decompress"));
|
|
9
|
-
const fs_1 = require("fs");
|
|
6
|
+
exports.installRecorder = exports.installGatlingJs = void 0;
|
|
10
7
|
const promises_1 = __importDefault(require("fs/promises"));
|
|
11
|
-
const
|
|
12
|
-
const
|
|
13
|
-
const
|
|
14
|
-
const log_1 = require("../log");
|
|
15
|
-
const versions_1 = require("./versions");
|
|
16
|
-
exports.execAsync = (0, util_1.promisify)(child_process_1.exec);
|
|
17
|
-
const installAll = async (options) => {
|
|
8
|
+
const coursier_1 = require("./coursier");
|
|
9
|
+
const graalVm_1 = require("./graalVm");
|
|
10
|
+
const installGatlingJs = async (options) => {
|
|
18
11
|
const downloadDir = `${options.gatlingHome}/tmp/download`;
|
|
19
12
|
await promises_1.default.mkdir(downloadDir, { recursive: true });
|
|
20
|
-
const graalvmHomePath = await installGraalVm(options.gatlingHome, downloadDir);
|
|
21
|
-
const coursierPath = await installCoursier(options.gatlingHome, downloadDir);
|
|
22
|
-
const classpath = await
|
|
13
|
+
const graalvmHomePath = await (0, graalVm_1.installGraalVm)(options.gatlingHome, downloadDir);
|
|
14
|
+
const coursierPath = await (0, coursier_1.installCoursier)(options.gatlingHome, downloadDir);
|
|
15
|
+
const classpath = await (0, coursier_1.resolveGatlingJsDependencies)(coursierPath, graalvmHomePath);
|
|
23
16
|
return {
|
|
24
17
|
graalvmHome: graalvmHomePath,
|
|
25
18
|
coursierBinary: coursierPath,
|
|
26
19
|
jvmClasspath: classpath.trim()
|
|
27
20
|
};
|
|
28
21
|
};
|
|
29
|
-
exports.
|
|
30
|
-
const
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
const
|
|
34
|
-
const
|
|
35
|
-
const
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
}
|
|
42
|
-
if ((0, fs_1.existsSync)(downloadPath)) {
|
|
43
|
-
await promises_1.default.rm(downloadPath);
|
|
44
|
-
}
|
|
45
|
-
await promises_1.default.mkdir(graalvmRootPath, { recursive: true });
|
|
46
|
-
log_1.logger.info(`Downloading GraalVM Community Edition ${versions_1.versions.graalvm.jdk} to ${downloadPath}`);
|
|
47
|
-
await (0, download_1.downloadFile)(url, downloadPath);
|
|
48
|
-
log_1.logger.info(`Unpacking GraalVM to ${graalvmRootPath}`);
|
|
49
|
-
await (0, decompress_1.default)(downloadPath, graalvmRootPath, {
|
|
50
|
-
map: (file) => {
|
|
51
|
-
// Remove first level of file name, because it already contains a root directory
|
|
52
|
-
file.path = file.path.split("/").slice(1).join("/");
|
|
53
|
-
return file;
|
|
54
|
-
}
|
|
55
|
-
});
|
|
56
|
-
await promises_1.default.rm(downloadPath);
|
|
57
|
-
}
|
|
58
|
-
else {
|
|
59
|
-
log_1.logger.info(`GraalVM Community Edition ${versions_1.versions.graalvm.jdk} already installed at ${graalvmRootPath}`);
|
|
60
|
-
}
|
|
61
|
-
return graalvmHomePath;
|
|
62
|
-
};
|
|
63
|
-
const graalVmPlatformParams = () => {
|
|
64
|
-
const osType = os_1.default.type(); // 'Darwin', 'Linux', 'Windows_NT'
|
|
65
|
-
const osArch = os_1.default.arch(); // 'x64', 'arm64', etc.
|
|
66
|
-
if (osType === "Linux") {
|
|
67
|
-
const os = "linux";
|
|
68
|
-
const extension = "tar.gz";
|
|
69
|
-
const homePath = "";
|
|
70
|
-
if (osArch === "x64") {
|
|
71
|
-
return { os, arch: "x64", extension, homePath };
|
|
72
|
-
}
|
|
73
|
-
else if (osArch === "arm64") {
|
|
74
|
-
return { os, arch: "aarch64", extension, homePath };
|
|
75
|
-
}
|
|
76
|
-
}
|
|
77
|
-
else if (osType === "Darwin") {
|
|
78
|
-
const os = "macos";
|
|
79
|
-
const extension = "tar.gz";
|
|
80
|
-
const homePath = "/Contents/Home";
|
|
81
|
-
if (osArch === "x64") {
|
|
82
|
-
return { os, arch: "x64", extension, homePath };
|
|
83
|
-
}
|
|
84
|
-
else if (osArch === "arm64") {
|
|
85
|
-
return { os, arch: "aarch64", extension, homePath };
|
|
86
|
-
}
|
|
87
|
-
}
|
|
88
|
-
else if (osType === "Windows_NT" && osArch === "x64") {
|
|
89
|
-
return { os: "windows", arch: "x64", extension: "zip", homePath: "" };
|
|
90
|
-
}
|
|
91
|
-
throw Error(`Operating system type '${osType}' with architecture '${osArch}' is not currently supported.`);
|
|
92
|
-
};
|
|
93
|
-
const installCoursier = async (gatlingHomeDir, downloadDir) => {
|
|
94
|
-
const coursierRootPath = `${gatlingHomeDir}/coursier/${versions_1.versions.coursier}`;
|
|
95
|
-
const coursierPath = `${coursierRootPath}/cs`;
|
|
96
|
-
if (!(0, fs_1.existsSync)(coursierPath)) {
|
|
97
|
-
// TODO test Linux/windows
|
|
98
|
-
const url = `https://github.com/coursier/coursier/releases/download/v${versions_1.versions.coursier}/coursier`;
|
|
99
|
-
const downloadPath = `${downloadDir}/cs`;
|
|
100
|
-
if ((0, fs_1.existsSync)(coursierRootPath)) {
|
|
101
|
-
await promises_1.default.rm(coursierRootPath, { recursive: true });
|
|
102
|
-
}
|
|
103
|
-
if ((0, fs_1.existsSync)(downloadPath)) {
|
|
104
|
-
await promises_1.default.rm(downloadPath);
|
|
105
|
-
}
|
|
106
|
-
await promises_1.default.mkdir(coursierRootPath, { recursive: true });
|
|
107
|
-
log_1.logger.info(`Downloading Coursier ${versions_1.versions.coursier} to ${downloadPath}`);
|
|
108
|
-
await (0, download_1.downloadFile)(url, downloadPath);
|
|
109
|
-
await promises_1.default.chmod(downloadPath, 0o744);
|
|
110
|
-
log_1.logger.info(`Installing Coursier to ${coursierPath}`);
|
|
111
|
-
await promises_1.default.rename(downloadPath, coursierPath);
|
|
112
|
-
}
|
|
113
|
-
else {
|
|
114
|
-
log_1.logger.info(`Coursier ${versions_1.versions.coursier} already installed at ${coursierPath}`);
|
|
115
|
-
}
|
|
116
|
-
return coursierPath;
|
|
117
|
-
};
|
|
118
|
-
const resolveDependencies = async (coursierPath, javaHome) => {
|
|
119
|
-
const gatlingDep = `"io.gatling.highcharts:gatling-charts-highcharts:${versions_1.versions.gatling.core}"`;
|
|
120
|
-
const gatlingAdapterDep = `"io.gatling:gatling-jvm-to-js-adapter:${versions_1.versions.gatling.jsAdapter}"`;
|
|
121
|
-
const graalvmJsDep = `"org.graalvm.polyglot:js-community:${versions_1.versions.graalvm.js}"`;
|
|
122
|
-
const command = `"${coursierPath}" fetch --classpath ${gatlingDep} ${gatlingAdapterDep} ${graalvmJsDep}`;
|
|
123
|
-
// TODO could add a timeout
|
|
124
|
-
log_1.logger.info(`Resolving dependencies with Coursier`);
|
|
125
|
-
const { stdout } = await (0, exports.execAsync)(command, { env: { ...process.env, JAVA_HOME: javaHome } });
|
|
126
|
-
return stdout;
|
|
22
|
+
exports.installGatlingJs = installGatlingJs;
|
|
23
|
+
const installRecorder = async (options) => {
|
|
24
|
+
const downloadDir = `${options.gatlingHome}/tmp/download`;
|
|
25
|
+
await promises_1.default.mkdir(downloadDir, { recursive: true });
|
|
26
|
+
const graalvmHomePath = await (0, graalVm_1.installGraalVm)(options.gatlingHome, downloadDir);
|
|
27
|
+
const coursierPath = await (0, coursier_1.installCoursier)(options.gatlingHome, downloadDir);
|
|
28
|
+
const classpath = await (0, coursier_1.resolveRecorderDependencies)(coursierPath, graalvmHomePath);
|
|
29
|
+
return {
|
|
30
|
+
graalvmHome: graalvmHomePath,
|
|
31
|
+
coursierBinary: coursierPath,
|
|
32
|
+
jvmClasspath: classpath.trim()
|
|
33
|
+
};
|
|
127
34
|
};
|
|
35
|
+
exports.installRecorder = installRecorder;
|
|
@@ -0,0 +1,28 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
3
|
+
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
4
|
+
};
|
|
5
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
6
|
+
exports.osArch = exports.osType = void 0;
|
|
7
|
+
const os_1 = __importDefault(require("os"));
|
|
8
|
+
const resolveOsType = () => {
|
|
9
|
+
const t = os_1.default.type();
|
|
10
|
+
if (t !== "Darwin" && t !== "Linux" && t !== "Windows_NT") {
|
|
11
|
+
throw Error(`Gatling JS does not support the Operating System '${t}'`);
|
|
12
|
+
}
|
|
13
|
+
return t;
|
|
14
|
+
};
|
|
15
|
+
exports.osType = resolveOsType();
|
|
16
|
+
const resolveOsArch = () => {
|
|
17
|
+
const a = os_1.default.arch();
|
|
18
|
+
if (a !== "x64" && a !== "arm64") {
|
|
19
|
+
throw Error(`Gatling JS does not support the architecture '${a}'`);
|
|
20
|
+
}
|
|
21
|
+
if (exports.osType === "Windows_NT" && a === "arm64") {
|
|
22
|
+
// GraalVM distribution not available for Windows on ARM
|
|
23
|
+
// TODO see if we can recommend a solution
|
|
24
|
+
throw Error(`Gatling JS does not support Windows on the ARM architecture`);
|
|
25
|
+
}
|
|
26
|
+
return a;
|
|
27
|
+
};
|
|
28
|
+
exports.osArch = resolveOsArch();
|
package/target/index.js
CHANGED
|
@@ -16,12 +16,11 @@ const program = new commander_1.Command()
|
|
|
16
16
|
.description("The Gatling Javascript run & packaging tool");
|
|
17
17
|
const gatlingHomeOption = new commander_1.Option("--gatling-home <value>", 'The folder used to download and install Gatling components (default: "~/.gatling")');
|
|
18
18
|
const gatlingHomeDirWithDefaults = (options) => options.gatlingHome || `${os_1.default.homedir()}/.gatling`;
|
|
19
|
-
const
|
|
20
|
-
const
|
|
21
|
-
const entrypointFileWithDefaults = (options) => options.entrypointFile || (options.typescript ? "src/index.ts" : "src/index.js");
|
|
19
|
+
const sourcesFolderOption = new commander_1.Option("--sources-folder <value>", "The sources folder path").default("src");
|
|
20
|
+
const simulationOption = new commander_1.Option("--simulation <value>", "The simulation entry point function name").default("default", '"default", compatible with using "export default"');
|
|
22
21
|
const bundleFileOption = new commander_1.Option("--bundle-file <value>", "The simulation target bundle file path").default("target/bundle.js");
|
|
23
22
|
const resourcesFolderOption = new commander_1.Option("--resources-folder <value>", "The resources folder path").default("resources");
|
|
24
|
-
const resultsFolderOption = new commander_1.Option("--results-folder <value>", "The results folder path").default("
|
|
23
|
+
const resultsFolderOption = new commander_1.Option("--results-folder <value>", "The results folder path").default("target/gatling");
|
|
25
24
|
const typescriptOption = new commander_1.Option("--typescript", "Use the typescript compiler to compile your code").default(false);
|
|
26
25
|
const graalvmHomeMandatoryOption = new commander_1.Option("--graalvm-home <value>", "Path to the GraalVM home").makeOptionMandatory(true);
|
|
27
26
|
const jvmClasspathMandatoryOption = new commander_1.Option("--jvm-classpath <value>", "The classpath containing all Gatling JVM components").makeOptionMandatory(true);
|
|
@@ -31,7 +30,7 @@ program
|
|
|
31
30
|
.addOption(gatlingHomeOption)
|
|
32
31
|
.action(async (options) => {
|
|
33
32
|
const gatlingHome = gatlingHomeDirWithDefaults(options);
|
|
34
|
-
const { graalvmHome, coursierBinary, jvmClasspath } = await (0, dependencies_1.
|
|
33
|
+
const { graalvmHome, coursierBinary, jvmClasspath } = await (0, dependencies_1.installGatlingJs)({ gatlingHome });
|
|
35
34
|
log_1.logger.info(`graalvmHome=${graalvmHome}`);
|
|
36
35
|
log_1.logger.info(`coursierBinary=${coursierBinary}`);
|
|
37
36
|
log_1.logger.info(`jvmClasspath=${jvmClasspath}`);
|
|
@@ -39,38 +38,45 @@ program
|
|
|
39
38
|
program
|
|
40
39
|
.command("build")
|
|
41
40
|
.description("Build a Gatling simulation")
|
|
42
|
-
.addOption(
|
|
41
|
+
.addOption(sourcesFolderOption)
|
|
43
42
|
.addOption(bundleFileOption)
|
|
44
43
|
.addOption(typescriptOption)
|
|
45
44
|
.action(async (options) => {
|
|
46
|
-
const
|
|
45
|
+
const sourcesFolder = options.sourcesFolder;
|
|
47
46
|
const bundleFile = options.bundleFile;
|
|
48
47
|
const typescript = options.typescript;
|
|
49
|
-
await (0, bundle_1.bundle)({
|
|
48
|
+
await (0, bundle_1.bundle)({ sourcesFolder, bundleFile, typescript });
|
|
50
49
|
});
|
|
51
50
|
program
|
|
52
51
|
.command("run-only")
|
|
53
52
|
.description("Run a Gatling simulation")
|
|
54
53
|
.addOption(graalvmHomeMandatoryOption)
|
|
55
54
|
.addOption(jvmClasspathMandatoryOption)
|
|
56
|
-
.addOption(
|
|
55
|
+
.addOption(simulationOption)
|
|
57
56
|
.addOption(bundleFileOption)
|
|
58
57
|
.addOption(resourcesFolderOption)
|
|
59
58
|
.addOption(resultsFolderOption)
|
|
60
59
|
.action(async (options) => {
|
|
61
60
|
const graalvmHome = options.graalvmHome;
|
|
62
61
|
const jvmClasspath = options.jvmClasspath;
|
|
63
|
-
const
|
|
62
|
+
const simulation = options.simulation;
|
|
64
63
|
const bundleFile = options.bundleFile;
|
|
65
64
|
const resourcesFolder = options.resourcesFolder;
|
|
66
65
|
const resultsFolder = options.resultsFolder;
|
|
67
|
-
await (0, run_1.
|
|
66
|
+
await (0, run_1.runSimulation)({
|
|
67
|
+
graalvmHome,
|
|
68
|
+
jvmClasspath,
|
|
69
|
+
simulation: simulation,
|
|
70
|
+
bundleFile,
|
|
71
|
+
resourcesFolder,
|
|
72
|
+
resultsFolder
|
|
73
|
+
});
|
|
68
74
|
});
|
|
69
75
|
program
|
|
70
76
|
.command("run")
|
|
71
77
|
.description("Build and run a Gatling simulation, after installing all required components and dependencies for Gatling")
|
|
72
|
-
.addOption(
|
|
73
|
-
.addOption(
|
|
78
|
+
.addOption(sourcesFolderOption)
|
|
79
|
+
.addOption(simulationOption)
|
|
74
80
|
.addOption(typescriptOption)
|
|
75
81
|
.addOption(bundleFileOption)
|
|
76
82
|
.addOption(resourcesFolderOption)
|
|
@@ -78,17 +84,35 @@ program
|
|
|
78
84
|
.addOption(gatlingHomeOption)
|
|
79
85
|
.action(async (options) => {
|
|
80
86
|
const gatlingHome = gatlingHomeDirWithDefaults(options);
|
|
81
|
-
const
|
|
82
|
-
const
|
|
87
|
+
const sourcesFolder = options.sourcesFolder;
|
|
88
|
+
const simulation = options.simulation;
|
|
83
89
|
const bundleFile = options.bundleFile;
|
|
84
90
|
const resourcesFolder = options.resourcesFolder;
|
|
85
91
|
const resultsFolder = options.resultsFolder;
|
|
86
92
|
const typescript = options.typescript;
|
|
87
|
-
const { graalvmHome, coursierBinary, jvmClasspath } = await (0, dependencies_1.
|
|
93
|
+
const { graalvmHome, coursierBinary, jvmClasspath } = await (0, dependencies_1.installGatlingJs)({ gatlingHome });
|
|
88
94
|
log_1.logger.debug(`graalvmHome=${graalvmHome}`);
|
|
89
95
|
log_1.logger.debug(`coursierBinary=${coursierBinary}`);
|
|
90
96
|
log_1.logger.debug(`jvmClasspath=${jvmClasspath}`);
|
|
91
|
-
await (0, bundle_1.bundle)({
|
|
92
|
-
await (0, run_1.
|
|
97
|
+
await (0, bundle_1.bundle)({ sourcesFolder, bundleFile, typescript });
|
|
98
|
+
await (0, run_1.runSimulation)({ graalvmHome, jvmClasspath, simulation, bundleFile, resourcesFolder, resultsFolder });
|
|
99
|
+
});
|
|
100
|
+
program
|
|
101
|
+
.command("recorder")
|
|
102
|
+
.description("Run the Gatling recorder")
|
|
103
|
+
.addOption(gatlingHomeOption)
|
|
104
|
+
.addOption(sourcesFolderOption)
|
|
105
|
+
.addOption(typescriptOption)
|
|
106
|
+
.addOption(resourcesFolderOption)
|
|
107
|
+
.action(async (options) => {
|
|
108
|
+
const gatlingHome = gatlingHomeDirWithDefaults(options);
|
|
109
|
+
const sourcesFolder = options.sourcesFolder;
|
|
110
|
+
const resourcesFolder = options.resourcesFolder;
|
|
111
|
+
const typescript = options.typescript;
|
|
112
|
+
const { graalvmHome, coursierBinary, jvmClasspath } = await (0, dependencies_1.installRecorder)({ gatlingHome });
|
|
113
|
+
log_1.logger.debug(`graalvmHome=${graalvmHome}`);
|
|
114
|
+
log_1.logger.debug(`coursierBinary=${coursierBinary}`);
|
|
115
|
+
log_1.logger.debug(`jvmClasspath=${jvmClasspath}`);
|
|
116
|
+
await (0, run_1.runRecorder)({ graalvmHome, jvmClasspath, sourcesFolder, typescript, resourcesFolder });
|
|
93
117
|
});
|
|
94
118
|
program.parse(process.argv);
|
package/target/run.d.ts
CHANGED
|
@@ -1,9 +1,17 @@
|
|
|
1
1
|
export interface RunOptions {
|
|
2
2
|
graalvmHome: string;
|
|
3
3
|
jvmClasspath: string;
|
|
4
|
-
|
|
4
|
+
}
|
|
5
|
+
export interface RunSimulationOptions extends RunOptions {
|
|
6
|
+
simulation: string;
|
|
5
7
|
bundleFile: string;
|
|
6
8
|
resourcesFolder: string;
|
|
7
9
|
resultsFolder: string;
|
|
8
10
|
}
|
|
9
|
-
export
|
|
11
|
+
export interface RunRecorderOptions extends RunOptions {
|
|
12
|
+
sourcesFolder: string;
|
|
13
|
+
typescript: boolean;
|
|
14
|
+
resourcesFolder: string;
|
|
15
|
+
}
|
|
16
|
+
export declare const runSimulation: (options: RunSimulationOptions) => Promise<void>;
|
|
17
|
+
export declare const runRecorder: (options: RunRecorderOptions) => Promise<void>;
|
package/target/run.js
CHANGED
|
@@ -1,56 +1,62 @@
|
|
|
1
1
|
"use strict";
|
|
2
|
-
var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
|
|
3
|
-
if (k2 === undefined) k2 = k;
|
|
4
|
-
var desc = Object.getOwnPropertyDescriptor(m, k);
|
|
5
|
-
if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
|
|
6
|
-
desc = { enumerable: true, get: function() { return m[k]; } };
|
|
7
|
-
}
|
|
8
|
-
Object.defineProperty(o, k2, desc);
|
|
9
|
-
}) : (function(o, m, k, k2) {
|
|
10
|
-
if (k2 === undefined) k2 = k;
|
|
11
|
-
o[k2] = m[k];
|
|
12
|
-
}));
|
|
13
|
-
var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
|
|
14
|
-
Object.defineProperty(o, "default", { enumerable: true, value: v });
|
|
15
|
-
}) : function(o, v) {
|
|
16
|
-
o["default"] = v;
|
|
17
|
-
});
|
|
18
|
-
var __importStar = (this && this.__importStar) || function (mod) {
|
|
19
|
-
if (mod && mod.__esModule) return mod;
|
|
20
|
-
var result = {};
|
|
21
|
-
if (mod != null) for (var k in mod) if (k !== "default" && Object.prototype.hasOwnProperty.call(mod, k)) __createBinding(result, mod, k);
|
|
22
|
-
__setModuleDefault(result, mod);
|
|
23
|
-
return result;
|
|
24
|
-
};
|
|
25
2
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
26
|
-
exports.
|
|
3
|
+
exports.runRecorder = exports.runSimulation = void 0;
|
|
27
4
|
const child_process_1 = require("child_process");
|
|
28
|
-
const path = __importStar(require("path"));
|
|
29
5
|
const log_1 = require("./log");
|
|
30
|
-
const
|
|
6
|
+
const versions_1 = require("./dependencies/versions");
|
|
7
|
+
const os_1 = require("./dependencies/os");
|
|
8
|
+
const runSimulation = async (options) => {
|
|
31
9
|
log_1.logger.info(`Running a Gatling simulation with options:
|
|
32
|
-
-
|
|
10
|
+
- simulation: ${options.simulation}
|
|
33
11
|
- bundleFile: ${options.bundleFile}`);
|
|
34
|
-
const
|
|
35
|
-
const
|
|
12
|
+
const additionalClasspathElements = [options.resourcesFolder];
|
|
13
|
+
const javaArgs = [
|
|
14
|
+
`-Dgatling.js.bundle.filePath=${options.bundleFile}`,
|
|
15
|
+
`-Dgatling.js.simulation=${options.simulation}`
|
|
16
|
+
];
|
|
17
|
+
const simulationArgs = [
|
|
18
|
+
"--results-folder",
|
|
19
|
+
options.resultsFolder,
|
|
20
|
+
"--simulation",
|
|
21
|
+
"io.gatling.js.JsSimulation",
|
|
22
|
+
"--launcher",
|
|
23
|
+
"gatling-js-cli",
|
|
24
|
+
"--build-tool-version",
|
|
25
|
+
versions_1.versions.gatling.jsAdapter
|
|
26
|
+
];
|
|
27
|
+
return run(options, "io.gatling.app.Gatling", additionalClasspathElements, javaArgs, simulationArgs);
|
|
28
|
+
};
|
|
29
|
+
exports.runSimulation = runSimulation;
|
|
30
|
+
const runRecorder = async (options) => {
|
|
31
|
+
log_1.logger.info("Running the Gatling Recorder");
|
|
32
|
+
const recorderArgs = [
|
|
33
|
+
"--simulations-folder",
|
|
34
|
+
options.sourcesFolder,
|
|
35
|
+
"--resources-folder",
|
|
36
|
+
options.resourcesFolder,
|
|
37
|
+
"--format",
|
|
38
|
+
options.typescript ? "typescript" : "javascript"
|
|
39
|
+
];
|
|
40
|
+
return run(options, "io.gatling.recorder.GatlingRecorder", [], [], recorderArgs);
|
|
41
|
+
};
|
|
42
|
+
exports.runRecorder = runRecorder;
|
|
43
|
+
const run = (options, mainClass, additionalClasspathElements, javaArgs, mainClassArgs) => {
|
|
36
44
|
const command = `${options.graalvmHome}/bin/java`;
|
|
37
|
-
const
|
|
45
|
+
const classpathSeparator = os_1.osType === "Windows_NT" ? ";" : ":";
|
|
46
|
+
const classpath = [...additionalClasspathElements, options.jvmClasspath].join(classpathSeparator);
|
|
47
|
+
const allArgs = [
|
|
38
48
|
"-server",
|
|
39
49
|
"-XX:+HeapDumpOnOutOfMemoryError",
|
|
40
50
|
"-XX:MaxInlineLevel=20",
|
|
41
51
|
"-XX:MaxTrivialSize=12",
|
|
42
52
|
"-Xmx1G",
|
|
43
53
|
"-classpath",
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
"--results-folder",
|
|
49
|
-
options.resultsFolder,
|
|
50
|
-
"--simulation",
|
|
51
|
-
"io.gatling.js.JsSimulation"
|
|
54
|
+
classpath,
|
|
55
|
+
...javaArgs,
|
|
56
|
+
mainClass,
|
|
57
|
+
...mainClassArgs
|
|
52
58
|
];
|
|
53
|
-
const process = (0, child_process_1.spawn)(command,
|
|
59
|
+
const process = (0, child_process_1.spawn)(command, allArgs);
|
|
54
60
|
return new Promise((resolve, reject) => {
|
|
55
61
|
process.stdout.on("data", (data) => log_1.logger.info(data.toString()));
|
|
56
62
|
process.stderr.on("data", (data) => log_1.logger.error(data.toString()));
|
|
@@ -65,4 +71,3 @@ const run = async (options) => {
|
|
|
65
71
|
});
|
|
66
72
|
});
|
|
67
73
|
};
|
|
68
|
-
exports.run = run;
|