Can I use HUnit with a test card in a monad other than IO?

I currently have the following test code:

testUpdate :: Test testUpdate = testCase "update does change artist" $ do (created, Just revised, parents) <- mbTest $ do Just editor <- fmap entityRef <$> findEditorByName "acid2" created <- create editor startWith let artistId = coreMbid created newRev <- update editor (coreRevision created) expected editId <- openEdit includeRevision editId newRev apply editId found <- findLatest artistId parents <- revisionParents newRev return (created, found, parents) coreData revised @?= expected assertBool "The old revision is a direct parent of the new revision" $ parents == [coreRevision created] where startWith = ... expected = ... 

This view works, but it is dirty. I would rather write something without returning the various items under testing, and instead there are statements in which they make sense.

I see that there is an Assertable class, but it looks like I probably have to invent a lot of things.

+7
source share
1 answer

Why not just return your monad to an IO calculation of type IO a , which is a pure value? Since, as in your comment, the case where the monad is an instance of MonadIO is trivial, suppose that the monad allows a clean calculation:

 newtype M a = M {runM :: ....} instance Monad M where ... makeTest :: M Assertion makeTest = do created <- .. found <- .. parents <- .. let test1 = coreData revised @?= expected ... let test2 = assertBool "The old revision..." $ parents == [coreRevision create] return $ test1 >> test2 testUpdate :: Test testUpdate = testCase "update does change artist" $ runM makeTest 

The bonus is that you can return a collection of tests with one monadic calculation, just like you would in a monad list.

+1
source

All Articles