From c80d07befbb8d47365269317f99f206f1cb5ac55 Mon Sep 17 00:00:00 2001 From: w6vvn Date: Tue, 2 Sep 2025 19:01:53 -0700 Subject: [PATCH] implement a procedure to visit documents. NOT compliant, but enough to move on. --- gem300.rkt | 33 +++++++++++++++++++++++++++++---- 1 file changed, 29 insertions(+), 4 deletions(-) diff --git a/gem300.rkt b/gem300.rkt index 3989a2a..3db3b5e 100644 --- a/gem300.rkt +++ b/gem300.rkt @@ -17,7 +17,6 @@ (car split)) link-#)))) - (define (gemtext-parse lines) (define (iter document lines state link-#) ;; when there are no more lines, we have finished parsing. @@ -85,6 +84,11 @@ (iter (list) lines 'normal 1)) + +;; sends a request to a gemini server, and returns the status, header, +;; and the input port for the rest of the body. +;; this procedure will fail if the response is malformed, however, it +;; is not up to it to validate the contents of the response. (define (request url-str) (define url (string->url url-str)) (define-values (c-in c-out) @@ -97,10 +101,31 @@ (define-values (status header) (read-response c-in)) - (println status) - (println header) + (values status header c-in)) - c-in) +(define (go-cmd url-str) + (define (iter url-str depth) + (let-values ([(status header c-in) (request url-str)]) + ;; TODO there are bunch of other status codes to deal with for + ;; compliance + (cond + ;; clients MUST reject status codes outside of the 10-69 range + [(or (< status 10) + (> status 69)) + (error "server returned invalid status code")] + + ;; 30-39 redirection + [(and (>= status 30) + (<= status 39)) + (if (> depth 5) + (error "maximum redirection depth exceeded") + (iter header (sub1 depth)))] + + [else + (values status header c-in)]))) + + (let-values ([(status header c-in) (iter url-str 5)]) + (render-gemtext (gemtext-parse (port->lines c-in))))) (define (read-response (c-in (current-input-port))) (define maxlen 1027)