selenium-webdriver 3.0.1 → 3.5.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/CHANGES.md +92 -0
- package/NOTICE +1 -1
- package/README.md +11 -14
- package/chrome.js +125 -36
- package/edge.js +3 -3
- package/example/async_await_test.js +68 -0
- package/example/chrome_headless.js +47 -0
- package/example/chrome_mobile_emulation.js +1 -1
- package/example/firefox_channels.js +73 -0
- package/example/google_search_test.js +1 -1
- package/firefox/binary.js +114 -57
- package/firefox/extension.js +118 -81
- package/firefox/index.js +67 -135
- package/firefox/profile.js +13 -49
- package/ie.js +2 -2
- package/index.js +6 -3
- package/io/index.js +59 -0
- package/io/zip.js +214 -0
- package/lib/README +2 -3
- package/lib/actions.js +4 -4
- package/lib/atoms/getAttribute.js +9 -11
- package/lib/atoms/is-displayed.js +102 -0
- package/lib/by.js +9 -1
- package/lib/capabilities.js +5 -5
- package/lib/command.js +2 -0
- package/lib/error.js +29 -4
- package/lib/events.js +1 -1
- package/lib/firefox/webdriver.json +2 -1
- package/lib/http.js +84 -69
- package/lib/input.js +1 -1
- package/lib/promise.js +205 -81
- package/lib/symbols.js +1 -1
- package/lib/test/data/click_tests/disabled_element.html +12 -0
- package/lib/test/data/firefox/webextension.xpi +0 -0
- package/lib/test/data/key_logger.html +34 -0
- package/lib/test/data/nestedElements.html +10 -1
- package/lib/test/data/single_text_input.html +12 -0
- package/lib/test/index.js +9 -35
- package/lib/until.js +1 -1
- package/lib/webdriver.js +130 -34
- package/net/portprober.js +1 -1
- package/opera.js +2 -2
- package/package.json +2 -2
- package/phantomjs.js +2 -2
- package/remote/index.js +17 -11
- package/safari.js +47 -8
- package/test/firefox/extension_test.js +41 -17
- package/test/firefox/firefox_test.js +70 -23
- package/test/firefox/profile_test.js +14 -59
- package/test/http/http_test.js +18 -0
- package/test/{io_test.js → io/io_test.js} +40 -1
- package/test/io/zip_test.js +128 -0
- package/test/lib/by_test.js +21 -0
- package/test/lib/error_test.js +20 -1
- package/test/lib/http_test.js +41 -2
- package/test/lib/promise_test.js +19 -0
- package/test/lib/until_test.js +28 -13
- package/test/lib/webdriver_test.js +107 -3
- package/test/page_loading_test.js +0 -6
- package/test/rect_test.js +60 -0
- package/test/remote_test.js +3 -3
- package/test/session_test.js +68 -23
- package/testing/index.js +16 -5
- package/lib/atoms/isDisplayed.js +0 -106
- package/lib/firefox/amd64/libnoblur64.so +0 -0
- package/lib/firefox/i386/libnoblur.so +0 -0
- package/lib/firefox/webdriver.xpi +0 -0
|
@@ -0,0 +1,128 @@
|
|
|
1
|
+
// Licensed to the Software Freedom Conservancy (SFC) under one
|
|
2
|
+
// or more contributor license agreements. See the NOTICE file
|
|
3
|
+
// distributed with this work for additional information
|
|
4
|
+
// regarding copyright ownership. The SFC licenses this file
|
|
5
|
+
// to you under the Apache License, Version 2.0 (the
|
|
6
|
+
// "License"); you may not use this file except in compliance
|
|
7
|
+
// with the License. You may obtain a copy of the License at
|
|
8
|
+
//
|
|
9
|
+
// http://www.apache.org/licenses/LICENSE-2.0
|
|
10
|
+
//
|
|
11
|
+
// Unless required by applicable law or agreed to in writing,
|
|
12
|
+
// software distributed under the License is distributed on an
|
|
13
|
+
// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
|
14
|
+
// KIND, either express or implied. See the License for the
|
|
15
|
+
// specific language governing permissions and limitations
|
|
16
|
+
// under the License.
|
|
17
|
+
|
|
18
|
+
'use strict';
|
|
19
|
+
|
|
20
|
+
const assert = require('assert');
|
|
21
|
+
const fs = require('fs');
|
|
22
|
+
const path = require('path');
|
|
23
|
+
|
|
24
|
+
const io = require('../../io');
|
|
25
|
+
const devmode = require('../../lib/devmode');
|
|
26
|
+
const zip = require('../../io/zip');
|
|
27
|
+
const {InvalidArgumentError} = require('../../lib/error');
|
|
28
|
+
|
|
29
|
+
|
|
30
|
+
const SAMPLE_XPI_PATH =
|
|
31
|
+
path.join(__dirname, '../../lib/test/data/firefox/sample.xpi');
|
|
32
|
+
|
|
33
|
+
describe('io/zip', function() {
|
|
34
|
+
describe('unzip', function() {
|
|
35
|
+
it('creates destination dir if necessary', function() {
|
|
36
|
+
return io.tmpDir()
|
|
37
|
+
.then(dir => zip.unzip(SAMPLE_XPI_PATH, dir))
|
|
38
|
+
.then(dir => {
|
|
39
|
+
assertExists(path.join(dir, 'chrome.manifest'));
|
|
40
|
+
assertExists(path.join(dir, 'content/overlay.js'));
|
|
41
|
+
assertExists(path.join(dir, 'content/overlay.xul'));
|
|
42
|
+
assertExists(path.join(dir, 'install.rdf'));
|
|
43
|
+
});
|
|
44
|
+
});
|
|
45
|
+
});
|
|
46
|
+
|
|
47
|
+
describe('Zip', function() {
|
|
48
|
+
let dir;
|
|
49
|
+
|
|
50
|
+
beforeEach(function() {
|
|
51
|
+
return io.tmpDir().then(d => dir = d);
|
|
52
|
+
});
|
|
53
|
+
|
|
54
|
+
it('can convert an archive to a buffer', function() {
|
|
55
|
+
let z = new zip.Zip;
|
|
56
|
+
return io.mkdirp(path.join(dir, 'a/b/c/d/e')).then(() => {
|
|
57
|
+
return Promise.all([
|
|
58
|
+
io.write(path.join(dir, 'foo'), 'a file'),
|
|
59
|
+
io.write(path.join(dir, 'a/b/c/carrot'), 'an orange carrot'),
|
|
60
|
+
io.write(path.join(dir, 'a/b/c/d/e/elephant'), 'e is for elephant')
|
|
61
|
+
]);
|
|
62
|
+
})
|
|
63
|
+
.then(() => z.addDir(dir))
|
|
64
|
+
.then(() => Promise.all([io.tmpDir(), z.toBuffer()]))
|
|
65
|
+
.then(([outDir, buf]) => {
|
|
66
|
+
let output = path.join(outDir, 'out.zip');
|
|
67
|
+
return io.write(output, buf)
|
|
68
|
+
.then(() => io.tmpDir())
|
|
69
|
+
.then(d => zip.unzip(output, d))
|
|
70
|
+
.then(d => {
|
|
71
|
+
assertContents(path.join(d, 'foo'), 'a file');
|
|
72
|
+
assertContents(path.join(d, 'a/b/c/carrot'), 'an orange carrot');
|
|
73
|
+
assertContents(
|
|
74
|
+
path.join(d, 'a/b/c/d/e/elephant'),
|
|
75
|
+
'e is for elephant');
|
|
76
|
+
});
|
|
77
|
+
});
|
|
78
|
+
});
|
|
79
|
+
|
|
80
|
+
describe('getFile', function() {
|
|
81
|
+
it('returns archive file contents as a buffer', function() {
|
|
82
|
+
let foo = path.join(dir, 'foo');
|
|
83
|
+
fs.writeFileSync(foo, 'hello, world!');
|
|
84
|
+
|
|
85
|
+
let z = new zip.Zip;
|
|
86
|
+
return z.addFile(foo).then(() => {
|
|
87
|
+
assert.ok(z.has('foo'));
|
|
88
|
+
return z.getFile('foo');
|
|
89
|
+
}).then(
|
|
90
|
+
buffer => assert.equal(buffer.toString('utf8'), 'hello, world!'));
|
|
91
|
+
});
|
|
92
|
+
|
|
93
|
+
it('returns an error if file is not in archive', function() {
|
|
94
|
+
let z = new zip.Zip;
|
|
95
|
+
assert.ok(!z.has('some-file'));
|
|
96
|
+
return z.getFile('some-file')
|
|
97
|
+
.then(() => assert.fail('should have failed'),
|
|
98
|
+
e => assert.strictEqual(e.constructor, InvalidArgumentError));
|
|
99
|
+
});
|
|
100
|
+
|
|
101
|
+
it(
|
|
102
|
+
'returns a rejected promise if the requested path is a directory',
|
|
103
|
+
function() {
|
|
104
|
+
let file = path.join(dir, 'aFile');
|
|
105
|
+
fs.writeFileSync(file, 'hello, world!');
|
|
106
|
+
|
|
107
|
+
let z = new zip.Zip;
|
|
108
|
+
return z.addDir(dir, 'foo')
|
|
109
|
+
.then(() => z.getFile('foo'))
|
|
110
|
+
.then(
|
|
111
|
+
() => assert.fail('should have failed'),
|
|
112
|
+
e => assert.strictEqual(
|
|
113
|
+
e.constructor, InvalidArgumentError))
|
|
114
|
+
.then(() => z.getFile('foo/aFile'))
|
|
115
|
+
.then(b => assert.equal(b.toString('utf8'), 'hello, world!'));
|
|
116
|
+
});
|
|
117
|
+
});
|
|
118
|
+
});
|
|
119
|
+
|
|
120
|
+
function assertExists(p) {
|
|
121
|
+
assert.ok(fs.existsSync(p), `expected ${p} to exist`);
|
|
122
|
+
}
|
|
123
|
+
|
|
124
|
+
function assertContents(p, c) {
|
|
125
|
+
assert.strictEqual(
|
|
126
|
+
fs.readFileSync(p, 'utf8'), c, `unexpected file contents for ${p}`);
|
|
127
|
+
}
|
|
128
|
+
});
|
package/test/lib/by_test.js
CHANGED
|
@@ -88,6 +88,27 @@ describe('by', function() {
|
|
|
88
88
|
});
|
|
89
89
|
|
|
90
90
|
describe('checkedLocator', function() {
|
|
91
|
+
it('accepts a By instance', function() {
|
|
92
|
+
let original = by.By.name('foo');
|
|
93
|
+
let locator = by.checkedLocator(original);
|
|
94
|
+
assert.strictEqual(locator, original);
|
|
95
|
+
});
|
|
96
|
+
|
|
97
|
+
it('accepts custom locator functions', function() {
|
|
98
|
+
let original = function() {};
|
|
99
|
+
let locator = by.checkedLocator(original);
|
|
100
|
+
assert.strictEqual(locator, original);
|
|
101
|
+
});
|
|
102
|
+
|
|
103
|
+
// See https://github.com/SeleniumHQ/selenium/issues/3056
|
|
104
|
+
it('accepts By-like objects', function() {
|
|
105
|
+
let fakeBy = {using: 'id', value: 'foo'};
|
|
106
|
+
let locator = by.checkedLocator(fakeBy);
|
|
107
|
+
assert.strictEqual(locator.constructor, by.By);
|
|
108
|
+
assert.equal(locator.using, 'id');
|
|
109
|
+
assert.equal(locator.value, 'foo');
|
|
110
|
+
});
|
|
111
|
+
|
|
91
112
|
it('accepts class name', function() {
|
|
92
113
|
let locator = by.checkedLocator({className: 'foo'});
|
|
93
114
|
assert.equal('css selector', locator.using);
|
package/test/lib/error_test.js
CHANGED
|
@@ -187,13 +187,32 @@ describe('error', function() {
|
|
|
187
187
|
test('unknown method', error.UnknownMethodError);
|
|
188
188
|
test('unsupported operation', error.UnsupportedOperationError);
|
|
189
189
|
|
|
190
|
+
it('leaves remoteStacktrace empty if not in encoding', function() {
|
|
191
|
+
assert.throws(
|
|
192
|
+
() => error.throwDecodedError({
|
|
193
|
+
error: 'session not created',
|
|
194
|
+
message: 'oops'
|
|
195
|
+
}),
|
|
196
|
+
(e) => {
|
|
197
|
+
assert.strictEqual(e.constructor, error.SessionNotCreatedError);
|
|
198
|
+
assert.strictEqual(e.message, 'oops');
|
|
199
|
+
assert.strictEqual(e.remoteStacktrace, '');
|
|
200
|
+
return true;
|
|
201
|
+
});
|
|
202
|
+
});
|
|
203
|
+
|
|
190
204
|
function test(status, expectedType) {
|
|
191
205
|
it(`"${status}" => ${expectedType.name}`, function() {
|
|
192
206
|
assert.throws(
|
|
193
|
-
() => error.throwDecodedError({
|
|
207
|
+
() => error.throwDecodedError({
|
|
208
|
+
error: status,
|
|
209
|
+
message: 'oops',
|
|
210
|
+
stacktrace: 'some-stacktrace'
|
|
211
|
+
}),
|
|
194
212
|
(e) => {
|
|
195
213
|
assert.strictEqual(e.constructor, expectedType);
|
|
196
214
|
assert.strictEqual(e.message, 'oops');
|
|
215
|
+
assert.strictEqual(e.remoteStacktrace, 'some-stacktrace');
|
|
197
216
|
return true;
|
|
198
217
|
});
|
|
199
218
|
});
|
package/test/lib/http_test.js
CHANGED
|
@@ -293,7 +293,14 @@ describe('http', function() {
|
|
|
293
293
|
});
|
|
294
294
|
|
|
295
295
|
it('auto-upgrades on W3C response', function() {
|
|
296
|
-
|
|
296
|
+
let rawResponse = {
|
|
297
|
+
value: {
|
|
298
|
+
sessionId: 's123',
|
|
299
|
+
value: {
|
|
300
|
+
name: 'Bob'
|
|
301
|
+
}
|
|
302
|
+
}
|
|
303
|
+
};
|
|
297
304
|
|
|
298
305
|
send.returns(Promise.resolve(
|
|
299
306
|
new http.Response(200, {}, JSON.stringify(rawResponse))));
|
|
@@ -325,6 +332,38 @@ describe('http', function() {
|
|
|
325
332
|
assert.ok(executor.w3c, 'should never downgrade');
|
|
326
333
|
});
|
|
327
334
|
});
|
|
335
|
+
|
|
336
|
+
it('handles legacy new session failures', function() {
|
|
337
|
+
let rawResponse = {
|
|
338
|
+
status: error.ErrorCode.NO_SUCH_ELEMENT,
|
|
339
|
+
value: {message: 'hi'}
|
|
340
|
+
};
|
|
341
|
+
|
|
342
|
+
send.returns(Promise.resolve(
|
|
343
|
+
new http.Response(500, {}, JSON.stringify(rawResponse))));
|
|
344
|
+
|
|
345
|
+
return executor.execute(command)
|
|
346
|
+
.then(() => assert.fail('should have failed'),
|
|
347
|
+
e => {
|
|
348
|
+
assert.ok(e instanceof error.NoSuchElementError);
|
|
349
|
+
assert.equal(e.message, 'hi');
|
|
350
|
+
});
|
|
351
|
+
});
|
|
352
|
+
|
|
353
|
+
it('handles w3c new session failures', function() {
|
|
354
|
+
let rawResponse =
|
|
355
|
+
{value: {error: 'no such element', message: 'oops'}};
|
|
356
|
+
|
|
357
|
+
send.returns(Promise.resolve(
|
|
358
|
+
new http.Response(500, {}, JSON.stringify(rawResponse))));
|
|
359
|
+
|
|
360
|
+
return executor.execute(command)
|
|
361
|
+
.then(() => assert.fail('should have failed'),
|
|
362
|
+
e => {
|
|
363
|
+
assert.ok(e instanceof error.NoSuchElementError);
|
|
364
|
+
assert.equal(e.message, 'oops');
|
|
365
|
+
});
|
|
366
|
+
});
|
|
328
367
|
});
|
|
329
368
|
|
|
330
369
|
describe('extracts Session from DESCRIBE_SESSION response', function() {
|
|
@@ -398,7 +437,7 @@ describe('http', function() {
|
|
|
398
437
|
});
|
|
399
438
|
|
|
400
439
|
it('does not auto-upgrade on W3C response', function() {
|
|
401
|
-
var rawResponse = {sessionId: 's123', value: {name: 'Bob'}};
|
|
440
|
+
var rawResponse = {value: {sessionId: 's123', value: {name: 'Bob'}}};
|
|
402
441
|
|
|
403
442
|
send.returns(Promise.resolve(
|
|
404
443
|
new http.Response(200, {}, JSON.stringify(rawResponse))));
|
package/test/lib/promise_test.js
CHANGED
|
@@ -301,6 +301,25 @@ describe('promise', function() {
|
|
|
301
301
|
});
|
|
302
302
|
|
|
303
303
|
promiseManagerSuite(() => {
|
|
304
|
+
describe('fulfilled', function() {
|
|
305
|
+
it('returns input value if it is already a valid promise', function() {
|
|
306
|
+
let p = promise.createPromise(function() {});
|
|
307
|
+
let r = promise.fulfilled(p);
|
|
308
|
+
assert.strictEqual(p, r);
|
|
309
|
+
});
|
|
310
|
+
|
|
311
|
+
it('creates a new promise fulfilled with input', function() {
|
|
312
|
+
return promise.fulfilled(1234).then(v => assert.equal(1234, v));
|
|
313
|
+
});
|
|
314
|
+
|
|
315
|
+
it('can convert thenables to valid promise', function() {
|
|
316
|
+
let thenable = {then: function(cb) {cb(1234)}};
|
|
317
|
+
let p = promise.fulfilled(thenable);
|
|
318
|
+
assert.notStrictEqual(thenable, p);
|
|
319
|
+
return p.then(v => assert.equal(1234, v));
|
|
320
|
+
});
|
|
321
|
+
});
|
|
322
|
+
|
|
304
323
|
describe('when', function() {
|
|
305
324
|
it('ReturnsAResolvedPromiseIfGivenANonPromiseValue', function() {
|
|
306
325
|
var ret = promise.when('abc');
|
package/test/lib/until_test.js
CHANGED
|
@@ -70,39 +70,54 @@ describe('until', function() {
|
|
|
70
70
|
.then(fail, (e2) => assert.strictEqual(e2, e));
|
|
71
71
|
});
|
|
72
72
|
|
|
73
|
+
const ELEMENT_ID = 'some-element-id';
|
|
74
|
+
const ELEMENT_INDEX = 1234;
|
|
75
|
+
|
|
76
|
+
function onSwitchFrame(expectedId) {
|
|
77
|
+
if (typeof expectedId === 'string') {
|
|
78
|
+
expectedId = WebElement.buildId(expectedId);
|
|
79
|
+
} else {
|
|
80
|
+
assert.equal(typeof expectedId, 'number', 'must be string or number');
|
|
81
|
+
}
|
|
82
|
+
return cmd => {
|
|
83
|
+
assert.deepEqual(
|
|
84
|
+
cmd.getParameter('id'), expectedId, 'frame ID not specified');
|
|
85
|
+
return true;
|
|
86
|
+
};
|
|
87
|
+
}
|
|
88
|
+
|
|
73
89
|
it('byIndex', function() {
|
|
74
|
-
executor.on(CommandName.SWITCH_TO_FRAME, ()
|
|
75
|
-
return driver.wait(until.ableToSwitchToFrame(
|
|
90
|
+
executor.on(CommandName.SWITCH_TO_FRAME, onSwitchFrame(ELEMENT_INDEX));
|
|
91
|
+
return driver.wait(until.ableToSwitchToFrame(ELEMENT_INDEX), 100);
|
|
76
92
|
});
|
|
77
93
|
|
|
78
94
|
it('byWebElement', function() {
|
|
79
|
-
executor.on(CommandName.SWITCH_TO_FRAME, ()
|
|
80
|
-
|
|
95
|
+
executor.on(CommandName.SWITCH_TO_FRAME, onSwitchFrame(ELEMENT_ID));
|
|
96
|
+
|
|
97
|
+
var el = new webdriver.WebElement(driver, ELEMENT_ID);
|
|
81
98
|
return driver.wait(until.ableToSwitchToFrame(el), 100);
|
|
82
99
|
});
|
|
83
100
|
|
|
84
101
|
it('byWebElementPromise', function() {
|
|
85
|
-
executor.on(CommandName.SWITCH_TO_FRAME, ()
|
|
102
|
+
executor.on(CommandName.SWITCH_TO_FRAME, onSwitchFrame(ELEMENT_ID));
|
|
86
103
|
var el = new webdriver.WebElementPromise(driver,
|
|
87
|
-
Promise.resolve(new webdriver.WebElement(driver,
|
|
104
|
+
Promise.resolve(new webdriver.WebElement(driver, ELEMENT_ID)));
|
|
88
105
|
return driver.wait(until.ableToSwitchToFrame(el), 100);
|
|
89
106
|
});
|
|
90
107
|
|
|
91
108
|
it('byLocator', function() {
|
|
92
|
-
executor.on(CommandName.FIND_ELEMENTS, () => [WebElement.buildId(
|
|
93
|
-
executor.on(CommandName.SWITCH_TO_FRAME, ()
|
|
109
|
+
executor.on(CommandName.FIND_ELEMENTS, () => [WebElement.buildId(ELEMENT_ID)]);
|
|
110
|
+
executor.on(CommandName.SWITCH_TO_FRAME, onSwitchFrame(ELEMENT_ID));
|
|
94
111
|
return driver.wait(until.ableToSwitchToFrame(By.id('foo')), 100);
|
|
95
112
|
});
|
|
96
113
|
|
|
97
114
|
it('byLocator_elementNotInitiallyFound', function() {
|
|
98
|
-
|
|
115
|
+
let foundResponses = [[], [], [WebElement.buildId(ELEMENT_ID)]];
|
|
99
116
|
executor.on(CommandName.FIND_ELEMENTS, () => foundResponses.shift());
|
|
100
|
-
executor.on(CommandName.SWITCH_TO_FRAME, ()
|
|
117
|
+
executor.on(CommandName.SWITCH_TO_FRAME, onSwitchFrame(ELEMENT_ID));
|
|
101
118
|
|
|
102
119
|
return driver.wait(until.ableToSwitchToFrame(By.id('foo')), 2000)
|
|
103
|
-
.then(
|
|
104
|
-
assert.equal(foundResponses.length, 0);
|
|
105
|
-
});
|
|
120
|
+
.then(() => assert.deepEqual(foundResponses, []));
|
|
106
121
|
});
|
|
107
122
|
|
|
108
123
|
it('timesOutIfNeverAbletoSwitchFrames', function() {
|
|
@@ -403,7 +403,7 @@ describe('WebDriver', function() {
|
|
|
403
403
|
|
|
404
404
|
var driver =
|
|
405
405
|
WebDriver.createSession(executor, {'browserName': 'firefox'},
|
|
406
|
-
null,
|
|
406
|
+
null, () => called = true);
|
|
407
407
|
return driver.getSession().then(fail, err => {
|
|
408
408
|
assert.ok(called);
|
|
409
409
|
assertIsStubError(err);
|
|
@@ -464,8 +464,7 @@ describe('WebDriver', function() {
|
|
|
464
464
|
.end();
|
|
465
465
|
|
|
466
466
|
WebDriver.createSession(
|
|
467
|
-
executor, {'browserName': 'firefox'}, null,
|
|
468
|
-
() => {throw e});
|
|
467
|
+
executor, {'browserName': 'firefox'}, null, () => {throw e});
|
|
469
468
|
return waitForAbort().then(err => assert.strictEqual(err, e));
|
|
470
469
|
});
|
|
471
470
|
});
|
|
@@ -1446,6 +1445,7 @@ describe('WebDriver', function() {
|
|
|
1446
1445
|
let executor = new FakeExecutor().
|
|
1447
1446
|
expect(CName.SEND_KEYS_TO_ELEMENT,
|
|
1448
1447
|
{'id': WebElement.buildId('one'),
|
|
1448
|
+
'text': '12abc3',
|
|
1449
1449
|
'value':'12abc3'.split('')}).
|
|
1450
1450
|
andReturnSuccess().
|
|
1451
1451
|
end();
|
|
@@ -1463,6 +1463,7 @@ describe('WebDriver', function() {
|
|
|
1463
1463
|
andReturnSuccess(WebElement.buildId('one')).
|
|
1464
1464
|
expect(CName.SEND_KEYS_TO_ELEMENT,
|
|
1465
1465
|
{'id':WebElement.buildId('one'),
|
|
1466
|
+
'text': 'abc123def',
|
|
1466
1467
|
'value':'abc123def'.split('')}).
|
|
1467
1468
|
andReturnSuccess().
|
|
1468
1469
|
end();
|
|
@@ -1482,6 +1483,7 @@ describe('WebDriver', function() {
|
|
|
1482
1483
|
andReturnSuccess(WebElement.buildId('one')).
|
|
1483
1484
|
expect(CName.SEND_KEYS_TO_ELEMENT,
|
|
1484
1485
|
{'id': WebElement.buildId('one'),
|
|
1486
|
+
'text': 'modified/path',
|
|
1485
1487
|
'value':'modified/path'.split('')}).
|
|
1486
1488
|
andReturnSuccess().
|
|
1487
1489
|
end();
|
|
@@ -1952,6 +1954,108 @@ describe('WebDriver', function() {
|
|
|
1952
1954
|
});
|
|
1953
1955
|
});
|
|
1954
1956
|
|
|
1957
|
+
describe('manage()', function() {
|
|
1958
|
+
describe('setTimeouts()', function() {
|
|
1959
|
+
describe('throws if no timeouts are specified', function() {
|
|
1960
|
+
let driver;
|
|
1961
|
+
before(() => driver = new FakeExecutor().createDriver());
|
|
1962
|
+
|
|
1963
|
+
it('; no arguments', function() {
|
|
1964
|
+
assert.throws(() => driver.manage().setTimeouts(), TypeError);
|
|
1965
|
+
});
|
|
1966
|
+
|
|
1967
|
+
it('; ignores unrecognized timeout keys', function() {
|
|
1968
|
+
assert.throws(
|
|
1969
|
+
() => driver.manage().setTimeouts({foo: 123}), TypeError);
|
|
1970
|
+
});
|
|
1971
|
+
|
|
1972
|
+
it('; ignores positional arguments', function() {
|
|
1973
|
+
assert.throws(
|
|
1974
|
+
() => driver.manage().setTimeouts(1234, 56), TypeError);
|
|
1975
|
+
});
|
|
1976
|
+
});
|
|
1977
|
+
|
|
1978
|
+
describe('throws timeout is not a number, null, or undefined', () => {
|
|
1979
|
+
let driver;
|
|
1980
|
+
before(() => driver = new FakeExecutor().createDriver());
|
|
1981
|
+
|
|
1982
|
+
function checkError(e) {
|
|
1983
|
+
return e instanceof TypeError
|
|
1984
|
+
&& /expected "(script|pageLoad|implicit)" to be a number/.test(
|
|
1985
|
+
e.message);
|
|
1986
|
+
}
|
|
1987
|
+
|
|
1988
|
+
it('script', function() {
|
|
1989
|
+
assert.throws(
|
|
1990
|
+
() => driver.manage().setTimeouts({script: 'abc'}),
|
|
1991
|
+
checkError);
|
|
1992
|
+
});
|
|
1993
|
+
|
|
1994
|
+
it('pageLoad', function() {
|
|
1995
|
+
assert.throws(
|
|
1996
|
+
() => driver.manage().setTimeouts({pageLoad: 'abc'}),
|
|
1997
|
+
checkError);
|
|
1998
|
+
});
|
|
1999
|
+
|
|
2000
|
+
it('implicit', function() {
|
|
2001
|
+
assert.throws(
|
|
2002
|
+
() => driver.manage().setTimeouts({implicit: 'abc'}),
|
|
2003
|
+
checkError);
|
|
2004
|
+
});
|
|
2005
|
+
});
|
|
2006
|
+
|
|
2007
|
+
it('can set multiple timeouts', function() {
|
|
2008
|
+
let executor = new FakeExecutor()
|
|
2009
|
+
.expect(CName.SET_TIMEOUT, {script:1, pageLoad: 2, implicit: 3})
|
|
2010
|
+
.andReturnSuccess()
|
|
2011
|
+
.end();
|
|
2012
|
+
let driver = executor.createDriver();
|
|
2013
|
+
return driver.manage()
|
|
2014
|
+
.setTimeouts({script: 1, pageLoad: 2, implicit: 3});
|
|
2015
|
+
});
|
|
2016
|
+
|
|
2017
|
+
it('falls back to legacy wire format if W3C version fails', () => {
|
|
2018
|
+
let executor = new FakeExecutor()
|
|
2019
|
+
.expect(CName.SET_TIMEOUT, {implicit: 3})
|
|
2020
|
+
.andReturnError(Error('oops'))
|
|
2021
|
+
.expect(CName.SET_TIMEOUT, {type: 'implicit', ms: 3})
|
|
2022
|
+
.andReturnSuccess()
|
|
2023
|
+
.end();
|
|
2024
|
+
let driver = executor.createDriver();
|
|
2025
|
+
return driver.manage().setTimeouts({implicit: 3});
|
|
2026
|
+
});
|
|
2027
|
+
|
|
2028
|
+
describe('deprecated API calls setTimeouts()', function() {
|
|
2029
|
+
it('implicitlyWait()', function() {
|
|
2030
|
+
let executor = new FakeExecutor()
|
|
2031
|
+
.expect(CName.SET_TIMEOUT, {implicit: 3})
|
|
2032
|
+
.andReturnSuccess()
|
|
2033
|
+
.end();
|
|
2034
|
+
let driver = executor.createDriver();
|
|
2035
|
+
return driver.manage().timeouts().implicitlyWait(3);
|
|
2036
|
+
});
|
|
2037
|
+
|
|
2038
|
+
it('setScriptTimeout()', function() {
|
|
2039
|
+
let executor = new FakeExecutor()
|
|
2040
|
+
.expect(CName.SET_TIMEOUT, {script: 3})
|
|
2041
|
+
.andReturnSuccess()
|
|
2042
|
+
.end();
|
|
2043
|
+
let driver = executor.createDriver();
|
|
2044
|
+
return driver.manage().timeouts().setScriptTimeout(3);
|
|
2045
|
+
});
|
|
2046
|
+
|
|
2047
|
+
it('pageLoadTimeout()', function() {
|
|
2048
|
+
let executor = new FakeExecutor()
|
|
2049
|
+
.expect(CName.SET_TIMEOUT, {pageLoad: 3})
|
|
2050
|
+
.andReturnSuccess()
|
|
2051
|
+
.end();
|
|
2052
|
+
let driver = executor.createDriver();
|
|
2053
|
+
return driver.manage().timeouts().pageLoadTimeout(3);
|
|
2054
|
+
});
|
|
2055
|
+
});
|
|
2056
|
+
});
|
|
2057
|
+
});
|
|
2058
|
+
|
|
1955
2059
|
describe('generator support', function() {
|
|
1956
2060
|
var driver;
|
|
1957
2061
|
|
|
@@ -57,12 +57,6 @@ test.suite(function(env) {
|
|
|
57
57
|
return assert(driver.getTitle()).equalTo('We Arrive Here');
|
|
58
58
|
});
|
|
59
59
|
|
|
60
|
-
test.ignore(browsers(Browser.SAFARI)).
|
|
61
|
-
it('should follow meta redirects', function*() {
|
|
62
|
-
yield driver.get(Pages.metaRedirectPage);
|
|
63
|
-
return assert(driver.getTitle()).equalTo('We Arrive Here');
|
|
64
|
-
});
|
|
65
|
-
|
|
66
60
|
// Skip Firefox; see https://bugzilla.mozilla.org/show_bug.cgi?id=1280300
|
|
67
61
|
test.ignore(browsers(Browser.FIREFOX)).
|
|
68
62
|
it('should be able to get a fragment on the current page', function*() {
|
|
@@ -0,0 +1,60 @@
|
|
|
1
|
+
// Licensed to the Software Freedom Conservancy (SFC) under one
|
|
2
|
+
// or more contributor license agreements. See the NOTICE file
|
|
3
|
+
// distributed with this work for additional information
|
|
4
|
+
// regarding copyright ownership. The SFC licenses this file
|
|
5
|
+
// to you under the Apache License, Version 2.0 (the
|
|
6
|
+
// "License"); you may not use this file except in compliance
|
|
7
|
+
// with the License. You may obtain a copy of the License at
|
|
8
|
+
//
|
|
9
|
+
// http://www.apache.org/licenses/LICENSE-2.0
|
|
10
|
+
//
|
|
11
|
+
// Unless required by applicable law or agreed to in writing,
|
|
12
|
+
// software distributed under the License is distributed on an
|
|
13
|
+
// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
|
14
|
+
// KIND, either express or implied. See the License for the
|
|
15
|
+
// specific language governing permissions and limitations
|
|
16
|
+
// under the License.
|
|
17
|
+
|
|
18
|
+
'use strict';
|
|
19
|
+
|
|
20
|
+
const assert = require('assert');
|
|
21
|
+
|
|
22
|
+
const {By} = require('..');
|
|
23
|
+
const test = require('../lib/test');
|
|
24
|
+
|
|
25
|
+
test.suite(function(env) {
|
|
26
|
+
describe('rect commands', function() {
|
|
27
|
+
let driver;
|
|
28
|
+
let el;
|
|
29
|
+
|
|
30
|
+
test.before(function*() {
|
|
31
|
+
driver = yield env.builder().build();
|
|
32
|
+
yield driver.get(
|
|
33
|
+
'data:text/html,<!DOCTYPE html><style>'
|
|
34
|
+
+ '*{padding:0; margin:0}'
|
|
35
|
+
+ 'div{position: absolute; top: 50px; left: 50px;'
|
|
36
|
+
+ 'height: 50px;width:50px;background: green;}'
|
|
37
|
+
+ '</style><div>Hello</div>');
|
|
38
|
+
el = yield driver.findElement(By.css('div'));
|
|
39
|
+
});
|
|
40
|
+
|
|
41
|
+
after(function() {
|
|
42
|
+
if (driver) {
|
|
43
|
+
return driver.quit();
|
|
44
|
+
}
|
|
45
|
+
});
|
|
46
|
+
|
|
47
|
+
test.it('WebElement.getLocation()', function*() {
|
|
48
|
+
let location = yield el.getLocation();
|
|
49
|
+
assert.equal(location.x, 50);
|
|
50
|
+
assert.equal(location.y, 50);
|
|
51
|
+
});
|
|
52
|
+
|
|
53
|
+
test.it('WebElement.getSize()', function*() {
|
|
54
|
+
let size = yield el.getSize();
|
|
55
|
+
assert.equal(size.width, 50);
|
|
56
|
+
assert.equal(size.height, 50);
|
|
57
|
+
});
|
|
58
|
+
|
|
59
|
+
});
|
|
60
|
+
});
|
package/test/remote_test.js
CHANGED
|
@@ -83,7 +83,7 @@ describe('FileDetector', function() {
|
|
|
83
83
|
}
|
|
84
84
|
|
|
85
85
|
it('returns the original path if the file does not exist', function() {
|
|
86
|
-
return io.tmpDir(dir => {
|
|
86
|
+
return io.tmpDir().then(dir => {
|
|
87
87
|
let theFile = path.join(dir, 'not-there');
|
|
88
88
|
return (new remote.FileDetector)
|
|
89
89
|
.handleFile(new ExplodingDriver, theFile)
|
|
@@ -92,7 +92,7 @@ describe('FileDetector', function() {
|
|
|
92
92
|
});
|
|
93
93
|
|
|
94
94
|
it('returns the original path if it is a directory', function() {
|
|
95
|
-
return io.tmpDir(dir => {
|
|
95
|
+
return io.tmpDir().then(dir => {
|
|
96
96
|
return (new remote.FileDetector)
|
|
97
97
|
.handleFile(new ExplodingDriver, dir)
|
|
98
98
|
.then(f => assert.equal(f, dir));
|
|
@@ -100,7 +100,7 @@ describe('FileDetector', function() {
|
|
|
100
100
|
});
|
|
101
101
|
|
|
102
102
|
it('attempts to upload valid files', function() {
|
|
103
|
-
return io.tmpFile(theFile => {
|
|
103
|
+
return io.tmpFile().then(theFile => {
|
|
104
104
|
return (new remote.FileDetector)
|
|
105
105
|
.handleFile(
|
|
106
106
|
new (class FakeDriver {
|