breve/src/Breve/Settings.hs

77 lines
2.5 KiB
Haskell

{-|
This module defines the Breve configuration
parser and application settings.
-}
module Breve.Settings
( AppSettings(..)
, createEmptyIfMissing
, settings
) where
import Paths_breve (getDataFileName)
import Control.Monad (when)
import System.Environment (lookupEnv)
import System.Directory (doesFileExist, getXdgDirectory, XdgDirectory(..))
import Data.Text (Text, pack)
import Data.Configurator
import Data.Monoid
import Network.Wai.Handler.WarpTLS (TLSSettings (..), tlsSettingsChain)
import Network.TLS (Version (..))
import Network.TLS.Extra (ciphersuite_strong)
-- | Breve settings
data AppSettings = AppSettings
{ bindHost :: Text -- ^ the host to bind to
, bindPort :: Int -- ^ the port to bind to
, bindUrl :: Text -- ^ the url used to reach breve
, urlTable :: FilePath -- ^ path where to save the url table
, staticDir :: FilePath -- ^ path of the static assets
, tlsSettings :: TLSSettings -- ^ warp TLS settings
}
-- | Initialises a file if it doesn't exist
createEmptyIfMissing :: FilePath -> IO ()
createEmptyIfMissing file = do
exists <- doesFileExist file
when (not exists) (writeFile file "")
-- | Configuration file parser
settings :: Maybe FilePath -> IO AppSettings
settings path = do
configPath <- case path of
Just path -> return path
Nothing -> getXdgDirectory XdgConfig "breve"
urlsPath <- getXdgDirectory XdgData "breve"
config <- load [Required configPath]
host <- lookupDefault "localhost" config "hostname"
portnum <- lookupDefault 3000 config "port"
urls <- lookupDefault urlsPath config "urltable"
cert <- lookupDefault "/usr/share/tls/breve.crt" config "tls.cert"
key <- lookupDefault "/usr/share/tls/breve.key" config "tls.key"
chain <- lookupDefault [] config "tls.chain"
let
port = if portnum == 443 then "" else ":" <> pack (show portnum)
url = "https://" <> host <> port <> "/"
baseURL <- lookupDefault url config "baseurl"
static <- getDataFileName "static/"
createEmptyIfMissing urls
return AppSettings
{ bindHost = host
, bindPort = portnum
, bindUrl = baseURL
, urlTable = urls
, staticDir = static
, tlsSettings = (tlsSettingsChain cert chain key)
{ tlsAllowedVersions = [TLS12, TLS11]
, tlsCiphers = ciphersuite_strong
}
}