Browse Source
did not duplicate content lentgh check in preparation for the removal of content_length as discussed in #131
Paul Hinze
12 years ago
5 changed files with 151 additions and 92 deletions
@ -0,0 +1,14 @@ |
|||
class Cask::CLI::Checklinks |
|||
def self.run(*args) |
|||
casks_to_check = args.empty? ? Cask.all : args.map { |arg| Cask.load(arg) } |
|||
casks_to_check.each do |cask| |
|||
checker = Cask::LinkChecker.new(cask) |
|||
checker.run |
|||
puts checker.summary |
|||
end |
|||
end |
|||
|
|||
def self.help |
|||
"checks for bad cask links" |
|||
end |
|||
end |
@ -0,0 +1,104 @@ |
|||
class Cask::LinkChecker |
|||
attr_accessor :cask, :errors, :response_status, :headers |
|||
|
|||
def initialize(cask, fetcher=Cask::Fetcher) |
|||
@cask = cask |
|||
@errors = [] |
|||
@warnings = [] |
|||
@headers = {} |
|||
@fetcher = fetcher |
|||
end |
|||
|
|||
def run |
|||
_get_data_from_request |
|||
return if errors? |
|||
_check_response_status |
|||
end |
|||
|
|||
def add_error(message) |
|||
@errors << message |
|||
end |
|||
|
|||
def add_warning(message) |
|||
@warnings << message |
|||
end |
|||
|
|||
def errors? |
|||
!@errors.empty? |
|||
end |
|||
|
|||
def warnings? |
|||
!@warnings.empty? |
|||
end |
|||
|
|||
def result |
|||
if errors? |
|||
"#{Tty.red}failed#{Tty.reset}" |
|||
elsif warnings? |
|||
"#{Tty.yellow}warning#{Tty.reset}" |
|||
else |
|||
"#{Tty.green}passed#{Tty.reset}" |
|||
end |
|||
end |
|||
|
|||
def summary |
|||
summary = ["audit for #{cask}: #{result}"] |
|||
|
|||
@errors.each do |error| |
|||
summary << " #{Tty.red}-#{Tty.reset} #{error}" |
|||
end |
|||
|
|||
@warnings.each do |warning| |
|||
summary << " #{Tty.yellow}-#{Tty.reset} #{warning}" |
|||
end |
|||
|
|||
summary.join("\n") |
|||
end |
|||
|
|||
HTTP_RESPONSES = [ |
|||
'HTTP/1.0 200 OK', |
|||
'HTTP/1.1 200 OK' |
|||
] |
|||
|
|||
OK_RESPONSES = { |
|||
'http' => HTTP_RESPONSES, |
|||
'https' => HTTP_RESPONSES, |
|||
'ftp' => [ 'OK' ] |
|||
} |
|||
|
|||
def _check_response_status |
|||
ok = OK_RESPONSES[cask.url.scheme] |
|||
unless ok.include?(@response_status) |
|||
add_error "unexpected http response, expecting #{ok.map(&:inspect).join(' or ')}, got #{@response_status.inspect}" |
|||
end |
|||
end |
|||
|
|||
def _get_data_from_request |
|||
response = @fetcher.head(cask.url) |
|||
|
|||
if response.empty? |
|||
add_error "timeout while requesting #{cask.url}" |
|||
return |
|||
end |
|||
|
|||
response_lines = response.split("\n").map(&:chomp) |
|||
|
|||
case cask.url.scheme |
|||
when 'http', 'https' then |
|||
@response_status = response_lines.grep(/^HTTP/).last |
|||
http_headers = response_lines[(response_lines.index(@response_status)+1)..-1] |
|||
http_headers.each { |line| |
|||
header_name, header_value = line.split(': ') |
|||
@headers[header_name] = header_value |
|||
} |
|||
when 'ftp' then |
|||
@response_status = 'OK' |
|||
response_lines.each { |line| |
|||
header_name, header_value = line.split(': ') |
|||
@headers[header_name] = header_value |
|||
} |
|||
else |
|||
add_error "unknown scheme for #{cask.url}" |
|||
end |
|||
end |
|||
end |
@ -0,0 +1,33 @@ |
|||
require 'test_helper' |
|||
|
|||
describe Cask::Installer do |
|||
describe "request processing" do |
|||
it "adds an error if response is empty" do |
|||
cask = TestHelper.test_cask |
|||
TestHelper.fake_response_for(cask.url, "") |
|||
checker = Cask::LinkChecker.new(cask, TestHelper.fake_fetcher) |
|||
checker.run |
|||
checker.errors.must_include "timeout while requesting #{cask.url}" |
|||
end |
|||
|
|||
it "properly populates the response code and headers from an http response" do |
|||
TestHelper.fake_response_for(TestHelper.test_cask.url, <<-RESPONSE.gsub(/^ */, '')) |
|||
HTTP/1.1 200 OK |
|||
Content-Type: application/x-apple-diskimage |
|||
ETag: "b4208f3e84967be4b078ecaa03fba941" |
|||
Content-Length: 23726161 |
|||
Last-Modified: Sun, 12 Aug 2012 21:17:21 GMT |
|||
RESPONSE |
|||
|
|||
checker = Cask::LinkChecker.new(TestHelper.test_cask, TestHelper.fake_fetcher) |
|||
checker.run |
|||
checker.response_status.must_equal 'HTTP/1.1 200 OK' |
|||
checker.headers.must_equal({ |
|||
'Content-Type' => 'application/x-apple-diskimage', |
|||
'ETag' => '"b4208f3e84967be4b078ecaa03fba941"', |
|||
'Content-Length' => '23726161', |
|||
'Last-Modified' => 'Sun, 12 Aug 2012 21:17:21 GMT' |
|||
}) |
|||
end |
|||
end |
|||
end |
Loading…
Reference in new issue