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
5 changes: 3 additions & 2 deletions lib/puppet/file_serving/http_metadata.rb
Original file line number Diff line number Diff line change
Expand Up @@ -13,8 +13,6 @@ def initialize(http_response, path = '/dev/null')

# hash available checksums for eventual collection
@checksums = {}
# use a default mtime in case there is no usable HTTP header
@checksums[:mtime] = "{mtime}#{Time.now}"

# RFC-1864, deprecated in HTTP/1.1 due to partial responses
checksum = http_response['content-md5']
Expand Down Expand Up @@ -82,5 +80,8 @@ def collect
@checksum = @checksums[type]
break if @checksum
end

# If no checksum was found in headers, leave checksum as nil
# The HTTP indirector will need to fetch content to compute a checksum
end
end
22 changes: 13 additions & 9 deletions lib/puppet/indirector/file_metadata/http.rb
Original file line number Diff line number Diff line change
Expand Up @@ -17,17 +17,21 @@ def find(request)
client = Puppet.runtime[:http]
head = client.head(uri, options: { include_system_store: true })

return create_httpmetadata(head, checksum_type) if head.success?
metadata = create_httpmetadata(head, checksum_type)
return metadata if metadata.checksum

case head.code
when 403, 405
# AMZ presigned URL and puppetserver may return 403
# instead of 405. Fallback to partial get
get = partial_get(client, uri)
return create_httpmetadata(get, checksum_type) if get.success?
end
# If no checksum headers were available, fetch the content to compute a checksum
get = client.get(uri, options: { include_system_store: true })
return nil unless get.success?

nil
# Compute checksum from the content
content = get.body
checksum_type ||= Puppet[:digest_algorithm].to_sym
checksum = "{#{checksum_type}}" + Digest.const_get(checksum_type.to_s.upcase).hexdigest(content)

metadata.checksum = checksum
metadata.checksum_type = checksum_type
metadata
end

def search(request)
Expand Down
6 changes: 4 additions & 2 deletions spec/unit/indirector/file_metadata/http_spec.rb
Original file line number Diff line number Diff line change
Expand Up @@ -29,16 +29,18 @@
end

context "when finding" do
it "returns http file metadata" do
it "returns http file metadata and fetches content to compute checksum when no headers available" do
stub_request(:head, key)
.to_return(status: 200, headers: DEFAULT_HEADERS)
stub_request(:get, key)
.to_return(status: 200, body: "test content")

result = model.indirection.find(key)
expect(result.ftype).to eq('file')
expect(result.path).to eq('/dev/null')
expect(result.relative_path).to be_nil
expect(result.destination).to be_nil
expect(result.checksum).to match(%r{mtime})
expect(result.checksum).to match(%r{sha256})
expect(result.owner).to be_nil
expect(result.group).to be_nil
expect(result.mode).to be_nil
Expand Down
Loading