DZone Snippets is a public source code repository. Easily build up your personal collection of code snippets, categorize them with tags / keywords, and share them with the world

Lance has posted 24 posts at DZone. View Full User Profile

Force Mechanize To Return HTTP Success When Condition Is Met In Ruby

08.16.2010
| 4174 views |
  • submit to reddit
        
require 'rubygems'
require 'uri'
require 'mechanize'
require 'rack/utils'

# so you can do `params.inspect` throughout Mechanize
class NilClass; def search(*args); []; end; end

Mechanize::Chain::PostConnectHook.class_eval do
  
  def handle(ctx, params)
    headers = params[:response].to_hash
    if headers.has_key?("location")
      headers["location"].each do |location|
        url = URI.parse(location)
        if url.host == "localhost" && url.port == 4567
          params[:res_klass] = Net::HTTPSuccess
        end
      end
    end
    
    p params.keys
    #=> [:res_klass, :uri, :response_body, :referer, :response, :agent, :verb, :redirects, :connection, :params, :request, :headers]
    p params[:uri]
    #=> #<URI::HTTPS:0x1aa0810 URL:https://somesite.com?key=value>
    p params[:response]
    #=> #<Net::HTTPFound 302 Found readbody=true>
    p params[:response].to_hash
    #=> {"location"=>["http://somesite.com"], "expires"=>["Sat, 01 Jan 2000 00:00:00 GMT"], "content-type"=>["text/html; charset=utf-8"], "date"=>["Mon, 16 Aug 2010 04:31:13 GMT"], "content-length"=>["0"], "cache-control"=>["private, no-cache, no-store, must-revalidate"], "x-cnection"=>["close"], "pragma"=>["no-cache"]}
    
    super(ctx, params)
  end
  
end

agent = Mechanize.new
page = agent.get("https://somesite.com")
# ... tons of redirects,
# then finally we find a match in our `handle` method above,
# and reset the `params[:res_klass]` to `Net::HTTPSuccess`.
# that is a hack to say basically,
# "return the page, we found what we want"
location = URI.parse(page.response.to_hash["location"].to_a.first)
params = Rack::Utils.parse_query(location.query)