[update JMacro tutorial to discuss the new ToMessage behavior Jeremy Shaw **20120705184732 Ignore-this: c1be295c84c3b275ecd6b6b4bead332f ] hunk ./JMacro.markdown.lhs 70 -> import Happstack.Server.JMacro () -- ToMessage instance for JStat +> import Happstack.Server.JMacro (jmResponse) -- ToMessage instance for JStat hunk ./JMacro.markdown.lhs 498 -> fun greet noun +> window.greet = function (noun) hunk ./JMacro.markdown.lhs 507 -Then we have a server part with two sub-parts: +Notice that we attached the `greet` function to the `window`. The `ToMessage` instance for `JStat` wraps the Javascript in an anonymous function to ensure that statements execute in a local scope. That helps prevents namespace collisions between different external scripts. But, it also means that top-level unhygienic variables will not be global available. So we need to attach them to the `window`. + +Next we have a server part with two sub-parts: hunk ./JMacro.markdown.lhs 517 + hunk ./JMacro.markdown.lhs 519 + hunk ./JMacro.markdown.lhs 527 + hunk ./JMacro.markdown.lhs 529 + hunk ./JMacro.markdown.lhs 543 +Instead of attaching the `greet` function to the `window`, we could instead use `jmResponse` to serve the `JStat`. `jmResponse` does not wrap the Javascript in an anonymous function so the `window` work-around is not needed. We do need to use `!` to make sure the name of the `greet2` function is not mangled though: + +
+ +> externalJs2 :: String -> JStat +> externalJs2 greeting = +> [$jmacro| +> function !greet2 (noun) +> { +> alert(`(greeting)` + ' ' + noun); +> } +> |] +> +> +> externalPart2 :: JMacroPart Response +> externalPart2 = dir "external2" $ msum +> [ dir "script.js" $ +> do greeting <- optional $ look "greeting" +> jmResponse $ externalJs2 (fromMaybe "hello" greeting) +> +> , toResponse <$> defaultTemplate "external 2" +>