Safe Haskell | Trustworthy |
---|---|
Language | Haskell98 |
Exports basic HTTP client functions inside the DC
Monad.
Computations are allowed to communicate over HTTP as long as they can
read and write to a labeled origin. An origin is associated with two
labels. When writing, the origin has a label of the form
< "scheme://authority", |True >
, where scheme
is
either 'http' or 'https', and authority
is the domain name or IP
address used in the request and port number of the connection. In
other words, the secrecy component contains the origin information,
while the integrity component is the same as that of public data.
When reading, the origin has a label of the form
< |True, "scheme://authority" >
.
This means that DC
computations can export data if the current label
is not higher than that of the labeled origin, and read data that is
no more trustworthy than that of the origin. Practically, this means
that untrusted computation can export data so long as the they have
not observed any data more sensitive than the label of the target
domain. Reading (which also occurs on every request/write) further
raises the current label to the join of the current label and origin.
For example, suppose some piece of data, myLoc
, has the label:
aliceLocL = dcLabel ("alice" /\ "http://maps.googleapis.com:80") dcTrue
created as:
myLoc <- labelP alicePriv aliceLocL "3101 24th Street, San Francisco, CA"
Then, untrusted code (with initial label set to public) running on behalf of "alice" , may perform the following operation:
let mapBase = "http://maps.googleapis.com/maps/api/geocode/json?sensor=false" aliceLoc <- unlabelP alicePriv myLoc resp <- simpleGetHttp $ mapBase ++ "&address=" ++ aliceLoc
In this case the unlabelP
will raise the current label to the label:
< "http://maps.googleapis.com:80", |True >
by exercising "alice"s privilges. Directly, the simpleHttp
will be permitted. However, if
let mapBase = "http://maps.evilalternatives.org/geocode/json?sensor=false"
an exception will be thrown since the current label does not flow to
the label of mapBase
.
This module uses 'http-conduit' as the underlying client, we recommend
looking at the Network.HTTP.Conduit documentation on how to
construct Request
s. Here, we highlight some important details:
- The headers
Content-Length
andHost
are automatically set, and should not be added torequestHeaders
. - By default, the functions in this package will not throw
exceptions for non-2xx status codes. If you would like to use the
default http-conduit behavior, you should use
checkStatus
, e.g.:
req <- parseUrl mapBase resp <- simpleGetHttp $ req { checkStatus = \s@(Status sci _) hs -> if 200 <= sci && sci < 300 then Nothing else Just $ toException $ StatusCodeException s hs }
- type Request = Request
- method :: Request -> Method
- secure :: Request -> Bool
- host :: Request -> ByteString
- port :: Request -> Int
- path :: Request -> ByteString
- queryString :: Request -> ByteString
- requestHeaders :: Request -> RequestHeaders
- requestBody :: Request -> RequestBody
- rawBody :: Request -> Bool
- redirectCount :: Request -> Int
- checkStatus :: Request -> Status -> ResponseHeaders -> CookieJar -> Maybe SomeException
- decompress :: Request -> ByteString -> Bool
- module Network.HTTP.Types
- data Response = Response {}
- parseUrl :: String -> DC Request
- applyBasicAuth :: ByteString -> ByteString -> Request -> Request
- simpleHttp :: Request -> DC Response
- simpleHttpP :: PrivDesc DCLabel p => Priv p -> Request -> DC Response
- simpleGetHttp :: String -> DC Response
- simpleGetHttpP :: DCPriv -> String -> DC Response
- simpleHeadHttp :: String -> DC Response
- simpleHeadHttpP :: DCPriv -> String -> DC Response
- data HttpException :: *
- = StatusCodeException Status ResponseHeaders CookieJar
- | InvalidUrlException String String
- | TooManyRedirects [Response ByteString]
- | UnparseableRedirect (Response ByteString)
- | TooManyRetries
- | HttpParserException String
- | HandshakeFailed
- | OverlongHeaders
- | ResponseTimeout
- | FailedConnectionException String Int
- | FailedConnectionException2 String Int Bool SomeException
- | ExpectedBlankAfter100Continue
- | InvalidStatusLine ByteString
- | InvalidHeader ByteString
- | InternalIOException IOException
- | ProxyConnectException ByteString Int (Either ByteString HttpException)
- | NoResponseDataReceived
- | TlsException SomeException
- | TlsNotSupported
- | ResponseBodyTooShort Word64 Word64
- | InvalidChunkHeaders
- | IncompleteHeaders
- | InvalidDestinationHost ByteString
- | HttpZlibException ZlibException
- | InvalidProxyEnvironmentVariable Text Text
- | ResponseLengthAndChunkingBothUsed
Request type
host :: Request -> ByteString
Requested host name, used for both the IP address to connect to and
the host
request header.
Since 0.1.0
The port to connect to. Also used for generating the host
request header.
Since 0.1.0
path :: Request -> ByteString
Everything from the host to the query string.
Since 0.1.0
queryString :: Request -> ByteString
Query string appended to the path.
Since 0.1.0
requestHeaders :: Request -> RequestHeaders
Custom HTTP request headers
The Content-Length and Transfer-Encoding headers are set automatically
by this module, and shall not be added to requestHeaders
.
If not provided by the user, Host
will automatically be set based on
the host
and port
fields.
Moreover, the Accept-Encoding header is set implicitly to gzip for
convenience by default. This behaviour can be overridden if needed, by
setting the header explicitly to a different value. In order to omit the
Accept-Header altogether, set it to the empty string "". If you need an
empty Accept-Header (i.e. requesting the identity encoding), set it to a
non-empty white-space string, e.g. " ". See RFC 2616 section 14.3 for
details about the semantics of the Accept-Header field. If you request a
content-encoding not supported by this module, you will have to decode
it yourself (see also the decompress
field).
Note: Multiple header fields with the same field-name will result in multiple header fields being sent and therefore it's the responsibility of the client code to ensure that the rules from RFC 2616 section 4.2 are honoured.
Since 0.1.0
requestBody :: Request -> RequestBody
Request body to be sent to the server.
Since 0.1.0
If True
, a chunked and/or gzipped body will not be
decoded. Use with caution.
Since 0.1.0
redirectCount :: Request -> Int
How many redirects to follow when getting a resource. 0 means follow no redirects. Default value: 10.
Since 0.1.0
checkStatus :: Request -> Status -> ResponseHeaders -> CookieJar -> Maybe SomeException
Check the status code. Note that this will run after all redirects are
performed. Default: return a StatusCodeException
on non-2XX responses.
Since 0.1.0
decompress :: Request -> ByteString -> Bool
Predicate to specify whether gzipped data should be
decompressed on the fly (see alwaysDecompress
and
browserDecompress
). Argument is the mime type.
Default: browserDecompress.
Since 0.1.0
module Network.HTTP.Types
Response type
A response sent by the app.
Response | |
|
Simple HTTP interface
parseUrl :: String -> DC Request Source
Convert a URL into a Request
.
This defaults some of the values in Request
, such as setting
method to GET and requestHeaders
to [].
applyBasicAuth :: ByteString -> ByteString -> Request -> Request
Add a Basic Auth header (with the specified user name and password) to the given Request. Ignore error handling:
applyBasicAuth "user" "pass" $ fromJust $ parseUrl url
Since 0.1.0
Same as simpleHttp
, but uses privileges.
simpleGetHttp :: String -> DC Response Source
Simple HTTP GET request.
simpleHeadHttp :: String -> DC Response Source
Simple HTTP HEAD request.
Exceptions
data HttpException :: *