1ecpp(7) Tntnet users guide ecpp(7)
2
3
4
6 ecpp - template language for tntnet(8)
7
8
10 ecpp is the template language used by the tntnet system to generate
11 dynamic content.
12
13
14 A template consists of normal content (normally html data) enriched
15 with special tags, which trigger some special handling.
16
17
18 One ecpp file is compiled into a C++ class. The C++ class is placed
19 into the namespace component. A ecpp file compiled into a C++ class is
20 called component. The name of the class is the basename of the file.
21
22
23 request, reply, qparam
24 Each component has 3 parameters: request, reply and qparam. request
25 holds information about the client request like http headers and the
26 url, but also additional parameters specified in the config file tnt‐
27 net.xml(7). The type of request is tnt::HttpRequest.
28
29
30 reply receives the answer from the component. The component can set
31 additional http headers here, set cookies and - most important - gener‐
32 ate output. The most important methods here are reply.out() and
33 reply.sout(). Both return a std::ostream, which receives the output of
34 the component. reply.sout() has a filter installed, which translates
35 some characters, with special meanings in html to the corresponding
36 html entities. The characters are <, >, , " and '. This is useful for
37 printing values from variables to the html code.
38
39
40 qparam holds the query parameters parsed from GET- or POST-parameters
41 or received from other components. The type of qparam is tnt::Query‐
42 Params. Normally you use a <%args> block to specify the parameters,
43 but there are special cases, where it is useful to access these
44 directly.
45
46
47 component addressing
48 Each component has a unique name. The name is composed from the class
49 name, the character '@' and the name of the shared library, it is
50 located. Components can have internal sub components. The name of the
51 internal sub component is appended to the class name separated by a dot
52 (.).
53
54
55 special rule for line feeds after a </%something>-tag
56 A line feed immediately after a closing tag for all <%something> blocks
57 are ignored. Hence blocks followed immediately one after another does
58 not generate white space in output, which is often undesirable.
59
60
61 errorhandling
62 Error handling is done by exception. Tntnet catches all exceptions
63 thrown by components and handles them properly. Exceptions must be
64 derived from std::exception. Exceptions derived from tnt::HttpError,
65 are handled separately. They carry a http return code, which is sent to
66 the client. Other exceptions derived from std::exception, result in a
67 http error code 500 (Internal Server Error).
68
69
71 <$ expr $>
72 Print expressions expr to the output stream. The characters <, >, , "
73 and ', which have special meanings in html, are translated to the
74 corresponding html entities.
75
76
77 <$$ expr $>
78 Print expressions expr without translating characters with special
79 meaning in
80 html to html entities to the output stream.
81
82
83 <? cond ? expr ?>
84 Conditional output. Print expression expr to the output stream, if
85 cond
86 evaluates to true. Characters with special meaning in html are trans‐
87 lated to
88 the corresponding html entities.
89
90
91 <?? cond ? expr ?>
92 Conditional output. Print expression expr to the output stream, if
93 cond
94 evaluates to true. Characters with special meaning in html are not
95 translated
96 to the corresponding html entities.
97
98
99 < component [ arguments ] >
100 Call the specified component. The output of the component is printed
101 into the
102 output stream. If the component name does not start with a letter,
103 the
104 ecpp compiler treats it as a expression, which returns the name of
105 the
106 component. You must surround the expression in brackets, if it con‐
107 tains
108 spaces.
109
110
111 The arguments part specify the parameters, the component will receive.
112 Arguments are name value pairs separated by '='. They are put in the
113 qparam parameter of the component and are normally declared in the
114 <%args> block. Values can be specified in 3 forms:
115
116
117 As a plain word without spaces
118
119
120 As a string enclosed in quotation marks
121
122
123 As a expression enclosed in brackets
124
125
126 A single plain word in the argument list is treated as a variable of
127 type
128 cxxtools::QueryParams and a copy is passed to the component. Other
129 parameters are added to this copy. If you want to pass all parameters
130 of the
131 current component put the variable qparam as a plain word in the
132 argument
133 list.
134
135
136 </component>
137 Closing tag for a component call. When components are called, this
138 closing tag might occur later. The code in <%close> block is placed
139 here.
140
141
142 <{...}>
143 C++ inline processing block. The code in this block is copied into
144 the
145 C++ class unchanged.
146
147
148 A linefeed after the closing tag is not ignored.
149
150
151 <#...#>
152 Comment block. Everything in this block is ignored.
153
154
155 <%application [ scope="component|page|shared|global" ] >...</%applica‐
156 tion>
157 Variables defined here, have the lifetime of the application.
158
159
160 Application scope is automatically locked.
161
162
163 <%args>...</%args>
164 Defines GET or POST parameters received by the component.
165
166
167 Each argument has a name and optionally a default value. The default
168 value is
169 delimited by '=' from the name. A single argument definition followed
170 by a
171 semicolon (;). In the component a variable with the same name of type
172 std::string is defined, which receives the value.
173
174
175 A argument name can be prefixed by a type definition. The ecpp compiler
176 generates code, which tries to convert the value with the cxxtools
177 deserialization operator. If the argument can't be converted, the
178 default
179 value is set.
180
181
182 Argument names can be postfixed by empty square brackets. This defines
183 a
184 std::vector with the specified type or std::string, if no type is
185 specified.
186 This way multiple values with the same name can be received. If a
187 type is
188 specified, each value is converted to the target type.
189
190
191 <%attr>...</%attr>
192 Components may define attributes, which can be queried from other
193 components.
194 These values are strings and are defined by specifying a name fol‐
195 lowed by '='
196 and the string value. No type is allowed here.
197
198
199 A other component can the fetch a reference to the component using
200 fetchComp(name). fetchComp is a member of the base class
201 tnt::EcppComponent of components built with ecpp.
202
203
204 The component has then a member method getAttribute(name), which
205 returns the
206 attribute or a empty string when not found. A different default
207 string can be
208 passed as a second parameter to getAttribute.
209
210
211 Example:
212 A content component specifies a title:
213
214
215 <%attr>
216 title = "my title";
217 </%attr>
218
219
220
221 A component webmain want to add a title depending on a content compo‐
222 nent:
223
224
225 <head>
226 <title>
227 <$ fetchComp("theContent").getAttribute("title", "default title") $>
228 </title>
229 ...
230
231
232
233 To separte the C++ code from the html, the actual doing can be moved to
234 a C++
235 section. The component can then be also called later to generate the
236 content:
237
238
239 <%cpp>
240 tnt::Component theContent = fetchComp("theContent");
241 std::string title = theContent.getAttribute("title", "default title");
242 </%cpp>
243 <head>
244 <title><$ title $></title>
245 ...
246 <div id="contnent">
247 <{ theContent(request, reply, qparam); }>
248 </div>
249
250
251
252 <%close>...</%close>
253 Code in these tags is placed into the calling component, when a clos‐
254 ing tag
255 </component> is found.
256
257
258 The <%close> receives the same parameters like the corresponding normal
259 component call.
260
261
262 This tag is deprecated and should not be used any more.
263
264
265 <%config>...</%config>
266 Often web applications need some configuration like database names or
267 login information to the database. These configuration variables can
268 be read
269 from the tntnet.xml. Variable names ended with a semicolon are
270 defined as
271 static std::string variables and filled from tntnet.xml. A variable
272 can be
273 prepended by a type. The value from tntnet.xml is then converted with
274 a
275 std::istream.
276
277
278 You can also specify a default value by appending a '=' and the value
279 to the
280 variable.
281
282
283 Example:
284 <%config>
285 dburl = "sqlite:db=mydbfile.sqlite";
286 int maxvalue = 10;
287 </%config>
288
289
290
291 tntnet.xml:
292 <dburl>postgresql:dbname=mydb</dburl>
293
294
295 <%cpp>...</%cpp>
296 C++ processing block. The code between these tags are copied into the
297 C++ class unchanged.
298
299
300 A linefeed after the closing tag is ignored.
301
302
303 <%def name>...</%def>
304 Defines a internal sub component with the name name, which can be
305 called like
306 other components.
307
308
309 <%doc>...</%doc>
310 Comment block. Everything in this block is ignored.
311
312
313 A linefeed after the closing tag is ignored.
314
315
316 <%get>...</%get>
317 Works like a <%args> block but receives only GET parameters.
318
319
320 <%include>filename</%include>
321 The specified file is read and compiled.
322
323
324 <%param>...</%param>
325 Defines parameter received from calling components. In contrast to
326 query parameters these variables can be of any type. The syntax (and
327 the
328 underlying technology) is the same like in scoped variables. See the
329 description about scoped variables to see how to define parameters.
330 The main
331 difference is, that a parameter variable has no scope, since the
332 parameter is
333 always local to the component.
334
335
336 <%out> expr </%out>
337 Same as <$$ ... $>. Prints the contained C++ expression expr.
338
339
340 <%post>...</%post>
341 Works like a <%args> block but receives only POST parameters.
342
343
344 <%pre>...</%pre>
345 Defines C++ code, which is placed outside the C++ class and outside
346 the
347 namespace definition. This is a good place to define #include direc‐
348 tives.
349
350
351 <%request [ scope="component|page|shared|global" ] >...</%request>
352 Define request scope variables. Variables defined here, has the life‐
353 time of
354 the request.
355
356
357 <%session [ scope="component|page|shared|global" ] >...</%session>
358 Variables defined here, has the lifetime of the session.
359
360
361 Sessions are identified with cookies. If a <%session> block is defined
362 somewhere in a component, a session cookie is sent to the client.
363
364
365 Sessions are automatically locked.
366
367
368 <%securesession [ scope="component|page|shared|global" ] >...</%secure‐
369 session>
370 Secure session is just like session but a secure cookie is used to
371 identify
372 the session. Secure cookies are transferred only over a ssl connec‐
373 tion from
374 the browser and hence the variables are only kept in a ssl secured
375 application.
376
377
378 If a variable defined here is used in a non ssl page, the variable val‐
379 ues are
380 lost after the current request.
381
382
383 <%sout> expr </%sout>
384 Same as <$ ... $>. Prints the contained C++ expression expr. The
385 characters
386 <, >, , " and ', which have special meanings in html, are translated
387 to the
388 corresponding html entities.
389
390
391 <%thread [ scope="component|page|shared|global" ] >...</%thread>
392 Variables defined here, has the lifetime of the thread. Each thread
393 has his
394 own instance of these variables.
395
396
397 Thread scope variables do not need to be locked at all, because they
398 are only
399 valid in the current thread.
400
401
403 Scoped variables are c++ variables, whose lifetime is handled by tnt‐
404 net. These variables has a lifetime and a scope. The lifetime is
405 defined by the tag, used to declare the variable and the scope is
406 passed as a parameter to the tag.
407
408
409 There are 5 different lifetimes for scoped variables:
410
411
412 request
413 The variable is valid in the current request. The tag is <%request>.
414
415
416 application
417 The variable is valid in the application. The tag is <%application>.
418 The
419 application is specified by the shared library of the top level com‐
420 ponent.
421
422
423 session
424 The variable is valid for the current session. The tag is <%session>.
425 If at
426 least session variable is declared in the current request, a session
427 cookie is
428 sent to the client.
429
430
431 thread
432 The variable is valid in the current thread. The tag is <%thread>.
433
434
435 param
436 The variable receives parameters. The tag is <%param>.
437
438
439 And 3 scopes:
440
441
442 component
443 The variable is only valid in the same component. This is the default
444 scope.
445
446
447 page
448 The variable is shared between the components in a single ecpp file.
449 You can
450 specify multiple internal sub components in a <%def> block. Vari‐
451 ables,
452 defined in page scope are shared between these sub components.
453
454
455 global or shared
456 Variables are shared between all components. If you define the same
457 variable
458 with shared scope in different components, they must have the same
459 type. This
460 is achieved most easily defining them in a separate file and include
461 them
462 with a <%include> block. The global and shared are just synonyms.
463
464
465 Variables are automatically locked as needed. If you use session vari‐
466 ables,
467 tntnet ensures, that all requests of the same session are serialized.
468 If you
469 use application variables, tntnet serializes all requests to the same
470 application scope. Request and thread scope variables do not need to
471 be
472 locked at all, because they are not shared between threads.
473
474
475 Syntax of scoped variables
476 Scoped variables are declared with exactly the same syntax as normal
477 variables in c++ code. They can be of any type and are instantiated,
478 when needed. Objects, which do not have default constructors, need to
479 be specified with proper constructor parameters in brackets or sepa‐
480 rated by '='. The parameters are only used, if the variable need to be
481 instantiated. This means, that parameters to e.g. application scope
482 variables are only used once. When the same component is called later
483 in the same or another request, the parameters are not used any more.
484
485
486 Examples
487 Specify a application specific shared variable, which is initialized
488 with 0:
489
490
491 <%application>
492 unsigned count = 0;
493 </%application>
494
495
496
497 Specify a variable with a user defined type, which holds the state of
498 the session:
499
500
501 <%session>
502 MyClass sessionState;
503 </%session>
504
505
506
507 Specify a persistent database connection, which is initialized, when
508 first needed and hold for the lifetime of the current thread. This
509 variable may be used in other components:
510
511
512 <%thread scope="shared">
513 tntdb::Connection conn(dburl);
514 </%thread>
515
516
517
519 This manual page was written by Tommi Mäkitalo ⟨tommi@tntnet.org⟩.
520
521
523 tntnet(8), ecppc(1)
524
525
526
527Tntnet 2006-07-23 ecpp(7)