Skip to content

Commit

Permalink
Merge pull request #1200 from MaxGabriel/logCSRFErrors
Browse files Browse the repository at this point in the history
Log a warning when a CSRF error occurs
  • Loading branch information
MaxGabriel committed Mar 29, 2016
2 parents f35c0c6 + 5a5cfd6 commit 09087c9
Show file tree
Hide file tree
Showing 3 changed files with 11 additions and 4 deletions.
4 changes: 4 additions & 0 deletions yesod-core/ChangeLog.md
Original file line number Diff line number Diff line change
@@ -1,3 +1,7 @@
## 1.4.20.1

* Log a warning when a CSRF error occurs [#1200](https://github.com/yesodweb/yesod/pull/1200)

## 1.4.20

* `addMessage`, `addMessageI`, and `getMessages` functions
Expand Down
9 changes: 6 additions & 3 deletions yesod-core/Yesod/Core/Handler.hs
Original file line number Diff line number Diff line change
Expand Up @@ -252,6 +252,7 @@ import qualified Yesod.Core.TypeCache as Cache
import qualified Data.Word8 as W8
import qualified Data.Foldable as Fold
import Data.Default
import Control.Monad.Logger (MonadLogger, logWarnS)

get :: MonadHandler m => m GHState
get = liftHandlerT $ HandlerT $ I.readIORef . handlerState
Expand Down Expand Up @@ -1439,14 +1440,16 @@ hasValidCsrfParamNamed paramName = do
-- If the value doesn't match the token stored in the session, this function throws a 'PermissionDenied' error.
--
-- Since 1.4.14
checkCsrfHeaderOrParam :: MonadHandler m
checkCsrfHeaderOrParam :: (MonadHandler m, MonadLogger m)
=> CI S8.ByteString -- ^ The header name to lookup the CSRF token
-> Text -- ^ The POST parameter name to lookup the CSRF token
-> m ()
checkCsrfHeaderOrParam headerName paramName = do
validHeader <- hasValidCsrfHeaderNamed headerName
validParam <- hasValidCsrfParamNamed paramName
unless (validHeader || validParam) (permissionDenied csrfErrorMessage)
unless (validHeader || validParam) $ do
$logWarnS "yesod-core" csrfErrorMessage
permissionDenied csrfErrorMessage

validCsrf :: Maybe Text -> Maybe S.ByteString -> Bool
-- It's important to use constant-time comparison (constEqBytes) in order to avoid timing attacks.
Expand All @@ -1455,4 +1458,4 @@ validCsrf Nothing _param = True
validCsrf (Just _token) Nothing = False

csrfErrorMessage :: Text
csrfErrorMessage = "A valid CSRF token wasn't present in HTTP headers or POST parameters. Check the Yesod.Core.Handler docs of the yesod-core package for details on CSRF protection."
csrfErrorMessage = "A valid CSRF token wasn't present in HTTP headers or POST parameters. Because the request could have been forged, it's been rejected altogether. Check the Yesod.Core.Handler docs of the yesod-core package for details on CSRF protection."
2 changes: 1 addition & 1 deletion yesod-core/yesod-core.cabal
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
name: yesod-core
version: 1.4.20
version: 1.4.20.1
license: MIT
license-file: LICENSE
author: Michael Snoyman <michael@snoyman.com>
Expand Down

0 comments on commit 09087c9

Please sign in to comment.