mockcat 0.5.2.0 → 0.5.3.0
raw patch · 5 files changed
+68/−7 lines, 5 filesdep +asyncdep +unliftiodep +unliftio-coredep ~hspecdep ~template-haskellPVP: major bump suggested
API removals or changes: PVP suggests a major version bump
Dependencies added: async, unliftio, unliftio-core
Dependency ranges changed: hspec, template-haskell
API changes (from Hackage documentation)
+ Test.MockCat.MockT: instance Control.Monad.IO.Unlift.MonadUnliftIO m => Control.Monad.IO.Unlift.MonadUnliftIO (Test.MockCat.MockT.MockT m)
- Test.MockCat.Mock: createMock :: MockBuilder params fun verifyParams => MonadIO m => params -> m (Mock fun verifyParams)
+ Test.MockCat.Mock: createMock :: (MockBuilder params fun verifyParams, MonadIO m) => params -> m (Mock fun verifyParams)
- Test.MockCat.Mock: createNamedMock :: MockBuilder params fun verifyParams => MonadIO m => MockName -> params -> m (Mock fun verifyParams)
+ Test.MockCat.Mock: createNamedMock :: (MockBuilder params fun verifyParams, MonadIO m) => MockName -> params -> m (Mock fun verifyParams)
- Test.MockCat.Mock: createNamedStubFn :: MockBuilder params fun verifyParams => MonadIO m => String -> params -> m fun
+ Test.MockCat.Mock: createNamedStubFn :: (MockBuilder params fun verifyParams, MonadIO m) => String -> params -> m fun
- Test.MockCat.Mock: createStubFn :: MockBuilder params fun verifyParams => MonadIO m => params -> m fun
+ Test.MockCat.Mock: createStubFn :: (MockBuilder params fun verifyParams, MonadIO m) => params -> m fun
- Test.MockCat.Mock: shouldApplyTimes :: (VerifyCount countType params a, HasCallStack) => Eq params => Mock fun params -> countType -> a -> IO ()
+ Test.MockCat.Mock: shouldApplyTimes :: (VerifyCount countType params a, HasCallStack, Eq params) => Mock fun params -> countType -> a -> IO ()
- Test.MockCat.Mock: shouldApplyTimesGreaterThan :: VerifyCount CountVerifyMethod params a => Eq params => Mock fun params -> Int -> a -> IO ()
+ Test.MockCat.Mock: shouldApplyTimesGreaterThan :: (VerifyCount CountVerifyMethod params a, Eq params) => Mock fun params -> Int -> a -> IO ()
- Test.MockCat.Mock: shouldApplyTimesGreaterThanEqual :: VerifyCount CountVerifyMethod params a => Eq params => Mock fun params -> Int -> a -> IO ()
+ Test.MockCat.Mock: shouldApplyTimesGreaterThanEqual :: (VerifyCount CountVerifyMethod params a, Eq params) => Mock fun params -> Int -> a -> IO ()
- Test.MockCat.Mock: shouldApplyTimesLessThan :: VerifyCount CountVerifyMethod params a => Eq params => Mock fun params -> Int -> a -> IO ()
+ Test.MockCat.Mock: shouldApplyTimesLessThan :: (VerifyCount CountVerifyMethod params a, Eq params) => Mock fun params -> Int -> a -> IO ()
- Test.MockCat.Mock: shouldApplyTimesLessThanEqual :: VerifyCount CountVerifyMethod params a => Eq params => Mock fun params -> Int -> a -> IO ()
+ Test.MockCat.Mock: shouldApplyTimesLessThanEqual :: (VerifyCount CountVerifyMethod params a, Eq params) => Mock fun params -> Int -> a -> IO ()
- Test.MockCat.MockT: MockT :: StateT [Definition] m a -> MockT m a
+ Test.MockCat.MockT: MockT :: StateT [Definition] m a -> MockT (m :: Type -> Type) a
- Test.MockCat.MockT: [st] :: MockT m a -> StateT [Definition] m a
+ Test.MockCat.MockT: [st] :: MockT (m :: Type -> Type) a -> StateT [Definition] m a
- Test.MockCat.MockT: applyTimesIs :: Monad m => MockT m () -> Int -> MockT m ()
+ Test.MockCat.MockT: applyTimesIs :: forall (m :: Type -> Type). Monad m => MockT m () -> Int -> MockT m ()
- Test.MockCat.MockT: neverApply :: Monad m => MockT m () -> MockT m ()
+ Test.MockCat.MockT: neverApply :: forall (m :: Type -> Type). Monad m => MockT m () -> MockT m ()
- Test.MockCat.MockT: newtype MockT m a
+ Test.MockCat.MockT: newtype MockT (m :: Type -> Type) a
Files
- CHANGELOG.md +2/−1
- README.md +1/−0
- mockcat.cabal +10/−5
- src/Test/MockCat/MockT.hs +9/−1
- test/Test/MockCat/TypeClassTHSpec.hs +46/−0
CHANGELOG.md view
@@ -8,4 +8,5 @@ ## Unreleased -## 0.1.0.0 - YYYY-MM-DD+## 0.5.3.0+- Add: MockT now implements MonadUnliftIO
README.md view
@@ -17,6 +17,7 @@ <details> <summary>Update History</summary> +- **0.5.3.0**: MockT now implements MonadUnliftIO - **0.5.0**: Stub functions of type `IO a` can now return different values each time they are applied - **0.4.0**: Can make partial mocks of type classes. - **0.3.0**: Can make mocks of type classes.
mockcat.cabal view
@@ -5,7 +5,7 @@ -- see: https://github.com/sol/hpack name: mockcat-version: 0.5.2.0+version: 0.5.3.0 synopsis: Mock library for test in Haskell. description: mockcat is a flexible and powerful mock library. .@@ -55,9 +55,11 @@ build-depends: base >=4.7 && <5 , mtl >=2.3.1 && <2.4- , template-haskell >=2.18 && <2.23+ , template-haskell >=2.18 && <2.24 , text >=2.0 && <2.2 , transformers >=0.5.6 && <0.7+ , unliftio >=0.2.25.0 && <0.2.26+ , unliftio-core >=0.2.1.0 && <0.2.2 default-language: Haskell2010 test-suite mockcat-test@@ -80,11 +82,14 @@ test ghc-options: -Wall -Wcompat -Widentities -Wincomplete-record-updates -Wincomplete-uni-patterns -Wmissing-export-lists -Wmissing-home-modules -Wpartial-fields -Wredundant-constraints -fprint-potential-instances -threaded -rtsopts -with-rtsopts=-N build-depends:- base >=4.7 && <5- , hspec+ async >=2.2.4 && <2.3+ , base >=4.7 && <5+ , hspec ==2.11.* , mockcat , mtl >=2.3.1 && <2.4- , template-haskell >=2.18 && <2.23+ , template-haskell >=2.18 && <2.24 , text >=2.0 && <2.2 , transformers >=0.5.6 && <0.7+ , unliftio >=0.2.25.0 && <0.2.26+ , unliftio-core >=0.2.1.0 && <0.2.2 default-language: Haskell2010
src/Test/MockCat/MockT.hs view
@@ -6,14 +6,22 @@ {-# OPTIONS_GHC -Wno-name-shadowing #-} module Test.MockCat.MockT (MockT(..), Definition(..), runMockT, applyTimesIs, neverApply) where import Control.Monad.State- ( StateT(..), MonadIO(..), MonadTrans(..), modify, execStateT )+ ( StateT(..), MonadIO(..), MonadTrans(..), modify, execStateT, runStateT ) import GHC.TypeLits (KnownSymbol) import Data.Data (Proxy) import Test.MockCat.Mock (Mock, shouldApplyTimesToAnything) import Data.Foldable (for_)+import UnliftIO (MonadUnliftIO(..))+import Data.Functor ((<&>)) newtype MockT m a = MockT { st :: StateT [Definition] m a } deriving (Functor, Applicative, Monad, MonadTrans, MonadIO)++instance MonadUnliftIO m => MonadUnliftIO (MockT m) where+ withRunInIO inner = MockT $ StateT $ \s -> do+ a <- withRunInIO $ \runInIO ->+ inner (\(MockT m) -> runInIO (runStateT m s) <&> fst)+ pure (a, s) data Definition = forall f p sym. KnownSymbol sym => Definition { symbol :: Proxy sym,
test/Test/MockCat/TypeClassTHSpec.hs view
@@ -21,6 +21,8 @@ import Control.Monad.State import Control.Monad.Reader (MonadReader, ask) import Control.Monad (unless)+import Control.Monad.IO.Unlift (withRunInIO, MonadUnliftIO)+import Control.Concurrent.Async (async, wait) class Monad m => FileOperation m where writeFile :: FilePath -> Text -> m ()@@ -139,6 +141,15 @@ makeMockWithOptions [t|ExplicitlyReturnMonadicValuesTest|] options { implicitMonadicReturn = False } +class MonadUnliftIO m => MonadAsync m where+ mapConcurrently :: Traversable t => (a -> m b) -> t a -> m (t b)++instance (MonadUnliftIO m) => MonadAsync (MockT m) where+ mapConcurrently = traverse++processFiles :: MonadAsync m => FileOperation m => [FilePath] -> m [Text]+processFiles = mapConcurrently readFile+ spec :: Spec spec = do it "Read, and output files" do@@ -215,3 +226,38 @@ echoProgram "s" result `shouldBe` ()++ it "MonadUnliftIO instance works correctly" do+ result <- runMockT do+ _readFile ("test.txt" |> pack "content")++ content <- withRunInIO $ \runInIO -> do+ asyncAction <- async $ runInIO (readFile "test.txt")+ wait asyncAction++ liftIO $ content `shouldBe` pack "content"+ pure content++ result `shouldBe` pack "content"++ it "MonadUnliftIO basic functionality" do+ result <- runMockT do+ _readFile ("test.txt" |> pack "test content")+ + content <- withRunInIO $ \runInIO -> do+ runInIO (readFile "test.txt")+ + liftIO $ content `shouldBe` pack "test content"+ pure content++ result `shouldBe` pack "test content"+ + it "MonadAsync type class can be instantiated for MockT" do+ result <- runMockT do+ _readFile $ do+ onCase $ "file1.txt" |> pack "content1"+ onCase $ "file2.txt" |> pack "content2"++ processFiles ["file1.txt", "file2.txt"]+ result `shouldBe` [pack "content1", pack "content2"]+