I am building a survey site in Yesod (0.10) and am getting lost in the types.
Here is a simplified version on what I am trying to do.
invitation url = do
render <- getUrlRender
return $ renderHtml [hamlet|
<p>Dear foo, please take our
<a href=@{ShowSurveyR url}>survey.
|] render
Another function is going to call this in hopes of getting something that can be passed to simpleMail from Network.Mail.Mime. The above function gives a type error:
Handler/Root.hs:404:13:
The function `renderHtml' is applied to two arguments,
but its type `Html -> LT.Text' has only one
This is confusing, because the templates tutorial seems to do things this way.
But if I modify the code, like this...
invitation url = do
return $ renderHtml [hamlet|
<p>Dear foo, please take our
<a href=@{ShowSurveyR url}>survey.
|]
I get this type error.
Handler/Root.hs:403:24:
The lambda expression `\ _render[a4TO] -> ...' has one argument,
but its type `Html' has none
In the first argument of `renderHtml', namely
I think that renderHtml is the wrong function to use, but I can't find what the right function is. Does anyone know what I am missing? How am I supposed to pass the routing function into my hamlet code?
The quasiquote ([hamlet|...|]
) returns a function whose argument is also a function. You must first apply that quasiquote value, and pass the results to renderHtml:
[Edit: as @MattoxBeckman discovered, another issue is the need to use getUrlRenderParams instead of gutUrlRender.]
invitation url = do
render <- getUrlRenderParams
return $ renderHtml $ [hamlet|
<p>Dear foo, please take our
<a href=@{ShowSurveyR url}>survey.
|] render
(Note the additional $
).
P.S. renderHtml is of type Html -> Text
, while the result of the quasiquote, [hamlet|..|]
, is of type Render url -> Html
. The first error message you saw notes that you tried to pass two arguments to renderHtml, while the second error message notes that you didn't pass any arguments to the quasiquote value.
To make this easier for the next person who goes searching for it...
There were two problems. One was pointed out by the first answer; the hamlet quasiquoter itself takes a function. The other problem was that I needed to use the function getUrlRenderParams, not getUrlRender.
The final code is
invitation :: Text -> Handler LT.Text
invitation url = do
render <- getUrlRenderParams
return $ renderHtml $ [hamlet|
<p>Dear foo, please take our
<a href=@{ShowSurveyR url}>survey.
|] render
Just replace shamlet
instead of hamlet
; it doesn't need a render
argument at all.
(As was pointed to me by joelteon at #yesod.)