packages feed

yesod-csp 0.2.6.0 → 0.2.7.0

raw patch · 5 files changed

+59/−5 lines, 5 filesdep +mimePVP ok

version bump matches the API change (PVP)

Dependencies added: mime

API changes (from Hackage documentation)

+ Yesod.Csp: BaseUri :: EscapedURI -> Directive
+ Yesod.Csp: ChildSrc :: SourceList -> Directive
+ Yesod.Csp: FormAction :: SourceList -> Directive
+ Yesod.Csp: PluginTypes :: MimeTypeList -> Directive
+ Yesod.Csp: instance Data.Data.Data Codec.MIME.Type.MIMEParam
+ Yesod.Csp: instance Data.Data.Data Codec.MIME.Type.MIMEType
+ Yesod.Csp: instance Data.Data.Data Codec.MIME.Type.Multipart
+ Yesod.Csp: instance Data.Data.Data Codec.MIME.Type.Type
+ Yesod.Csp.TH: pluginTypes :: Parser Directive

Files

CHANGELOG.md view
@@ -1,5 +1,9 @@ # Changelog +## Version 0.2.7.0+++ Add support for remaining CSP Level 2 directives (see https://github.com/pSub/yesod-csp/pull/5)+ ## Version 0.2.6.0  + Fixes compilation failure with ghc-9.0.2 or newer (see https://github.com/bobjflong/yesod-csp/issues/8)
src/Yesod/Csp.hs view
@@ -1,3 +1,4 @@+{-# LANGUAGE StandaloneDeriving #-} {-# LANGUAGE DeriveDataTypeable #-} {-# LANGUAGE OverloadedStrings  #-} -- | Add <http://content-security-policy.com/ CSP> headers to Yesod apps.@@ -18,6 +19,7 @@   , textSource   ) where +import           Codec.MIME.Type as Mime import qualified Data.CaseInsensitive as CI import           Data.Data          (Data) import           Data.List.NonEmpty@@ -140,6 +142,12 @@ textSource (MetaSource _) = "" textSource (Nonce x) = (T.pack . show) x +deriving instance Data Multipart+deriving instance Data Mime.MIMEType+deriving instance Data Mime.MIMEParam+deriving instance Data Mime.Type+type MimeTypeList = NonEmpty Mime.Type+ -- | A list of restrictions to apply. type DirectiveList = [Directive] @@ -154,11 +162,18 @@                  | ObjectSrc SourceList                  | MediaSrc SourceList                  | FrameSrc SourceList-                 | FrameAncestors SourceList                  -- | Applies a sandbox to the result. <http://content-security-policy.com/ See here> for more info.                  | Sandbox [SandboxOptions]-                 | ReportUri EscapedURI deriving (Eq, Show, Data, Typeable)+                 | ReportUri EscapedURI+                 -- | CSP level 2 directives+                 | FrameAncestors SourceList+                 | ChildSrc SourceList+                 | FormAction SourceList+                 | BaseUri EscapedURI+                 | PluginTypes MimeTypeList+                 deriving (Eq, Show, Data, Typeable) + -- | Configuration options for the sandbox. data SandboxOptions = AllowForms                       | AllowScripts@@ -175,7 +190,6 @@ textDirective (ObjectSrc x) =  w "object-src" x textDirective (MediaSrc x) =  w "media-src" x textDirective (FrameSrc x) =  w "frame-src" x-textDirective (FrameAncestors x) =  w "frame-ancestors" x textDirective (ReportUri t) = mconcat ["report-uri ", (T.pack . show) t] textDirective (Sandbox []) = "sandbox" textDirective (Sandbox s) = mconcat ["sandbox ", T.unwords . fmap textSandbox $ s]@@ -183,3 +197,8 @@         textSandbox AllowScripts = "allow-scripts"         textSandbox AllowSameOrigin = "allow-same-origin"         textSandbox AllowTopNavigation = "allow-top-navigation"+textDirective (FrameAncestors x) =  w "frame-ancestors" x+textDirective (ChildSrc x) = w "child-src" x+textDirective (FormAction x) = w "form-action" x+textDirective (BaseUri t) = mconcat ["base-uri ", (T.pack . show) t]+textDirective (PluginTypes t) = mconcat ["plugin-types ", (T.unwords . fmap Mime.showType . toList) t]
src/Yesod/Csp/TH.hs view
@@ -4,12 +4,14 @@     source     , withSourceList     , reportUri+    , pluginTypes     , sandbox     , sandboxOptions     , directive     , csp   ) where +import           Codec.MIME.Parse          (parseMIMEType) import           Control.Applicative import           Data.Attoparsec.Text import           Data.Generics@@ -106,6 +108,8 @@                  <|> mediaSrc                  <|> frameSrc                  <|> frameAncestors+                 <|> childSrc+                 <|> formAction   where defaultSrc = d "default-src" DefaultSrc         scriptSrc = d "script-src" ScriptSrc         styleSrc = d "style-src" StyleSrc@@ -116,6 +120,8 @@         mediaSrc = d "media-src" MediaSrc         frameSrc = d "frame-src" FrameSrc         frameAncestors = d "frame-ancestors" FrameAncestors+        childSrc = d "child-src" ChildSrc+        formAction = d "form-action" FormAction         d x y = string x >> s >> slist >>= mkWithSource y         slist = sepBy1 source (char ' ')         s = spaces@@ -132,6 +138,24 @@     Nothing -> fail "reportUri" -- n.b. compile time error     Just uri -> return $ ReportUri uri +baseUri :: Parser Directive+baseUri = do+  _ <- string "base-uri"+  _ <- spaces+  u <- takeTill separated+  case escapeAndParseURI u of+    Nothing -> fail "baseUri" -- n.b. compile time error+    Just uri -> return $ BaseUri uri++pluginTypes :: Parser Directive+pluginTypes = do+  _ <- string "plugin-types"+  _ <- spaces+  u <- takeTill separated+  case parseMIMEType u of+    Nothing -> fail "plugin-types" -- n.b. compile time error+    Just mimeType -> return $ PluginTypes $ pure mimeType+ sandbox :: Parser Directive sandbox = do   _ <- string "sandbox"@@ -155,4 +179,4 @@  directive :: Parser DirectiveList directive = sepBy (spaces *> d) separator <* (spaces *> endOfInput)-  where d = withSourceList <|> reportUri <|> sandbox+  where d = withSourceList <|> reportUri <|> baseUri <|> pluginTypes <|> sandbox
test/Test.hs view
@@ -4,6 +4,7 @@ {-# LANGUAGE TemplateHaskell       #-} {-# LANGUAGE TypeFamilies          #-} +import           Codec.MIME.Parse          (parseMIMEType) import           Data.Attoparsec.Text import           Data.Functor         ((<$>)) import           Data.List.NonEmpty@@ -57,6 +58,10 @@     yit "enforces nones" $ do       let header = getCspPolicy [ScriptSrc (None :| [Https])]       assertEq "none should be alone" header "script-src 'none'"+    yit "works with plugin-types" $ do+      let dom = pure $ fromJust $ parseMIMEType "text/plain"+          header = getCspPolicy [PluginTypes dom]+      assertEq "plugin-types" header "plugin-types text/plain"   ydescribe "Headers" $     yit "get set" $ do       get HomeR
yesod-csp.cabal view
@@ -2,7 +2,7 @@ -- documentation, see http://haskell.org/cabal/users-guide/  name:                yesod-csp-version:             0.2.6.0+version:             0.2.7.0 synopsis:            Add CSP headers to Yesod apps description:         Add CSP headers to Yesod apps. This helps reduce exposure to XSS attacks and bad assets. license:             MIT@@ -35,6 +35,7 @@                        , syb >= 0.7.2 && < 0.8                        , wai >= 3.2.3 && < 3.3                        , case-insensitive >= 1.2.1 && < 1.3+                       , mime >= 0.4.0.0 && < 0.5   hs-source-dirs:      src   default-language:    Haskell2010   ghc-options:         -Wall@@ -53,4 +54,5 @@                        , network-uri                        , attoparsec                        , template-haskell+                       , mime   default-language:    Haskell2010