Search code examples
haskellyesodyesod-julius

using Julius outside Yesod


I am trying to figure out how to emit Javascript code using standalone Julius outside yesod:

{-# LANGUAGE QuasiQuotes #-}

import qualified Data.Text.Lazy.IO as LazyIO
import Text.Julius

main = do
    let delta = 1 :: Int
    LazyIO.putStrLn $ renderJavascript $ [julius|
        function f(x) {
          return x + #{delta};
        }
    |] undefined

But I am getting this error:

t2.hs:8:48:
    No instance for (ToJavascript Integer)
      arising from a use of ‘toJavascript’
    In the expression: toJavascript delta
    ...

Please help. I have no idea what it needs, I have just started looking at Julius. If I remove the interpolation then it renders the text successfully.


Solution

  • Try this:

    import qualified Data.Text.Lazy.IO as LazyIO
    import Text.Julius
    import Data.Aeson
    
    main = do
        let delta = toJSON (1 :: Int)
        LazyIO.putStrLn $ renderJavascript $ [julius|
            function f(x) {
              return x + #{delta};
            }
        |] undefined
    

    Explanation:

    The error message is saying that delta needs to have a ToJavascript instance. Looking up the ToJavascript class shows that these instances are defined by default:

    ToJavascript Bool    
    ToJavascript Value   
    ToJavascript RawJavascript   
    

    The lack of an Int (or Integer) instance explains the error message.

    However, there is a Value instance, and by using toJSON from the Aeson library we can turn an Int into a Value.