{-# LANGUAGE OverloadedStrings, LambdaCase #-} module Config ( Config(..), getConfig, makeOpenSearch ) where import Prelude hiding (lookup) import Control.Applicative ((<|>)) import Data.Aeson.KeyMap (empty, lookup) import Data.Functor ((<&>)) import Data.Maybe (fromMaybe) import Data.String (fromString, IsString) import Data.Text (Text) import Data.Yaml import Network.Wai.Handler.Warp (HostPreference) import System.Environment (lookupEnv) data Config = Config { confPort :: Int, confHost :: HostPreference, confBaseUrl :: Text, confFavicon :: Text, confUser :: Text, confPwHash :: Text } deriving (Show, Eq) getConfig :: IO Config getConfig = do confFile <- decodeFileEither "fastbangs.yaml" <&> \case Right ob -> ob Left _ -> empty Config <$> (read <$> resolveVal (lookup "port" confFile) "PORT" "20546") <*> resolveVal (lookup "bind-addr" confFile) "BIND_ADDR" "*6" <*> resolveVal (lookup "base-url" confFile) "BASE_URL" "http://localhost:20546" <*> resolveVal (lookup "favicon-url" confFile) "FAVICON_URL" "" <*> resolveVal (lookup "admin-user" confFile) "ADMIN_USER" "bleb" <*> resolveVal (lookup "admin-pw-hash" confFile) "ADMIN_PW_HASH" "" -- prevent login without manual pw where resolveVal :: IsString s => Maybe String -> String -> String -> IO s resolveVal mayConf q def = do mayEnv <- lookupEnv q return $ fromString $ fromMaybe def $ mayEnv <|> mayConf makeOpenSearch :: Config -> Maybe Text -> Text makeOpenSearch cfg defBang = " " xmlns:moz=\"http://www.mozilla.org/2006/browser/search/\">\n" <> " " <> name <> "\n" <> " Handles search bangs (mostly) locally.\n" <> " UTF-8\n" <> " " <> confFavicon cfg <> "\n" <> " searchUrl <> "\"/>\n" <> "\n" where (searchUrl, name) = case defBang of Nothing -> (confBaseUrl cfg <> "/#{searchTerms}", "FastBangs") Just b -> (confBaseUrl cfg <> "/#" <> b <> "#{searchTerms}", "FastBangs (" <> b <> ")")