I'm trying to use the function postBody
postBody :: (Yesod site, RedirectUrl site url) => url -> ByteString -> YesodExample site ()
from the Yesod.Test package. The documentation says it can be used like this
import Data.Aeson
postBody HomeR (encode $ object ["age" .= (1 :: Integer)])
However when I tried to use it in my app
describe "Posts" $ do
it "posts post and returns post" $ do
postBody PostR (encode $ object [
"body" .= ("test post" :: Text),
"title" .= ("test post" :: Text),
"coverImage" .= ("test post" :: Text),
"author" .= (0 :: Int)
])
statusIs 200
I got the error
• Couldn't match expected type ‘Post’ with actual type ‘Route App’
• In the first argument of ‘postBody’, namely ‘PostR’
In a stmt of a 'do' block:
postBody
PostR
(encode
$ object
["body" .= ("test post" :: Text), "title" .= ("test post" :: Text),
"coverImage" .= ("test post" :: Text), "author" .= (0 :: Int)])
In the second argument of ‘($)’, namely
‘do { postBody
PostR
(encode
$ object
["body" .= ("test post" :: Text), "title" .= ("test post" :: Text),
....]);
statusIs 200 }’
My usage seems to be the same as the example so I can't see why it would fail.
PostR is in the routes file here
/posts PostR POST
and the handler for it
postPostR :: Handler Value
postPostR = do
post <- requireJsonBody :: Handler Post
maybeUserID <- maybeAuthId
case maybeUserID of
Just userID -> do
let post' = post {postAuthor = userID}
inserted <- runDB $ insertEntity post'
returnJson inserted
Nothing -> sendResponseStatus status403 ("Unauthorized" :: Text)
The problem ended up being that in the posts table there was a column body so Yesod created postBody for this which conflicted with the postBody from Yesod.Test.
The solution is using a qualified import on yesod test
import qualified Yesod.Test as T