selenium-webdriver 4.0.0-alpha.7 → 4.0.0-beta.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.
Files changed (50) hide show
  1. package/CHANGES.md +56 -0
  2. package/LICENSE +202 -0
  3. package/NOTICE +2 -0
  4. package/README.md +2 -0
  5. package/chrome.js +69 -79
  6. package/chromium.js +231 -164
  7. package/{lib/atoms/make-atoms-module.js → devtools/CDPConnection.js} +15 -9
  8. package/edge.js +104 -146
  9. package/example/chrome_android.js +45 -0
  10. package/example/chrome_mobile_emulation.js +46 -0
  11. package/example/firefox_channels.js +84 -0
  12. package/example/google_search.js +50 -0
  13. package/example/google_search_test.js +70 -0
  14. package/example/headless.js +63 -0
  15. package/example/logging.js +64 -0
  16. package/firefox.js +199 -200
  17. package/http/index.js +128 -116
  18. package/http/util.js +56 -64
  19. package/ie.js +180 -104
  20. package/index.js +246 -199
  21. package/io/exec.js +35 -40
  22. package/io/index.js +146 -157
  23. package/io/zip.js +75 -66
  24. package/lib/atoms/find-elements.js +123 -0
  25. package/lib/atoms/get-attribute.js +75 -59
  26. package/lib/atoms/is-displayed.js +72 -72
  27. package/lib/atoms/mutation-listener.js +55 -0
  28. package/lib/by.js +192 -65
  29. package/lib/capabilities.js +76 -86
  30. package/lib/command.js +19 -35
  31. package/lib/error.js +134 -168
  32. package/lib/http.js +308 -232
  33. package/lib/input.js +192 -453
  34. package/lib/logging.js +126 -137
  35. package/lib/promise.js +53 -71
  36. package/lib/proxy.js +31 -41
  37. package/lib/session.js +12 -15
  38. package/lib/symbols.js +3 -4
  39. package/lib/until.js +162 -160
  40. package/lib/webdriver.js +1014 -549
  41. package/net/index.js +30 -36
  42. package/net/portprober.js +30 -143
  43. package/opera.js +406 -0
  44. package/package.json +15 -7
  45. package/proxy.js +2 -2
  46. package/remote/index.js +189 -187
  47. package/safari.js +40 -49
  48. package/testing/index.js +504 -0
  49. package/lib/README +0 -5
  50. package/lib/actions.js +0 -609
package/io/exec.js CHANGED
@@ -15,10 +15,9 @@
15
15
  // specific language governing permissions and limitations
16
16
  // under the License.
17
17
 
18
- 'use strict';
19
-
20
- const childProcess = require('child_process');
18
+ 'use strict'
21
19
 
20
+ const childProcess = require('child_process')
22
21
 
23
22
  /**
24
23
  * Options for configuring an executed command.
@@ -31,7 +30,7 @@ class Options {
31
30
  * Command line arguments for the child process, if any.
32
31
  * @type (!Array<string>|undefined)
33
32
  */
34
- this.args;
33
+ this.args
35
34
 
36
35
  /**
37
36
  * Environment variables for the spawned process. If unspecified, the
@@ -39,7 +38,7 @@ class Options {
39
38
  *
40
39
  * @type {(!Object<string, string>|undefined)}
41
40
  */
42
- this.env;
41
+ this.env
43
42
 
44
43
  /**
45
44
  * IO conifguration for the spawned server child process. If unspecified,
@@ -49,11 +48,10 @@ class Options {
49
48
  * undefined)}
50
49
  * @see <https://nodejs.org/dist/latest-v8.x/docs/api/child_process.html#child_process_options_stdio>
51
50
  */
52
- this.stdio;
51
+ this.stdio
53
52
  }
54
53
  }
55
54
 
56
-
57
55
  /**
58
56
  * Describes a command's termination conditions.
59
57
  */
@@ -66,21 +64,20 @@ class Result {
66
64
  */
67
65
  constructor(code, signal) {
68
66
  /** @type {?number} */
69
- this.code = code;
67
+ this.code = code
70
68
 
71
69
  /** @type {?string} */
72
- this.signal = signal;
70
+ this.signal = signal
73
71
  }
74
72
 
75
73
  /** @override */
76
74
  toString() {
77
- return `Result(code=${this.code}, signal=${this.signal})`;
75
+ return `Result(code=${this.code}, signal=${this.signal})`
78
76
  }
79
77
  }
80
78
 
81
-
82
- const COMMAND_RESULT = /** !WeakMap<!Command, !Promise<!Result>> */new WeakMap;
83
- const KILL_HOOK = /** !WeakMap<!Command, function(string)> */new WeakMap;
79
+ const COMMAND_RESULT = /** !WeakMap<!Command, !Promise<!Result>> */ new WeakMap()
80
+ const KILL_HOOK = /** !WeakMap<!Command, function(string)> */ new WeakMap()
84
81
 
85
82
  /**
86
83
  * Represents a command running in a sub-process.
@@ -92,8 +89,8 @@ class Command {
92
89
  * is called.
93
90
  */
94
91
  constructor(result, onKill) {
95
- COMMAND_RESULT.set(this, result);
96
- KILL_HOOK.set(this, onKill);
92
+ COMMAND_RESULT.set(this, result)
93
+ KILL_HOOK.set(this, onKill)
97
94
  }
98
95
 
99
96
  /**
@@ -101,7 +98,7 @@ class Command {
101
98
  * command.
102
99
  */
103
100
  result() {
104
- return /** @type {!Promise<!Result>} */(COMMAND_RESULT.get(this));
101
+ return /** @type {!Promise<!Result>} */ (COMMAND_RESULT.get(this))
105
102
  }
106
103
 
107
104
  /**
@@ -109,14 +106,12 @@ class Command {
109
106
  * @param {string=} opt_signal The signal to send; defaults to `SIGTERM`.
110
107
  */
111
108
  kill(opt_signal) {
112
- KILL_HOOK.get(this)(opt_signal || 'SIGTERM');
109
+ KILL_HOOK.get(this)(opt_signal || 'SIGTERM')
113
110
  }
114
111
  }
115
112
 
116
-
117
113
  // PUBLIC API
118
114
 
119
-
120
115
  /**
121
116
  * Spawns a child process. The returned {@link Command} may be used to wait
122
117
  * for the process result or to send signals to the process.
@@ -126,42 +121,42 @@ class Command {
126
121
  * @return {!Command} The launched command.
127
122
  */
128
123
  module.exports = function exec(command, opt_options) {
129
- var options = opt_options || {};
124
+ const options = opt_options || {}
130
125
 
131
- var proc = childProcess.spawn(command, options.args || [], {
126
+ let proc = childProcess.spawn(command, options.args || [], {
132
127
  env: options.env || process.env,
133
- stdio: options.stdio || 'ignore'
134
- });
128
+ stdio: options.stdio || 'ignore',
129
+ })
135
130
 
136
131
  // This process should not wait on the spawned child, however, we do
137
132
  // want to ensure the child is killed when this process exits.
138
- proc.unref();
139
- process.once('exit', onProcessExit);
133
+ proc.unref()
134
+ process.once('exit', onProcessExit)
140
135
 
141
- let result = new Promise(resolve => {
136
+ const result = new Promise((resolve) => {
142
137
  proc.once('exit', (code, signal) => {
143
- proc = null;
144
- process.removeListener('exit', onProcessExit);
145
- resolve(new Result(code, signal));
146
- });
147
- });
148
- return new Command(result, killCommand);
138
+ proc = null
139
+ process.removeListener('exit', onProcessExit)
140
+ resolve(new Result(code, signal))
141
+ })
142
+ })
143
+ return new Command(result, killCommand)
149
144
 
150
145
  function onProcessExit() {
151
- killCommand('SIGTERM');
146
+ killCommand('SIGTERM')
152
147
  }
153
148
 
154
149
  function killCommand(signal) {
155
- process.removeListener('exit', onProcessExit);
150
+ process.removeListener('exit', onProcessExit)
156
151
  if (proc) {
157
- proc.kill(signal);
158
- proc = null;
152
+ proc.kill(signal)
153
+ proc = null
159
154
  }
160
155
  }
161
- };
156
+ }
162
157
 
163
158
  // Exported to improve generated API documentation.
164
159
 
165
- module.exports.Command = Command;
166
- module.exports.Options = Options;
167
- module.exports.Result = Result;
160
+ module.exports.Command = Command
161
+ module.exports.Options = Options
162
+ module.exports.Result = Result
package/io/index.js CHANGED
@@ -15,13 +15,12 @@
15
15
  // specific language governing permissions and limitations
16
16
  // under the License.
17
17
 
18
- 'use strict';
19
-
20
- var fs = require('fs'),
21
- path = require('path'),
22
- rimraf = require('rimraf'),
23
- tmp = require('tmp');
18
+ 'use strict'
24
19
 
20
+ const fs = require('fs')
21
+ const path = require('path')
22
+ const rimraf = require('rimraf')
23
+ const tmp = require('tmp')
25
24
 
26
25
  /**
27
26
  * @param {!Function} fn .
@@ -33,23 +32,19 @@ function checkedCall(fn) {
33
32
  try {
34
33
  fn((err, value) => {
35
34
  if (err) {
36
- reject(err);
35
+ reject(err)
37
36
  } else {
38
- resolve(value);
37
+ resolve(value)
39
38
  }
40
- });
39
+ })
41
40
  } catch (e) {
42
- reject(e);
41
+ reject(e)
43
42
  }
44
- });
43
+ })
45
44
  }
46
45
 
47
-
48
-
49
46
  // PUBLIC API
50
47
 
51
-
52
-
53
48
  /**
54
49
  * Recursively removes a directory and all of its contents. This is equivalent
55
50
  * to {@code rm -rf} on a POSIX system.
@@ -57,27 +52,26 @@ function checkedCall(fn) {
57
52
  * @return {!Promise} A promise to be resolved when the operation has
58
53
  * completed.
59
54
  */
60
- exports.rmDir = function(dirPath) {
61
- return new Promise(function(fulfill, reject) {
62
- var numAttempts = 0;
63
- attemptRm();
55
+ exports.rmDir = function (dirPath) {
56
+ return new Promise(function (fulfill, reject) {
57
+ var numAttempts = 0
58
+ attemptRm()
64
59
  function attemptRm() {
65
- numAttempts += 1;
66
- rimraf(dirPath, function(err) {
60
+ numAttempts += 1
61
+ rimraf(dirPath, function (err) {
67
62
  if (err) {
68
63
  if (err.code && err.code === 'ENOTEMPTY' && numAttempts < 2) {
69
- attemptRm();
70
- return;
64
+ attemptRm()
65
+ return
71
66
  }
72
- reject(err);
67
+ reject(err)
73
68
  } else {
74
- fulfill();
69
+ fulfill()
75
70
  }
76
- });
71
+ })
77
72
  }
78
- });
79
- };
80
-
73
+ })
74
+ }
81
75
 
82
76
  /**
83
77
  * Copies one file to another.
@@ -85,19 +79,18 @@ exports.rmDir = function(dirPath) {
85
79
  * @param {string} dst The destination file.
86
80
  * @return {!Promise<string>} A promise for the copied file's path.
87
81
  */
88
- exports.copy = function(src, dst) {
89
- return new Promise(function(fulfill, reject) {
90
- var rs = fs.createReadStream(src);
91
- rs.on('error', reject);
82
+ exports.copy = function (src, dst) {
83
+ return new Promise(function (fulfill, reject) {
84
+ var rs = fs.createReadStream(src)
85
+ rs.on('error', reject)
92
86
 
93
- var ws = fs.createWriteStream(dst);
94
- ws.on('error', reject);
95
- ws.on('close', () => fulfill(dst));
96
-
97
- rs.pipe(ws);
98
- });
99
- };
87
+ var ws = fs.createWriteStream(dst)
88
+ ws.on('error', reject)
89
+ ws.on('close', () => fulfill(dst))
100
90
 
91
+ rs.pipe(ws)
92
+ })
93
+ }
101
94
 
102
95
  /**
103
96
  * Recursively copies the contents of one directory to another.
@@ -109,63 +102,62 @@ exports.copy = function(src, dst) {
109
102
  * @return {!Promise<string>} A promise for the destination
110
103
  * directory's path once all files have been copied.
111
104
  */
112
- exports.copyDir = function(src, dst, opt_exclude) {
113
- var predicate = opt_exclude;
105
+ exports.copyDir = function (src, dst, opt_exclude) {
106
+ var predicate = opt_exclude
114
107
  if (opt_exclude && typeof opt_exclude !== 'function') {
115
- predicate = function(p) {
116
- return !opt_exclude.test(p);
117
- };
108
+ predicate = function (p) {
109
+ return !opt_exclude.test(p)
110
+ }
118
111
  }
119
112
 
120
113
  // TODO(jleyba): Make this function completely async.
121
114
  if (!fs.existsSync(dst)) {
122
- fs.mkdirSync(dst);
115
+ fs.mkdirSync(dst)
123
116
  }
124
117
 
125
- var files = fs.readdirSync(src);
126
- files = files.map(function(file) {
127
- return path.join(src, file);
128
- });
118
+ var files = fs.readdirSync(src)
119
+ files = files.map(function (file) {
120
+ return path.join(src, file)
121
+ })
129
122
 
130
123
  if (predicate) {
131
- files = files.filter(/** @type {function(string): boolean} */(predicate));
124
+ files = files.filter(/** @type {function(string): boolean} */ (predicate))
132
125
  }
133
126
 
134
- var results = [];
135
- files.forEach(function(file) {
136
- var stats = fs.statSync(file);
137
- var target = path.join(dst, path.basename(file));
127
+ var results = []
128
+ files.forEach(function (file) {
129
+ var stats = fs.statSync(file)
130
+ var target = path.join(dst, path.basename(file))
138
131
 
139
132
  if (stats.isDirectory()) {
140
133
  if (!fs.existsSync(target)) {
141
- fs.mkdirSync(target, stats.mode);
134
+ fs.mkdirSync(target, stats.mode)
142
135
  }
143
- results.push(exports.copyDir(file, target, predicate));
136
+ results.push(exports.copyDir(file, target, predicate))
144
137
  } else {
145
- results.push(exports.copy(file, target));
138
+ results.push(exports.copy(file, target))
146
139
  }
147
- });
148
-
149
- return Promise.all(results).then(() => dst);
150
- };
140
+ })
151
141
 
142
+ return Promise.all(results).then(() => dst)
143
+ }
152
144
 
153
145
  /**
154
146
  * Tests if a file path exists.
155
147
  * @param {string} aPath The path to test.
156
148
  * @return {!Promise<boolean>} A promise for whether the file exists.
157
149
  */
158
- exports.exists = function(aPath) {
159
- return new Promise(function(fulfill, reject) {
160
- let type = typeof aPath;
150
+ exports.exists = function (aPath) {
151
+ return new Promise(function (fulfill, reject) {
152
+ let type = typeof aPath
161
153
  if (type !== 'string') {
162
- reject(TypeError(`expected string path, but got ${type}`));
154
+ reject(TypeError(`expected string path, but got ${type}`))
163
155
  } else {
164
- fs.exists(aPath, fulfill);
156
+ // eslint-disable-next-line node/no-deprecated-api
157
+ fs.exists(aPath, fulfill)
165
158
  }
166
- });
167
- };
168
-
159
+ })
160
+ }
169
161
 
170
162
  /**
171
163
  * Calls `stat(2)`.
@@ -173,9 +165,8 @@ exports.exists = function(aPath) {
173
165
  * @return {!Promise<!fs.Stats>} A promise for the file stats.
174
166
  */
175
167
  exports.stat = function stat(aPath) {
176
- return checkedCall(callback => fs.stat(aPath, callback));
177
- };
178
-
168
+ return checkedCall((callback) => fs.stat(aPath, callback))
169
+ }
179
170
 
180
171
  /**
181
172
  * Deletes a name from the filesystem and possibly the file it refers to. Has
@@ -183,47 +174,44 @@ exports.stat = function stat(aPath) {
183
174
  * @param {string} aPath The path to remove.
184
175
  * @return {!Promise} A promise for when the file has been removed.
185
176
  */
186
- exports.unlink = function(aPath) {
187
- return new Promise(function(fulfill, reject) {
188
- fs.exists(aPath, function(exists) {
177
+ exports.unlink = function (aPath) {
178
+ return new Promise(function (fulfill, reject) {
179
+ // eslint-disable-next-line node/no-deprecated-api
180
+ fs.exists(aPath, function (exists) {
189
181
  if (exists) {
190
- fs.unlink(aPath, function(err) {
191
- err && reject(err) || fulfill();
192
- });
182
+ fs.unlink(aPath, function (err) {
183
+ ;(err && reject(err)) || fulfill()
184
+ })
193
185
  } else {
194
- fulfill();
186
+ fulfill()
195
187
  }
196
- });
197
- });
198
- };
199
-
188
+ })
189
+ })
190
+ }
200
191
 
201
192
  /**
202
193
  * @return {!Promise<string>} A promise for the path to a temporary directory.
203
194
  * @see https://www.npmjs.org/package/tmp
204
195
  */
205
- exports.tmpDir = function() {
206
- return checkedCall(callback => tmp.dir({ unsafeCleanup : true }, callback));
207
- };
208
-
196
+ exports.tmpDir = function () {
197
+ return checkedCall((callback) => tmp.dir({ unsafeCleanup: true }, callback))
198
+ }
209
199
 
210
200
  /**
211
201
  * @param {{postfix: string}=} opt_options Temporary file options.
212
202
  * @return {!Promise<string>} A promise for the path to a temporary file.
213
203
  * @see https://www.npmjs.org/package/tmp
214
204
  */
215
- exports.tmpFile = function(opt_options) {
216
- return checkedCall(callback => {
217
- // |tmp.file| checks arguments length to detect options rather than doing a
218
- // truthy check, so we must only pass options if there are some to pass.
219
- if (opt_options) {
220
- tmp.file(opt_options, callback);
221
- } else {
222
- tmp.file(callback);
223
- }
224
- });
225
- };
226
-
205
+ exports.tmpFile = function (opt_options) {
206
+ return checkedCall((callback) => {
207
+ /** check fixed in v > 0.2.1 if
208
+ * (typeof options === 'function') {
209
+ * return [{}, options];
210
+ * }
211
+ */
212
+ tmp.file(opt_options, callback)
213
+ })
214
+ }
227
215
 
228
216
  /**
229
217
  * Searches the {@code PATH} environment variable for the given file.
@@ -234,26 +222,25 @@ exports.tmpFile = function(opt_options) {
234
222
  * @return {?string} Path to the located file, or {@code null} if it could
235
223
  * not be found.
236
224
  */
237
- exports.findInPath = function(file, opt_checkCwd) {
238
- let dirs = [];
225
+ exports.findInPath = function (file, opt_checkCwd) {
226
+ const dirs = []
239
227
  if (opt_checkCwd) {
240
- dirs.push(process.cwd());
228
+ dirs.push(process.cwd())
241
229
  }
242
- dirs.push.apply(dirs, process.env['PATH'].split(path.delimiter));
230
+ dirs.push.apply(dirs, process.env['PATH'].split(path.delimiter))
243
231
 
244
- let foundInDir = dirs.find(dir => {
245
- let tmp = path.join(dir, file);
232
+ let foundInDir = dirs.find((dir) => {
233
+ let tmp = path.join(dir, file)
246
234
  try {
247
- let stats = fs.statSync(tmp);
248
- return stats.isFile() && !stats.isDirectory();
235
+ let stats = fs.statSync(tmp)
236
+ return stats.isFile() && !stats.isDirectory()
249
237
  } catch (ex) {
250
- return false;
238
+ return false
251
239
  }
252
- });
253
-
254
- return foundInDir ? path.join(foundInDir, file) : null;
255
- };
240
+ })
256
241
 
242
+ return foundInDir ? path.join(foundInDir, file) : null
243
+ }
257
244
 
258
245
  /**
259
246
  * Reads the contents of the given file.
@@ -262,10 +249,9 @@ exports.findInPath = function(file, opt_checkCwd) {
262
249
  * @return {!Promise<!Buffer>} A promise that will resolve with a buffer of the
263
250
  * file contents.
264
251
  */
265
- exports.read = function(aPath) {
266
- return checkedCall(callback => fs.readFile(aPath, callback));
267
- };
268
-
252
+ exports.read = function (aPath) {
253
+ return checkedCall((callback) => fs.readFile(aPath, callback))
254
+ }
269
255
 
270
256
  /**
271
257
  * Writes to a file.
@@ -275,10 +261,9 @@ exports.read = function(aPath) {
275
261
  * @return {!Promise} A promise that will resolve when the operation has
276
262
  * completed.
277
263
  */
278
- exports.write = function(aPath, data) {
279
- return checkedCall(callback => fs.writeFile(aPath, data, callback));
280
- };
281
-
264
+ exports.write = function (aPath, data) {
265
+ return checkedCall((callback) => fs.writeFile(aPath, data, callback))
266
+ }
282
267
 
283
268
  /**
284
269
  * Creates a directory.
@@ -287,18 +272,17 @@ exports.write = function(aPath, data) {
287
272
  * @return {!Promise<string>} A promise that will resolve with the path of the
288
273
  * created directory.
289
274
  */
290
- exports.mkdir = function(aPath) {
291
- return checkedCall(callback => {
292
- fs.mkdir(aPath, undefined, err => {
275
+ exports.mkdir = function (aPath) {
276
+ return checkedCall((callback) => {
277
+ fs.mkdir(aPath, undefined, (err) => {
293
278
  if (err && err.code !== 'EEXIST') {
294
- callback(err);
279
+ callback(err)
295
280
  } else {
296
- callback(null, aPath);
281
+ callback(null, aPath)
297
282
  }
298
- });
299
- });
300
- };
301
-
283
+ })
284
+ })
285
+ }
302
286
 
303
287
  /**
304
288
  * Recursively creates a directory and any ancestors that do not yet exist.
@@ -308,29 +292,31 @@ exports.mkdir = function(aPath) {
308
292
  * created directory.
309
293
  */
310
294
  exports.mkdirp = function mkdirp(dir) {
311
- return checkedCall(callback => {
312
- fs.mkdir(dir, undefined, err => {
295
+ return checkedCall((callback) => {
296
+ fs.mkdir(dir, undefined, (err) => {
313
297
  if (!err) {
314
- callback(null, dir);
315
- return;
298
+ callback(null, dir)
299
+ return
316
300
  }
317
301
 
318
302
  switch (err.code) {
319
303
  case 'EEXIST':
320
- callback(null, dir);
321
- return;
304
+ callback(null, dir)
305
+ return
322
306
  case 'ENOENT':
323
307
  return mkdirp(path.dirname(dir))
324
- .then(() => mkdirp(dir))
325
- .then(() => callback(null, dir), err => callback(err));
308
+ .then(() => mkdirp(dir))
309
+ .then(
310
+ () => callback(null, dir),
311
+ (err) => callback(err)
312
+ )
326
313
  default:
327
- callback(err);
328
- return;
314
+ callback(err)
315
+ return
329
316
  }
330
- });
331
- });
332
- };
333
-
317
+ })
318
+ })
319
+ }
334
320
 
335
321
  /**
336
322
  * Recursively walks a directory, returning a promise that will resolve with
@@ -341,19 +327,22 @@ exports.mkdirp = function mkdirp(dir) {
341
327
  * resolve with a list of entries seen. For each entry, the recorded path
342
328
  * will be relative to `rootPath`.
343
329
  */
344
- exports.walkDir = function(rootPath) {
345
- let seen = [];
330
+ exports.walkDir = function (rootPath) {
331
+ const seen = []
346
332
  return (function walk(dir) {
347
- return checkedCall(callback => fs.readdir(dir, callback))
348
- .then(files => Promise.all(files.map(file => {
349
- file = path.join(dir, file);
350
- return checkedCall(cb => fs.stat(file, cb)).then(stats => {
333
+ return checkedCall((callback) => fs.readdir(dir, callback)).then((files) =>
334
+ Promise.all(
335
+ files.map((file) => {
336
+ file = path.join(dir, file)
337
+ return checkedCall((cb) => fs.stat(file, cb)).then((stats) => {
351
338
  seen.push({
352
339
  path: path.relative(rootPath, file),
353
- dir: stats.isDirectory()
354
- });
355
- return stats.isDirectory() && walk(file);
356
- });
357
- })));
358
- })(rootPath).then(() => seen);
359
- };
340
+ dir: stats.isDirectory(),
341
+ })
342
+ return stats.isDirectory() && walk(file)
343
+ })
344
+ })
345
+ )
346
+ )
347
+ })(rootPath).then(() => seen)
348
+ }