Login
7 branches 0 tags
Ben (M2 MBA) Fixed windows build ef725a4 2 years ago 1083 Commits
nujel / binlib / net.nuj
(defn http/get* (host path)
      (def req (fmt "GET {path} HTTP/1.0\r\n\r\n"))
      (def buf (buffer/allocate 0))
      (def fh (socket/connect host 80))
      (file/write* fh req (:length req))
      (file/flush* fh)
      (def bytes-read 0)
      (def bytes-read-now 1)
      (while (not (zero? bytes-read-now))
        (:length! buf (+ 65536 (:length buf)))
        (set! bytes-read-now (file/read* fh buf 65536 bytes-read))
        (set! bytes-read (+ bytes-read bytes-read-now)))
      (file/close* fh)

      (def raw-res (buffer->string buf bytes-read))
      (def eosl (:index-of raw-res "\r\n"))
      (when (< eosl 0) (return #nil))
      (def eoh (:index-of raw-res "\r\n\r\n"))
      (when (< eoh 0) (return #nil))
      (def status-line (buffer->string buf eosl))
      (def status-list (split status-line " "))
      (def headers {})
      (def header-raw (buffer->string buf eoh (+ 2 eosl)))
      (def header-lines (split header-raw "\r\n"))
      (doseq (header header-lines)
             (def eok (:index-of header ":"))
             (when (>= eok 0)
               (def key (string->keyword (:cut header 0 eok)))
               (def v (trim (:cut header (inc eok))))
               (set! headers key v)))
      (def body (:cut buf (+ 4 eoh)))
      { :http-version (car status-list)
        :status-code (read/int (cadr status-list))
        :status-message (join (cddr status-list) " ")
        :headers headers
        :body body})

(defn http/get (url)
      (when (>= (:index-of url "https://") 0)
        (error "https is unsupported right now"))
      (when (>= (:index-of url "http://") 0)
        (set! url (:cut url 7))
        (def path-start (:index-of url "/"))
        (return (if (>= path-start 0)
                    (http/get* (:cut url 0 path-start)
                               (:cut url path-start))
                    (http/get* url "/"))))
      (error "unsupported scheme"))