diff options
author | Andrew Kane <andrew@ankane.org> | 2023-01-13 20:27:05 -0800 |
---|---|---|
committer | git <svn-admin@ruby-lang.org> | 2023-12-07 07:00:53 +0000 |
commit | d97479f9c966bd2c9d52c8be28aca9431760c610 (patch) | |
tree | e2f53abae3b46f2c269fe61be3fff35ef3f34e84 | |
parent | 7d32830b8ce14cc130d052a4aa67495a34ed55dc (diff) | |
download | ruby-d97479f9c966bd2c9d52c8be28aca9431760c610.tar.gz |
[ruby/open-uri] Add :max_redirects option
https://github.com/ruby/open-uri/commit/7fd5ea09a7
-rw-r--r-- | lib/open-uri.rb | 3 | ||||
-rw-r--r-- | test/open-uri/test_open-uri.rb | 19 |
2 files changed, 22 insertions, 0 deletions
diff --git a/lib/open-uri.rb b/lib/open-uri.rb index 00e4c2d9b8..56dac75b29 100644 --- a/lib/open-uri.rb +++ b/lib/open-uri.rb @@ -108,6 +108,7 @@ module OpenURI :ftp_active_mode => false, :redirect => true, :encoding => nil, + :max_redirects => nil, } def OpenURI.check_options(options) # :nodoc: @@ -211,6 +212,7 @@ module OpenURI end uri_set = {} + max_redirects = options[:max_redirects] buf = nil while true redirect = catch(:open_uri_redirect) { @@ -238,6 +240,7 @@ module OpenURI uri = redirect raise "HTTP redirection loop: #{uri}" if uri_set.include? uri.to_s uri_set[uri.to_s] = true + raise "Too many redirects" if max_redirects && uri_set.size > max_redirects else break end diff --git a/test/open-uri/test_open-uri.rb b/test/open-uri/test_open-uri.rb index 86aefc52c8..6bad7f4bdf 100644 --- a/test/open-uri/test_open-uri.rb +++ b/test/open-uri/test_open-uri.rb @@ -558,6 +558,25 @@ class TestOpenURI < Test::Unit::TestCase } end + def test_max_redirects_success + with_http {|srv, dr, url| + srv.mount_proc("/r1/") {|req, res| res.status = 301; res["location"] = "#{url}/r2"; res.body = "r1" } + srv.mount_proc("/r2/") {|req, res| res.status = 301; res["location"] = "#{url}/r3"; res.body = "r2" } + srv.mount_proc("/r3/") {|req, res| res.body = "r3" } + URI.open("#{url}/r1/", max_redirects: 2) { |f| assert_equal("r3", f.read) } + } + end + + def test_max_redirects_too_many + with_http {|srv, dr, url| + srv.mount_proc("/r1/") {|req, res| res.status = 301; res["location"] = "#{url}/r2"; res.body = "r1" } + srv.mount_proc("/r2/") {|req, res| res.status = 301; res["location"] = "#{url}/r3"; res.body = "r2" } + srv.mount_proc("/r3/") {|req, res| res.body = "r3" } + exc = assert_raise(RuntimeError) { URI.open("#{url}/r1/", max_redirects: 1) {} } + assert_equal("Too many redirects", exc.message) + } + end + def test_userinfo assert_raise(ArgumentError) { URI.open("http://user:pass@127.0.0.1/") {} } end |