6 -- |Definition of things related on HTTP request.
8 -- In general you don't have to use this module directly.
9 module Network.HTTP.Lucu.Request
16 import Control.Applicative
17 import Control.Monad.Unicode
18 import Data.Ascii (Ascii)
19 import Data.Attoparsec.Char8
20 import qualified Data.ByteString.Char8 as C8
21 import Network.HTTP.Lucu.Headers
22 import Network.HTTP.Lucu.HttpVersion
23 import Network.HTTP.Lucu.Parser.Http
25 import Prelude.Unicode
27 -- |This is the definition of HTTP request methods, which shouldn't
28 -- require any descriptions.
37 | ExtensionMethod !Ascii
40 -- |This is the definition of an HTTP reqest.
45 , reqVersion ∷ !HttpVersion
46 , reqHeaders ∷ !Headers
50 instance HasHeaders Request where
51 {-# INLINE getHeaders #-}
52 getHeaders = reqHeaders
53 {-# INLINE setHeaders #-}
54 setHeaders req hdr = req { reqHeaders = hdr }
56 -- |Returns 'True' iff the 'Request' must have an entity body.
57 reqMustHaveBody ∷ Request → Bool
58 {-# INLINEABLE reqMustHaveBody #-}
59 reqMustHaveBody (reqMethod → m)
64 -- |'Parser' for a 'Request'.
65 requestP ∷ Parser Request
66 requestP = do skipMany crlf
67 (method, uri, version) ← requestLineP
72 , reqVersion = version
73 , reqHeaders = headers
76 requestLineP ∷ Parser (Method, URI, HttpVersion)
77 requestLineP = do method ← methodP
83 return (method, uri, ver)
85 methodP ∷ Parser Method
87 [ string "OPTIONS" ≫ return OPTIONS
88 , string "GET" ≫ return GET
89 , string "HEAD" ≫ return HEAD
90 , string "POST" ≫ return POST
91 , string "PUT" ≫ return PUT
92 , string "DELETE" ≫ return DELETE
93 , string "TRACE" ≫ return TRACE
94 , string "CONNECT" ≫ return CONNECT
95 , ExtensionMethod <$> token
99 uriP = do bs ← takeWhile1 (\c → (¬) (isCtl c ∨ c ≡ '\x20'))
100 let str = C8.unpack bs
101 case parseURIReference str of
102 Nothing -> fail ("Unparsable URI: " ⧺ str)
103 Just uri -> return uri