Don't follow external redirects
This commit is contained in:
parent
4565a3cea6
commit
9825aee47e
@ -110,7 +110,7 @@ For example:
|
|||||||
@http_method = http_method
|
@http_method = http_method
|
||||||
@data = data
|
@data = data
|
||||||
|
|
||||||
request_page(response.headers["Location"], :get, data) if redirect?
|
request_page(response_location, :get, data) if internal_redirect?
|
||||||
|
|
||||||
return response
|
return response
|
||||||
end
|
end
|
||||||
@ -123,6 +123,10 @@ For example:
|
|||||||
response_code / 100 == 3
|
response_code / 100 == 3
|
||||||
end
|
end
|
||||||
|
|
||||||
|
def internal_redirect? #:nodoc:
|
||||||
|
redirect? && current_host == response_location_host
|
||||||
|
end
|
||||||
|
|
||||||
def exception_caught? #:nodoc:
|
def exception_caught? #:nodoc:
|
||||||
response_body =~ /Exception caught/
|
response_body =~ /Exception caught/
|
||||||
end
|
end
|
||||||
@ -222,6 +226,18 @@ For example:
|
|||||||
|
|
||||||
private
|
private
|
||||||
|
|
||||||
|
def response_location
|
||||||
|
response.headers["Location"]
|
||||||
|
end
|
||||||
|
|
||||||
|
def current_host
|
||||||
|
URI.parse(current_url).host || "www.example.com"
|
||||||
|
end
|
||||||
|
|
||||||
|
def response_location_host
|
||||||
|
URI.parse(response_location).host || "www.example.com"
|
||||||
|
end
|
||||||
|
|
||||||
def reset
|
def reset
|
||||||
@elements = {}
|
@elements = {}
|
||||||
@_scopes = nil
|
@_scopes = nil
|
||||||
|
@ -7,8 +7,12 @@ class Testing < Application
|
|||||||
def submit_form
|
def submit_form
|
||||||
end
|
end
|
||||||
|
|
||||||
def redirect_to_root
|
def internal_redirect
|
||||||
redirect "/"
|
redirect "/"
|
||||||
end
|
end
|
||||||
|
|
||||||
|
def external_redirect
|
||||||
|
redirect "http://google.com"
|
||||||
|
end
|
||||||
|
|
||||||
end
|
end
|
@ -28,5 +28,6 @@
|
|||||||
Merb.logger.info("Compiling routes...")
|
Merb.logger.info("Compiling routes...")
|
||||||
Merb::Router.prepare do
|
Merb::Router.prepare do
|
||||||
match("/").to(:controller => "testing", :action => "show_form")
|
match("/").to(:controller => "testing", :action => "show_form")
|
||||||
match("/redirect").to(:controller => "testing", :action => "redirect_to_root")
|
match("/internal_redirect").to(:controller => "testing", :action => "internal_redirect")
|
||||||
|
match("/external_redirect").to(:controller => "testing", :action => "external_redirect")
|
||||||
end
|
end
|
@ -14,8 +14,14 @@ describe "Webrat" do
|
|||||||
click_button "Test"
|
click_button "Test"
|
||||||
end
|
end
|
||||||
|
|
||||||
it "should follow redirects" do
|
it "should follow internal redirects" do
|
||||||
response = visit "/redirect"
|
response = visit "/internal_redirect"
|
||||||
|
response.status.should == 200
|
||||||
response.should contain("Webrat Form")
|
response.should contain("Webrat Form")
|
||||||
end
|
end
|
||||||
|
|
||||||
|
it "should not follow external redirects" do
|
||||||
|
response = visit "/external_redirect"
|
||||||
|
response.status.should == 302
|
||||||
|
end
|
||||||
end
|
end
|
@ -7,8 +7,12 @@ class WebratController < ApplicationController
|
|||||||
render :text => "OK"
|
render :text => "OK"
|
||||||
end
|
end
|
||||||
|
|
||||||
def redirect
|
def internal_redirect
|
||||||
redirect_to :submit
|
redirect_to :submit
|
||||||
end
|
end
|
||||||
|
|
||||||
|
def external_redirect
|
||||||
|
redirect_to "http://google.com"
|
||||||
|
end
|
||||||
|
|
||||||
end
|
end
|
@ -1,7 +1,8 @@
|
|||||||
ActionController::Routing::Routes.draw do |map|
|
ActionController::Routing::Routes.draw do |map|
|
||||||
map.with_options :controller => "webrat" do |webrat|
|
map.with_options :controller => "webrat" do |webrat|
|
||||||
webrat.submit "/submit", :action => "submit"
|
webrat.submit "/submit", :action => "submit"
|
||||||
webrat.redirect "/redirect", :action => "redirect"
|
webrat.internal_redirect "/internal_redirect", :action => "internal_redirect"
|
||||||
|
webrat.external_redirect "/external_redirect", :action => "external_redirect"
|
||||||
|
|
||||||
webrat.root :action => "form"
|
webrat.root :action => "form"
|
||||||
end
|
end
|
||||||
|
@ -15,8 +15,13 @@ class WebratTest < ActionController::IntegrationTest
|
|||||||
click_button "Test"
|
click_button "Test"
|
||||||
end
|
end
|
||||||
|
|
||||||
test "should follow redirects" do
|
test "should follow internal redirects" do
|
||||||
visit redirect_path
|
visit internal_redirect_path
|
||||||
assert response.body.include?("OK")
|
assert response.body.include?("OK")
|
||||||
end
|
end
|
||||||
|
|
||||||
|
test "should not follow external redirects" do
|
||||||
|
visit external_redirect_path
|
||||||
|
assert response.redirect?
|
||||||
|
end
|
||||||
end
|
end
|
||||||
|
@ -11,10 +11,14 @@ get "/go" do
|
|||||||
erb :go
|
erb :go
|
||||||
end
|
end
|
||||||
|
|
||||||
get "/redirect" do
|
get "/internal_redirect" do
|
||||||
redirect "/"
|
redirect "/"
|
||||||
end
|
end
|
||||||
|
|
||||||
|
get "/external_redirect" do
|
||||||
|
redirect "http://google.com"
|
||||||
|
end
|
||||||
|
|
||||||
post "/go" do
|
post "/go" do
|
||||||
@user = params[:name]
|
@user = params[:name]
|
||||||
@email = params[:email]
|
@email = params[:email]
|
||||||
|
@ -19,8 +19,13 @@ class WebratTest < Test::Unit::TestCase
|
|||||||
assert response_body.include?("Your email is: world@example.org")
|
assert response_body.include?("Your email is: world@example.org")
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_follows_redirects
|
def test_follows_internal_redirects
|
||||||
visit "/redirect"
|
visit "/internal_redirect"
|
||||||
assert response_body.include?("visit")
|
assert response_body.include?("visit")
|
||||||
end
|
end
|
||||||
|
|
||||||
|
def test_does_not_follow_external_redirects
|
||||||
|
visit "/external_redirect"
|
||||||
|
assert response_code == 302
|
||||||
|
end
|
||||||
end
|
end
|
||||||
|
@ -113,14 +113,22 @@ describe Webrat::Session do
|
|||||||
lambda { webrat_session.request_page('some url', :get, {}) }.should raise_error(Webrat::PageLoadError)
|
lambda { webrat_session.request_page('some url', :get, {}) }.should raise_error(Webrat::PageLoadError)
|
||||||
end
|
end
|
||||||
|
|
||||||
it "should follow redirects" do
|
it "should follow internal redirects" do
|
||||||
webrat_session.should_receive(:redirect?).twice.and_return(true, false)
|
webrat_session.should_receive(:internal_redirect?).twice.and_return(true, false)
|
||||||
webrat_session.response.should_receive(:headers).once.and_return({ "Location" => "/newurl" })
|
webrat_session.response.should_receive(:headers).once.and_return({ "Location" => "/newurl" })
|
||||||
|
|
||||||
webrat_session.request_page("/oldurl", :get, {})
|
webrat_session.request_page("/oldurl", :get, {})
|
||||||
|
|
||||||
webrat_session.current_url.should == "/newurl"
|
webrat_session.current_url.should == "/newurl"
|
||||||
end
|
end
|
||||||
|
|
||||||
|
it "should now follow external redirects" do
|
||||||
|
webrat_session.should_receive(:internal_redirect?).and_return(false)
|
||||||
|
|
||||||
|
webrat_session.request_page("/oldurl", :get, {})
|
||||||
|
|
||||||
|
webrat_session.current_url.should == "/oldurl"
|
||||||
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
describe "#redirect?" do
|
describe "#redirect?" do
|
||||||
@ -138,4 +146,29 @@ describe Webrat::Session do
|
|||||||
webrat_session.redirect?.should be_false
|
webrat_session.redirect?.should be_false
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
describe "#internal_redirect?" do
|
||||||
|
before(:each) do
|
||||||
|
webrat_session = Webrat::Session.new
|
||||||
|
end
|
||||||
|
|
||||||
|
it "should return true if the last response was a redirect and the host of the current_url matches that of the response location" do
|
||||||
|
webrat_session.stub!(:redirect? => true)
|
||||||
|
webrat_session.stub!(:current_url => "http://example.com")
|
||||||
|
webrat_session.stub!(:response_location => "http://example.com")
|
||||||
|
webrat_session.internal_redirect?.should be_true
|
||||||
|
end
|
||||||
|
|
||||||
|
it "should return false if the last response was not a redirect" do
|
||||||
|
webrat_session.stub!(:redirect? => false)
|
||||||
|
webrat_session.internal_redirect?.should be_false
|
||||||
|
end
|
||||||
|
|
||||||
|
it "should return false if the last response was a redirect but the host of the current_url doesn't matches that of the response location" do
|
||||||
|
webrat_session.stub!(:redirect? => true)
|
||||||
|
webrat_session.stub!(:current_url => "http://example.com")
|
||||||
|
webrat_session.stub!(:response_location => "http://google.com")
|
||||||
|
webrat_session.internal_redirect?.should be_false
|
||||||
|
end
|
||||||
|
end
|
||||||
end
|
end
|
@ -31,14 +31,22 @@ describe "visit" do
|
|||||||
lambda { fill_in "foo", :with => "blah" }.should raise_error(Webrat::WebratError)
|
lambda { fill_in "foo", :with => "blah" }.should raise_error(Webrat::WebratError)
|
||||||
end
|
end
|
||||||
|
|
||||||
it "should follow redirects" do
|
it "should follow internal redirects" do
|
||||||
webrat_session.should_receive(:redirect?).twice.and_return(true, false)
|
webrat_session.should_receive(:internal_redirect?).twice.and_return(true, false)
|
||||||
webrat_session.response.should_receive(:headers).once.and_return({ "Location" => "/newurl" })
|
webrat_session.response.should_receive(:headers).once.and_return({ "Location" => "/newurl" })
|
||||||
|
|
||||||
visit("/oldurl")
|
visit("/oldurl")
|
||||||
|
|
||||||
current_url.should == "/newurl"
|
current_url.should == "/newurl"
|
||||||
end
|
end
|
||||||
|
|
||||||
|
it "should not follow external redirects" do
|
||||||
|
webrat_session.should_receive(:internal_redirect?).and_return(false)
|
||||||
|
|
||||||
|
visit("/oldurl")
|
||||||
|
|
||||||
|
current_url.should == "/oldurl"
|
||||||
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
describe "visit with referer" do
|
describe "visit with referer" do
|
||||||
|
Loading…
Reference in New Issue
Block a user