cypress 15.1.0 → 15.3.0
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/bin/cypress +3 -1
- package/dist/VerboseRenderer.js +61 -0
- package/dist/cli.js +544 -0
- package/dist/cypress.js +104 -0
- package/dist/errors.js +391 -0
- package/dist/exec/info.js +103 -0
- package/dist/exec/open.js +103 -0
- package/dist/exec/run.js +177 -0
- package/dist/exec/shared.js +55 -0
- package/dist/exec/spawn.js +301 -0
- package/dist/exec/versions.js +67 -0
- package/dist/exec/xvfb.js +118 -0
- package/dist/index.js +52 -0
- package/dist/index.mjs +9 -0
- package/dist/logger.js +55 -0
- package/dist/tasks/cache.js +144 -0
- package/dist/tasks/download.js +304 -0
- package/dist/tasks/get-folder-size.js +44 -0
- package/dist/tasks/install.js +326 -0
- package/dist/tasks/state.js +184 -0
- package/dist/tasks/unzip.js +192 -0
- package/dist/tasks/verify.js +303 -0
- package/dist/util.js +452 -0
- package/package.json +10 -13
- package/types/cypress-automation.d.ts +2 -1
- package/types/cypress.d.ts +1 -0
- package/index.js +0 -27
- package/index.mjs +0 -17
- package/lib/VerboseRenderer.js +0 -58
- package/lib/cli.js +0 -411
- package/lib/cypress.js +0 -98
- package/lib/errors.js +0 -392
- package/lib/exec/info.js +0 -92
- package/lib/exec/open.js +0 -90
- package/lib/exec/run.js +0 -176
- package/lib/exec/shared.js +0 -62
- package/lib/exec/spawn.js +0 -247
- package/lib/exec/versions.js +0 -53
- package/lib/exec/xvfb.js +0 -93
- package/lib/fs.js +0 -4
- package/lib/logger.js +0 -50
- package/lib/tasks/cache.js +0 -132
- package/lib/tasks/download.js +0 -324
- package/lib/tasks/get-folder-size.js +0 -33
- package/lib/tasks/install.js +0 -368
- package/lib/tasks/state.js +0 -185
- package/lib/tasks/unzip.js +0 -200
- package/lib/tasks/verify.js +0 -300
- package/lib/util.js +0 -448
package/lib/exec/run.js
DELETED
@@ -1,176 +0,0 @@
|
|
1
|
-
"use strict";
|
2
|
-
|
3
|
-
const _ = require('lodash');
|
4
|
-
const debug = require('debug')('cypress:cli:run');
|
5
|
-
const util = require('../util');
|
6
|
-
const spawn = require('./spawn');
|
7
|
-
const verify = require('../tasks/verify');
|
8
|
-
const {
|
9
|
-
exitWithError,
|
10
|
-
errors
|
11
|
-
} = require('../errors');
|
12
|
-
const {
|
13
|
-
processTestingType,
|
14
|
-
throwInvalidOptionError,
|
15
|
-
checkConfigFile
|
16
|
-
} = require('./shared');
|
17
|
-
|
18
|
-
/**
|
19
|
-
* Typically a user passes a string path to the project.
|
20
|
-
* But "cypress open" allows using `false` to open in global mode,
|
21
|
-
* and the user can accidentally execute `cypress run --project false`
|
22
|
-
* which should be invalid.
|
23
|
-
*/
|
24
|
-
const isValidProject = v => {
|
25
|
-
if (typeof v === 'boolean') {
|
26
|
-
return false;
|
27
|
-
}
|
28
|
-
if (v === '' || v === 'false' || v === 'true') {
|
29
|
-
return false;
|
30
|
-
}
|
31
|
-
return true;
|
32
|
-
};
|
33
|
-
|
34
|
-
/**
|
35
|
-
* Maps options collected by the CLI
|
36
|
-
* and forms list of CLI arguments to the server.
|
37
|
-
*
|
38
|
-
* Note: there is lightweight validation, with errors
|
39
|
-
* thrown synchronously.
|
40
|
-
*
|
41
|
-
* @returns {string[]} list of CLI arguments
|
42
|
-
*/
|
43
|
-
const processRunOptions = (options = {}) => {
|
44
|
-
debug('processing run options %o', options);
|
45
|
-
if (!isValidProject(options.project)) {
|
46
|
-
debug('invalid project option %o', {
|
47
|
-
project: options.project
|
48
|
-
});
|
49
|
-
return throwInvalidOptionError(errors.invalidRunProjectPath);
|
50
|
-
}
|
51
|
-
const args = ['--run-project', options.project];
|
52
|
-
if (options.autoCancelAfterFailures || options.autoCancelAfterFailures === 0 || options.autoCancelAfterFailures === false) {
|
53
|
-
args.push('--auto-cancel-after-failures', options.autoCancelAfterFailures);
|
54
|
-
}
|
55
|
-
if (options.browser) {
|
56
|
-
args.push('--browser', options.browser);
|
57
|
-
}
|
58
|
-
if (options.ciBuildId) {
|
59
|
-
args.push('--ci-build-id', options.ciBuildId);
|
60
|
-
}
|
61
|
-
if (options.config) {
|
62
|
-
args.push('--config', options.config);
|
63
|
-
}
|
64
|
-
if (options.configFile !== undefined) {
|
65
|
-
checkConfigFile(options);
|
66
|
-
args.push('--config-file', options.configFile);
|
67
|
-
}
|
68
|
-
if (options.env) {
|
69
|
-
args.push('--env', options.env);
|
70
|
-
}
|
71
|
-
if (options.exit === false) {
|
72
|
-
args.push('--no-exit');
|
73
|
-
}
|
74
|
-
if (options.group) {
|
75
|
-
args.push('--group', options.group);
|
76
|
-
}
|
77
|
-
if (options.headed) {
|
78
|
-
args.push('--headed', options.headed);
|
79
|
-
}
|
80
|
-
if (options.headless) {
|
81
|
-
if (options.headed) {
|
82
|
-
return throwInvalidOptionError(errors.incompatibleHeadlessFlags);
|
83
|
-
}
|
84
|
-
args.push('--headed', !options.headless);
|
85
|
-
}
|
86
|
-
|
87
|
-
// if key is set use that - else attempt to find it by environment variable
|
88
|
-
if (options.key == null) {
|
89
|
-
debug('--key is not set, looking up environment variable CYPRESS_RECORD_KEY');
|
90
|
-
options.key = util.getEnv('CYPRESS_RECORD_KEY');
|
91
|
-
}
|
92
|
-
|
93
|
-
// if we have a key assume we're in record mode
|
94
|
-
if (options.key) {
|
95
|
-
args.push('--key', options.key);
|
96
|
-
}
|
97
|
-
if (options.outputPath) {
|
98
|
-
args.push('--output-path', options.outputPath);
|
99
|
-
}
|
100
|
-
if (options.parallel) {
|
101
|
-
args.push('--parallel');
|
102
|
-
}
|
103
|
-
if (options.port) {
|
104
|
-
args.push('--port', options.port);
|
105
|
-
}
|
106
|
-
if (options.quiet) {
|
107
|
-
args.push('--quiet');
|
108
|
-
}
|
109
|
-
|
110
|
-
// if record is defined and we're not
|
111
|
-
// already in ci mode, then send it up
|
112
|
-
if (options.record != null) {
|
113
|
-
args.push('--record', options.record);
|
114
|
-
}
|
115
|
-
|
116
|
-
// if we have a specific reporter push that into the args
|
117
|
-
if (options.reporter) {
|
118
|
-
args.push('--reporter', options.reporter);
|
119
|
-
}
|
120
|
-
|
121
|
-
// if we have a specific reporter push that into the args
|
122
|
-
if (options.reporterOptions) {
|
123
|
-
args.push('--reporter-options', options.reporterOptions);
|
124
|
-
}
|
125
|
-
if (options.runnerUi != null) {
|
126
|
-
args.push('--runner-ui', options.runnerUi);
|
127
|
-
}
|
128
|
-
|
129
|
-
// if we have specific spec(s) push that into the args
|
130
|
-
if (options.spec) {
|
131
|
-
args.push('--spec', options.spec);
|
132
|
-
}
|
133
|
-
if (options.tag) {
|
134
|
-
args.push('--tag', options.tag);
|
135
|
-
}
|
136
|
-
if (options.inspect) {
|
137
|
-
args.push('--inspect');
|
138
|
-
}
|
139
|
-
if (options.inspectBrk) {
|
140
|
-
args.push('--inspectBrk');
|
141
|
-
}
|
142
|
-
args.push(...processTestingType(options));
|
143
|
-
return args;
|
144
|
-
};
|
145
|
-
module.exports = {
|
146
|
-
processRunOptions,
|
147
|
-
isValidProject,
|
148
|
-
// resolves with the number of failed tests
|
149
|
-
start(options = {}) {
|
150
|
-
_.defaults(options, {
|
151
|
-
key: null,
|
152
|
-
spec: null,
|
153
|
-
reporter: null,
|
154
|
-
reporterOptions: null,
|
155
|
-
project: process.cwd()
|
156
|
-
});
|
157
|
-
function run() {
|
158
|
-
try {
|
159
|
-
const args = processRunOptions(options);
|
160
|
-
debug('run to spawn.start args %j', args);
|
161
|
-
return spawn.start(args, {
|
162
|
-
dev: options.dev
|
163
|
-
});
|
164
|
-
} catch (err) {
|
165
|
-
if (err.details) {
|
166
|
-
return exitWithError(err.details)();
|
167
|
-
}
|
168
|
-
throw err;
|
169
|
-
}
|
170
|
-
}
|
171
|
-
if (options.dev) {
|
172
|
-
return run();
|
173
|
-
}
|
174
|
-
return verify.start().then(run);
|
175
|
-
}
|
176
|
-
};
|
package/lib/exec/shared.js
DELETED
@@ -1,62 +0,0 @@
|
|
1
|
-
"use strict";
|
2
|
-
|
3
|
-
const {
|
4
|
-
errors
|
5
|
-
} = require('../errors');
|
6
|
-
|
7
|
-
/**
|
8
|
-
* Throws an error with "details" property from
|
9
|
-
* "errors" object.
|
10
|
-
* @param {Object} details - Error details
|
11
|
-
*/
|
12
|
-
const throwInvalidOptionError = details => {
|
13
|
-
if (!details) {
|
14
|
-
details = errors.unknownError;
|
15
|
-
}
|
16
|
-
|
17
|
-
// throw this error synchronously, it will be caught later on and
|
18
|
-
// the details will be propagated to the promise chain
|
19
|
-
const err = new Error();
|
20
|
-
err.details = details;
|
21
|
-
throw err;
|
22
|
-
};
|
23
|
-
|
24
|
-
/**
|
25
|
-
* Selects exec args based on the configured `testingType`
|
26
|
-
* @param {string} testingType The type of tests being executed
|
27
|
-
* @returns {string[]} The array of new exec arguments
|
28
|
-
*/
|
29
|
-
const processTestingType = options => {
|
30
|
-
if (options.e2e && options.component) {
|
31
|
-
return throwInvalidOptionError(errors.incompatibleTestTypeFlags);
|
32
|
-
}
|
33
|
-
if (options.testingType && (options.component || options.e2e)) {
|
34
|
-
return throwInvalidOptionError(errors.incompatibleTestTypeFlags);
|
35
|
-
}
|
36
|
-
if (options.testingType === 'component' || options.component || options.ct) {
|
37
|
-
return ['--testing-type', 'component'];
|
38
|
-
}
|
39
|
-
if (options.testingType === 'e2e' || options.e2e) {
|
40
|
-
return ['--testing-type', 'e2e'];
|
41
|
-
}
|
42
|
-
if (options.testingType) {
|
43
|
-
return throwInvalidOptionError(errors.invalidTestingType);
|
44
|
-
}
|
45
|
-
return [];
|
46
|
-
};
|
47
|
-
|
48
|
-
/**
|
49
|
-
* Throws an error if configFile is string 'false' or boolean false
|
50
|
-
* @param {*} options
|
51
|
-
*/
|
52
|
-
const checkConfigFile = options => {
|
53
|
-
// CLI will parse as string, module API can pass in boolean
|
54
|
-
if (options.configFile === 'false' || options.configFile === false) {
|
55
|
-
throwInvalidOptionError(errors.invalidConfigFile);
|
56
|
-
}
|
57
|
-
};
|
58
|
-
module.exports = {
|
59
|
-
throwInvalidOptionError,
|
60
|
-
processTestingType,
|
61
|
-
checkConfigFile
|
62
|
-
};
|
package/lib/exec/spawn.js
DELETED
@@ -1,247 +0,0 @@
|
|
1
|
-
"use strict";
|
2
|
-
|
3
|
-
const _ = require('lodash');
|
4
|
-
const os = require('os');
|
5
|
-
const cp = require('child_process');
|
6
|
-
const path = require('path');
|
7
|
-
const Promise = require('bluebird');
|
8
|
-
const debug = require('debug')('cypress:cli');
|
9
|
-
const util = require('../util');
|
10
|
-
const state = require('../tasks/state');
|
11
|
-
const xvfb = require('./xvfb');
|
12
|
-
const verify = require('../tasks/verify');
|
13
|
-
const errors = require('../errors');
|
14
|
-
const readline = require('readline');
|
15
|
-
function isPlatform(platform) {
|
16
|
-
return os.platform() === platform;
|
17
|
-
}
|
18
|
-
function needsStderrPiped(needsXvfb) {
|
19
|
-
return _.some([isPlatform('darwin'), needsXvfb && isPlatform('linux'), util.isPossibleLinuxWithIncorrectDisplay()]);
|
20
|
-
}
|
21
|
-
function needsEverythingPipedDirectly() {
|
22
|
-
return isPlatform('win32');
|
23
|
-
}
|
24
|
-
function getStdio(needsXvfb) {
|
25
|
-
if (needsEverythingPipedDirectly()) {
|
26
|
-
return 'pipe';
|
27
|
-
}
|
28
|
-
|
29
|
-
// https://github.com/cypress-io/cypress/issues/921
|
30
|
-
// https://github.com/cypress-io/cypress/issues/1143
|
31
|
-
// https://github.com/cypress-io/cypress/issues/1745
|
32
|
-
if (needsStderrPiped(needsXvfb)) {
|
33
|
-
// returning pipe here so we can massage stderr
|
34
|
-
// and remove garbage from Xlib and libuv
|
35
|
-
// due to starting the Xvfb process on linux
|
36
|
-
return ['inherit', 'inherit', 'pipe'];
|
37
|
-
}
|
38
|
-
return 'inherit';
|
39
|
-
}
|
40
|
-
module.exports = {
|
41
|
-
start(args, options = {}) {
|
42
|
-
const needsXvfb = xvfb.isNeeded();
|
43
|
-
let executable = state.getPathToExecutable(state.getBinaryDir());
|
44
|
-
if (util.getEnv('CYPRESS_RUN_BINARY')) {
|
45
|
-
executable = path.resolve(util.getEnv('CYPRESS_RUN_BINARY'));
|
46
|
-
}
|
47
|
-
debug('needs to start own Xvfb?', needsXvfb);
|
48
|
-
|
49
|
-
// Always push cwd into the args
|
50
|
-
// which additionally acts as a signal to the
|
51
|
-
// binary that it was invoked through the NPM module
|
52
|
-
args = args || [];
|
53
|
-
if (typeof args === 'string') {
|
54
|
-
args = [args];
|
55
|
-
}
|
56
|
-
args = [...args, '--cwd', process.cwd(), '--userNodePath', process.execPath, '--userNodeVersion', process.versions.node];
|
57
|
-
_.defaults(options, {
|
58
|
-
dev: false,
|
59
|
-
env: process.env,
|
60
|
-
detached: false,
|
61
|
-
stdio: getStdio(needsXvfb)
|
62
|
-
});
|
63
|
-
const spawn = (overrides = {}) => {
|
64
|
-
return new Promise((resolve, reject) => {
|
65
|
-
_.defaults(overrides, {
|
66
|
-
onStderrData: false
|
67
|
-
});
|
68
|
-
const {
|
69
|
-
onStderrData
|
70
|
-
} = overrides;
|
71
|
-
const envOverrides = util.getEnvOverrides(options);
|
72
|
-
const electronArgs = [];
|
73
|
-
const node11WindowsFix = isPlatform('win32');
|
74
|
-
let startScriptPath;
|
75
|
-
if (options.dev) {
|
76
|
-
executable = 'node';
|
77
|
-
// if we're in dev then reset
|
78
|
-
// the launch cmd to be 'npm run dev'
|
79
|
-
startScriptPath = path.resolve(__dirname, '..', '..', '..', 'scripts', 'start.js'), debug('in dev mode the args became %o', args);
|
80
|
-
}
|
81
|
-
if (!options.dev && verify.needsSandbox()) {
|
82
|
-
electronArgs.push('--no-sandbox');
|
83
|
-
}
|
84
|
-
|
85
|
-
// strip dev out of child process options
|
86
|
-
/**
|
87
|
-
* @type {import('child_process').ForkOptions}
|
88
|
-
*/
|
89
|
-
let stdioOptions = _.pick(options, 'env', 'detached', 'stdio');
|
90
|
-
|
91
|
-
// figure out if we're going to be force enabling or disabling colors.
|
92
|
-
// also figure out whether we should force stdout and stderr into thinking
|
93
|
-
// it is a tty as opposed to a pipe.
|
94
|
-
stdioOptions.env = _.extend({}, stdioOptions.env, envOverrides);
|
95
|
-
if (node11WindowsFix) {
|
96
|
-
stdioOptions = _.extend({}, stdioOptions, {
|
97
|
-
windowsHide: false
|
98
|
-
});
|
99
|
-
}
|
100
|
-
if (util.isPossibleLinuxWithIncorrectDisplay()) {
|
101
|
-
// make sure we use the latest DISPLAY variable if any
|
102
|
-
debug('passing DISPLAY', process.env.DISPLAY);
|
103
|
-
stdioOptions.env.DISPLAY = process.env.DISPLAY;
|
104
|
-
}
|
105
|
-
if (stdioOptions.env.ELECTRON_RUN_AS_NODE) {
|
106
|
-
// Since we are running electron as node, we need to add an entry point file.
|
107
|
-
startScriptPath = path.join(state.getBinaryPkgPath(path.dirname(executable)), '..', 'index.js');
|
108
|
-
} else {
|
109
|
-
// Start arguments with "--" so Electron knows these are OUR
|
110
|
-
// arguments and does not try to sanitize them. Otherwise on Windows
|
111
|
-
// an url in one of the arguments crashes it :(
|
112
|
-
// https://github.com/cypress-io/cypress/issues/5466
|
113
|
-
args = [...electronArgs, '--', ...args];
|
114
|
-
}
|
115
|
-
if (startScriptPath) {
|
116
|
-
args.unshift(startScriptPath);
|
117
|
-
}
|
118
|
-
if (process.env.CYPRESS_INTERNAL_DEV_DEBUG) {
|
119
|
-
args.unshift(process.env.CYPRESS_INTERNAL_DEV_DEBUG);
|
120
|
-
}
|
121
|
-
debug('spawn args %o %o', args, _.omit(stdioOptions, 'env'));
|
122
|
-
debug('spawning Cypress with executable: %s', executable);
|
123
|
-
const child = cp.spawn(executable, args, stdioOptions);
|
124
|
-
function resolveOn(event) {
|
125
|
-
return function (code, signal) {
|
126
|
-
debug('child event fired %o', {
|
127
|
-
event,
|
128
|
-
code,
|
129
|
-
signal
|
130
|
-
});
|
131
|
-
if (code === null) {
|
132
|
-
const errorObject = errors.errors.childProcessKilled(event, signal);
|
133
|
-
return errors.getError(errorObject).then(reject);
|
134
|
-
}
|
135
|
-
resolve(code);
|
136
|
-
};
|
137
|
-
}
|
138
|
-
child.on('close', resolveOn('close'));
|
139
|
-
child.on('exit', resolveOn('exit'));
|
140
|
-
child.on('error', reject);
|
141
|
-
if (isPlatform('win32')) {
|
142
|
-
const rl = readline.createInterface({
|
143
|
-
input: process.stdin,
|
144
|
-
output: process.stdout
|
145
|
-
});
|
146
|
-
|
147
|
-
// on windows, SIGINT does not propagate to the child process when ctrl+c is pressed
|
148
|
-
// this makes sure all nested processes are closed(ex: firefox inside the server)
|
149
|
-
rl.on('SIGINT', function () {
|
150
|
-
let kill = require('tree-kill');
|
151
|
-
kill(child.pid, 'SIGINT');
|
152
|
-
});
|
153
|
-
}
|
154
|
-
|
155
|
-
// if stdio options is set to 'pipe', then
|
156
|
-
// we should set up pipes:
|
157
|
-
// process STDIN (read stream) => child STDIN (writeable)
|
158
|
-
// child STDOUT => process STDOUT
|
159
|
-
// child STDERR => process STDERR with additional filtering
|
160
|
-
if (child.stdin) {
|
161
|
-
debug('piping process STDIN into child STDIN');
|
162
|
-
process.stdin.pipe(child.stdin);
|
163
|
-
}
|
164
|
-
if (child.stdout) {
|
165
|
-
debug('piping child STDOUT to process STDOUT');
|
166
|
-
child.stdout.pipe(process.stdout);
|
167
|
-
}
|
168
|
-
|
169
|
-
// if this is defined then we are manually piping for linux
|
170
|
-
// to filter out the garbage
|
171
|
-
if (child.stderr) {
|
172
|
-
debug('piping child STDERR to process STDERR');
|
173
|
-
child.stderr.on('data', data => {
|
174
|
-
const str = data.toString();
|
175
|
-
|
176
|
-
// if we have a callback and this explicitly returns
|
177
|
-
// false then bail
|
178
|
-
if (onStderrData && onStderrData(str)) {
|
179
|
-
return;
|
180
|
-
}
|
181
|
-
|
182
|
-
// else pass it along!
|
183
|
-
process.stderr.write(data);
|
184
|
-
});
|
185
|
-
}
|
186
|
-
|
187
|
-
// https://github.com/cypress-io/cypress/issues/1841
|
188
|
-
// https://github.com/cypress-io/cypress/issues/5241
|
189
|
-
// In some versions of node, it will throw on windows
|
190
|
-
// when you close the parent process after piping
|
191
|
-
// into the child process. unpiping does not seem
|
192
|
-
// to have any effect. so we're just catching the
|
193
|
-
// error here and not doing anything.
|
194
|
-
process.stdin.on('error', err => {
|
195
|
-
if (['EPIPE', 'ENOTCONN'].includes(err.code)) {
|
196
|
-
return;
|
197
|
-
}
|
198
|
-
throw err;
|
199
|
-
});
|
200
|
-
if (stdioOptions.detached) {
|
201
|
-
child.unref();
|
202
|
-
}
|
203
|
-
});
|
204
|
-
};
|
205
|
-
const spawnInXvfb = () => {
|
206
|
-
return xvfb.start().then(userFriendlySpawn).finally(xvfb.stop);
|
207
|
-
};
|
208
|
-
const userFriendlySpawn = linuxWithDisplayEnv => {
|
209
|
-
debug('spawning, should retry on display problem?', Boolean(linuxWithDisplayEnv));
|
210
|
-
let brokenGtkDisplay;
|
211
|
-
const overrides = {};
|
212
|
-
if (linuxWithDisplayEnv) {
|
213
|
-
_.extend(overrides, {
|
214
|
-
electronLogging: true,
|
215
|
-
onStderrData(str) {
|
216
|
-
// if we receive a broken pipe anywhere
|
217
|
-
// then we know that's why cypress exited early
|
218
|
-
if (util.isBrokenGtkDisplay(str)) {
|
219
|
-
brokenGtkDisplay = true;
|
220
|
-
}
|
221
|
-
}
|
222
|
-
});
|
223
|
-
}
|
224
|
-
return spawn(overrides).then(code => {
|
225
|
-
if (code !== 0 && brokenGtkDisplay) {
|
226
|
-
util.logBrokenGtkDisplayWarning();
|
227
|
-
return spawnInXvfb();
|
228
|
-
}
|
229
|
-
return code;
|
230
|
-
})
|
231
|
-
// we can format and handle an error message from the code above
|
232
|
-
// prevent wrapping error again by using "known: undefined" filter
|
233
|
-
.catch({
|
234
|
-
known: undefined
|
235
|
-
}, errors.throwFormErrorText(errors.errors.unexpected));
|
236
|
-
};
|
237
|
-
if (needsXvfb) {
|
238
|
-
return spawnInXvfb();
|
239
|
-
}
|
240
|
-
|
241
|
-
// if we are on linux and there's already a DISPLAY
|
242
|
-
// set, then we may need to rerun cypress after
|
243
|
-
// spawning our own Xvfb server
|
244
|
-
const linuxWithDisplayEnv = util.isPossibleLinuxWithIncorrectDisplay();
|
245
|
-
return userFriendlySpawn(linuxWithDisplayEnv);
|
246
|
-
}
|
247
|
-
};
|
package/lib/exec/versions.js
DELETED
@@ -1,53 +0,0 @@
|
|
1
|
-
"use strict";
|
2
|
-
|
3
|
-
const Promise = require('bluebird');
|
4
|
-
const debug = require('debug')('cypress:cli');
|
5
|
-
const path = require('path');
|
6
|
-
const util = require('../util');
|
7
|
-
const state = require('../tasks/state');
|
8
|
-
const {
|
9
|
-
throwFormErrorText,
|
10
|
-
errors
|
11
|
-
} = require('../errors');
|
12
|
-
const getVersions = () => {
|
13
|
-
return Promise.try(() => {
|
14
|
-
if (util.getEnv('CYPRESS_RUN_BINARY')) {
|
15
|
-
let envBinaryPath = path.resolve(util.getEnv('CYPRESS_RUN_BINARY'));
|
16
|
-
return state.parseRealPlatformBinaryFolderAsync(envBinaryPath).then(envBinaryDir => {
|
17
|
-
if (!envBinaryDir) {
|
18
|
-
return throwFormErrorText(errors.CYPRESS_RUN_BINARY.notValid(envBinaryPath))();
|
19
|
-
}
|
20
|
-
debug('CYPRESS_RUN_BINARY has binaryDir:', envBinaryDir);
|
21
|
-
return envBinaryDir;
|
22
|
-
}).catch({
|
23
|
-
code: 'ENOENT'
|
24
|
-
}, err => {
|
25
|
-
return throwFormErrorText(errors.CYPRESS_RUN_BINARY.notValid(envBinaryPath))(err.message);
|
26
|
-
});
|
27
|
-
}
|
28
|
-
return state.getBinaryDir();
|
29
|
-
}).then(state.getBinaryPkgAsync).then(pkg => {
|
30
|
-
const versions = {
|
31
|
-
binary: state.getBinaryPkgVersion(pkg),
|
32
|
-
electronVersion: state.getBinaryElectronVersion(pkg),
|
33
|
-
electronNodeVersion: state.getBinaryElectronNodeVersion(pkg)
|
34
|
-
};
|
35
|
-
debug('binary versions %o', versions);
|
36
|
-
return versions;
|
37
|
-
}).then(binaryVersions => {
|
38
|
-
const buildInfo = util.pkgBuildInfo();
|
39
|
-
let packageVersion = util.pkgVersion();
|
40
|
-
if (!buildInfo) packageVersion += ' (development)';else if (!buildInfo.stable) packageVersion += ' (pre-release)';
|
41
|
-
const versions = {
|
42
|
-
package: packageVersion,
|
43
|
-
binary: binaryVersions.binary || 'not installed',
|
44
|
-
electronVersion: binaryVersions.electronVersion || 'not found',
|
45
|
-
electronNodeVersion: binaryVersions.electronNodeVersion || 'not found'
|
46
|
-
};
|
47
|
-
debug('combined versions %o', versions);
|
48
|
-
return versions;
|
49
|
-
});
|
50
|
-
};
|
51
|
-
module.exports = {
|
52
|
-
getVersions
|
53
|
-
};
|
package/lib/exec/xvfb.js
DELETED
@@ -1,93 +0,0 @@
|
|
1
|
-
"use strict";
|
2
|
-
|
3
|
-
const os = require('os');
|
4
|
-
const Promise = require('bluebird');
|
5
|
-
const Xvfb = require('@cypress/xvfb');
|
6
|
-
const {
|
7
|
-
stripIndent
|
8
|
-
} = require('common-tags');
|
9
|
-
const Debug = require('debug');
|
10
|
-
const {
|
11
|
-
throwFormErrorText,
|
12
|
-
errors
|
13
|
-
} = require('../errors');
|
14
|
-
const util = require('../util');
|
15
|
-
const debug = Debug('cypress:cli');
|
16
|
-
const debugXvfb = Debug('cypress:xvfb');
|
17
|
-
debug.Debug = debugXvfb.Debug = Debug;
|
18
|
-
const xvfbOptions = {
|
19
|
-
displayNum: process.env.XVFB_DISPLAY_NUM,
|
20
|
-
timeout: 30000,
|
21
|
-
// milliseconds
|
22
|
-
// need to explicitly define screen otherwise electron will crash
|
23
|
-
// https://github.com/cypress-io/cypress/issues/6184
|
24
|
-
xvfb_args: ['-screen', '0', '1280x1024x24'],
|
25
|
-
onStderrData(data) {
|
26
|
-
if (debugXvfb.enabled) {
|
27
|
-
debugXvfb(data.toString());
|
28
|
-
}
|
29
|
-
}
|
30
|
-
};
|
31
|
-
const xvfb = Promise.promisifyAll(new Xvfb(xvfbOptions));
|
32
|
-
module.exports = {
|
33
|
-
_debugXvfb: debugXvfb,
|
34
|
-
// expose for testing
|
35
|
-
|
36
|
-
_xvfb: xvfb,
|
37
|
-
// expose for testing
|
38
|
-
|
39
|
-
_xvfbOptions: xvfbOptions,
|
40
|
-
// expose for testing
|
41
|
-
|
42
|
-
start() {
|
43
|
-
debug('Starting Xvfb');
|
44
|
-
return xvfb.startAsync().return(null).catch({
|
45
|
-
nonZeroExitCode: true
|
46
|
-
}, throwFormErrorText(errors.nonZeroExitCodeXvfb)).catch(err => {
|
47
|
-
if (err.known) {
|
48
|
-
throw err;
|
49
|
-
}
|
50
|
-
return throwFormErrorText(errors.missingXvfb)(err);
|
51
|
-
});
|
52
|
-
},
|
53
|
-
stop() {
|
54
|
-
debug('Stopping Xvfb');
|
55
|
-
return xvfb.stopAsync().return(null).catch(() => {
|
56
|
-
// noop
|
57
|
-
});
|
58
|
-
},
|
59
|
-
isNeeded() {
|
60
|
-
if (process.env.ELECTRON_RUN_AS_NODE) {
|
61
|
-
debug('Environment variable ELECTRON_RUN_AS_NODE detected, xvfb is not needed');
|
62
|
-
return false; // xvfb required for electron processes only.
|
63
|
-
}
|
64
|
-
if (os.platform() !== 'linux') {
|
65
|
-
return false;
|
66
|
-
}
|
67
|
-
if (process.env.DISPLAY) {
|
68
|
-
const issueUrl = util.getGitHubIssueUrl(4034);
|
69
|
-
const message = stripIndent`
|
70
|
-
DISPLAY environment variable is set to ${process.env.DISPLAY} on Linux
|
71
|
-
Assuming this DISPLAY points at working X11 server,
|
72
|
-
Cypress will not spawn own Xvfb
|
73
|
-
|
74
|
-
NOTE: if the X11 server is NOT working, Cypress will exit without explanation,
|
75
|
-
see ${issueUrl}
|
76
|
-
Solution: Unset the DISPLAY variable and try again:
|
77
|
-
DISPLAY= npx cypress run ...
|
78
|
-
`;
|
79
|
-
debug(message);
|
80
|
-
return false;
|
81
|
-
}
|
82
|
-
debug('undefined DISPLAY environment variable');
|
83
|
-
debug('Cypress will spawn its own Xvfb');
|
84
|
-
return true;
|
85
|
-
},
|
86
|
-
// async method, resolved with Boolean
|
87
|
-
verify() {
|
88
|
-
return xvfb.startAsync().return(true).catch(err => {
|
89
|
-
debug('Could not verify xvfb: %s', err.message);
|
90
|
-
return false;
|
91
|
-
}).finally(xvfb.stopAsync);
|
92
|
-
}
|
93
|
-
};
|
package/lib/fs.js
DELETED
package/lib/logger.js
DELETED
@@ -1,50 +0,0 @@
|
|
1
|
-
"use strict";
|
2
|
-
|
3
|
-
const chalk = require('chalk');
|
4
|
-
let logs = [];
|
5
|
-
const logLevel = () => {
|
6
|
-
return process.env.npm_config_loglevel || 'notice';
|
7
|
-
};
|
8
|
-
const error = (...messages) => {
|
9
|
-
logs.push(messages.join(' '));
|
10
|
-
console.log(chalk.red(...messages)); // eslint-disable-line no-console
|
11
|
-
};
|
12
|
-
const warn = (...messages) => {
|
13
|
-
if (logLevel() === 'silent') return;
|
14
|
-
logs.push(messages.join(' '));
|
15
|
-
console.log(chalk.yellow(...messages)); // eslint-disable-line no-console
|
16
|
-
};
|
17
|
-
const log = (...messages) => {
|
18
|
-
if (logLevel() === 'silent' || logLevel() === 'warn') return;
|
19
|
-
logs.push(messages.join(' '));
|
20
|
-
console.log(...messages); // eslint-disable-line no-console
|
21
|
-
};
|
22
|
-
const always = (...messages) => {
|
23
|
-
logs.push(messages.join(' '));
|
24
|
-
console.log(...messages); // eslint-disable-line no-console
|
25
|
-
};
|
26
|
-
|
27
|
-
// splits long text into lines and calls log()
|
28
|
-
// on each one to allow easy unit testing for specific message
|
29
|
-
const logLines = text => {
|
30
|
-
const lines = text.split('\n');
|
31
|
-
for (const line of lines) {
|
32
|
-
log(line);
|
33
|
-
}
|
34
|
-
};
|
35
|
-
const print = () => {
|
36
|
-
return logs.join('\n');
|
37
|
-
};
|
38
|
-
const reset = () => {
|
39
|
-
logs = [];
|
40
|
-
};
|
41
|
-
module.exports = {
|
42
|
-
log,
|
43
|
-
warn,
|
44
|
-
error,
|
45
|
-
always,
|
46
|
-
logLines,
|
47
|
-
print,
|
48
|
-
reset,
|
49
|
-
logLevel
|
50
|
-
};
|