lint: 'validate-uri' reports suspiciously small 200 responses.

* guix/scripts/lint.scm (validate-uri): Upon 200 http-response, check
the 'response-content-length' and emit a warning when it is <= 1000.
* tests/lint.scm (call-with-http-server): Add 'data' parameter.
(with-http-server): Likewise.
(%long-string): New variable.
("home-page: 200"): Pass %LONG-STRING to 'with-http-server'.
("home-page: 404", "source: 200", "source: 404"): Likewise.
("home-page: 200 but short length"): New test.
("source: 200 but short length"): New test.
This commit is contained in:
Ludovic Courtès 2016-07-13 00:50:05 +02:00
parent cd4c41fdcf
commit bfcb3d767b
No known key found for this signature in database
GPG Key ID: 090B11993D9AEBB5
2 changed files with 57 additions and 12 deletions

View File

@ -359,7 +359,22 @@ warning for PACKAGE mentionning the FIELD."
(probe-uri uri #:timeout 3))) ;wait at most 3 seconds (probe-uri uri #:timeout 3))) ;wait at most 3 seconds
(case status (case status
((http-response) ((http-response)
(or (= 200 (response-code argument)) (if (= 200 (response-code argument))
(match (response-content-length argument)
((? number? length)
;; As of July 2016, SourceForge returns 200 (instead of 404)
;; with a small HTML page upon failure. Attempt to detect such
;; malicious behavior.
(or (> length 1000)
(begin
(emit-warning package
(format #f
(_ "URI ~a returned \
suspiciously small file (~a bytes)")
(uri->string uri)
length))
#f)))
(_ #t))
(begin (begin
(emit-warning package (emit-warning package
(format #f (format #f

View File

@ -102,14 +102,14 @@
http-write http-write
(@@ (web server http) http-close)) (@@ (web server http) http-close))
(define (call-with-http-server code thunk) (define (call-with-http-server code data thunk)
"Call THUNK with an HTTP server running and returning CODE on HTTP "Call THUNK with an HTTP server running and returning CODE and DATA (a
requests." string) on HTTP requests."
(define (server-body) (define (server-body)
(define (handle request body) (define (handle request body)
(values (build-response #:code code (values (build-response #:code code
#:reason-phrase "Such is life") #:reason-phrase "Such is life")
"Hello, world.")) data))
(catch 'quit (catch 'quit
(lambda () (lambda ()
@ -123,8 +123,11 @@ requests."
;; Normally SERVER exits automatically once it has received a request. ;; Normally SERVER exits automatically once it has received a request.
(thunk)))) (thunk))))
(define-syntax-rule (with-http-server code body ...) (define-syntax-rule (with-http-server code data body ...)
(call-with-http-server code (lambda () body ...))) (call-with-http-server code data (lambda () body ...)))
(define %long-string
(make-string 2000 #\a))
(test-begin "lint") (test-begin "lint")
@ -402,18 +405,30 @@ requests."
(test-equal "home-page: 200" (test-equal "home-page: 200"
"" ""
(with-warnings (with-warnings
(with-http-server 200 (with-http-server 200 %long-string
(let ((pkg (package (let ((pkg (package
(inherit (dummy-package "x")) (inherit (dummy-package "x"))
(home-page %local-url)))) (home-page %local-url))))
(check-home-page pkg))))) (check-home-page pkg)))))
(test-skip (if %http-server-socket 0 1))
(test-assert "home-page: 200 but short length"
(->bool
(string-contains
(with-warnings
(with-http-server 200 "This is too small."
(let ((pkg (package
(inherit (dummy-package "x"))
(home-page %local-url))))
(check-home-page pkg))))
"suspiciously small")))
(test-skip (if %http-server-socket 0 1)) (test-skip (if %http-server-socket 0 1))
(test-assert "home-page: 404" (test-assert "home-page: 404"
(->bool (->bool
(string-contains (string-contains
(with-warnings (with-warnings
(with-http-server 404 (with-http-server 404 %long-string
(let ((pkg (package (let ((pkg (package
(inherit (dummy-package "x")) (inherit (dummy-package "x"))
(home-page %local-url)))) (home-page %local-url))))
@ -501,7 +516,7 @@ requests."
(test-equal "source: 200" (test-equal "source: 200"
"" ""
(with-warnings (with-warnings
(with-http-server 200 (with-http-server 200 %long-string
(let ((pkg (package (let ((pkg (package
(inherit (dummy-package "x")) (inherit (dummy-package "x"))
(source (origin (source (origin
@ -510,12 +525,27 @@ requests."
(sha256 %null-sha256)))))) (sha256 %null-sha256))))))
(check-source pkg))))) (check-source pkg)))))
(test-skip (if %http-server-socket 0 1))
(test-assert "source: 200 but short length"
(->bool
(string-contains
(with-warnings
(with-http-server 200 "This is too small."
(let ((pkg (package
(inherit (dummy-package "x"))
(source (origin
(method url-fetch)
(uri %local-url)
(sha256 %null-sha256))))))
(check-source pkg))))
"suspiciously small")))
(test-skip (if %http-server-socket 0 1)) (test-skip (if %http-server-socket 0 1))
(test-assert "source: 404" (test-assert "source: 404"
(->bool (->bool
(string-contains (string-contains
(with-warnings (with-warnings
(with-http-server 404 (with-http-server 404 %long-string
(let ((pkg (package (let ((pkg (package
(inherit (dummy-package "x")) (inherit (dummy-package "x"))
(source (origin (source (origin
@ -617,6 +647,6 @@ requests."
(test-end "lint") (test-end "lint")
;; Local Variables: ;; Local Variables:
;; eval: (put 'with-http-server 'scheme-indent-function 1) ;; eval: (put 'with-http-server 'scheme-indent-function 2)
;; eval: (put 'with-warnings 'scheme-indent-function 0) ;; eval: (put 'with-warnings 'scheme-indent-function 0)
;; End: ;; End: