summaryrefslogtreecommitdiff
path: root/docs/devel_guide_src/design.tex
blob: 3008a635f7d3b4450e7337678c7818edfbb9f121 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
\section{Design Decisions and Tradeoffs}
\label{design}


%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
\subsection{Delimiters}
\label{design.Delimiters}

One of the first decisions we encountered was which delimiter syntax to use.
We decided to follow Velocity's \code{\$placeholder} and \code{\#directive}
syntax because the former is widely used in other languages for the same
purpose, and the latter stands out in an HTML or text document.  We also
implemented the \verb+${longPlaceholder}+ syntax like the shells for cases
where Cheetah or you might be confused where a placeholder ends.  Tavis went
ahead and made \verb+${longPlaceholder}+ and \verb+$[longPlaceholder]+
interchangeable with it since it was trivial to implement.  Finally,
the \code{\#compiler} directive allows you to change the delimiters if you
don't like them or if they conflict with the text in your document.
(Obviously, if your document contains a Perl program listing, you don't 
necessarily want to backslash each and every \code{\$} and \code{\#}, do you?)

The choice of comment delimiters was more arbitrary.  \code{\#\#} and
\code{\#* \ldots *\#} doesn't match any language, but it's reminiscent of
Python and C while also being consistent with our ``\code{\#} is for
directives'' convention.

We specifically chose {\em not} to use pseudo HTML tags for placeholders and
directives, as described more thoroughly in the Cheetah Users' Guide
introduction.  Pseudo HTML tags may be easier to see in a visual editor
(supposedly), but in text editors they're hard to distinguish from ``real''
HTML tags unless you look closely, and they're many more keystrokes to type.
Also, if you make a mistake, the tag will show up as literal text in the
rendered HTML page where it will be easy to notice and eradicate, rather than
disappearing as bogus HTML tags do in browsers.

%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
\subsection{Late binding}
\label{design.lateBinding}

One of Cheetah's unique features is the name mapper, which lets you write
\code{\$a.b} without worrying much about the type of \code{a} or \code{b}.
Prior to version 0.9.7, Cheetah did the entire NameMapper lookup at runtime.
This provided maximum flexibility at the expense of speed.  Doing a NameMapper
lookup is intrinsically more expensive than an ordinary Python expression
because Cheetah has to decide what type of container \code{a} is, whether the
the value is a function (autocall it), issue the appropriate Python incantation
to look up \code{b} in it, autocall again if necessary, and then convert the
result to a string.

To maximize run-time (filling-time) performance, Cheetah 0.9.7 pushed much of
this work back into the compiler.  The compiler looked up \code{a} in the
searchList at compile time, noted its type, and generated an eval'able Python
expression based on that.  

This approach had two significant drawbacks.  What if \code{a} later changes
type before a template filling?  Answer: unpredictable exceptions occur.  What
if \code{a} does not exist in the searchList at compile time?  Answer: the
template can't compile.

To prevent these catastrophes, users were required to prepopulate the
searchList before instantiating the template instance, and then not to change
\code{a}'s type.  Static typing is repugnant in a dynamic language like Python,
and having to prepopulate the searchList made certain usages impossible.  For
example, you couldn't instantiate the template object without a searchList and
then set \code{self} attributes to specify the values.  

After significant user complaints about the fragility of this system, Tavis
rewrote placeholder handling, and in version 0.9.8a3 (August 2001), Tavis
moved the name mapper lookup back into runtime.  Performance wasn't crippled
because he discovered that writing a C version of the name mapper was easier
than anticipated, and the C version completed the lookup quickly.  Now Cheetah
had ``late binding'', meaning the compiler does not look up \code{a} or care
whether it exists.  This allows users to create \code{a} or change its type
anytime before a template filling.

The lesson we learned is that it's better to decide what you want and then
figure out how to do it, rather than assuming that certain goals are 
unattainable due to performance considerations.  



%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
\subsection{Caching framework}
\label{design.cache}



%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
\subsection{Webware compatibility and the transaction framework}
\label{design.webware}

%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
\subsection{Single inheritance}
\label{design.singleInheritance}





% Local Variables:
% TeX-master: "devel_guide"
% End: