push-style templating - an xml-like way to process xhtml

  • Thread starter Terrence Brannon
  • Start date
T

Terrence Brannon

Hello,

The most common way of dynamically producing HTML is via template
engines like genshi, cheetah, makotemplates, etc.

These engines are 'inline' --- they intersperse programming constructs
with the HTML document itself.

An opposite approach to this form of dynamic HTML production is called
push-style templating, as coined by Terence Parr:
http://www.cs.usfca.edu/~parrt/papers/mvc.templates.pdf

I keep a list of push-style templating solutions for all languages
here:
http://www.perlmonks.org/?node_id=674225#python

And wanted to update the list of Python ones.

Notes:
- nagare has updated meld3 so the replace method can replace with
entire HTML trees, not just plain text node. the author of meld3
(chrism) seems to be out of touch: he hasnt responded to my last 2
emails
- basic xml processors are typically a bit too low level for
convenient xhtml processing. for example, lxml and elementtree are
both powerful xml processors, but webstring makes them much more
useable for xhtml processing
- the amara xml toolkit is very attractive. It shows how to climb on
top of a low-level XML processing suite (the 4suite tools) and
dynamically produce XHTML with Pythonic idioms. But I get the willies
when the quickref tutorial is a broken link - http://uche.ogbuji.net/tech/4suite/amara/quickref
- if there are any other new solutions in Python for this, I would
like to know about them.
 
T

Terrence Brannon

Tino said:
Hm.

"<a href=$attr.url$>$attr.title$</a>
$if(attr.active)$
$attr.submenu:menuItem()$
$endif$"

This looks ugly to me. It looks ugly to me too.
Why not just using well tested TAL, which is
also available for a number of languages?
well, to me, TAL has to be learned. It is a language. Why is this an
issue? Let me answer: I already know Python. I already know the XHTML
standard. I do not wish to learn TAL. If you know Python, and can read
the API to a high-quality XML processing toolkit, then you are done. TAL
introduces another language and I have to learn its conventions and
idiosyncrasies.

Now, the same would be true of Terence Parr's StringTemplate engine. It
is small, only 4 commands, but it litters the template with too much if
you ask me.

I like the approach of my own HTML::Seamstress --- object-oriented Perl
and knowledge of an object-oriented tree-rewriting library is all you need:
http://search.cpan.org/~tbone/HTML-...t_substitution_via_replace_content()_API_call.
http://en.wikipedia.org/wiki/Template_Attribute_Language

In contrast there would be something like TSSL, which
unfortunately never saw the light of the day yet :)

http://mail.zope.org/pipermail/zpt/2002-May/003304.html

(This solution would not even touch the HTML directly)
just remember: XHTML is a subset of XML and no one ever touches XML
directly. There really is no reason for HTML to be handled any
differently than XML.
That TSSL is a nightmare. It's trying to be a programming language. And
again, we already have Perl/Python, so why bother? You can avoid
touching HTML by using Python.

Thank you for writing. I enjoyed the discussion.
 
P

Paul Boddie

I like the approach of my own HTML::Seamstress --- object-oriented Perl
and knowledge of an object-oriented tree-rewriting library is all you need:
http://search.cpan.org/~tbone/HTML-Seamstress-5.0b/lib/HTML/Seamstres....

The Python equivalent to your list of templating systems can be found
here (under "Engines with Annotated Templates"):

http://wiki.python.org/moin/Templating

I note that your list mentions XMLC which was probably one of the
first solutions I encountered employing the approach you describe. One
issue typically arises when using such solutions, however: trivial
modifications to the output document are convenient, but how do you
effectively manage situations where you need to modify or populate
large numbers of "slots" in the output document?

Paul
 
T

Terrence Brannon

Tino said:
Your templating engine you have in your paper has yet another language.
So where is the difference?
if you are talking about StringTemplate, yes, that is a weakness of its
approach. It is another language and it must be learned.
TAL's core has also only a few "commands". So not much to learn. If
thats to much, development is not for you I fear ;)
no, Python is for me. Python handles all external data formats (csv,
xml, imap, rdbms) without those formats requiring an embedded language.
Dynamically unwinding HTML need be no different.
if I am provided a high quality API for processing all those formats, I
only need one for XHTML as well... meld3 is pretty good for example.

TAL does not have as large a userbase or robust testing as Python does.
I only want robust languages with large numbers of users. Language with
quality libraries. Not language + mini-language.
Still you need to learn. There is no way out.
Seamstress only requires learning an *API* --- that is not the same as
learning another language and its limitations and idiosyncrasies.
Mini languages is the correct term. And yes they have their
purpose. (Think of SQL for example).
yes mini-language. But let's look at SQL. SQL is pure. You dont stick
Python in your database and unroll the database with it. You dont stick
Python in SQL. And you dont put SQL in your tables.

the keyword is *orthogonal* --- things may interact, but they should not
mix.
 
D

Diez B. Roggisch

Hi,

first a bit of background: I've been using push-style templating in the
form of XMLC before. Actually, I've been a core-developer of
BarracudaMVC, a java web-framework that for rendering massively relied
on XMLC and has been driving XMLC's development (at least used to).

And I liked it. But eventually, Barracuda grew a attribute-defined
templating system, similar to what we see in TAL or Genshi or KID. It
was still relying on XMLC, but extended the capabilities. And was/is
simply much more powerful.

if you are talking about StringTemplate, yes, that is a weakness of its
approach. It is another language and it must be learned.
no, Python is for me. Python handles all external data formats (csv,
xml, imap, rdbms) without those formats requiring an embedded language.
Dynamically unwinding HTML need be no different.
if I am provided a high quality API for processing all those formats, I
only need one for XHTML as well... meld3 is pretty good for example.

TAL does not have as large a userbase or robust testing as Python does.
I only want robust languages with large numbers of users. Language with
quality libraries. Not language + mini-language.

TAL *is* a library. Just because language constructs are mapped to
API-calls does not change that. The same argument about numbers of users
and can be made for your preferred approach as well.
Seamstress only requires learning an *API* --- that is not the same as
learning another language and its limitations and idiosyncrasies.

That is debatable. I don't know TAL much, but I do know (and use) Genshi
and KID, two similar approaches to HTML-creation. They use python-syntax
where possible, e.g.

<ul py:for="item in items">
<li py:content="item.some_property"/>
</ul>

Learning the handful of constructs is the same as learning a handful of
API calls. The same goes for idiosyncrasies of e.g. inserting
sub-templates or dealing with repeating content.
yes mini-language. But let's look at SQL. SQL is pure. You dont stick
Python in your database and unroll the database with it. You dont stick
Python in SQL. And you dont put SQL in your tables.

Matter of factly people *do* stick Python into SQL - or PL, or other
languanges - by defining triggers and stored procedures. With varying
degrees of actually mixing the two languanges. The same goes for
embedding SQL into e.g. Java.

I don't say I very much like that or consider it a better way than
separating things. Yet it does serve as example that other people think
different about mixing languages (and language paradigms), most probably
rightfully so.
the keyword is *orthogonal* --- things may interact, but they should not
mix.

TAL, KID & Genshi don't mix, the stand for their own. They are languages
extending XHTML mostly via clever namespace usage, and don't require you
to actually learn much syntax that you don't know already.

And there is one big point about using them in favor of push-style
templating that hasn't been brought up before (or maybe it has, but
somehow slipped me - I seem to only see parts of the discussion in this
thread for some wicked reason), which is IMHO of utmost importance: the
separation of controller-logic and data representation for e.g. layout
purposes, as the MVC-pattern encourages.

If writing code for a webapplication, my controller provides data to be
rendered in an output-language of my choice. Using templating, I can
keep that totally separated from the rendering. I can use the same code
for providing (X)HTML or JSON, depending on e.g. the HTTP-header - so my
Ajax-calls use the same method.

Additionally, getting a grasp of what a piece of template is about is
much easier when I use a proper templating language - because I can
infer easily and mostly without looking at actual code what the template
is expecting of it's data. Even more so, I can give the template to
somebody who's more knowledgable with HTML, CSS and the like who can
alter it's appearance and does not need to alter my code to switch from
a list to a table for example.

Push-style though enhances the risk of mixing program logic with
presentation-logic (as simple print-statements do), and makes it a
precondition that anybody who's supposed to tinker with the softare
needs to be knowledgable in Python as well as in HTML.

Diez
 
A

Aahz

The most common way of dynamically producing HTML is via template
engines like genshi, cheetah, makotemplates, etc.

These engines are 'inline' --- they intersperse programming constructs
with the HTML document itself.

An opposite approach to this form of dynamic HTML production is called
push-style templating, as coined by Terence Parr:
http://www.cs.usfca.edu/~parrt/papers/mvc.templates.pdf

I'm not sure what you mean because I'm not going to bother reading a
PDF, but you might look into Quixote:

http://www.mems-exchange.org/software/quixote/
 
H

has

Hm.

"<a href=$attr.url$>$attr.title$</a>
$if(attr.active)$
$attr.submenu:menuItem()$
$endif$"

This looks ugly to me.

It also looks like an embedded mini-language to me.

At any rate, I think making a 'push/pull' distinction misses the
point.

There are basically three approaches a templating system can use:

1. embed your control logic in your presentation markup,

2. embed your presentation markup in your control logic, or

3. keep the two separate and transform the presentation markup into
some sort of DOM that can then be manipulated by the control code.

What's significant here is the division of labour within the overall
program. With the first two approaches, the templating engine handles
both presentation and control (i.e. pretty much the entire View
layer). The third approach only provides the presentation part, and
does and says nothing about how the control part is implemented. So
you can't really make a direct comparison of, say, Cheetah against
PyMeld, as they don't cover the same amount of ground. Instead, you
ought to consider how the entire View layer is put together in each
case:

- A Cheetah-based View is implemented as an HTML file with all of the
required control code embedded in it.

- A PyMeld-based View is implemented as an HTML file with id
attributes that indicate which HTML elements should be converted into
object model nodes, *plus* a Python module containing the control code
that manipulates those nodes when rendering a finished document.

Once you do compare like with like, the 'push/pull' distinction
becomes somewhat irrelevant, as the control code for a PyMeld-based
View could be pushing or it could be pulling. It's up to each
program's developer to decide which way they want to do it - and in a
proper MVC design it should always be pulling.

....

A more useful distinction to make is between templating systems that
combine appearance and control, and those that keep them separate, as
this has significant implications when considering which type of
templating system to choose, e.g.:

- how complex the interface is, e.g. Cheetah's interface is larger and
more complex than PyMeld's (even though they do the same thing), which
means a longer learning curve

- how clean the division of responsibility is, e.g. PyMeld separates
HTML markup from Python code, which provides an obvious advantage if
you've got a web designer handling one task and a Python programmer
handling the other, or a likely disadvantage if both tasks are being
handled by a relatively non-technical web designer

- how abstract the program's View implementation is, e.g. a PyMeld-
based View is more abstract than a Cheetah one, as markup and code are
physically separate and are only combined in memory, which means the
logic developer has to work harder in mentally modelling their View
layer's structure and behaviour.


HTH

has
 
G

Glenn Linderman

It also looks like an embedded mini-language to me.

At any rate, I think making a 'push/pull' distinction misses the
point.

There are basically three approaches a templating system can use:

1. embed your control logic in your presentation markup,

2. embed your presentation markup in your control logic, or

3. keep the two separate and transform the presentation markup into
some sort of DOM that can then be manipulated by the control code.

What's significant here is the division of labour within the overall
program. With the first two approaches, the templating engine handles
both presentation and control (i.e. pretty much the entire View
layer). The third approach only provides the presentation part, and
does and says nothing about how the control part is implemented. So
you can't really make a direct comparison of, say, Cheetah against
PyMeld, as they don't cover the same amount of ground. Instead, you
ought to consider how the entire View layer is put together in each
case:

- A Cheetah-based View is implemented as an HTML file with all of the
required control code embedded in it.

- A PyMeld-based View is implemented as an HTML file with id
attributes that indicate which HTML elements should be converted into
object model nodes, *plus* a Python module containing the control code
that manipulates those nodes when rendering a finished document.

It would be nicest to keep the two separate... such that the HTML could
be directly displayed in a browser, albeit with placeholder data items.
The StringTemplate approach of nested, inherited subtemplates probably
provides more power, and less cut-n-paste redundancy in development, but
provides nothing for the designer to preview until the whole application
is complete and specific data generated. It also results a
view-independent superstructure from which it may be possible to
generate other textual views without total recoding. One question is if
designers come understanding multiple views, or if one has HTML-only
designers, and other-modality-only designers, and that they don't speak
enough of each others modalities to appreciate the view-independent
superstructures enough to learn the mini-language that abstracts it.
Even if there is a single view modality to be targeted, as is usually
the case, if the cost to use a system that allows other modalities to be
targeted, it is not an uncommon follow-on requirement to provide other
view modalities. Systems that don't provide such wind up getting
screen-scraped, which is a pitiful solution, although sometimes
cost-effective.

Unfortunately, keeping the two languages separate adds significantly to
the burden of figuring out how to mix them together.
Intermingled/embedded control and presentation (either embedded print
statements, or templating systems), have become popular (in my opinion)
because they do solve the problem of figuring out how do the mix.
Terence Parr's more formal research into this topic, and his attempts to
enforce separation between Model, View, Controller, and the new concept
of Renderer, embodied in StringTemplate, may help to prove that these 4
items can be separated, which is architecturally good... but does little
or nothing to make the mixing of languages less ugly.

I took a brief look at the PyMeld approach, and it seems that the HTML
file, while providing all the HTML syntax necessary for the project,
leaves all decisions about what items should be replicated, and how and
when to replicate them, to the controller. The use of Python (hey, I
don't mind using Python!) as the language (together with an API) for the
controller, though, does seem to avoid enforcement of the separation
between view and model; there is nothing to prevent Python from
massaging the model data in whatever manner it likes, being a general
purpose language. Likewise, the controller can manipulate the
presentation data, potentially in ways other than simply replicating an
item. Apparently it can insert and delete items from the presentation
at will. Hence, this avoids the enforcement of the separation between
the view and the controller. So while PyMeld is no doubt a rich
templating system, and allows a way of implementing separated MVC items,
it is apparently not attempting to enforce that separation, as
StringTemplate does. While the ID attribute is intended (in the HTML
spec) to uniquely identify a particular item, its use to identify items
for PyMeld manipulation may or may not conflict with other desired
uses. There is nothing in the HTML syntax that prevents the use of an
attribute similar to ID, perhaps called PyMeld, such that <a
PyMeld="whatever" id="something-HTMLish" href="..."> could be used in
the HTML. The PyMeld controller would have to parse these, and
potentially could remove them from the output, to avoid confusing
browsers (but most browsers would just ignore them anyway).

It would be nice if a collection of static data items could be provided,
such that the controller code could transform the presentation markup
into browser-displayable data, without the application. Such a generic
controller for each modality, together with files of data samples, could
help in the negotiations between designer and coder. Using
StringTemplate for an example again, the attribute layout (I forget what
term was used for that) that is the specification of what the model must
provide and what the view has available is interesting, and the data
samples would have to provide a subset of all the attributes in the
layout, and the generic controller the code for putting them together.

Most designers are unlikely, in my opinion, to be able to create a
StringTemplate subtemplate superstructure without the visual feedback of
generating the modality-specific end-product with which they are
comfortable. Available data samples (even if changing due to changing
requirements and/or negotiations between the view and model development
teams as requirements get better understood), and a generic controller,
would seem to allow parallel development of the model and view.
Once you do compare like with like, the 'push/pull' distinction
becomes somewhat irrelevant, as the control code for a PyMeld-based
View could be pushing or it could be pulling. It's up to each
program's developer to decide which way they want to do it - and in a
proper MVC design it should always be pulling.

Indeed, I can totally agree that the 'push/pull' distinction is somewhat
irrelevant, when pull is properly implemented.

I think the push/pull distinction is mostly one of implementation
convenience. Certainly the data from the model must be available to the
view. If you look at the StringTemplate architecture, which is the one
promoting 'push', you find that it provides a set of attributes... which
it calls 'push'... but doesn't require the model to look at them... when
the model looks at them, that can be considered 'pull'. The very
definition of 'push' that Terence describes is simply that "A safe pull
strategy degenerates to push in the worst case" (his Theorem 4 from the
mvc.templates.pdf paper).

So while Terence claims that "Pull strategy violates separation" as the
title of section 7.1, his claim is really that "some implementations of
a model providing a pull strategy, which observe and make assumptions
about the order in which a view may do its pulls of individual
attributes, violate the separation between View and Model." As long as
the 'pull' model doesn't have dependencies on the the order in which
items are pulled, and can provide a consistent set of data regardless of
that order, it really doesn't matter whether you use push or pull.

The "take away" point is that an easy way to implement the pull
strategy, is for the model to precalculate and cache all the data needed
by the view, and provide it as a complete lump of attributes available
to the view, from which the view may pull the data at its leisure.
A more useful distinction to make is between templating systems that
combine appearance and control, and those that keep them separate, as
this has significant implications when considering which type of
templating system to choose, e.g.:

- how complex the interface is, e.g. Cheetah's interface is larger and
more complex than PyMeld's (even though they do the same thing), which
means a longer learning curve

- how clean the division of responsibility is, e.g. PyMeld separates
HTML markup from Python code, which provides an obvious advantage if
you've got a web designer handling one task and a Python programmer
handling the other, or a likely disadvantage if both tasks are being
handled by a relatively non-technical web designer

- how abstract the program's View implementation is, e.g. a PyMeld-
based View is more abstract than a Cheetah one, as markup and code are
physically separate and are only combined in memory, which means the
logic developer has to work harder in mentally modelling their View
layer's structure and behaviour.

These would certainly be useful measures to make, and like you point
out, there can be advantages and disadvantages of each approach.
 
C

Cameron Laird

.
.
.
Mini languages is the correct term. And yes they have their
purpose. (Think of SQL for example).
.
.
.
I am, incidentally, among those who finds templating languages
in general and TAL in particular more "perplexing annoyance"
than "solution". I certainly use TAL, though ...
 
H

has

"<a href=$attr.url$>$attr.title$</a>
$if(attr.active)$
$attr.submenu:menuItem()$
$endif$"

This looks ugly to me.

It also looks like an embedded mini-language to me.

At any rate, I think making a 'push/pull' distinction misses the
point.

There are basically three approaches a templating system can use:

1. embed your control logic in your presentation markup,

2. embed your presentation markup in your control logic, or

3. keep the two separate and transform the presentation markup into
some sort of DOM that can then be manipulated by the control code.
[...]
- A Cheetah-based View is implemented as an HTML file with all of the
required control code embedded in it.

- A PyMeld-based View is implemented as an HTML file with id
attributes that indicate which HTML elements should be converted into
object model nodes, *plus* a Python module containing the control
code
that manipulates those nodes when rendering a finished document.

It would be nicest to keep the two separate... such that the HTML
could be directly displayed in a browser, albeit with placeholder
data items.

That's what DOM-style templating engines (which StringTemplate
isn't)
generally do: since they leverage the existing HTML element
structure,
the only additions to the HTML that are needed are tag attributes to
indicate which elements should be represented as DOM nodes. Most
allow
you to create a 100% valid HTML/XHTML document, complete with
placeholder text for previewing the template in a browser.

The StringTemplate approach of nested, inherited subtemplates
probably provides more power, and less cut-n-paste redundancy in
development, but provides nothing for the designer to preview until
the whole application is complete and specific data generated.

Not going to argue with that, but if you read my previous post,
StringTemplate barely came into it. IMO StringTemplate is closest to
approach 1 above, since it uses a simple embedded language to pull
data from a pre-arranged data structure. Its only similarity to
approach 3 is that the embedded language isn't powerful enough to
implement all of your View logic in, so you end up having to write
at
least some of your View logic outside of the template, using the
host
language to pull data from the Model layer and massage it into a
format suitable for consumption by a StringTemplate template.

Unfortunately, keeping the two languages separate adds significantly
to the burden of figuring out how to mix them together.

Some embedded templating systems involve one language; others
require
two. e.g. Cheetah-based applications involve two languages: Python
for
the Model, its own HTML-embedded language for the View. OTOH, DOM-
style templating languages should only ever require one language:
there's no logic in the HTML to begin with, so all you need is a
language to manipulate the DOM API, which might as well be the same
language as the rest of your application.

Intermingled/embedded control and presentation (either embedded
print statements, or templating systems), have become popular (in my
opinion) because they do solve the problem of figuring out how do
the mix.

Disagree. Embedded templating systems have become popular for two
reasons:

1. PHP, which, for better or worse, has raised a huge number of web
developers on its logic-in-HTML approach

2. minimal abstraction - i.e. it's easier to see how sections of
HTML
are manipulated when they are directly surrounded by the logic that
manipulates them - which makes for a lower barrier of entry.

I took a brief look at the PyMeld approach, and it seems that the
HTML file, while providing all the HTML syntax necessary for the
project, leaves all decisions about what items should be replicated,
and how and when to replicate them, to the controller.

I'm guessing you're a Mac person, since Apple are the only ones to
refer to presentation logic as the 'Controller'; web folks usually
uses the Smalltalk definition, where 'View' includes control logic
as
well as the display objects (windows, buttons, etc), and the
'Controller' layer sits on the opposite side of the Model and
handles
all input.

If you are a Mac person, you shouldn't have any trouble getting your
head around the DOM-style approach, as it's pretty much the same
approach Apple use in their Carbon and Cocoa frameworks. (In fact,
Apple's approach to GUI construction was a direct inspiration for my
own DOM-style engine, HTMLTemplate.)

So while PyMeld is no doubt a rich templating system, and allows a
way of implementing separated MVC items, it is apparently not
attempting to enforce that separation, as StringTemplate does.

You are correct that PyMeld and other DOM-style engines do not
enforce
MVC separation. That said, I would argue that StringTemplate doesn't
enforce it either, except maybe in simple or contrived cases where
the
Model API is sufficiently close to the structure required by ST that
the template can pull data directly from it. Otherwise you have to
write additional code outside of the template to pull data from the
Model, rearrange it into the required shape, and push it into
StringTemplate. Guess what: that's View logic too (by the Smalltalk
definition), and StringTemplate isn't enforcing separation of that
logic from the Model either.


There are some template systems that [try to] cater to non- or
novice programmers by limiting the amount of functionality, and
therefore damage, they have access to; sort of the Java philosophy
where you need to cater to the weakest developer on the team.

DOM- style engines never do this, nor do they even try. Like Lisp and
C,
they always assume that whoever's writing the code knows what
they're
doing, and gives them free reign to do it however they see fit. (BTW,
they also assume that the person writing the HTML knows nothing of
programming, so place virtually zero burden on them.) So if a
developer chooses not to provide MVC separation between template
control code and the rest of their application, that's their
business
and/or problem; it's the templating engine's job to generate HTML
documents, not tell users how to program.

While the ID attribute is intended (in the HTML spec) to uniquely
identify a particular item, its use to identify items for PyMeld
manipulation may or may not conflict with other desired uses. There
is nothing in the HTML syntax that prevents the use of an attribute
similar to ID, perhaps called PyMeld, such that <a PyMeld="whatever"
id="something-HTMLish" href="..."> could be used in the HTML. The
PyMeld controller would have to parse these, and potentially could
remove them from the output, to avoid confusing browsers (but most
browsers would just ignore them anyway).

I can't really speak for PyMeld as it's some years since I've looked
at it, but HTMLTemplate allows you to use any attribute you like,
either standard HTML, XML namespace-based, or custom (the default is
custom, 'node', and it's automatically stripped from output as you
describe).


Indeed, I can totally agree that the 'push/pull' distinction is
somewhat irrelevant, when pull is properly implemented.

I think the push/pull distinction is mostly one of implementation
convenience. Certainly the data from the model must be available to
the view. If you look at the StringTemplate architecture, which is
the one promoting 'push', you find that it provides a set of
attributes... which it calls 'push'... but doesn't require the model
to look at them... when the model looks at them, that can be
considered 'pull'. The very definition of 'push' that Terence
describes is simply that "A safe pull strategy degenerates to push
in the worst case" (his Theorem 4 from the mvc.templates.pdf paper).

So while Terence claims that "Pull strategy violates separation" as
the title of section 7.1, his claim is really that "some
implementations of a model providing a pull strategy, which observe
and make assumptions about the order in which a view may do its
pulls of individual attributes, violate the separation between View
and Model."

Having trouble parsing that (I didn't read the paper in detail
either;
too much work). Suffice to say that a View (using the Smalltalk
definition) should *always* pull data from the Model; the Model
should
*never* push data into a View.

As long as the 'pull' model doesn't have dependencies on the the
order in which items are pulled, and can provide a consistent set of
data regardless of that order, it really doesn't matter whether you
use push or pull.

The "take away" point is that an easy way to implement the pull
strategy, is for the model to precalculate and cache all the data
needed by the view, and provide it as a complete lump of attributes
available to the view, from which the view may pull the data at its
leisure.

This is wrong. In MVC, the Model should know *nothing* of Views. If
a
Model can't function without a View attached, or with a hundred
different types of Views attached, then it isn't MVC.


A more useful distinction to make is between templating systems that
combine appearance and control, and those that keep them separate, as
this has significant implications when considering which type of
templating system to choose, e.g.:

- how complex the interface is, [...]

- how clean the division of responsibility is, [...]

- how abstract the program's View implementation is, [...]

These would certainly be useful measures to make, and like you point
out, there can be advantages and disadvantages of each approach.

Absolutely. I think it'd make for a very interesting and productive
analysis if folks'd like to run with it.

has
 
G

Glenn Linderman

"<a href=$attr.url$>$attr.title$</a>
$if(attr.active)$
$attr.submenu:menuItem()$
$endif$"

This looks ugly to me.

It also looks like an embedded mini-language to me.

At any rate, I think making a 'push/pull' distinction misses the
point.

There are basically three approaches a templating system can use:

1. embed your control logic in your presentation markup,

2. embed your presentation markup in your control logic, or

3. keep the two separate and transform the presentation markup into
some sort of DOM that can then be manipulated by the control code.
[...]
- A Cheetah-based View is implemented as an HTML file with all of the
required control code embedded in it.

- A PyMeld-based View is implemented as an HTML file with id
attributes that indicate which HTML elements should be converted into
object model nodes, *plus* a Python module containing the control
code
that manipulates those nodes when rendering a finished document.
It would be nicest to keep the two separate... such that the HTML
could be directly displayed in a browser, albeit with placeholder
data items.

That's what DOM-style templating engines (which StringTemplate
isn't)
generally do: since they leverage the existing HTML element
structure,
the only additions to the HTML that are needed are tag attributes to
indicate which elements should be represented as DOM nodes. Most
allow
you to create a 100% valid HTML/XHTML document, complete with
placeholder text for previewing the template in a browser.

Sure. But DOM-style templating engines, although perhaps clearly handy
in today's browser-and-internet-centric world, are limited to one view
modality.

Unless, of course, you target other textual data structures that are, or
can be made to be, DOM-style. But I infer here that you are primarily
referring to a particular DOM, that of internet documents, and that
other DOMs could be sufficiently different syntactically, that an
internet-DOM would not apply very easily.

Not going to argue with that, but if you read my previous post,
StringTemplate barely came into it.

I did; but the thread was started with a reference to Terence Parr's
StringTemplate paper.
IMO StringTemplate is closest to
approach 1 above, since it uses a simple embedded language to pull
data from a pre-arranged data structure.

I would agree with this.
Its only similarity to
approach 3 is that the embedded language isn't powerful enough to
implement all of your View logic in, so you end up having to write
at
least some of your View logic outside of the template, using the
host
language to pull data from the Model layer and massage it into a
format suitable for consumption by a StringTemplate template.

Hmm. One of the things Terence seems to be trying to point out is that
even though the embedded language of StringTemplate is less than Turing,
that it is sufficient for Viewing.

The language of StringTemplate does have the ability to make reference
to model attributes; that is sufficient "to pull data from the Model
layer". And the massaging is assigned to the Controller, or a new
subpiece called the renderer, and is limited to formatting type
operations on single data items at a time (if I understand it
correctly). I've only read a couple StringTemplate papers, I haven't
played with it yet.
Some embedded templating systems involve one language; others
require
two.

Indeed; but it is not clear those embedded templating systems involving
only one language enforce MVC.
e.g. Cheetah-based applications involve two languages: Python
for
the Model, its own HTML-embedded language for the View. OTOH, DOM-
style templating languages should only ever require one language:
there's no logic in the HTML to begin with, so all you need is a
language to manipulate the DOM API, which might as well be the same
language as the rest of your application.

And if the app manipulates the DOM API, it again doesn't enforce MVC.
Disagree. Embedded templating systems have become popular for two
reasons:

1. PHP, which, for better or worse, has raised a huge number of web
developers on its logic-in-HTML approach

2. minimal abstraction - i.e. it's easier to see how sections of
HTML
are manipulated when they are directly surrounded by the logic that
manipulates them - which makes for a lower barrier of entry.

Hmm. Your points are clearly agreeing with my statement, although you
claim disagreement. PHP is an outgrowth of ASP, JSP, and PSP, if I
recall the history correctly. It was an attempt to avoid the perceived
pitfalls of PSP by replacing the Perl of PSP with a simpler language
that beginners could learn faster, without the gotchas of the more
powerful, terse, Perl syntax. PHP certainly found a sweet-spot... being
available and well-touted at the point when a huge number of wannabe web
developers were being weaned. Being a newcomer to Python, I'm not sure
if there was a "PSP"-style Python approach, or if Python skipped that
technology, and went to things like Django directly.
I'm guessing you're a Mac person, since Apple are the only ones to
refer to presentation logic as the 'Controller'; web folks usually
uses the Smalltalk definition, where 'View' includes control logic
as
well as the display objects (windows, buttons, etc), and the
'Controller' layer sits on the opposite side of the Model and
handles
all input.

I'm not a Mac person; that's probably the only significant platform that
I haven't done at least a bit of coding for somewhere along the line.
But the MVC pattern, and the StringTemplate document both speak of
controllers.
If you are a Mac person, you shouldn't have any trouble getting your
head around the DOM-style approach, as it's pretty much the same
approach Apple use in their Carbon and Cocoa frameworks. (In fact,
Apple's approach to GUI construction was a direct inspiration for my
own DOM-style engine, HTMLTemplate.)

If you say so. I don't see the DOM-style approach as being hard to
understand; just that it doesn't seem to help enforce the MVC pattern...
oh yeah, that's where I went next last time, as we see below.
You are correct that PyMeld and other DOM-style engines do not
enforce
MVC separation. That said, I would argue that StringTemplate doesn't
enforce it either, except maybe in simple or contrived cases where
the
Model API is sufficiently close to the structure required by ST that
the template can pull data directly from it. Otherwise you have to
write additional code outside of the template to pull data from the
Model, rearrange it into the required shape, and push it into
StringTemplate. Guess what: that's View logic too (by the Smalltalk
definition), and StringTemplate isn't enforcing separation of that
logic from the Model either.

I fear Smalltalk, like Macs, is another area of omission in my
experience, so I don't know the Smalltalk definition of View, but it
seems that Smalltalk predates the design patterns book that codified the
MVC paradigm, and hence, I would suggest that the Smalltalk view was
seen as too encompassing, and that there were good design reasons to
split the view and controller into a third piece of the pattern. Of
course, there may be ways to implement MVC within Smalltalk, but not
likely enforcable.
There are some template systems that [try to] cater to non- or
novice programmers by limiting the amount of functionality, and
therefore damage, they have access to; sort of the Java philosophy
where you need to cater to the weakest developer on the team.

Indeed, PHP was founded on that philosophy, and has brought in lots of
weak developers (witnessing by all the PHP exploits on the web, seems
almost as many as the number of M$ exploits in COM & ActiveX etc. I've
never heard of Java catering to the weakest developer on the team, but
it is a B&D language, which could be perceived as doing that, to some
extent.
DOM- style engines never do this, nor do they even try. Like Lisp and
C,
they always assume that whoever's writing the code knows what
they're
doing, and gives them free reign to do it however they see fit. (BTW,
they also assume that the person writing the HTML knows nothing of
programming, so place virtually zero burden on them.) So if a
developer chooses not to provide MVC separation between template
control code and the rest of their application, that's their
business
and/or problem; it's the templating engine's job to generate HTML
documents, not tell users how to program.

Sure; one can implement MVC without using training wheels; and one can
implement multiply using shift and add and a bit of other program
logic... a new design pattern is seldom introduced with a complete,
enforced implementation, largely because no one realizes how useful it
will be until after it is invented; the next generation of languages
then incorporates the best of several design patterns, and the next
generation of programmers benefits.

I can't really speak for PyMeld as it's some years since I've looked
at it, but HTMLTemplate allows you to use any attribute you like,
either standard HTML, XML namespace-based, or custom (the default is
custom, 'node', and it's automatically stripped from output as you
describe).

I hadn't looked at HTMLTemplate; what you describe sounds better than
requiring the use of ID.

Having trouble parsing that (I didn't read the paper in detail
either;
too much work). Suffice to say that a View (using the Smalltalk
definition) should *always* pull data from the Model; the Model
should
*never* push data into a View.

Reading the paper was worth the time, as far I'm concerned; it was a bit
of work, but it lays out some pretty interesting theoretical
foundations. StringTemplate is an interesting embodiment of that, and
seems somewhat a practical solution, although it perhaps hasn't reached
full maturity as yet, and the syntax is unusual, although apparently
powerful.

This is wrong. In MVC, the Model should know *nothing* of Views. If
a
Model can't function without a View attached, or with a hundred
different types of Views attached, then it isn't MVC.

A Model is totally useless without a View. This harks back to "If a
tree falls in the forest and no one hears it, did it make noise?"

I agree that a Model should be reusable by many Views. And the more you
believe that (you mention a hundred Views), the more you want to ensure
that the architecture truly is MVC, so that the multitude of Views are
not reimplementing logic that belongs in the Model. And having a
implementation languages and systems that enforce the architecture could
be a big help, although it does require learning and/or making those
languages and systems.
A more useful distinction to make is between templating systems that
combine appearance and control, and those that keep them separate, as
this has significant implications when considering which type of
templating system to choose, e.g.:

- how complex the interface is, [...]

- how clean the division of responsibility is, [...]

- how abstract the program's View implementation is, [...]
These would certainly be useful measures to make, and like you point
out, there can be advantages and disadvantages of each approach.

Absolutely. I think it'd make for a very interesting and productive
analysis if folks'd like to run with it.
 
L

lkcl

Push-style though enhances the risk of mixing program logic with
presentation-logic (as simple print-statements do), and makes it a
precondition that anybody who's supposed to tinker with the softare
needs to be knowledgable in Python as well as in HTML.

i'd like to add perhaps a different perspective. i've developed and
used the following:

* xmlvl (http://sf.net/projects/virgule) - it's a (non-NP-complete)
XML-based programming language, which was derived from advogato's
codebase. it outputs XHTML, is "template-based" and implements what
is best described as an XML-based lattice-like, "crystalline" and
hierarchical OO database (!!). i understood it while i was writing
it, but woudldn't dare go near it, ever again.

the lessons learned from this were: don't take templating to extremes
(i.e. do the absolute minimum), and never ever write programming
languages in XML.

* python-htmltmpl (http://htmltmpl.sourceforge.net/) - it's a simple,
utterly simple, HTML-syntax-like templating language, which can do
"substitution", "if/else statements", and "loops". that's about it.
the nice thing about htmltmpl is that it can do pre-compilation of its
templates, inserting jump-points (which are used to seek() to the next
precompiled statement) into the .tmplc files. this saves a _great_
deal of time and CPU cycles.

the lesson from this one is hard to get across, because htmltmpl
basically... works. it doesn't _need_ developing, it's complete, it
works, it's never going to get up in the sourceforge "rankings"
because... it does everything that it's designed to do.

so it drops off of people's radar, and they reinvent the wheel.

if you think you need anything more than htmltmpl, which separates out
html from programming, think again. you can pass in a list of
dictionaries into htmltmpl, that generates the table content, form
content, whatever-content.

job done.

* pyjamas (http://pyjs.org) - this is treating the web page and the
web browser as a desktop "canvas", i.e. turning the web browser
concept on its head, and allowing you to program it in exactly the
same way that you would if you were writing a desktop app with PyQt4
or PyGtk2.

no kidding about, here.

why on earth would you want to do something like this? it's very
simple: HTML "programming" is madness. it's madness from two angles:

1) CSS abortions. as an example: i tried doing a centred-box, once.
it took two weeks, and it still was a failure: worked fine in firefox,
but in IE6 if you squashed the browser size, so that normally under FF
you got a horizontal scrollbar, what happened in IE6 was that the
content scrolled off the *top* of the screen!! unbelievable - and
completely impossible to fix.

2) HTML template "option-itis" resulting in thousands of lines of HTML
that becomes impossible to read, and impossible to maintain. i think
the worst example i ever saw - and i'm sure people will find worse -
was a technique involving _four_ separate near-identical pages (each
over 3,000 lines long) - one for new entry form, one for new entry but
with error-messages interspersed, one for edit, and one for edit but
with error-messages interspersed. cut-and-paste gone mad.

HTML templating is, for complex applications, a baaaad idea. even
when you start "breaking down" the content into smaller server-side-
includes, and even when you start doing multi-layered HTML templating
(one template gets marked up and then substituted into another
template and so on), even _that_ technique gets very quickly out-of-
hand and you're left with a headache.

so now i choose pyjamas over _any_ kind of web programming, any day of
the week.

the reason is very straightforward: the amount of code being written
is small; it's in python; i can re-use classes and modules; i can even
take standard python modules such as an XMLRPC client or a JSONRPC
client and actually compile them (to javascript) for use... in a web
browser!

you can put in a < div > with an id, you can find that div using a one-
line function, and you can substitute "widgets" - your classes - into
that div. it's a very, very powerful technique.

complex application programming should be done in a complexity-capable
programming _language_.

HTML, which is a markup language, is simply not designed - and was
never designed - to be "programmed" or to be an NP-complete
programming "language". it's great for "static content", which can be
edited by graphical tools, and that's about it.

so, there _is_ an alternative approach, with pyjamas, to what you're
saying, diez ("Push-style ... anybody who's supposed to tinker with
the softare needs to be knowledgable in Python as well as in HTML.")

the alternative is: program the entire web site in pure python. as if
it was a pygtk2, pyqt4 or python-wxWidgets desktop application.

l.
 
T

Terrence Brannon

Learning the handful of constructs is the same as learning a handful of
API calls. The same goes for idiosyncrasies of e.g. inserting
sub-templates or dealing with repeating content.

I'm not sure I agree with you.

1 - the constructs probably call an internal API. that's two levels of
complexity to implement
2 - the API is based directly on Python. Python has a much larger
userbase and test suite than any template language
3 - the Python language has 15 years of refinement in what it offers
as language constructs. Most of these template language are ad hoc
products fashioned and re-fashioned over at most a 3 year period.
 

Members online

No members online now.

Forum statistics

Threads
473,744
Messages
2,569,482
Members
44,900
Latest member
Nell636132

Latest Threads

Top