Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
13 changes: 10 additions & 3 deletions lib/aws/s3/authentication.rb
Original file line number Diff line number Diff line change
Expand Up @@ -156,7 +156,8 @@ def initialize(request, options = {})
# "For non-authenticated or anonymous requests. A NotImplemented error result code will be returned if
# an authenticated (signed) request specifies a Host: header other than 's3.amazonaws.com'"
# (from http://docs.amazonwebservices.com/AmazonS3/2006-03-01/VirtualHosting.html)
request['Host'] = DEFAULT_HOST
# ... and now CanonicalString will be fix if request['Host'] is set
# request['Host'] = DEFAULT_HOST
build
end

Expand Down Expand Up @@ -213,9 +214,15 @@ def extract_significant_parameter
end

def only_path
request.path[/^[^?]*/]
# Check if a VirtualHost "bucket.s3.amazonaws.com" is set
# If the the path in the canonical string has to be "/bucket/request_path"
if ( request['Host'] =~ /^(.+)\.s3\.amazonaws\.com$/ )
'/' + $1 + request.path[/^[^?]*/]
else
request.path[/^[^?]*/]
end
end
end
end
end
end
end
22 changes: 21 additions & 1 deletion lib/aws/s3/connection.rb
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,8 @@ def initialize(options = {})
def request(verb, path, headers = {}, body = nil, attempts = 0, &block)
body.rewind if body.respond_to?(:rewind) unless attempts.zero?

path, headers['Host'] = virtual_host_fix(path)

requester = Proc.new do
path = self.class.prepare_path(path) if attempts.zero? # Only escape the path once
request = request_method(verb).new(path, headers)
Expand Down Expand Up @@ -61,13 +63,31 @@ def url_for(path, options = {})
# Default to true unless explicitly false
authenticate = true if authenticate.nil?
path = self.class.prepare_path(path)
request = request_method(:get).new(path, {})

path, virtual_host = virtual_host_fix(path)

request = request_method(:get).new(path, { 'Host' => virtual_host })
query_string = query_string_authentication(request, options)
returning "#{protocol(options)}#{http.address}#{port_string}#{path}" do |url|
url << "?#{query_string}" if authenticate
end
end

def virtual_host_fix(path)
# Quick and dirty fix to access buckets the VirtualHost-way
# / => goes to "s3.amazonaws.com" /
# /bucket => goes to "bucket.s3.amazonaws.com" /
# /bucket/key => goest to "bucket.s3.amazonaws.com" /key
case path
when /^(\/(\?.*)?)$/ then
return $1, DEFAULT_HOST
when /^\/([^\?\/]+)((\?.*)?)$/ then
return '/' + $2, $1 + '.' + DEFAULT_HOST
when /^\/([^\?\/]+)(([^\?]+)(\?.*)?)$/ then
return $2, $1 + '.' + DEFAULT_HOST
end
end

def subdomain
http.address[/^([^.]+).#{DEFAULT_HOST}$/, 1]
end
Expand Down