line-2.0.0.0: test/Line/Messaging/WebhookSpec.hs
module Line.Messaging.WebhookSpec where
import Test.Hspec
import Test.Hspec.Wai
import Control.Monad.Trans.Except (runExceptT)
import Crypto.Hash.SHA256 (hmaclazy)
import Data.Either (isRight)
import Data.Text.Encoding (encodeUtf8)
import Line.Messaging.Webhook
import qualified Data.ByteString.Lazy as BL
import qualified Data.ByteString.Base64 as Base64
import qualified Web.Scotty as Scotty
emptyBody :: BL.ByteString
emptyBody = "{ \"events\": [] }"
wrongBody :: BL.ByteString
wrongBody = "{ \"event\": [] }"
createSig :: ChannelSecret -> BL.ByteString -> Signature
createSig sec body = Base64.encode $ hmaclazy (encodeUtf8 sec) body
spec :: Spec
spec = do
describe "Basic webhook" $ do
it "right result" $ do
let secret = "some-secret"
sig = createSig secret emptyBody
result <- runExceptT $ webhook secret emptyBody sig
result `shouldSatisfy` isRight
it "wrong sig" $ do
let secret = "some-secret"
sig = "wrong-sig"
result <- runExceptT $ webhook secret emptyBody sig
result `shouldBe` Left SignatureVerificationFailed
it "malformed body" $ do
let secret = "some-secret"
sig = createSig secret wrongBody
result <- runExceptT $ webhook secret wrongBody sig
result `shouldBe` Left MessageDecodeFailed
describe "WAI webhook" $
let waiApp = return $ webhookApp "some-secret" (const $ return ()) defaultOnFailure
webhookReq sec body hasCorrectSig = request "GET" "/" headers body
where
sig = if hasCorrectSig then createSig sec body else "wrong sig"
headers = [ ("X-Line-Signature", sig) ]
in with waiApp $ do
it "handle req well" $ do
webhookReq "some-secret" emptyBody True `shouldRespondWith` 200
it "with wrong sig" $ do
webhookReq "some-secret" emptyBody False `shouldRespondWith`
"SignatureVerificationFailed" { matchStatus = 400 }
it "malformed body" $ do
webhookReq "some-secret" wrongBody True `shouldRespondWith`
"MessageDecodeFailed" { matchStatus = 400 }
describe "Scotty webhook" $
let waiApp = Scotty.scottyApp $
Scotty.get "/" $ webhookAction "some-secret" (const $ return ()) defaultOnFailure'
webhookReq sec body hasCorrectSig = request "GET" "/" headers body
where
sig = if hasCorrectSig then createSig sec body else "wrong sig"
headers = [ ("X-Line-Signature", sig) ]
in with waiApp $ do
it "handle req well" $ do
webhookReq "some-secret" emptyBody True `shouldRespondWith` 200
it "with wrong sig" $ do
webhookReq "some-secret" emptyBody False `shouldRespondWith`
"SignatureVerificationFailed" { matchStatus = 400 }
it "malformed body" $ do
webhookReq "some-secret" wrongBody True `shouldRespondWith`
"MessageDecodeFailed" { matchStatus = 400 }