[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
Re: [lmi] How logic-less is mustache?
From: |
Vadim Zeitlin |
Subject: |
Re: [lmi] How logic-less is mustache? |
Date: |
Wed, 25 Oct 2017 22:47:49 +0200 |
On Wed, 25 Oct 2017 19:51:56 +0000 Greg Chicares <address@hidden> wrote:
GC> I'm guessing that mustache templates are absolutely "logic-less".
Yes. This is the difference between Mustache and Handlebars, which uses
the same syntax, but extends it with some minimal logic. I admit that I
regretted the absence of logic in Mustache quite a few times while writing
this code, especially because the separation of presentation from data, which
is the main advantage of the Mustache approach, is not that strong anyhow in
our case due to all the tables which need to be defined in C++ code.
GC> It's just a little surprising to see, e.g.,
GC> {{^StateIsNewYork}}
GC> when we already know the state and only want to compare it to "NY"; or
GC> Separate Account:
{{GenAcctAllocationComplementPercent}}<br>☜
GC> Guaranteed Principal Account (GPA):
{{GenAcctAllocationPercent}}<br>☜
GC> where one variable is just 100% minus the other,
I hesitated for a long time, but I finally felt that the inconvenience of
having to define all these variables wasn't worth the extra effort of
writing and the extra complexity of maintaining an expression parser. I
could have been wrong and I could write such a parser now, of course, if
you think it'd be worth it.
GC> especially in light of the way I initially read mustache's "Hello,
GC> world!" equivalent:
GC>
GC> | A typical Mustache template:
GC> |
GC> | Hello {{name}}
GC> | You have just won {{value}} dollars!
GC> | {{#in_ca}}
GC> | Well, {{taxed_value}} dollars, after taxes.
GC> | {{/in_ca}}
GC> | Given the following hash:
GC> |
GC> | {
GC> | "name": "Chris",
GC> | "value": 10000,
GC> | "taxed_value": 10000 - (10000 * 0.4),
GC> | "in_ca": true
GC> | }
GC>
GC> I mean, we can do arithmetic:
GC> | "taxed_value": 10000 - (10000 * 0.4),
GC> but that's input provided to mustache, rather than mustache code, right?
Yes, this is JavaScript: this JSON-looking data is actually a JavaScript
object ("JSON" name does contain a hint of it...).
GC> Mustache has 'lambdas', but they aren't a back door through which
GC> we can introduce, e.g., a "complement" function like:
GC> (lambda (x) (- 1 x))
Yes, what we'd really like to have would be Handlebars "helpers" and
conditionals (see http://handlebarsjs.com/block_helpers.html if you're
curious).
GC> I'm sure this is all by design. It's just startling that we need to
GC> define a "StateIsNewYork" variable.
At least it's hopefully simple to understand (I'm glad that you find
"UWTypeIsGuaranteedIssueInTexasWithFootnote" easier to understand than the
original XSLT code too, as I still remember that it took me a bit of time
to realize that this was what it really meant). The only real drawback I
see is that you often need to modify C++ code just in order to add another
trivial variable. Of course, there are other ones too, e.g. the absence of
"else" construction which forces us to write
{{#Foo}}something{{/Foo}}
{{^Foo}}something else{{/Foo}}
instead. However it's just inconvenient while the need to modify C++ code
to just change the output slightly is fundamentally wrong.
But, again, I made this tradeoff because I thought it was better to keep
things simpler, at least initially. I'm fully prepared to go through
another round of changes after these ones are merged and implement support
for expressions, conditionals, embedded Lisp interpreter, flight simulator
and everything else needed in the real production system.
Just please let me know if/when should I do it,
VZ