mechanize 2.7.5 → 2.7.6

Sign up to get free protection for your applications and to get access to all the features.

Potentially problematic release.


This version of mechanize might be problematic. Click here for more details.

Files changed (40) hide show
  1. checksums.yaml +4 -4
  2. data/.travis.yml +22 -17
  3. data/CHANGELOG.rdoc +12 -0
  4. data/Gemfile +3 -0
  5. data/README.rdoc +1 -1
  6. data/lib/mechanize/element_matcher.rb +4 -1
  7. data/lib/mechanize/form.rb +62 -14
  8. data/lib/mechanize/form/field.rb +46 -0
  9. data/lib/mechanize/form/multi_select_list.rb +3 -7
  10. data/lib/mechanize/form/option.rb +2 -1
  11. data/lib/mechanize/http/agent.rb +37 -24
  12. data/lib/mechanize/http/content_disposition_parser.rb +4 -1
  13. data/lib/mechanize/http/www_authenticate_parser.rb +1 -1
  14. data/lib/mechanize/page.rb +4 -2
  15. data/lib/mechanize/page/frame.rb +2 -0
  16. data/lib/mechanize/parser.rb +3 -3
  17. data/lib/mechanize/test_case/http_refresh_servlet.rb +1 -2
  18. data/lib/mechanize/test_case/infinite_refresh_servlet.rb +1 -2
  19. data/lib/mechanize/version.rb +1 -1
  20. data/mechanize.gemspec +2 -1
  21. data/test/htdocs/find_link.html +1 -4
  22. data/test/test_mechanize.rb +4 -9
  23. data/test/test_mechanize_cookie.rb +56 -41
  24. data/test/test_mechanize_cookie_jar.rb +27 -6
  25. data/test/test_mechanize_file_response.rb +1 -1
  26. data/test/test_mechanize_form.rb +15 -11
  27. data/test/test_mechanize_form_check_box.rb +10 -0
  28. data/test/test_mechanize_form_encoding.rb +1 -1
  29. data/test/test_mechanize_form_multi_select_list.rb +5 -1
  30. data/test/test_mechanize_http_agent.rb +52 -0
  31. data/test/test_mechanize_http_content_disposition_parser.rb +8 -1
  32. data/test/test_mechanize_http_www_authenticate_parser.rb +8 -0
  33. data/test/test_mechanize_link.rb +19 -0
  34. data/test/test_mechanize_page.rb +28 -0
  35. data/test/test_mechanize_page_image.rb +1 -1
  36. data/test/test_mechanize_page_link.rb +2 -2
  37. data/test/test_mechanize_page_meta_refresh.rb +1 -1
  38. data/test/test_mechanize_parser.rb +12 -2
  39. data/test/test_mechanize_util.rb +1 -1
  40. metadata +10 -16
@@ -6,6 +6,30 @@ class TestMechanizeCookieJar < Mechanize::TestCase
6
6
  super
7
7
 
8
8
  @jar = Mechanize::CookieJar.new
9
+
10
+ @jar.extend Minitest::Assertions
11
+
12
+ def @jar.add(*args)
13
+ capture_io { super }
14
+ end
15
+
16
+ def @jar.jar(*args)
17
+ result = nil
18
+ capture_io { result = super }
19
+ result
20
+ end
21
+
22
+ def @jar.save_as(*args)
23
+ result = nil
24
+ capture_io { result = super }
25
+ result
26
+ end
27
+
28
+ def @jar.clear!(*args)
29
+ result = nil
30
+ capture_io { result = super }
31
+ result
32
+ end
9
33
  end
10
34
 
11
35
  def cookie_values(options = {})
@@ -270,8 +294,7 @@ class TestMechanizeCookieJar < Mechanize::TestCase
270
294
  # Add one cookie with an expiration date in the future
271
295
  cookie = Mechanize::Cookie.new(cookie_values)
272
296
  s_cookie = Mechanize::Cookie.new(cookie_values(:name => 'Bar',
273
- :expires => nil,
274
- :session => true))
297
+ :expires => nil))
275
298
 
276
299
  @jar.add(url, cookie)
277
300
  @jar.add(url, s_cookie)
@@ -297,8 +320,7 @@ class TestMechanizeCookieJar < Mechanize::TestCase
297
320
  # Add one cookie with an expiration date in the future
298
321
  cookie = Mechanize::Cookie.new(cookie_values)
299
322
  s_cookie = Mechanize::Cookie.new(cookie_values(:name => 'Bar',
300
- :expires => nil,
301
- :session => true))
323
+ :expires => nil))
302
324
 
303
325
  @jar.add(url, cookie)
304
326
  @jar.add(url, s_cookie)
@@ -324,8 +346,7 @@ class TestMechanizeCookieJar < Mechanize::TestCase
324
346
  # Add one cookie with an expiration date in the future
325
347
  cookie = Mechanize::Cookie.new(cookie_values)
326
348
  s_cookie = Mechanize::Cookie.new(cookie_values(:name => 'Bar',
327
- :expires => nil,
328
- :session => true))
349
+ :expires => nil))
329
350
 
330
351
  @jar.add(url, cookie)
331
352
  @jar.add(url, s_cookie)
@@ -5,7 +5,7 @@ class TestMechanizeFileResponse < Mechanize::TestCase
5
5
  def test_content_type
6
6
  Tempfile.open %w[pi .nothtml] do |tempfile|
7
7
  res = Mechanize::FileResponse.new tempfile.path
8
- assert_equal nil, res['content-type']
8
+ assert_nil res['content-type']
9
9
  end
10
10
 
11
11
  Tempfile.open %w[pi .xhtml] do |tempfile|
@@ -214,7 +214,7 @@ class TestMechanizeForm < Mechanize::TestCase
214
214
 
215
215
  @form['name'] = 'Aaron'
216
216
 
217
- assert @form.has_field?('name')
217
+ assert_equal true, @form.has_field?('name')
218
218
  end
219
219
 
220
220
  def test_has_value_eh
@@ -222,7 +222,7 @@ class TestMechanizeForm < Mechanize::TestCase
222
222
 
223
223
  @form['name'] = 'Aaron'
224
224
 
225
- assert @form.has_value?('Aaron')
225
+ assert_equal true, @form.has_value?('Aaron')
226
226
  end
227
227
 
228
228
  def test_keys
@@ -863,15 +863,19 @@ class TestMechanizeForm < Mechanize::TestCase
863
863
  def test_form_and_fields_dom_id
864
864
  # blatant copypasta of test above
865
865
  page = @mech.get("http://localhost/form_test.html")
866
- form = page.form_with(:dom_id => 'generic_form')
867
- form_by_id = page.form_with(:id => 'generic_form')
866
+ form = page.form_with(dom_id: 'generic_form')
868
867
 
869
- assert_equal(1, form.fields_with(:dom_id => 'name_first').length)
870
- assert_equal('first_name', form.field_with(:dom_id => 'name_first').name)
868
+ assert_equal(1, form.fields_with(dom_id: 'name_first').length)
869
+ assert_equal('first_name', form.field_with(dom_id: 'name_first').name)
871
870
 
872
- # *_with(:id => blah) should work exactly like (:dom_id => blah)
873
- assert_equal(form, form_by_id)
874
- assert_equal(form.fields_with(:dom_id => 'name_first'), form.fields_with(:id => 'name_first'))
871
+ assert_equal(form, page.form_with(id: 'generic_form'))
872
+ assert_equal(form, page.form_with(css: '#generic_form'))
873
+
874
+ fields_by_dom_id = form.fields_with(dom_id: 'name_first')
875
+ assert_equal(fields_by_dom_id, form.fields_with(id: 'name_first'))
876
+ assert_equal(fields_by_dom_id, form.fields_with(css: '#name_first'))
877
+ assert_equal(fields_by_dom_id, form.fields_with(xpath: '//*[@id="name_first"]'))
878
+ assert_equal(fields_by_dom_id, form.fields_with(search: '//*[@id="name_first"]'))
875
879
  end
876
880
 
877
881
  def test_form_and_fields_dom_class
@@ -914,9 +918,9 @@ class TestMechanizeForm < Mechanize::TestCase
914
918
  page = @mech.get("http://localhost/form_multival.html")
915
919
  form = page.form_with(:name => 'post_form')
916
920
 
917
- assert(!form.has_field?('intarweb'))
921
+ assert_equal false, form.has_field?('intarweb')
918
922
  assert form.add_field!('intarweb')
919
- assert(form.has_field?('intarweb'))
923
+ assert_equal true, form.has_field?('intarweb')
920
924
  end
921
925
 
922
926
  def test_fill_unexisting_form
@@ -8,6 +8,16 @@ class TestMechanizeFormCheckBox < Mechanize::TestCase
8
8
  @page = @mech.get('http://localhost/tc_checkboxes.html')
9
9
  end
10
10
 
11
+ def test_search
12
+ form = @page.forms.first
13
+
14
+ checkbox = form.checkbox_with(name: 'green')
15
+ assert_equal('green', checkbox.name)
16
+
17
+ assert_equal(checkbox, form.checkbox_with('green'))
18
+ assert_equal(checkbox, form.checkbox_with(search: 'input[@type=checkbox][@name=green]'))
19
+ end
20
+
11
21
  def test_check
12
22
  form = @page.forms.first
13
23
 
@@ -67,7 +67,7 @@ class TestMechanizeFormEncoding < Mechanize::TestCase
67
67
  node['enctype'] = 'application/x-www-form-urlencoded'
68
68
  form = Mechanize::Form.new(node)
69
69
 
70
- assert_equal nil, form.encoding
70
+ assert_nil form.encoding
71
71
  end
72
72
 
73
73
  def test_post_form_with_form_encoding
@@ -32,9 +32,13 @@ class TestMechanizeFormMultiSelectList < Mechanize::TestCase
32
32
  end
33
33
 
34
34
  def test_option_with
35
- option = @select.option_with :value => '1'
35
+ option = @select.option_with value: '1'
36
36
 
37
37
  assert_equal '1', option.value
38
+
39
+ option = @select.option_with search: 'option[@selected]'
40
+
41
+ assert_equal '2', option.value
38
42
  end
39
43
 
40
44
  def test_options_with
@@ -682,6 +682,14 @@ class TestMechanizeHttpAgent < Mechanize::TestCase
682
682
  assert_equal 'absolute URL needed (not google)', e.message
683
683
  end
684
684
 
685
+ def test_resolve_uri_without_path
686
+ e = assert_raises ArgumentError do
687
+ @agent.resolve 'http:%5C%5Cfoo'
688
+ end
689
+
690
+ assert_equal 'hierarchical URL needed (not http:%5C%5Cfoo)', e.message
691
+ end
692
+
685
693
  def test_resolve_utf8
686
694
  uri = 'http://example?q=ü'
687
695
 
@@ -1057,6 +1065,14 @@ class TestMechanizeHttpAgent < Mechanize::TestCase
1057
1065
  assert_equal 'part', body.read
1058
1066
  end
1059
1067
 
1068
+ def test_response_content_encoding_identity
1069
+ @res.instance_variable_set :@header, 'content-encoding' => %w[identity]
1070
+
1071
+ body = @agent.response_content_encoding @res, StringIO.new('part')
1072
+
1073
+ assert_equal 'part', body.read
1074
+ end
1075
+
1060
1076
  def test_response_content_encoding_tempfile_7_bit
1061
1077
  body_io = tempfile 'part'
1062
1078
 
@@ -1650,6 +1666,42 @@ class TestMechanizeHttpAgent < Mechanize::TestCase
1650
1666
  assert_equal 'invalid value for port: "nonexistent service"', e.message
1651
1667
  end
1652
1668
 
1669
+ def test_set_proxy_with_scheme
1670
+ @agent.set_proxy 'http://www.example.com', 9001, 'joe', 'lol'
1671
+
1672
+ assert_equal @agent.proxy_uri.host, 'www.example.com'
1673
+ assert_equal @agent.proxy_uri.port, 9001
1674
+ assert_equal @agent.proxy_uri.user, 'joe'
1675
+ assert_equal @agent.proxy_uri.password, 'lol'
1676
+ end
1677
+
1678
+ def test_set_proxy_url
1679
+ @agent.set_proxy 'http://joe:lol@www.example.com:9001'
1680
+
1681
+ assert_equal @agent.proxy_uri.host, 'www.example.com'
1682
+ assert_equal @agent.proxy_uri.port, 9001
1683
+ assert_equal @agent.proxy_uri.user, 'joe'
1684
+ assert_equal @agent.proxy_uri.password, 'lol'
1685
+ end
1686
+
1687
+ def test_set_proxy_uri
1688
+ @agent.set_proxy URI('http://joe:lol@www.example.com:9001')
1689
+
1690
+ assert_equal @agent.proxy_uri.host, 'www.example.com'
1691
+ assert_equal @agent.proxy_uri.port, 9001
1692
+ assert_equal @agent.proxy_uri.user, 'joe'
1693
+ assert_equal @agent.proxy_uri.password, 'lol'
1694
+ end
1695
+
1696
+ def test_set_proxy_url_and_credentials
1697
+ @agent.set_proxy 'http://www.example.com:9001', nil, 'joe', 'lol'
1698
+
1699
+ assert_equal @agent.proxy_uri.host, 'www.example.com'
1700
+ assert_equal @agent.proxy_uri.port, 9001
1701
+ assert_equal @agent.proxy_uri.user, 'joe'
1702
+ assert_equal @agent.proxy_uri.password, 'lol'
1703
+ end
1704
+
1653
1705
  def test_setting_agent_name
1654
1706
  mech = Mechanize.new 'user-set-name'
1655
1707
  assert_equal 'user-set-name', mech.agent.http.name
@@ -119,7 +119,7 @@ class TestMechanizeHttpContentDispositionParser < Mechanize::TestCase
119
119
 
120
120
  assert_equal 'end "', string
121
121
  end
122
-
122
+
123
123
  def test_parse_uppercase
124
124
  content_disposition = @parser.parse \
125
125
  'content-disposition: attachment; Filename=value', true
@@ -128,5 +128,12 @@ class TestMechanizeHttpContentDispositionParser < Mechanize::TestCase
128
128
  assert_equal 'value', content_disposition.filename
129
129
  end
130
130
 
131
+ def test_parse_filename_starting_with_escaped_quote
132
+ content_disposition = @parser.parse \
133
+ 'content-disposition: attachment; Filename="\"value\""', true
134
+
135
+ assert_equal '"value"', content_disposition.filename
136
+ end
137
+
131
138
  end
132
139
 
@@ -133,6 +133,14 @@ class TestMechanizeHttpWwwAuthenticateParser < Mechanize::TestCase
133
133
  assert_equal expected, @parser.parse('Basic realm = "foo"')
134
134
  end
135
135
 
136
+ def test_parse_bad_single_quote
137
+ expected = [
138
+ challenge('Basic', { 'realm' => "'foo" }, "Basic realm='foo"),
139
+ ]
140
+
141
+ assert_equal expected, @parser.parse("Basic realm='foo bar', qop='baz'")
142
+ end
143
+
136
144
  def test_quoted_string
137
145
  @parser.scanner = StringScanner.new '"text"'
138
146
 
@@ -2,6 +2,25 @@ require 'mechanize/test_case'
2
2
 
3
3
  class TestMechanizeLink < Mechanize::TestCase
4
4
 
5
+ def test_search
6
+ page = @mech.get("http://localhost/find_link.html")
7
+ link = page.link_with(text: "Form Test")
8
+
9
+ assert_equal('Form Test', link.text)
10
+
11
+ link_with_search = page.link_with(search: "//*[text()='Form Test']")
12
+ assert_equal(link, link_with_search)
13
+
14
+ link_with_xpath = page.link_with(xpath: "//*[text()='Form Test']")
15
+ assert_equal(link, link_with_xpath)
16
+
17
+ link_with_css = page.link_with(css: ".formtest")
18
+ assert_equal(link, link_with_css)
19
+
20
+ link_with_class = page.link_with(class: "formtest")
21
+ assert_equal(link, link_with_class)
22
+ end
23
+
5
24
  def test_click
6
25
  page = @mech.get("http://localhost/frame_test.html")
7
26
  link = page.link_with(:text => "Form Test")
@@ -108,6 +108,8 @@ class TestMechanizePage < Mechanize::TestCase
108
108
  assert_equal "frame3", page.frames[2].name
109
109
  assert_equal "/file_upload.html", page.frames[2].src
110
110
  assert_equal "File Upload Form", page.frames[2].content.title
111
+
112
+ assert_equal %w[/google.html /file_upload.html], page.frames_with(search: '*[name=frame1], *[name=frame3]').map(&:src)
111
113
  end
112
114
 
113
115
  def test_iframes
@@ -248,5 +250,31 @@ class TestMechanizePage < Mechanize::TestCase
248
250
  assert_empty page.links_with(:search => '//img')
249
251
  end
250
252
 
253
+ def test_multiple_titles
254
+ page = html_page <<-BODY
255
+ <!doctype html>
256
+ <html>
257
+ <head>
258
+ <title>HTML&gt;TITLE</title>
259
+ </head>
260
+ <body>
261
+ <svg>
262
+ <title>SVGTITLE</title>
263
+ <metadata id="metadata5">
264
+ <rdf:RDF>
265
+ <cc:Work>
266
+ <dc:title>RDFDCTITLE</dc:title>
267
+ </cc:Work>
268
+ </rdf:RDF>
269
+ </metadata>
270
+ <g></g>
271
+ </svg>
272
+ </body>
273
+ </html>
274
+ BODY
275
+
276
+ assert_equal page.title, "HTML>TITLE"
277
+ end
278
+
251
279
  end
252
280
 
@@ -147,7 +147,7 @@ class TestMechanizePageImage < Mechanize::TestCase
147
147
 
148
148
  assert_equal 'https', page.uri.scheme
149
149
  assert_equal false, page.images.first.relative?
150
- assert_equal nil, requests.first['Referer']
150
+ assert_nil requests.first['Referer']
151
151
  end
152
152
 
153
153
  def test_image_referer_http_page_abs_src
@@ -72,7 +72,7 @@ class TestMechanizePageLink < Mechanize::TestCase
72
72
  assert_equal(URI("http://localhost/canonical_uri"), page.canonical_uri)
73
73
 
74
74
  page = @mech.get("http://localhost/file_upload.html")
75
- assert_equal(nil, page.canonical_uri)
75
+ assert_nil page.canonical_uri
76
76
  end
77
77
 
78
78
  def test_canonical_uri_unescaped
@@ -339,7 +339,7 @@ class TestMechanizePageLink < Mechanize::TestCase
339
339
  def test_title_none
340
340
  page = util_page '' # invalid HTML
341
341
 
342
- assert_equal(nil, page.title)
342
+ assert_nil(page.title)
343
343
  end
344
344
 
345
345
  def test_page_decoded_with_charset
@@ -112,7 +112,7 @@ class TestMechanizePageMetaRefresh < Mechanize::TestCase
112
112
  page = util_page 5, nil
113
113
  link = util_meta_refresh page
114
114
  assert_equal 5, link.delay
115
- assert_equal nil, link.href
115
+ assert_nil link.href
116
116
 
117
117
  page = util_page 5, @uri
118
118
  link = util_meta_refresh page
@@ -99,10 +99,10 @@ class TestMechanizeParser < Mechanize::TestCase
99
99
  @parser.uri = URI 'http://example'
100
100
 
101
101
  @parser.response = {
102
- 'content-disposition' => 'attachment; filename="some \"file\""'
102
+ 'content-disposition' => 'attachment; filename="\"some \"file\""'
103
103
  }
104
104
 
105
- assert_equal 'some__file_', @parser.extract_filename
105
+ assert_equal '_some__file_', @parser.extract_filename
106
106
  end
107
107
 
108
108
  def test_extract_filename_content_disposition_special
@@ -162,6 +162,16 @@ class TestMechanizeParser < Mechanize::TestCase
162
162
  end
163
163
  end
164
164
 
165
+ def test_extract_filename_content_disposition_empty
166
+ @parser.uri = URI 'http://example'
167
+
168
+ @parser.response = {
169
+ 'content-disposition' => 'inline; filename="/"'
170
+ }
171
+
172
+ assert_equal '', @parser.extract_filename
173
+ end
174
+
165
175
  def test_extract_filename_host
166
176
  @parser.response = {}
167
177
  @parser.uri = URI 'http://example'
@@ -27,7 +27,7 @@ class TestMechanizeUtil < Mechanize::TestCase
27
27
 
28
28
  def test_from_native_charset_returns_nil_when_no_string
29
29
  @result = @MU.from_native_charset(nil, CONTENT_ENCODING)
30
- assert_equal nil, @result
30
+ assert_nil @result
31
31
  end
32
32
 
33
33
  def test_from_native_charset_doesnot_convert_when_no_encoding
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: mechanize
3
3
  version: !ruby/object:Gem::Version
4
- version: 2.7.5
4
+ version: 2.7.6
5
5
  platform: ruby
6
6
  authors:
7
7
  - Eric Hodel
@@ -12,7 +12,7 @@ authors:
12
12
  autorequire:
13
13
  bindir: bin
14
14
  cert_chain: []
15
- date: 2016-08-22 00:00:00.000000000 Z
15
+ date: 2018-06-02 00:00:00.000000000 Z
16
16
  dependencies:
17
17
  - !ruby/object:Gem::Dependency
18
18
  name: net-http-digest_auth
@@ -35,39 +35,33 @@ dependencies:
35
35
  - !ruby/object:Gem::Version
36
36
  version: '1.1'
37
37
  - !ruby/object:Gem::Dependency
38
- name: net-http-persistent
38
+ name: mime-types
39
39
  requirement: !ruby/object:Gem::Requirement
40
40
  requirements:
41
41
  - - ">="
42
42
  - !ruby/object:Gem::Version
43
- version: 2.5.2
44
- - - "~>"
45
- - !ruby/object:Gem::Version
46
- version: '2.5'
43
+ version: 1.17.2
47
44
  type: :runtime
48
45
  prerelease: false
49
46
  version_requirements: !ruby/object:Gem::Requirement
50
47
  requirements:
51
48
  - - ">="
52
49
  - !ruby/object:Gem::Version
53
- version: 2.5.2
54
- - - "~>"
55
- - !ruby/object:Gem::Version
56
- version: '2.5'
50
+ version: 1.17.2
57
51
  - !ruby/object:Gem::Dependency
58
- name: mime-types
52
+ name: net-http-persistent
59
53
  requirement: !ruby/object:Gem::Requirement
60
54
  requirements:
61
55
  - - ">="
62
56
  - !ruby/object:Gem::Version
63
- version: 1.17.2
57
+ version: 2.5.2
64
58
  type: :runtime
65
59
  prerelease: false
66
60
  version_requirements: !ruby/object:Gem::Requirement
67
61
  requirements:
68
62
  - - ">="
69
63
  - !ruby/object:Gem::Version
70
- version: 1.17.2
64
+ version: 2.5.2
71
65
  - !ruby/object:Gem::Dependency
72
66
  name: http-cookie
73
67
  requirement: !ruby/object:Gem::Requirement
@@ -227,8 +221,8 @@ email:
227
221
  executables: []
228
222
  extensions: []
229
223
  extra_rdoc_files:
230
- - CHANGELOG.rdoc
231
224
  - EXAMPLES.rdoc
225
+ - CHANGELOG.rdoc
232
226
  - GUIDE.rdoc
233
227
  - LICENSE.rdoc
234
228
  - README.rdoc
@@ -462,7 +456,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
462
456
  version: '0'
463
457
  requirements: []
464
458
  rubyforge_project:
465
- rubygems_version: 2.5.1
459
+ rubygems_version: 2.6.14.1
466
460
  signing_key:
467
461
  specification_version: 4
468
462
  summary: The Mechanize library is used for automating interaction with websites