Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

invalid URI - How to prevent, URI::InvalidURIError errors?

I got the following back from delayed_job:

[Worker(XXXXXX pid:3720)] Class#XXXXXXX failed with URI::InvalidURIError: bad URI(is not URI?): https://s3.amazonaws.com/cline-local-dev/2/attachments/542/original/mac-os-x[1].jpeg?AWSAccessKeyId=xxxxxxxx&Expires=1295403309&Signature=xxxxxxx%3D - 3 failed attempts

The way this URI comes from in my app is.

In my user_mailer I do:

  @comment.attachments.each do |a|
    attachments[a.attachment_file_name] = open(a.authenticated_url()) {|f| f.read }
  end

Then in my attachments model:

  def authenticated_url(style = nil, expires_in = 90.minutes)
    AWS::S3::S3Object.url_for(attachment.path(style || attachment.default_style), attachment.bucket_name, :expires_in => expires_in, :use_ssl => attachment.s3_protocol == 'https')
  end

That being said, is there some type of URI.encode or parsing I can do to prevent a valid URI (as I checked the URL works in my browser) for erroring and killing delayed_job in rails 3?

Thank you!

like image 933
AnApprentice Avatar asked Jan 19 '11 00:01

AnApprentice


1 Answers

Ruby has (at least) two modules for dealing with URIs.

URI is part of the standard library.

Addressable::URI, is a separate gem, and more comprehensive, and claims to conform to the spec.

Parse a URL with either one, modify any parameters using the gem's methods, then convert it using to_s before passing it on, and you should be good to go.

I tried ' open( URI.parse(URI.encode( a.authenticated_url() )) ' but that errord with OpenURI::HTTPError: 403 Forbidden

If you navigated to that page via a browser and it succeeded, then later failed going to it directly via code, it's likely there is a cookie or session state that is missing. You might need to use something like Mechanize, which will maintain that state while allowing you to navigate through a site.


EDIT:

require 'addressable/uri'

url = 'http://www.example.com'

uri = Addressable::URI.parse(url)
uri.query_values = {
  :foo => :bar,
  :q   => '"one two"'
}

uri.to_s # => "http://www.example.com?foo=bar&q=%22one%20two%22"
like image 107
the Tin Man Avatar answered Nov 09 '22 11:11

the Tin Man