poltergeist 1.13.0 → 1.14.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/README.md +12 -4
- data/lib/capybara/poltergeist/browser.rb +4 -4
- data/lib/capybara/poltergeist/client/agent.coffee +21 -1
- data/lib/capybara/poltergeist/client/browser.coffee +10 -6
- data/lib/capybara/poltergeist/client/compiled/agent.js +42 -2
- data/lib/capybara/poltergeist/client/compiled/browser.js +14 -6
- data/lib/capybara/poltergeist/client/compiled/web_page.js +108 -42
- data/lib/capybara/poltergeist/client/web_page.coffee +77 -48
- data/lib/capybara/poltergeist/driver.rb +19 -7
- data/lib/capybara/poltergeist/node.rb +1 -1
- data/lib/capybara/poltergeist/version.rb +1 -1
- metadata +2 -2
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: dc319cb98595a9cedd482bffd3756720c4ed24b4
|
4
|
+
data.tar.gz: a79f76c1344f910aac1aa9f38a0cb6fd40dfa075
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: f0c6a5e24513e4c34e755c2a4cee6191580648d98bea2ba26877b8d4267dafb75a6aedd0d61d49b767b02dd825cdbcbbd1a59d05a85fc35a3230aaf92eccadaa
|
7
|
+
data.tar.gz: c634a8ee97d076785499dd803553174d1ed5932cede4f80bdc23dc11a364cec694d024a8e51bf10cf0155948ddc9a38515d5f43fbc7d3c1590ace315a88d3169
|
data/README.md
CHANGED
@@ -9,7 +9,7 @@ provided by [PhantomJS](http://phantomjs.org/).
|
|
9
9
|
**If you're viewing this at https://github.com/teampoltergeist/poltergeist,
|
10
10
|
you're reading the documentation for the master branch.
|
11
11
|
[View documentation for the latest release
|
12
|
-
(1.
|
12
|
+
(1.13.0).](https://github.com/teampoltergeist/poltergeist/tree/v1.13.0)**
|
13
13
|
|
14
14
|
## Getting help ##
|
15
15
|
|
@@ -88,7 +88,8 @@ was 1.0.2, so you should use that if you still need Ruby 1.8 support.
|
|
88
88
|
There are no special steps to take. You don't need Xvfb or any running X
|
89
89
|
server at all.
|
90
90
|
|
91
|
-
[Travis CI](https://travis-ci.org/)
|
91
|
+
[Travis CI](https://travis-ci.org/), [CircleCI](https://circleci.com/)
|
92
|
+
and [Codeship](https://codeship.com/) has PhantomJS pre-installed.
|
92
93
|
|
93
94
|
Depending on your tests, one thing that you may need is some fonts. If
|
94
95
|
you're getting errors on a CI that don't occur during development then
|
@@ -192,8 +193,9 @@ visit(login_path)
|
|
192
193
|
page.driver.headers # => { "User-Agent" => "Poltergeist" }
|
193
194
|
```
|
194
195
|
|
195
|
-
This way your temporary headers will be sent only for the initial request,
|
196
|
-
subsequent request will only contain your permanent headers.
|
196
|
+
This way your temporary headers will be sent only for the initial request, and related 30x redirects. All
|
197
|
+
subsequent request will only contain your permanent headers. If the temporary
|
198
|
+
headers should not be sent on related 30x redirects, specify `permanent: :no_redirect`.
|
197
199
|
|
198
200
|
### Inspecting network traffic ###
|
199
201
|
|
@@ -201,6 +203,12 @@ You can inspect the network traffic (i.e. what resources have been
|
|
201
203
|
loaded) on the current page by calling `page.driver.network_traffic`.
|
202
204
|
This returns an array of request objects. A request object has a
|
203
205
|
`response_parts` method containing data about the response chunks.
|
206
|
+
|
207
|
+
You can inspect requests that were blocked by a whitelist or blacklist
|
208
|
+
by calling `page.driver.network_traffic(:blocked)`. This returns an array of
|
209
|
+
request objects. The `response_parts` portion of these requests will always
|
210
|
+
be empty.
|
211
|
+
|
204
212
|
Please note that network traffic is not cleared when you visit new page.
|
205
213
|
You can manually clear the network traffic by calling `page.driver.clear_network_traffic`
|
206
214
|
or `page.driver.reset`
|
@@ -260,8 +260,8 @@ module Capybara::Poltergeist
|
|
260
260
|
command 'path', page_id, id
|
261
261
|
end
|
262
262
|
|
263
|
-
def network_traffic
|
264
|
-
command('network_traffic').
|
263
|
+
def network_traffic(type = nil)
|
264
|
+
command('network_traffic', type).map do |event|
|
265
265
|
NetworkTraffic::Request.new(
|
266
266
|
event['request'],
|
267
267
|
event['responseParts'].map { |response| NetworkTraffic::Response.new(response) },
|
@@ -297,8 +297,8 @@ module Capybara::Poltergeist
|
|
297
297
|
command 'add_headers', headers
|
298
298
|
end
|
299
299
|
|
300
|
-
def add_header(header,
|
301
|
-
command 'add_header', header,
|
300
|
+
def add_header(header, options={})
|
301
|
+
command 'add_header', header, options
|
302
302
|
end
|
303
303
|
|
304
304
|
def response_headers
|
@@ -57,6 +57,26 @@ class PoltergeistAgent
|
|
57
57
|
clearLocalStorage: ->
|
58
58
|
localStorage?.clear()
|
59
59
|
|
60
|
+
wrapResults: (result, page_id)->
|
61
|
+
@_visitedObjects ||= [];
|
62
|
+
switch
|
63
|
+
when result in @_visitedObjects
|
64
|
+
'(cyclic structure)'
|
65
|
+
when Array.isArray(result) || (result instanceof NodeList)
|
66
|
+
@wrapResults(res, page_id) for res in result
|
67
|
+
when result && result.nodeType == 1 && result['tagName']
|
68
|
+
{'ELEMENT': { id: @register(result), page_id: page_id } };
|
69
|
+
when not result?
|
70
|
+
undefined
|
71
|
+
when typeof result == 'object'
|
72
|
+
@_visitedObjects.push(result);
|
73
|
+
obj = {}
|
74
|
+
obj[key] = @wrapResults(val, page_id) for own key, val of result
|
75
|
+
@_visitedObjects.pop();
|
76
|
+
obj
|
77
|
+
else
|
78
|
+
result
|
79
|
+
|
60
80
|
class PoltergeistAgent.ObsoleteNode
|
61
81
|
toString: -> "PoltergeistAgent.ObsoleteNode"
|
62
82
|
|
@@ -89,7 +109,7 @@ class PoltergeistAgent.Node
|
|
89
109
|
|
90
110
|
isObsolete: ->
|
91
111
|
obsolete = (element) =>
|
92
|
-
if (parent = element
|
112
|
+
if (parent = element?.parentNode)?
|
93
113
|
if parent == document
|
94
114
|
return false
|
95
115
|
else
|
@@ -75,8 +75,10 @@ class Poltergeist.Browser
|
|
75
75
|
return
|
76
76
|
|
77
77
|
add_extension: (extension) ->
|
78
|
-
@currentPage.injectExtension extension
|
79
|
-
|
78
|
+
if @currentPage.injectExtension extension
|
79
|
+
@current_command.sendResponse 'success'
|
80
|
+
else
|
81
|
+
@current_command.sendError(new Poltergeist.BrowserError("Unable to load extension: #{extension}"))
|
80
82
|
|
81
83
|
node: (page_id, id) ->
|
82
84
|
if @currentPage.id == page_id
|
@@ -417,8 +419,8 @@ class Poltergeist.Browser
|
|
417
419
|
@currentPage.setViewportSize(width: width, height: height)
|
418
420
|
@current_command.sendResponse(true)
|
419
421
|
|
420
|
-
network_traffic: ->
|
421
|
-
@current_command.sendResponse(@currentPage.networkTraffic())
|
422
|
+
network_traffic: (type) ->
|
423
|
+
@current_command.sendResponse(@currentPage.networkTraffic(type))
|
422
424
|
|
423
425
|
clear_network_traffic: ->
|
424
426
|
@currentPage.clearNetworkTraffic()
|
@@ -443,8 +445,10 @@ class Poltergeist.Browser
|
|
443
445
|
allHeaders[name] = value
|
444
446
|
this.set_headers(allHeaders)
|
445
447
|
|
446
|
-
add_header: (header, permanent) ->
|
447
|
-
|
448
|
+
add_header: (header, { permanent = true }) ->
|
449
|
+
unless permanent == true
|
450
|
+
@currentPage.addTempHeader(header)
|
451
|
+
@currentPage.addTempHeaderToRemoveOnRedirect(header) if permanent == "no_redirect"
|
448
452
|
this.add_headers(header)
|
449
453
|
|
450
454
|
response_headers: ->
|
@@ -1,4 +1,6 @@
|
|
1
|
-
var PoltergeistAgent
|
1
|
+
var PoltergeistAgent,
|
2
|
+
indexOf = [].indexOf || function(item) { for (var i = 0, l = this.length; i < l; i++) { if (i in this && this[i] === item) return i; } return -1; },
|
3
|
+
hasProp = {}.hasOwnProperty;
|
2
4
|
|
3
5
|
PoltergeistAgent = (function() {
|
4
6
|
function PoltergeistAgent() {
|
@@ -100,6 +102,44 @@ PoltergeistAgent = (function() {
|
|
100
102
|
return typeof localStorage !== "undefined" && localStorage !== null ? localStorage.clear() : void 0;
|
101
103
|
};
|
102
104
|
|
105
|
+
PoltergeistAgent.prototype.wrapResults = function(result, page_id) {
|
106
|
+
var j, key, len, obj, res, results1, val;
|
107
|
+
this._visitedObjects || (this._visitedObjects = []);
|
108
|
+
switch (false) {
|
109
|
+
case indexOf.call(this._visitedObjects, result) < 0:
|
110
|
+
return '(cyclic structure)';
|
111
|
+
case !(Array.isArray(result) || (result instanceof NodeList)):
|
112
|
+
results1 = [];
|
113
|
+
for (j = 0, len = result.length; j < len; j++) {
|
114
|
+
res = result[j];
|
115
|
+
results1.push(this.wrapResults(res, page_id));
|
116
|
+
}
|
117
|
+
return results1;
|
118
|
+
break;
|
119
|
+
case !(result && result.nodeType === 1 && result['tagName']):
|
120
|
+
return {
|
121
|
+
'ELEMENT': {
|
122
|
+
id: this.register(result),
|
123
|
+
page_id: page_id
|
124
|
+
}
|
125
|
+
};
|
126
|
+
case !(result == null):
|
127
|
+
return void 0;
|
128
|
+
case typeof result !== 'object':
|
129
|
+
this._visitedObjects.push(result);
|
130
|
+
obj = {};
|
131
|
+
for (key in result) {
|
132
|
+
if (!hasProp.call(result, key)) continue;
|
133
|
+
val = result[key];
|
134
|
+
obj[key] = this.wrapResults(val, page_id);
|
135
|
+
}
|
136
|
+
this._visitedObjects.pop();
|
137
|
+
return obj;
|
138
|
+
default:
|
139
|
+
return result;
|
140
|
+
}
|
141
|
+
};
|
142
|
+
|
103
143
|
return PoltergeistAgent;
|
104
144
|
|
105
145
|
})();
|
@@ -162,7 +202,7 @@ PoltergeistAgent.Node = (function() {
|
|
162
202
|
obsolete = (function(_this) {
|
163
203
|
return function(element) {
|
164
204
|
var parent;
|
165
|
-
if ((parent = element.parentNode) != null) {
|
205
|
+
if ((parent = element != null ? element.parentNode : void 0) != null) {
|
166
206
|
if (parent === document) {
|
167
207
|
return false;
|
168
208
|
} else {
|
@@ -100,8 +100,11 @@ Poltergeist.Browser = (function() {
|
|
100
100
|
};
|
101
101
|
|
102
102
|
Browser.prototype.add_extension = function(extension) {
|
103
|
-
this.currentPage.injectExtension(extension)
|
104
|
-
|
103
|
+
if (this.currentPage.injectExtension(extension)) {
|
104
|
+
return this.current_command.sendResponse('success');
|
105
|
+
} else {
|
106
|
+
return this.current_command.sendError(new Poltergeist.BrowserError("Unable to load extension: " + extension));
|
107
|
+
}
|
105
108
|
};
|
106
109
|
|
107
110
|
Browser.prototype.node = function(page_id, id) {
|
@@ -588,8 +591,8 @@ Poltergeist.Browser = (function() {
|
|
588
591
|
return this.current_command.sendResponse(true);
|
589
592
|
};
|
590
593
|
|
591
|
-
Browser.prototype.network_traffic = function() {
|
592
|
-
return this.current_command.sendResponse(this.currentPage.networkTraffic());
|
594
|
+
Browser.prototype.network_traffic = function(type) {
|
595
|
+
return this.current_command.sendResponse(this.currentPage.networkTraffic(type));
|
593
596
|
};
|
594
597
|
|
595
598
|
Browser.prototype.clear_network_traffic = function() {
|
@@ -624,9 +627,14 @@ Poltergeist.Browser = (function() {
|
|
624
627
|
return this.set_headers(allHeaders);
|
625
628
|
};
|
626
629
|
|
627
|
-
Browser.prototype.add_header = function(header,
|
628
|
-
|
630
|
+
Browser.prototype.add_header = function(header, arg1) {
|
631
|
+
var permanent, ref;
|
632
|
+
permanent = (ref = arg1.permanent) != null ? ref : true;
|
633
|
+
if (permanent !== true) {
|
629
634
|
this.currentPage.addTempHeader(header);
|
635
|
+
if (permanent === "no_redirect") {
|
636
|
+
this.currentPage.addTempHeaderToRemoveOnRedirect(header);
|
637
|
+
}
|
630
638
|
}
|
631
639
|
return this.add_headers(header);
|
632
640
|
};
|
@@ -29,6 +29,7 @@ Poltergeist.WebPage = (function() {
|
|
29
29
|
this._blockedUrls = [];
|
30
30
|
this._requestedResources = {};
|
31
31
|
this._responseHeaders = [];
|
32
|
+
this._tempHeadersToRemoveOnRedirect = {};
|
32
33
|
ref = WebPage.CALLBACKS;
|
33
34
|
for (i = 0, len = ref.length; i < len; i++) {
|
34
35
|
callback = ref[i];
|
@@ -68,6 +69,7 @@ Poltergeist.WebPage = (function() {
|
|
68
69
|
this.source = null;
|
69
70
|
this.injectAgent();
|
70
71
|
this.removeTempHeaders();
|
72
|
+
this.removeTempHeadersForRedirect();
|
71
73
|
return this.setScrollPosition({
|
72
74
|
left: 0,
|
73
75
|
top: 0
|
@@ -118,22 +120,14 @@ Poltergeist.WebPage = (function() {
|
|
118
120
|
};
|
119
121
|
|
120
122
|
WebPage.prototype.onResourceRequestedNative = function(request, net) {
|
121
|
-
var
|
122
|
-
|
123
|
-
|
124
|
-
|
125
|
-
|
126
|
-
|
127
|
-
|
128
|
-
|
129
|
-
abort = false;
|
130
|
-
if (useWhitelist && !whitelisted) {
|
131
|
-
abort = true;
|
132
|
-
}
|
133
|
-
if (blacklisted) {
|
134
|
-
abort = true;
|
135
|
-
}
|
136
|
-
if (abort) {
|
123
|
+
var ref2;
|
124
|
+
this._networkTraffic[request.id] = {
|
125
|
+
request: request,
|
126
|
+
responseParts: [],
|
127
|
+
error: null
|
128
|
+
};
|
129
|
+
if (this._blockRequest(request.url)) {
|
130
|
+
this._networkTraffic[request.id].blocked = true;
|
137
131
|
if (ref2 = request.url, indexOf.call(this._blockedUrls, ref2) < 0) {
|
138
132
|
this._blockedUrls.push(request.url);
|
139
133
|
}
|
@@ -141,14 +135,10 @@ Poltergeist.WebPage = (function() {
|
|
141
135
|
} else {
|
142
136
|
this.lastRequestId = request.id;
|
143
137
|
if (this.normalizeURL(request.url) === this.redirectURL) {
|
138
|
+
this.removeTempHeadersForRedirect();
|
144
139
|
this.redirectURL = null;
|
145
140
|
this.requestId = request.id;
|
146
141
|
}
|
147
|
-
this._networkTraffic[request.id] = {
|
148
|
-
request: request,
|
149
|
-
responseParts: [],
|
150
|
-
error: null
|
151
|
-
};
|
152
142
|
this._requestedResources[request.id] = request.url;
|
153
143
|
}
|
154
144
|
return true;
|
@@ -164,6 +154,7 @@ Poltergeist.WebPage = (function() {
|
|
164
154
|
}
|
165
155
|
if (this.requestId === response.id) {
|
166
156
|
if (response.redirectURL) {
|
157
|
+
this.removeTempHeadersForRedirect();
|
167
158
|
this.redirectURL = this.normalizeURL(response.redirectURL);
|
168
159
|
} else {
|
169
160
|
this.statusCode = response.status;
|
@@ -294,8 +285,43 @@ Poltergeist.WebPage = (function() {
|
|
294
285
|
return true;
|
295
286
|
};
|
296
287
|
|
297
|
-
WebPage.prototype.networkTraffic = function() {
|
298
|
-
|
288
|
+
WebPage.prototype.networkTraffic = function(type) {
|
289
|
+
var id, ref2, ref3, ref4, request, results, results1, results2;
|
290
|
+
switch (type) {
|
291
|
+
case 'all':
|
292
|
+
ref2 = this._networkTraffic;
|
293
|
+
results = [];
|
294
|
+
for (id in ref2) {
|
295
|
+
if (!hasProp.call(ref2, id)) continue;
|
296
|
+
request = ref2[id];
|
297
|
+
results.push(request);
|
298
|
+
}
|
299
|
+
return results;
|
300
|
+
break;
|
301
|
+
case 'blocked':
|
302
|
+
ref3 = this._networkTraffic;
|
303
|
+
results1 = [];
|
304
|
+
for (id in ref3) {
|
305
|
+
if (!hasProp.call(ref3, id)) continue;
|
306
|
+
request = ref3[id];
|
307
|
+
if (request.blocked) {
|
308
|
+
results1.push(request);
|
309
|
+
}
|
310
|
+
}
|
311
|
+
return results1;
|
312
|
+
break;
|
313
|
+
default:
|
314
|
+
ref4 = this._networkTraffic;
|
315
|
+
results2 = [];
|
316
|
+
for (id in ref4) {
|
317
|
+
if (!hasProp.call(ref4, id)) continue;
|
318
|
+
request = ref4[id];
|
319
|
+
if (!request.blocked) {
|
320
|
+
results2.push(request);
|
321
|
+
}
|
322
|
+
}
|
323
|
+
return results2;
|
324
|
+
}
|
299
325
|
};
|
300
326
|
|
301
327
|
WebPage.prototype.clearNetworkTraffic = function() {
|
@@ -422,6 +448,26 @@ Poltergeist.WebPage = (function() {
|
|
422
448
|
return this._tempHeaders;
|
423
449
|
};
|
424
450
|
|
451
|
+
WebPage.prototype.addTempHeaderToRemoveOnRedirect = function(header) {
|
452
|
+
var name, value;
|
453
|
+
for (name in header) {
|
454
|
+
value = header[name];
|
455
|
+
this._tempHeadersToRemoveOnRedirect[name] = value;
|
456
|
+
}
|
457
|
+
return this._tempHeadersToRemoveOnRedirect;
|
458
|
+
};
|
459
|
+
|
460
|
+
WebPage.prototype.removeTempHeadersForRedirect = function() {
|
461
|
+
var allHeaders, name, ref2, value;
|
462
|
+
allHeaders = this.getCustomHeaders();
|
463
|
+
ref2 = this._tempHeadersToRemoveOnRedirect;
|
464
|
+
for (name in ref2) {
|
465
|
+
value = ref2[name];
|
466
|
+
delete allHeaders[name];
|
467
|
+
}
|
468
|
+
return this.setCustomHeaders(allHeaders);
|
469
|
+
};
|
470
|
+
|
425
471
|
WebPage.prototype.removeTempHeaders = function() {
|
426
472
|
var allHeaders, name, ref2, value;
|
427
473
|
allHeaders = this.getCustomHeaders();
|
@@ -513,10 +559,11 @@ Poltergeist.WebPage = (function() {
|
|
513
559
|
};
|
514
560
|
|
515
561
|
WebPage.prototype.evaluate = function() {
|
516
|
-
var args, fn, ref2;
|
562
|
+
var args, fn, ref2, result;
|
517
563
|
fn = arguments[0], args = 2 <= arguments.length ? slice.call(arguments, 1) : [];
|
518
564
|
this.injectAgent();
|
519
|
-
|
565
|
+
result = (ref2 = this["native"]()).evaluate.apply(ref2, ["function() { var page_id = arguments[0]; var args = []; for(var i=1; i < arguments.length; i++){ if ((typeof(arguments[i]) == 'object') && (typeof(arguments[i]['ELEMENT']) == 'object')){ args.push(window.__poltergeist.get(arguments[i]['ELEMENT']['id']).element); } else { args.push(arguments[i]) } } var _result = " + (this.stringifyCall(fn, "args")) + "; return window.__poltergeist.wrapResults(_result, page_id); }", this.id].concat(slice.call(args)));
|
566
|
+
return result;
|
520
567
|
};
|
521
568
|
|
522
569
|
WebPage.prototype.execute = function() {
|
@@ -525,8 +572,11 @@ Poltergeist.WebPage = (function() {
|
|
525
572
|
return (ref2 = this["native"]()).evaluate.apply(ref2, ["function() { for(var i=0; i < arguments.length; i++){ if ((typeof(arguments[i]) == 'object') && (typeof(arguments[i]['ELEMENT']) == 'object')){ arguments[i] = window.__poltergeist.get(arguments[i]['ELEMENT']['id']).element; } } " + (this.stringifyCall(fn)) + " }"].concat(slice.call(args)));
|
526
573
|
};
|
527
574
|
|
528
|
-
WebPage.prototype.stringifyCall = function(fn) {
|
529
|
-
|
575
|
+
WebPage.prototype.stringifyCall = function(fn, args_name) {
|
576
|
+
if (args_name == null) {
|
577
|
+
args_name = "arguments";
|
578
|
+
}
|
579
|
+
return "(" + (fn.toString()) + ").apply(this, " + args_name + ")";
|
530
580
|
};
|
531
581
|
|
532
582
|
WebPage.prototype.bindCallback = function(name) {
|
@@ -549,22 +599,20 @@ Poltergeist.WebPage = (function() {
|
|
549
599
|
result = this.evaluate(function(name, args) {
|
550
600
|
return __poltergeist.externalCall(name, args);
|
551
601
|
}, name, args);
|
552
|
-
if (result
|
553
|
-
|
554
|
-
|
555
|
-
|
556
|
-
|
557
|
-
|
558
|
-
|
559
|
-
|
560
|
-
|
561
|
-
|
562
|
-
|
563
|
-
throw new Poltergeist.BrowserError(result.error.message, result.error.stack);
|
564
|
-
}
|
565
|
-
} else {
|
566
|
-
return result.value;
|
602
|
+
if ((result != null ? result.error : void 0) != null) {
|
603
|
+
switch (result.error.message) {
|
604
|
+
case 'PoltergeistAgent.ObsoleteNode':
|
605
|
+
throw new Poltergeist.ObsoleteNode;
|
606
|
+
break;
|
607
|
+
case 'PoltergeistAgent.InvalidSelector':
|
608
|
+
method = args[0], selector = args[1];
|
609
|
+
throw new Poltergeist.InvalidSelector(method, selector);
|
610
|
+
break;
|
611
|
+
default:
|
612
|
+
throw new Poltergeist.BrowserError(result.error.message, result.error.stack);
|
567
613
|
}
|
614
|
+
} else {
|
615
|
+
return result != null ? result.value : void 0;
|
568
616
|
}
|
569
617
|
};
|
570
618
|
|
@@ -593,6 +641,24 @@ Poltergeist.WebPage = (function() {
|
|
593
641
|
}
|
594
642
|
};
|
595
643
|
|
644
|
+
WebPage.prototype._blockRequest = function(url) {
|
645
|
+
var blacklisted, useWhitelist, whitelisted;
|
646
|
+
useWhitelist = this.urlWhitelist.length > 0;
|
647
|
+
whitelisted = this.urlWhitelist.some(function(whitelisted_regex) {
|
648
|
+
return whitelisted_regex.test(url);
|
649
|
+
});
|
650
|
+
blacklisted = this.urlBlacklist.some(function(blacklisted_regex) {
|
651
|
+
return blacklisted_regex.test(url);
|
652
|
+
});
|
653
|
+
if (useWhitelist && !whitelisted) {
|
654
|
+
return true;
|
655
|
+
}
|
656
|
+
if (blacklisted) {
|
657
|
+
return true;
|
658
|
+
}
|
659
|
+
return false;
|
660
|
+
};
|
661
|
+
|
596
662
|
WebPage.prototype._overrideNativeEvaluate = function() {
|
597
663
|
return this._native.evaluate = function (func, args) {
|
598
664
|
function quoteString(str) {
|
@@ -28,6 +28,7 @@ class Poltergeist.WebPage
|
|
28
28
|
@_blockedUrls = []
|
29
29
|
@_requestedResources = {}
|
30
30
|
@_responseHeaders = []
|
31
|
+
@_tempHeadersToRemoveOnRedirect = {}
|
31
32
|
|
32
33
|
for callback in WebPage.CALLBACKS
|
33
34
|
this.bindCallback(callback)
|
@@ -49,8 +50,9 @@ class Poltergeist.WebPage
|
|
49
50
|
@id += 1
|
50
51
|
@source = null
|
51
52
|
@injectAgent()
|
52
|
-
|
53
|
-
|
53
|
+
@removeTempHeaders()
|
54
|
+
@removeTempHeadersForRedirect()
|
55
|
+
@setScrollPosition(left: 0, top: 0)
|
54
56
|
|
55
57
|
onClosingNative: ->
|
56
58
|
@handle = null
|
@@ -84,38 +86,25 @@ class Poltergeist.WebPage
|
|
84
86
|
return true
|
85
87
|
|
86
88
|
onResourceRequestedNative: (request, net) ->
|
87
|
-
|
88
|
-
|
89
|
-
|
90
|
-
|
91
|
-
|
92
|
-
|
93
|
-
|
94
|
-
|
95
|
-
abort = false
|
96
|
-
|
97
|
-
if useWhitelist && !whitelisted
|
98
|
-
abort = true
|
99
|
-
|
100
|
-
if blacklisted
|
101
|
-
abort = true
|
102
|
-
|
103
|
-
if abort
|
89
|
+
@_networkTraffic[request.id] = {
|
90
|
+
request: request,
|
91
|
+
responseParts: []
|
92
|
+
error: null
|
93
|
+
}
|
94
|
+
|
95
|
+
if @_blockRequest(request.url)
|
96
|
+
@_networkTraffic[request.id].blocked = true
|
104
97
|
@_blockedUrls.push request.url unless request.url in @_blockedUrls
|
98
|
+
|
105
99
|
net.abort()
|
106
100
|
else
|
107
101
|
@lastRequestId = request.id
|
108
102
|
|
109
103
|
if @normalizeURL(request.url) == @redirectURL
|
104
|
+
@removeTempHeadersForRedirect()
|
110
105
|
@redirectURL = null
|
111
106
|
@requestId = request.id
|
112
107
|
|
113
|
-
@_networkTraffic[request.id] = {
|
114
|
-
request: request,
|
115
|
-
responseParts: []
|
116
|
-
error: null
|
117
|
-
}
|
118
|
-
|
119
108
|
@_requestedResources[request.id] = request.url
|
120
109
|
return true
|
121
110
|
|
@@ -127,6 +116,7 @@ class Poltergeist.WebPage
|
|
127
116
|
|
128
117
|
if @requestId == response.id
|
129
118
|
if response.redirectURL
|
119
|
+
@removeTempHeadersForRedirect()
|
130
120
|
@redirectURL = @normalizeURL(response.redirectURL)
|
131
121
|
else
|
132
122
|
@statusCode = response.status
|
@@ -197,8 +187,14 @@ class Poltergeist.WebPage
|
|
197
187
|
this.native().settings.password = password
|
198
188
|
return true
|
199
189
|
|
200
|
-
networkTraffic: ->
|
201
|
-
|
190
|
+
networkTraffic: (type) ->
|
191
|
+
switch type
|
192
|
+
when 'all'
|
193
|
+
request for own id, request of @_networkTraffic
|
194
|
+
when 'blocked'
|
195
|
+
request for own id, request of @_networkTraffic when request.blocked
|
196
|
+
else
|
197
|
+
request for own id, request of @_networkTraffic when not request.blocked
|
202
198
|
|
203
199
|
clearNetworkTraffic: ->
|
204
200
|
@_networkTraffic = {}
|
@@ -286,11 +282,22 @@ class Poltergeist.WebPage
|
|
286
282
|
@_tempHeaders[name] = value
|
287
283
|
@_tempHeaders
|
288
284
|
|
285
|
+
addTempHeaderToRemoveOnRedirect: (header) ->
|
286
|
+
for name, value of header
|
287
|
+
@_tempHeadersToRemoveOnRedirect[name] = value
|
288
|
+
@_tempHeadersToRemoveOnRedirect
|
289
|
+
|
290
|
+
removeTempHeadersForRedirect: ->
|
291
|
+
allHeaders = @getCustomHeaders()
|
292
|
+
for name, value of @_tempHeadersToRemoveOnRedirect
|
293
|
+
delete allHeaders[name]
|
294
|
+
@setCustomHeaders(allHeaders)
|
295
|
+
|
289
296
|
removeTempHeaders: ->
|
290
|
-
allHeaders =
|
297
|
+
allHeaders = @getCustomHeaders()
|
291
298
|
for name, value of @_tempHeaders
|
292
299
|
delete allHeaders[name]
|
293
|
-
|
300
|
+
@setCustomHeaders(allHeaders)
|
294
301
|
|
295
302
|
pushFrame: (name) ->
|
296
303
|
return true if this.native().switchToFrame(name)
|
@@ -346,14 +353,20 @@ class Poltergeist.WebPage
|
|
346
353
|
|
347
354
|
evaluate: (fn, args...) ->
|
348
355
|
this.injectAgent()
|
349
|
-
this.native().evaluate("function() {
|
350
|
-
|
356
|
+
result = this.native().evaluate("function() {
|
357
|
+
var page_id = arguments[0];
|
358
|
+
var args = [];
|
359
|
+
|
360
|
+
for(var i=1; i < arguments.length; i++){
|
351
361
|
if ((typeof(arguments[i]) == 'object') && (typeof(arguments[i]['ELEMENT']) == 'object')){
|
352
|
-
|
362
|
+
args.push(window.__poltergeist.get(arguments[i]['ELEMENT']['id']).element);
|
363
|
+
} else {
|
364
|
+
args.push(arguments[i])
|
353
365
|
}
|
354
366
|
}
|
355
|
-
var _result = #{this.stringifyCall(fn)};
|
356
|
-
return (_result
|
367
|
+
var _result = #{this.stringifyCall(fn, "args")};
|
368
|
+
return window.__poltergeist.wrapResults(_result, page_id); }", @id, args...)
|
369
|
+
result
|
357
370
|
|
358
371
|
execute: (fn, args...) ->
|
359
372
|
this.native().evaluate("function() {
|
@@ -364,8 +377,8 @@ class Poltergeist.WebPage
|
|
364
377
|
}
|
365
378
|
#{this.stringifyCall(fn)} }", args...)
|
366
379
|
|
367
|
-
stringifyCall: (fn) ->
|
368
|
-
"(#{fn.toString()}).apply(this,
|
380
|
+
stringifyCall: (fn, args_name = "arguments") ->
|
381
|
+
"(#{fn.toString()}).apply(this, #{args_name})"
|
369
382
|
|
370
383
|
bindCallback: (name) ->
|
371
384
|
@native()[name] = =>
|
@@ -382,18 +395,17 @@ class Poltergeist.WebPage
|
|
382
395
|
name, args
|
383
396
|
)
|
384
397
|
|
385
|
-
if result
|
386
|
-
|
387
|
-
|
388
|
-
|
389
|
-
|
390
|
-
|
391
|
-
|
392
|
-
|
393
|
-
|
394
|
-
|
395
|
-
|
396
|
-
result.value
|
398
|
+
if result?.error?
|
399
|
+
switch result.error.message
|
400
|
+
when 'PoltergeistAgent.ObsoleteNode'
|
401
|
+
throw new Poltergeist.ObsoleteNode
|
402
|
+
when 'PoltergeistAgent.InvalidSelector'
|
403
|
+
[method, selector] = args
|
404
|
+
throw new Poltergeist.InvalidSelector(method, selector)
|
405
|
+
else
|
406
|
+
throw new Poltergeist.BrowserError(result.error.message, result.error.stack)
|
407
|
+
else
|
408
|
+
result?.value
|
397
409
|
|
398
410
|
canGoBack: ->
|
399
411
|
this.native().canGoBack
|
@@ -413,6 +425,23 @@ class Poltergeist.WebPage
|
|
413
425
|
else
|
414
426
|
throw new Poltergeist.UnsupportedFeature("clearMemoryCache is supported since PhantomJS 2.0.0")
|
415
427
|
|
428
|
+
_blockRequest: (url) ->
|
429
|
+
useWhitelist = @urlWhitelist.length > 0
|
430
|
+
|
431
|
+
whitelisted = @urlWhitelist.some (whitelisted_regex) ->
|
432
|
+
whitelisted_regex.test url
|
433
|
+
|
434
|
+
blacklisted = @urlBlacklist.some (blacklisted_regex) ->
|
435
|
+
blacklisted_regex.test url
|
436
|
+
|
437
|
+
if useWhitelist && !whitelisted
|
438
|
+
return true
|
439
|
+
|
440
|
+
if blacklisted
|
441
|
+
return true
|
442
|
+
|
443
|
+
false
|
444
|
+
|
416
445
|
_overrideNativeEvaluate: ->
|
417
446
|
# PhantomJS 1.9.x WebPage#evaluate depends on the browser context JSON, this replaces it
|
418
447
|
# with the evaluate from 2.1.1 which uses the PhantomJS JSON
|
@@ -135,7 +135,8 @@ module Capybara::Poltergeist
|
|
135
135
|
end
|
136
136
|
|
137
137
|
def evaluate_script(script, *args)
|
138
|
-
browser.evaluate(script, *args.map { |arg| arg.is_a?(Capybara::Poltergeist::Node) ? arg.native : arg})
|
138
|
+
result = browser.evaluate(script, *args.map { |arg| arg.is_a?(Capybara::Poltergeist::Node) ? arg.native : arg})
|
139
|
+
unwrap_script_result(result)
|
139
140
|
end
|
140
141
|
|
141
142
|
def execute_script(script, *args)
|
@@ -228,8 +229,8 @@ module Capybara::Poltergeist
|
|
228
229
|
browser.scroll_to(left, top)
|
229
230
|
end
|
230
231
|
|
231
|
-
def network_traffic
|
232
|
-
browser.network_traffic
|
232
|
+
def network_traffic(type = nil)
|
233
|
+
browser.network_traffic(type)
|
233
234
|
end
|
234
235
|
|
235
236
|
def clear_network_traffic
|
@@ -253,8 +254,7 @@ module Capybara::Poltergeist
|
|
253
254
|
end
|
254
255
|
|
255
256
|
def add_header(name, value, options = {})
|
256
|
-
permanent
|
257
|
-
browser.add_header({ name => value }, permanent)
|
257
|
+
browser.add_header({ name => value }, { permanent: true }.merge(options))
|
258
258
|
end
|
259
259
|
|
260
260
|
def response_headers
|
@@ -340,8 +340,8 @@ module Capybara::Poltergeist
|
|
340
340
|
rescue EOFError, IO::WaitReadable # Ignore problems reading from STDIN.
|
341
341
|
end unless signal
|
342
342
|
|
343
|
-
|
344
|
-
|
343
|
+
ensure
|
344
|
+
trap('SIGCONT', old_trap) # Restore the previous signal handler, if there was one.
|
345
345
|
STDERR.puts 'Continuing'
|
346
346
|
end
|
347
347
|
|
@@ -410,5 +410,17 @@ module Capybara::Poltergeist
|
|
410
410
|
end
|
411
411
|
modal_text
|
412
412
|
end
|
413
|
+
|
414
|
+
def unwrap_script_result(arg)
|
415
|
+
case arg
|
416
|
+
when Array
|
417
|
+
arg.map { |e| unwrap_script_result(e) }
|
418
|
+
when Hash
|
419
|
+
return Capybara::Poltergeist::Node.new(self, arg['ELEMENT']['page_id'], arg['ELEMENT']['id']) if arg['ELEMENT']
|
420
|
+
arg.each { |k, v| arg[k] = unwrap_script_result(v) }
|
421
|
+
else
|
422
|
+
arg
|
423
|
+
end
|
424
|
+
end
|
413
425
|
end
|
414
426
|
end
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: poltergeist
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 1.
|
4
|
+
version: 1.14.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Jon Leighton
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2017-
|
11
|
+
date: 2017-03-16 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: capybara
|