{-# LANGUAGE OverloadedStrings #-}
{-# LANGUAGE FlexibleContexts #-}
{-# LANGUAGE ConstraintKinds #-}
module Test.Hspec.Wai (
WaiSession
, WaiExpectation
, get
, post
, put
, patch
, options
, delete
, request
, postHtmlForm
, shouldRespondWith
, ResponseMatcher(..)
, MatchHeader(..)
, MatchBody(..)
, Body
, (<:>)
, liftIO
, with
, withState
, getState
, pending
, pendingWith
) where
import Prelude ()
import Prelude.Compat
import Data.Foldable
import Data.ByteString (ByteString)
import qualified Data.ByteString.Lazy as LB
import Control.Monad.IO.Class
import Control.Monad.Trans.Class (lift)
import Network.Wai (Request(..))
import Network.HTTP.Types
import Network.Wai.Test hiding (request)
import qualified Network.Wai.Test as Wai
import Test.Hspec.Expectations
import Test.Hspec.Core.Spec hiding (pending, pendingWith)
import qualified Test.Hspec.Core.Spec as Core
import Test.Hspec.Core.Hooks
import Test.Hspec.Wai.Util
import Test.Hspec.Wai.Internal
import Test.Hspec.Wai.Matcher
import Network.Wai (Application)
with :: IO Application -> SpecWith ((), Application) -> Spec
with :: IO Application -> SpecWith ((), Application) -> Spec
with IO Application
action = IO ((), Application) -> SpecWith ((), Application) -> Spec
forall a. IO a -> SpecWith a -> Spec
before ((,) () (Application -> ((), Application))
-> IO Application -> IO ((), Application)
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> IO Application
action)
withState :: IO (st, Application) -> SpecWith (st, Application) -> Spec
withState :: forall st.
IO (st, Application) -> SpecWith (st, Application) -> Spec
withState = IO (st, Application) -> SpecWith (st, Application) -> Spec
forall a. IO a -> SpecWith a -> Spec
before
pending :: WaiSession st ()
pending :: forall st. WaiSession st ()
pending = IO () -> WaiSession st ()
forall (m :: * -> *) a. MonadIO m => IO a -> m a
liftIO IO ()
HasCallStack => IO ()
Core.pending
pendingWith :: String -> WaiSession st ()
pendingWith :: forall st. String -> WaiSession st ()
pendingWith = IO () -> WaiSession st ()
forall (m :: * -> *) a. MonadIO m => IO a -> m a
liftIO (IO () -> WaiSession st ())
-> (String -> IO ()) -> String -> WaiSession st ()
forall b c a. (b -> c) -> (a -> b) -> a -> c
. HasCallStack => String -> IO ()
String -> IO ()
Core.pendingWith
shouldRespondWith :: HasCallStack => WaiSession st SResponse -> ResponseMatcher -> WaiExpectation st
shouldRespondWith :: forall st.
HasCallStack =>
WaiSession st SResponse -> ResponseMatcher -> WaiExpectation st
shouldRespondWith WaiSession st SResponse
action ResponseMatcher
matcher = do
SResponse
r <- WaiSession st SResponse
action
Maybe String -> (String -> WaiExpectation st) -> WaiExpectation st
forall (t :: * -> *) (m :: * -> *) a b.
(Foldable t, Monad m) =>
t a -> (a -> m b) -> m ()
forM_ (SResponse -> ResponseMatcher -> Maybe String
match SResponse
r ResponseMatcher
matcher) (IO () -> WaiExpectation st
forall (m :: * -> *) a. MonadIO m => IO a -> m a
liftIO (IO () -> WaiExpectation st)
-> (String -> IO ()) -> String -> WaiExpectation st
forall b c a. (b -> c) -> (a -> b) -> a -> c
. HasCallStack => String -> IO ()
String -> IO ()
expectationFailure)
get :: ByteString -> WaiSession st SResponse
get :: forall st. ByteString -> WaiSession st SResponse
get ByteString
path = ByteString
-> ByteString -> [Header] -> ByteString -> WaiSession st SResponse
forall st.
ByteString
-> ByteString -> [Header] -> ByteString -> WaiSession st SResponse
request ByteString
methodGet ByteString
path [] ByteString
""
post :: ByteString -> LB.ByteString -> WaiSession st SResponse
post :: forall st. ByteString -> ByteString -> WaiSession st SResponse
post ByteString
path = ByteString
-> ByteString -> [Header] -> ByteString -> WaiSession st SResponse
forall st.
ByteString
-> ByteString -> [Header] -> ByteString -> WaiSession st SResponse
request ByteString
methodPost ByteString
path []
put :: ByteString -> LB.ByteString -> WaiSession st SResponse
put :: forall st. ByteString -> ByteString -> WaiSession st SResponse
put ByteString
path = ByteString
-> ByteString -> [Header] -> ByteString -> WaiSession st SResponse
forall st.
ByteString
-> ByteString -> [Header] -> ByteString -> WaiSession st SResponse
request ByteString
methodPut ByteString
path []
patch :: ByteString -> LB.ByteString -> WaiSession st SResponse
patch :: forall st. ByteString -> ByteString -> WaiSession st SResponse
patch ByteString
path = ByteString
-> ByteString -> [Header] -> ByteString -> WaiSession st SResponse
forall st.
ByteString
-> ByteString -> [Header] -> ByteString -> WaiSession st SResponse
request ByteString
methodPatch ByteString
path []
options :: ByteString -> WaiSession st SResponse
options :: forall st. ByteString -> WaiSession st SResponse
options ByteString
path = ByteString
-> ByteString -> [Header] -> ByteString -> WaiSession st SResponse
forall st.
ByteString
-> ByteString -> [Header] -> ByteString -> WaiSession st SResponse
request ByteString
methodOptions ByteString
path [] ByteString
""
delete :: ByteString -> WaiSession st SResponse
delete :: forall st. ByteString -> WaiSession st SResponse
delete ByteString
path = ByteString
-> ByteString -> [Header] -> ByteString -> WaiSession st SResponse
forall st.
ByteString
-> ByteString -> [Header] -> ByteString -> WaiSession st SResponse
request ByteString
methodDelete ByteString
path [] ByteString
""
request :: Method -> ByteString -> [Header] -> LB.ByteString -> WaiSession st SResponse
request :: forall st.
ByteString
-> ByteString -> [Header] -> ByteString -> WaiSession st SResponse
request ByteString
method ByteString
path [Header]
headers = ReaderT st (ReaderT Application (StateT ClientState IO)) SResponse
-> WaiSession st SResponse
forall st a.
ReaderT st (ReaderT Application (StateT ClientState IO)) a
-> WaiSession st a
WaiSession (ReaderT st (ReaderT Application (StateT ClientState IO)) SResponse
-> WaiSession st SResponse)
-> (ByteString
-> ReaderT
st (ReaderT Application (StateT ClientState IO)) SResponse)
-> ByteString
-> WaiSession st SResponse
forall b c a. (b -> c) -> (a -> b) -> a -> c
. ReaderT Application (StateT ClientState IO) SResponse
-> ReaderT
st (ReaderT Application (StateT ClientState IO)) SResponse
forall (t :: (* -> *) -> * -> *) (m :: * -> *) a.
(MonadTrans t, Monad m) =>
m a -> t m a
lift (ReaderT Application (StateT ClientState IO) SResponse
-> ReaderT
st (ReaderT Application (StateT ClientState IO)) SResponse)
-> (ByteString
-> ReaderT Application (StateT ClientState IO) SResponse)
-> ByteString
-> ReaderT
st (ReaderT Application (StateT ClientState IO)) SResponse
forall b c a. (b -> c) -> (a -> b) -> a -> c
. SRequest -> ReaderT Application (StateT ClientState IO) SResponse
Wai.srequest (SRequest -> ReaderT Application (StateT ClientState IO) SResponse)
-> (ByteString -> SRequest)
-> ByteString
-> ReaderT Application (StateT ClientState IO) SResponse
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Request -> ByteString -> SRequest
SRequest Request
req
where
req :: Request
req = Request -> ByteString -> Request
setPath Request
defaultRequest {requestMethod :: ByteString
requestMethod = ByteString
method, requestHeaders :: [Header]
requestHeaders = [Header]
headers} ByteString
path
postHtmlForm :: ByteString -> [(String, String)] -> WaiSession st SResponse
postHtmlForm :: forall st.
ByteString -> [(String, String)] -> WaiSession st SResponse
postHtmlForm ByteString
path = ByteString
-> ByteString -> [Header] -> ByteString -> WaiSession st SResponse
forall st.
ByteString
-> ByteString -> [Header] -> ByteString -> WaiSession st SResponse
request ByteString
methodPost ByteString
path [(HeaderName
hContentType, ByteString
"application/x-www-form-urlencoded")] (ByteString -> WaiSession st SResponse)
-> ([(String, String)] -> ByteString)
-> [(String, String)]
-> WaiSession st SResponse
forall b c a. (b -> c) -> (a -> b) -> a -> c
. [(String, String)] -> ByteString
formUrlEncodeQuery