warp-tlsでSSL Testの評価をA+にする
warp-tlsでそのままwebサーバを立てるとSSL Server Testで評価がAとなる.
評価をA+にするにはHTTPヘッダにHSTS(HTTP Strict Transport Security)を追加すればいい.
コード
{-# LANGUAGE OverloadedStrings #-}
module Lib
( runService
) where
-- wai
import Network.Wai
( Application
, responseLBS
)
-- http-types
import Network.HTTP.Types
( status200
, hContentType
, Header
, ResponseHeaders
)
-- warp
import Network.Wai.Handler.Warp
( setServerName
, setPort
, defaultSettings
, Settings
, runSettings
, Port
)
-- warp-tls
import Network.Wai.Handler.WarpTLS
( tlsSettingsChain
, runTLS
, defaultTlsSettings
)
-- base
import Control.Concurrent(forkIO)
hstsHeader :: Header
hstsHeader = (s, t)
where s = "Strict-Transport-Security"
t = "max-age=63072000; includeSubdomains; preload"
htmlHeaders :: ResponseHeaders
htmlHeaders = [ (hContentType, "text/html"), hstsHeader ]
app :: Application
app req f = f $ responseLBS status200 htmlHeaders s
where s = "<!DOCTYPE html>\n<html><body>Hello, world</body></html>"
settings :: Port -> Settings
settings port = setServerName "Warp" $ setPort port defaultSettings
runService :: IO ()
runService = do
forkIO $ runSettings (settings 80) app
runTLS tlsSettings'' (settings 443) app
where tlsSettings'' = tlsSettingsChain cert chain privkey
cert = "/etc/letsencrypt/live/example.com/cert.pem"
chain = ["/etc/letsencrypt/live/example.com/chain.pem"]
privkey = "/etc/letsencrypt/live/example.com/privkey.pem"
解説
HSTSヘッダとしてhstsHeader
を書いた.
responseLBS
で指定するヘッダに追加することでHSTSヘッダを送るようにしている.
参考文献
- wai
- warp
- warp-tls
- HSTS