#if __GLASGOW_HASKELL__>=708
#endif
module Configuration.Utils.Http
(
HttpServiceTLSConfiguration
, hstcCertFile
, hstcKeyFile
, defaultHttpServiceTLSConfiguration
, pHttpServiceTLSConfiguration
, validateHttpServiceTLSConfiguration
, HttpServiceConfiguration
, hscHost
, hscPort
, hscUseTLS
, defaultHttpServiceConfiguration
, pHttpServiceConfiguration
, validateHttpServiceConfiguration
, HttpClientConfiguration
, hccHost
, hccPort
, hccUseTLS
, defaultHttpClientConfiguration
, pHttpClientConfiguration
, validateHttpClientConfiguration
, httpService2clientConfiguration
) where
import Configuration.Utils
import Configuration.Utils.Internal
import Configuration.Utils.Validation
import Control.Monad (when)
#if __GLASGOW_HASKELL__>=708
import Control.Monad.Writer.Class (tell)
#endif
import qualified Data.ByteString.Char8 as B8
import qualified Data.DList as DL
import Data.Maybe (isJust)
import Data.Monoid.Unicode
import Prelude.Unicode
data HttpServiceTLSConfiguration = HttpServiceTLSConfiguration
{ _hstcCertFile ∷ !FilePath
, _hstcKeyFile ∷ !FilePath
}
deriving (Show, Read, Eq, Ord)
hstcCertFile ∷ Lens' HttpServiceTLSConfiguration FilePath
hstcCertFile = lens _hstcCertFile $ \s a → s { _hstcCertFile = a}
hstcKeyFile ∷ Lens' HttpServiceTLSConfiguration FilePath
hstcKeyFile = lens _hstcKeyFile $ \s a → s { _hstcKeyFile = a}
defaultHttpServiceTLSConfiguration ∷ HttpServiceTLSConfiguration
defaultHttpServiceTLSConfiguration = HttpServiceTLSConfiguration
{ _hstcCertFile = "cert.pem"
, _hstcKeyFile = "key.pem"
}
validateHttpServiceTLSConfiguration
∷ ConfigValidation HttpServiceTLSConfiguration λ
validateHttpServiceTLSConfiguration conf = do
validateFileReadable "cert-file" $ _hstcCertFile conf
validateFileReadable "key-file" $ _hstcKeyFile conf
instance FromJSON (HttpServiceTLSConfiguration → HttpServiceTLSConfiguration) where
parseJSON = withObject "HttpServiceTLSConfiguration" $ \o → id
<$< hstcCertFile ..: "cert-file" × o
<*< hstcKeyFile ..: "pem-file" × o
instance FromJSON HttpServiceTLSConfiguration where
parseJSON v = parseJSON v <*> pure defaultHttpServiceTLSConfiguration
instance ToJSON HttpServiceTLSConfiguration where
toJSON HttpServiceTLSConfiguration{..} = object
[ "cert-file" .= _hstcCertFile
, "key-file" .= _hstcKeyFile
]
pHttpServiceTLSConfiguration ∷ String → MParser HttpServiceTLSConfiguration
pHttpServiceTLSConfiguration prefix = id
<$< hstcCertFile .:: strOption
× long (prefix ⊕ "cert-file")
⊕ help "File with PEM encoded TLS Certificate"
<*< hstcKeyFile .:: strOption
× long (prefix ⊕ "key-file")
⊕ help "File with PEM encoded TLS key"
data HttpServiceConfiguration = HttpServiceConfiguration
{ _hscHost ∷ !B8.ByteString
, _hscPort ∷ !Int
, _hscInterface ∷ !B8.ByteString
, _hscUseTLS ∷ !(Maybe HttpServiceTLSConfiguration)
}
deriving (Show, Read, Eq, Ord)
hscHost ∷ Lens' HttpServiceConfiguration B8.ByteString
hscHost = lens _hscHost $ \s a → s { _hscHost = a}
hscPort ∷ Lens' HttpServiceConfiguration Int
hscPort = lens _hscPort $ \s a → s { _hscPort = a}
hscInterface ∷ Lens' HttpServiceConfiguration B8.ByteString
hscInterface = lens _hscInterface $ \s a → s { _hscInterface = a}
hscUseTLS ∷ Lens' HttpServiceConfiguration (Maybe HttpServiceTLSConfiguration)
hscUseTLS = lens _hscUseTLS $ \s a → s { _hscUseTLS = a}
defaultHttpServiceConfiguration ∷ HttpServiceConfiguration
defaultHttpServiceConfiguration = HttpServiceConfiguration
{ _hscHost = "localhost"
, _hscPort = 80
, _hscInterface = "0.0.0.0"
, _hscUseTLS = Nothing
}
validateHttpServiceConfiguration ∷ ConfigValidation HttpServiceConfiguration DL.DList
validateHttpServiceConfiguration conf = do
maybe (return ()) validateHttpServiceTLSConfiguration $ _hscUseTLS conf
validatePort "port" $ _hscPort conf
#if __GLASGOW_HASKELL__>=708
when (_hscPort conf < 1024) $
tell ["listening on a priviledged port requires super user rights"]
#endif
validateNonEmpty "host" $ _hscHost conf
validateIPv4 "interface" . B8.unpack $ _hscInterface conf
instance FromJSON (HttpServiceConfiguration → HttpServiceConfiguration) where
parseJSON = withObject "HttpServiceConfiguration" $ \o → id
<$< hscHost ∘ bs ..: "host" × o
<*< hscPort ..: "port" × o
<*< hscInterface ∘ bs ..: "interface" × o
<*< hscUseTLS %.: "use-tls" × o
where
bs ∷ Iso' B8.ByteString String
bs = iso B8.unpack B8.pack
instance ToJSON HttpServiceConfiguration where
toJSON HttpServiceConfiguration{..} = object
[ "host" .= B8.unpack _hscHost
, "port" .= _hscPort
, "interface" .= B8.unpack _hscInterface
, "use-tls" .= _hscUseTLS
]
pHttpServiceConfiguration ∷ String → MParser HttpServiceConfiguration
pHttpServiceConfiguration prefix = id
<$< hscHost ∘ bs .:: strOption
× long (prefix ⊕ "host")
⊕ help "Hostname of the service"
<*< hscPort .:: option auto
× long (prefix ⊕ "port")
⊕ help "Port of the service"
<*< hscInterface ∘ bs .:: option auto
× long (prefix ⊕ "interface")
⊕ help "Interface of the service"
<*< (hscUseTLS %:: (fmap <$> pHttpServiceTLSConfiguration prefix))
where
bs ∷ Iso' B8.ByteString String
bs = iso B8.unpack B8.pack
data HttpClientConfiguration = HttpClientConfiguration
{ _hccHost ∷ !B8.ByteString
, _hccPort ∷ !Int
, _hccUseTLS ∷ !Bool
}
deriving (Show, Read, Eq, Ord)
hccHost ∷ Lens' HttpClientConfiguration B8.ByteString
hccHost = lens _hccHost $ \s a → s { _hccHost = a}
hccPort ∷ Lens' HttpClientConfiguration Int
hccPort = lens _hccPort $ \s a → s { _hccPort = a}
hccUseTLS ∷ Lens' HttpClientConfiguration Bool
hccUseTLS = lens _hccUseTLS $ \s a → s { _hccUseTLS = a}
defaultHttpClientConfiguration ∷ HttpClientConfiguration
defaultHttpClientConfiguration = HttpClientConfiguration
{ _hccHost = "localhost"
, _hccPort = 80
, _hccUseTLS = False
}
validateHttpClientConfiguration ∷ ConfigValidation HttpClientConfiguration λ
validateHttpClientConfiguration conf = do
validatePort "port" $ _hccPort conf
validateNonEmpty "host" $ _hccHost conf
instance FromJSON (HttpClientConfiguration → HttpClientConfiguration) where
parseJSON = withObject "HttpClientConfiguration" $ \o → id
<$< hccHost ∘ bs ..: "host" × o
<*< hccPort ..: "port" × o
<*< hccUseTLS ..: "use-tls" × o
where
bs ∷ Iso' B8.ByteString String
bs = iso B8.unpack B8.pack
instance ToJSON HttpClientConfiguration where
toJSON HttpClientConfiguration{..} = object
[ "host" .= B8.unpack _hccHost
, "port" .= _hccPort
, "use-tls" .= _hccUseTLS
]
pHttpClientConfiguration ∷ String → MParser HttpClientConfiguration
pHttpClientConfiguration serviceName = id
<$< hccHost ∘ bs .:: strOption
× long (serviceName ⊕ "-host")
⊕ help ("Hostname of " ⊕ serviceName)
<*< hccPort .:: option auto
× long (serviceName ⊕ "-port")
⊕ help ("Port of " ⊕ serviceName)
<*< hccUseTLS .:: switch
× long (serviceName ⊕ "-use-tls")
⊕ help ("Connect to " ⊕ serviceName ⊕ " via TLS")
where
bs ∷ Iso' B8.ByteString String
bs = iso B8.unpack B8.pack
httpService2clientConfiguration ∷ HttpServiceConfiguration → HttpClientConfiguration
httpService2clientConfiguration HttpServiceConfiguration{..} = HttpClientConfiguration
{ _hccHost = _hscHost
, _hccPort = _hscPort
, _hccUseTLS = isJust _hscUseTLS
}