1Titanium(3) User Contributed Perl Documentation Titanium(3)
2
3
4
6 Titanium - A strong, lightweight web application framework
7
9 Coding
10 # In "WebApp.pm"...
11 package WebApp;
12 use base 'Titanium';
13
14 sub setup {
15 my $c = shift;
16
17 $c->start_mode('form_display');
18 $c->run_modes([qw/
19 form_display
20 form_process
21 /]);
22 }
23 sub form_display {
24 my $c = shift;
25 my $errs = shift;
26
27 my $t = $c->load_tmpl;
28 $t->param($errs) if $errs;
29 return $t->output;
30 }
31 sub form_process {
32 my $c = shift;
33
34 # Validate the form against a profile. If it fails validation, re-display
35 # the form for the user with their data pre-filled and the errors highlighted.
36 my ($results, $err_page) = $c->check_rm('form_display','_form_profile');
37 return $err_page if $err_page;
38
39 return $c->forward('form_success');
40 }
41
42 # Return a Data::FormValidator profile
43 sub _form_profile {
44 my $c = shift;
45 return {
46 required => 'email',
47 };
48 }
49
50 sub form_success { ... }
51
52 1;
53
54 ### In "webapp.cgi"...
55 use WebApp;
56 my $c = WebApp->new();
57 $c->run();
58
59 Inside the run modes, the following methods are available:
60
61 $c->query; # A query object. CGI.pm by default.
62 $c->redirect('http://othersite.com'); # Basic redirection
63 $c->dbh; # DBI database handle
64 $c->session(); # A CGI::Session object
65 $c->check_rm; # Form validation with Data::FormValidator
66 $c->cfg('root_uri'); # Config file access (YAML, Perl or INI formats)
67 $c->fill_form; # Form filling with HTML::FillInForm
68 $c->error( title => '..', msg => '..' ); # Easy error page generation
69 $c->stream_file($file); # file streaming
70 $c->log; # A Log::Dispatch object
71
72 Development and Testing
73 Easily setup the project skeleton using the bundled cgiapp-starter
74 script.
75
76 In development you can turn on a debugging screen and a developer pop-
77 up to quickly catch code, html and performance issues, thanks to
78 CGI::Application::Plugin::DebugScreen and
79 CGI::Application::Plugin::DevPopup.
80
81 For automated testing, Test::WWW::Mechanize::CGIApp is bundled,
82 allowing you to functionally test your web application without
83 involving a full web server. If you'd rather test against full web
84 server, Test::WWW::Mechanize is there, too.
85
86 Dispatching with Clean URIs
87 Modern web frameworks dispense with cruft in URIs. Instead of:
88
89 /cgi-bin/item.cgi?rm=view&id=15
90
91 A clean URI to describe the same resource might be:
92
93 /item/15/view
94
95 The process of mapping these URIs to run modes is called dispatching
96 and is handled by CGI::Application::Dispatch. It comes with a default
97 dispatch table that automatically creates URLs in this pattern for you:
98
99 /app/module_name/run_mode
100
101 There's plenty of flexibility to design your own URIs if you'd like.
102
104 * Titanium is solid and mature. While it has a new name, the reality is
105 that Titanium is simply a more user-friendly packaging of the mature
106 CGI::Application framework and some useful plugins. These packages have
107 already been refined and vetted. The seed framework was first released
108 in 2000 and by 2005 was mature. Titanium contains no real code of its
109 own, and there is no intention to do so in the future. Instead, we may
110 select other mature plugins to include in the future. Other "Titanium
111 alloys" in the "Titanium::Alloy::" name space may also come to exist,
112 following the same philosophy, but choosing to bundle a different
113 combination of plugins.
114
115 * Titanium is lightweight. Titanium has a very light core and the
116 plugins it uses employ lazy-loading whenever possible. That means that
117 while we have built-in database plugin, we don't have to load DBI or
118 make a database connection until you actually use the database
119 connection. Titanium runs well in a plain CGI environment and provides
120 excellent performance in a persistent environment such as FastCGI or
121 mod_perl. Titanium apps are compatible with the dozens of published
122 plugins for CGI::Application, so you can add additional features as
123 your needs evolve.
124
126 It is intended that your Application Module will be implemented as a
127 sub-class of Titanium. This is done simply as follows:
128
129 package My::App;
130 use base 'Titanium';
131
132 Notation and Conventions
133
134 For the purpose of this document, we will refer to the following
135 conventions:
136
137 WebApp.pm : The Perl module which implements your Application Module class.
138 WebApp : Your Application Module class; a sub-class of Titanium.
139 webapp.cgi : The Instance Script which implements your Application Module.
140 $c : Used in instance methods to pass around the
141 current object. (Sometimes referred as "$self" in other projects.)
142 Think of the "$c" as short for "controller".
143
144 Script/Dispatching Methods
145 By inheriting from Titanium you have access to a number of built-in
146 methods. The following are those which are expected to be called from
147 your Instance Script or through your CGI::Application::Dispatch
148 dispatcher.
149
150 new()
151
152 The new() method is the constructor for a Titanium. It returns a
153 blessed reference to your Application Module class. Optionally, new()
154 may take a set of parameters as key => value pairs:
155
156 my $c = WebApp->new(
157 TMPL_PATH => 'App/',
158 PARAMS => {
159 'custom_thing_1' => 'some val',
160 'another_custom_thing' => [qw/123 456/]
161 }
162 );
163
164 This method may take some specific parameters:
165
166 TMPL_PATH - This optional parameter defines a path to a directory of
167 templates. This is used by the load_tmpl() method (specified below),
168 and may also be used for the same purpose by other template plugins.
169 This run-time parameter allows you to further encapsulate instantiating
170 templates, providing potential for more re-usability. It can be either
171 a scalar or an array reference of multiple paths.
172
173 QUERY - This optional parameter allows you to specify an already-
174 created CGI query object. Under normal use, Titanium will instantiate
175 its own CGI.pm query object. Under certain conditions, it might be
176 useful to be able to use one which has already been created.
177
178 PARAMS - This parameter, if used, allows you to set a number of custom
179 parameters at run-time. By passing in different values in different
180 instance scripts which use the same application module you can achieve
181 a higher level of re-usability. For instance, imagine an application
182 module, "Mailform.pm". The application takes the contents of a HTML
183 form and emails it to a specified recipient. You could have multiple
184 instance scripts throughout your site which all use this "Mailform.pm"
185 module, but which set different recipients or different forms.
186
187 One common use of instance scripts is to provide a path to a config
188 file. This design allows you to define project wide configuration
189 objects used by many several instance scripts. There are several
190 plugins which simplify the syntax for this and provide lazy loading.
191 Here's an example using CGI::Application::Plugin::ConfigAuto, which
192 uses Config::Auto to support many configuration file formats.
193
194 my $app = WebApp->new(PARAMS => { cfg_file => 'config.pl' });
195
196 # Later in your app:
197 my %cfg = $c->cfg()
198 # or ... $c->cfg('HTML_ROOT_DIR');
199
200 See the list of of plugins below for more config file integration
201 solutions.
202
203 run()
204
205 The run() method is called upon your Application Module object, from
206 your Instance Script. When called, it executes the functionality in
207 your Application Module.
208
209 my $c = WebApp->new;
210 $c->run;
211
212 This method determines the application state by looking at the dispatch
213 table, as described in CGI::Application::Dispatch.
214
215 Once the mode has been determined, run() looks at the hash stored in
216 run_modes() and finds the subroutine which is tied to a specific hash
217 key. If found, the function is called and the data returned is
218 print()'ed to STDOUT and to the browser. If the specified mode is not
219 found in the run_modes() table, run() will croak(). This 'death' can
220 possibly be captured and handled using error_mode(), described below.
221
222 Essential Method to Override
223 Titanium implements some methods which are expected to be overridden by
224 implementing them in your sub-class module. One of these is essential
225 to do:
226
227 setup()
228
229 This method is called by the inherited new() constructor method. The
230 setup() method should be used to define the following property/methods:
231
232 start_mode() - string containing the default run mode.
233 run_modes() - hash table containing mode => function mappings.
234
235 error_mode() - string containing the error mode.
236 tmpl_path() - string or array reference containing path(s) to template directories.
237
238 Your setup() method may call any of the instance methods of your
239 application. This function is a good place to define properties
240 specific to your application via the $c->param() method.
241
242 Your setup() method might be implemented something like this:
243
244 sub setup {
245 my $c = shift;
246 $c->start_mode('putform');
247 $c->run_modes([qw/
248 form
249 form_process
250 /]);
251 }
252
253 Essential Application Methods
254 The following methods are inherited from Titanium, and are available to
255 be called by your application within your Application Module. They are
256 called essential because you will use all are most of them to get any
257 application up and running. These functions are listed in alphabetical
258 order.
259
260 load_tmpl()
261
262 my $tmpl_obj = $c->load_tmpl;
263 my $tmpl_obj = $c->load_tmpl('some.html');
264 my $tmpl_obj = $c->load_tmpl( \$template_content );
265 my $tmpl_obj = $c->load_tmpl( FILEHANDLE );
266
267 This method takes the name of a template file, a reference to template
268 data or a FILEHANDLE and returns an HTML::Template object. If the
269 filename is undefined or missing, Titanium will default to trying to
270 use the current run mode name, plus the extension ".html".
271
272 If you use the default template naming system, you should also use
273 CGI::Application::Plugin::Forward, which simply helps to keep the
274 current name accurate when you pass control from one run mode to
275 another.
276
277 ( For integration with other template systems and automated template
278 names, see "Alternatives to load_tmpl() below. )
279
280 When you pass in a filename, the HTML::Template->new_file() constructor
281 is used for create the object. When you pass in a reference to the
282 template content, the HTML::Template->new_scalar_ref() constructor is
283 used and when you pass in a filehandle, the
284 HTML::Template->new_filehandle() constructor is used.
285
286 Refer to HTML::Template for specific usage of HTML::Template.
287
288 If tmpl_path() has been specified, load_tmpl() will set the
289 HTML::Template "path" option to the path(s) provided. This further
290 assists in encapsulating template usage.
291
292 The load_tmpl() method will pass any extra parameters sent to it
293 directly to HTML::Template->new_file() (or new_scalar_ref() or
294 new_filehandle()). This will allow the HTML::Template object to be
295 further customized:
296
297 my $tmpl_obj = $c->load_tmpl('some_other.html',
298 die_on_bad_params => 0,
299 cache => 1
300 );
301
302 Note that if you want to pass extra arguments but use the default
303 template name, you still need to provide a name of "undef":
304
305 my $tmpl_obj = $c->load_tmpl(undef',
306 die_on_bad_params => 0,
307 cache => 1
308 );
309
310 Alternatives to load_tmpl()
311
312 If your application requires more specialized behavior than this, you
313 can always replace it by overriding load_tmpl() by implementing your
314 own load_tmpl() in your Titanium sub-class application module.
315
316 First, you may want to check out the template related plugins.
317
318 CGI::Application::Plugin::TT focuses just on Template Toolkit
319 integration, and features pre-and-post features, singleton support and
320 more.
321
322 param()
323
324 $c->param('pname', $somevalue);
325
326 The param() method provides a facility through which you may set
327 application instance properties which are accessible throughout your
328 application.
329
330 The param() method may be used in two basic ways. First, you may use
331 it to get or set the value of a parameter:
332
333 $c->param('scalar_param', '123');
334 my $scalar_param_values = $c->param('some_param');
335
336 Second, when called in the context of an array, with no parameter name
337 specified, param() returns an array containing all the parameters which
338 currently exist:
339
340 my @all_params = $c->param();
341
342 The param() method also allows you to set a bunch of parameters at once
343 by passing in a hash (or hashref):
344
345 $c->param(
346 'key1' => 'val1',
347 'key2' => 'val2',
348 'key3' => 'val3',
349 );
350
351 The param() method enables a very valuable system for customizing your
352 applications on a per-instance basis. One Application Module might be
353 instantiated by different Instance Scripts. Each Instance Script might
354 set different values for a set of parameters. This allows similar
355 applications to share a common code-base, but behave differently. For
356 example, imagine a mail form application with a single Application
357 Module, but multiple Instance Scripts. Each Instance Script might
358 specify a different recipient. Another example would be a web bulletin
359 boards system. There could be multiple boards, each with a different
360 topic and set of administrators.
361
362 The new() method provides a shortcut for specifying a number of run-
363 time parameters at once. Internally, Titanium calls the param() method
364 to set these properties. The param() method is a powerful tool for
365 greatly increasing your application's re-usability.
366
367 query()
368
369 my $q = $c->query();
370 my $remote_user = $q->remote_user();
371
372 This method retrieves the CGI.pm query object which has been created by
373 instantiating your Application Module. For details on usage of this
374 query object, refer to CGI. Titanium is built on the CGI module.
375 Generally speaking, you will want to become very familiar with CGI.pm,
376 as you will use the query object whenever you want to interact with
377 form data.
378
379 When the new() method is called, a CGI query object is automatically
380 created. If, for some reason, you want to use your own CGI query
381 object, the new() method supports passing in your existing query object
382 on construction using the QUERY attribute.
383
384 run_modes()
385
386 # The common usage: an arrayref of run mode names that exactly match subroutine names
387 $c->run_modes([qw/
388 form_display
389 form_process
390 /]);
391
392 # With a hashref, use a different name or a code ref
393 $c->run_modes(
394 'mode1' => 'some_sub_by_name',
395 'mode2' => \&some_other_sub_by_ref
396 );
397
398 This accessor/mutator specifies a lookup table for the application
399 states, using the syntax examples above. It returns the dispatch table
400 as a hash.
401
402 The run_modes() method may be called more than once. Additional values
403 passed into run_modes() will be added to the run modes table. In the
404 case that an existing run mode is re-defined, the new value will
405 override the existing value. This behavior might be useful for
406 applications which are created via inheritance from another
407 application, or some advanced application which modifies its own
408 capabilities based on user input.
409
410 The run() method uses the data in this table to send the application to
411 the correct function as determined by the dispatcher, as described in
412 CGI::Application::Dispatch. These functions are referred to as "run
413 mode methods".
414
415 The hash table set by this method is expected to contain the mode name
416 as a key. The value should be either a hard reference (a subref) to
417 the run mode method which you want to be called when the application
418 enters the specified run mode, or the name of the run mode method to be
419 called:
420
421 'mode_name_by_ref' => \&mode_function
422 'mode_name_by_name' => 'mode_function'
423
424 The run mode method specified is expected to return a block of text
425 (e.g.: HTML) which will eventually be sent back to the web browser.
426 The run mode method may return its block of text as a scalar or a
427 scalar-ref.
428
429 An advantage of specifying your run mode methods by name instead of by
430 reference is that you can more easily create derivative applications
431 using inheritance. For instance, if you have a new application which
432 is exactly the same as an existing application with the exception of
433 one run mode, you could simply inherit from that other application and
434 override the run mode method which is different. If you specified your
435 run mode method by reference, your child class would still use the
436 function from the parent class.
437
438 An advantage of specifying your run mode methods by reference instead
439 of by name is performance. Dereferencing a subref is faster than
440 eval()-ing a code block. If run-time performance is a critical issue,
441 specify your run mode methods by reference and not by name. The speed
442 differences are generally small, however, so specifying by name is
443 preferred.
444
445 Specifying the run modes by array reference:
446
447 $c->run_modes([ 'mode1', 'mode2', 'mode3' ]);
448
449 Is is the same as using a hash, with keys equal to values
450
451 $c->run_modes(
452 'mode1' => 'mode1',
453 'mode2' => 'mode2',
454 'mode3' => 'mode3'
455 );
456
457 Often, it makes good organizational sense to have your run modes map to
458 methods of the same name. The array-ref interface provides a shortcut
459 to that behavior while reducing verbosity of your code.
460
461 Note that another importance of specifying your run modes in either a
462 hash or array-ref is to assure that only those Perl methods which are
463 specifically designated may be called via your application.
464 Application environments which don't specify allowed methods and
465 disallow all others are insecure, potentially opening the door to
466 allowing execution of arbitrary code. Titanium maintains a strict
467 "default-deny" stance on all method invocation, thereby allowing secure
468 applications to be built upon it.
469
470 IMPORTANT NOTE ABOUT RUN MODE METHODS
471
472 Your application should *NEVER* print() to STDOUT. Using print() to
473 send output to STDOUT (including HTTP headers) is exclusively the
474 domain of the inherited run() method. Breaking this rule is a common
475 source of errors. If your program is erroneously sending content
476 before your HTTP header, you are probably breaking this rule.
477
478 THE RUN MODE OF LAST RESORT: "AUTOLOAD"
479
480 If Titanium is asked to go to a run mode which doesn't exist, by
481 default it will return an error page to the user, implemented like
482 this:
483
484 return $c->error(
485 title => 'The requested page was not found.',
486 msg => "(The page tried was: ".$c->get_current_runmode.")"
487 );
488
489 See CGI::Application::Plugin::ErrorPage for more details on the built-
490 in error page system. If this is not your desired behavior for
491 handling unknown run mode requests, implement your own run mode with
492 the reserved name "AUTOLOAD":
493
494 $c->run_modes(
495 "AUTOLOAD" => \&catch_my_exception
496 );
497
498 Before Titanium invokes its own error page handling it will check for
499 the existence of a run mode called "AUTOLOAD". If specified, this run
500 mode will in invoked just like a regular run mode, with one exception:
501 It will receive, as an argument, the name of the run mode which invoked
502 it:
503
504 sub catch_my_exception {
505 my $c = shift;
506 my $intended_runmode = shift;
507
508 my $output = "Looking for '$intended_runmode', but found 'AUTOLOAD' instead";
509 return $output;
510 }
511
512 This functionality could be for more sophisticated application
513 behaviors.
514
515 start_mode()
516
517 $c->start_mode('mode1');
518
519 The start_mode contains the name of the mode as specified in the
520 run_modes() table. Default mode is "start". The mode key specified
521 here will be used whenever the value of the CGI form parameter
522 specified by mode_param() is not defined. Generally, this is the first
523 time your application is executed.
524
525 tmpl_path()
526
527 $c->tmpl_path('/path/to/some/templates/');
528
529 This access/mutator method sets the file path to the directory (or
530 directories) where the templates are stored. It is used by load_tmpl()
531 to find the template files, using HTML::Template's "path" option. To
532 set the path you can either pass in a text scalar or an array reference
533 of multiple paths.
534
535 More Methods to override
536 Several more non-essential methods are useful to declare in your
537 application class, or in a project "super class" that inherits from
538 your Titanium only to serve in turn as a base class for project
539 modules. These additional methods are as follows:
540
541 teardown()
542
543 If implemented, this method is called automatically after your
544 application runs. It can be used to clean up after your operations. A
545 typical use of the teardown() function is to disconnect a database
546 connection which was established in the setup() function, or flush open
547 session data. You could also use the teardown() method to store state
548 information about the application to the server.
549
550 cgiapp_init()
551
552 If implemented, this method is called automatically right before the
553 setup() method is called. The cgiapp_init() method receives, as its
554 parameters, all the arguments which were sent to the new() method.
555
556 An example of the benefits provided by utilizing this hook is creating
557 a custom "application super-class" from which which all your web
558 applications would inherit, instead of directly from Titanium.
559
560 Consider the following:
561
562 # In MySuperclass.pm:
563 package MySuperclass;
564 use base 'Titanium';
565 sub cgiapp_init {
566 my $c = shift;
567 # Perform some project-specific init behavior
568 # such as to load settings from a database or file.
569 }
570
571
572 # In MyApplication.pm:
573 package MyApplication;
574 use base 'MySuperclass';
575 sub setup { ... }
576 sub teardown { ... }
577 # The rest of your Titanium-based follows...
578
579 By using Titanium and the cgiapp_init() method as illustrated, a suite
580 of applications could be designed to share certain characteristics,
581 creating cleaner code.
582
583 cgiapp_prerun()
584
585 If implemented, this method is called automatically right before the
586 selected run mode method is called. This method provides an optional
587 pre-runmode hook, which permits functionality to be added at the point
588 right before the run mode method is called. The value of the run mode
589 is passed into cgiapp_prerun().
590
591 This could be used by a custom "application super-class" from which all
592 your web applications would inherit, instead of Titanium.
593
594 Consider the following:
595
596 # In MySuperclass.pm:
597 package MySuperclass;
598 use base 'Titanium';
599 sub cgiapp_prerun {
600 my $c = shift;
601 # Perform some project-specific init behavior
602 # such as to implement run mode specific
603 # authorization functions.
604 }
605
606
607 # In MyApplication.pm:
608 package MyApplication;
609 use base 'MySuperclass';
610 sub setup { ... }
611 sub teardown { ... }
612 # The rest of your Titanium-based follows...
613
614 It is also possible, within your cgiapp_prerun() method, to change the
615 run mode of your application. This can be done via the prerun_mode()
616 method, which is discussed elsewhere.
617
618 cgiapp_postrun()
619
620 If implemented, this hook will be called after the run mode method has
621 returned its output, but before HTTP headers are generated. This will
622 give you an opportunity to modify the body and headers before they are
623 returned to the web browser.
624
625 A typical use for this hook is pipelining the output of a CGI-
626 Application through a series of "filter" processors. For example:
627
628 * You want to enclose the output of all your CGI-Applications in
629 an HTML table in a larger page.
630
631 * Your run modes return structured data (such as XML), which you
632 want to transform using a standard mechanism (such as XSLT).
633
634 * You want to post-process CGI-App output through another system,
635 such as HTML::Mason.
636
637 * You want to modify HTTP headers in a particular way across all
638 run modes, based on particular criteria.
639
640 The cgiapp_postrun() hook receives a reference to the output from your
641 run mode method, in addition to the CGI-App object. A typical
642 cgiapp_postrun() method might be implemented as follows:
643
644 sub cgiapp_postrun {
645 my $c = shift;
646 my $output_ref = shift;
647
648 # Enclose output HTML table
649 my $new_output = "<table border=1>";
650 $new_output .= "<tr><td> Hello, World! </td></tr>";
651 $new_output .= "<tr><td>". $$output_ref ."</td></tr>";
652 $new_output .= "</table>";
653
654 # Replace old output with new output
655 $$output_ref = $new_output;
656 }
657
658 Obviously, with access to the CGI-App object you have full access to
659 use all the methods normally available in a run mode. You could, for
660 example, use load_tmpl() to replace the static HTML in this example
661 with HTML::Template. You could change the HTTP headers (via
662 header_add() ). You could also use the objects properties to apply
663 changes only under certain circumstance, such as a in only certain run
664 modes, and when a param() is a particular value.
665
666 cgiapp_get_query()
667
668 my $q = $c->cgiapp_get_query;
669
670 Override this method to retrieve the query object if you wish to use a
671 different query interface instead of CGI.pm.
672
673 CGI.pm is only loaded to provided query object is only loaded if it
674 used on a given request.
675
676 If you can use an alternative to CGI.pm, it needs to have some
677 compatibility with the CGI.pm API. For normal use, just having a
678 compatible "param" method should be sufficient.
679
680 If use the "path_info" option to the mode_param() method, then we will
681 call the path_info() method on the query object.
682
683 If you use the "Dump" method in Titanium, we will call the "Dump" and
684 "escapeHTML" methods on the query object.
685
686 More Application Methods
687 You can skip this section if you are just getting started.
688
689 The following additional methods are inherited from Titanium, and are
690 available to be called by your application within your Application
691 Module. These functions are listed in alphabetical order.
692
693 error_mode()
694
695 $c->error_mode('my_error_rm');
696
697 If the runmode dies for whatever reason, "run() will" see if you have
698 set a value for error_mode(). If you have, run() will call that method
699 as a run mode, passing $@ as the only parameter.
700
701 No "error_mode" is defined by default. The death of your error_mode()
702 run mode is not trapped, so you can also use it to die in your own
703 special way.
704
705 For a complete integrated logging solution, check out
706 CGI::Application::Plugin::LogDispatch.
707
708 header_add()
709
710 # add or replace the 'type' header
711 $c->header_add( -type => 'image/png' );
712
713 - or -
714
715 # add an additional cookie
716 $c->header_add(-cookie=>[$extra_cookie]);
717
718 The header_add() method is used to add one or more headers to the
719 outgoing response headers. The parameters will eventually be passed on
720 to the CGI.pm header() method, so refer to the CGI docs for exact usage
721 details.
722
723 Unlike calling header_props(), header_add() will preserve any existing
724 headers. If a scalar value is passed to header_add() it will replace
725 the existing value for that key.
726
727 If an array reference is passed as a value to header_add(), values in
728 that array ref will be appended to any existing values values for that
729 key. This is primarily useful for setting an additional cookie after
730 one has already been set.
731
732 header_props()
733
734 $c->header_props(-type=>'image/gif',-expires=>'+3d');
735
736 The header_props() method expects a hash of CGI.pm-compatible HTTP
737 header properties. These properties will be passed directly to
738 CGI.pm's header() or redirect() methods. Refer to CGI for exact usage
739 details.
740
741 Calling header_props any arguments will clobber any existing headers
742 that have previously set.
743
744 header_props() return a hash of all the headers that have currently
745 been set. It can be called with no arguments just to get the hash
746 current headers back.
747
748 To add additional headers later without clobbering the old ones, see
749 header_add().
750
751 IMPORTANT NOTE REGARDING HTTP HEADERS
752
753 It is through the header_props() and header_add() method that you may
754 modify the outgoing HTTP headers. This is necessary when you want to
755 set a cookie, set the mime type to something other than "text/html", or
756 perform a redirect. Understanding this relationship is important if
757 you wish to manipulate the HTTP header properly.
758
759 redirect()
760
761 return $c->redirect('http://www.example.com/');
762
763 Redirect to another URL.
764
765 forward()
766
767 return $c->forward('rm_name');
768
769 Pass control to another run mode and return its output. This is
770 equivalent to calling $self->$other_runmode, except that the internal
771 value of the current run mode is updated. This bookkeeping is important
772 to load_tmpl() when called with no arguments and some other plugins.
773
774 dbh()
775
776 sub cgiapp_init {
777 my $c = shift;
778
779 # use the same args as DBI->connect();
780 $c->dbh_config($data_source, $username, $auth, \%attr);
781
782 }
783
784 sub form_process {
785 my $c = shift;
786
787 my $dbh = $c->dbh;
788 }
789
790 Easy access to a DBI database handle. The database connection is not
791 created until the first call to dbh(). See
792 CGI::Application::Plugin::DBH for more features and details.
793
794 session()
795
796 # in cgiapp_init()
797 $c->session_config(
798 CGI_SESSION_OPTIONS => [ "driver:PostgreSQL;serializer:Storable", $self->query, {Handle=>$dbh} ],
799 );
800
801 # in a run mode
802 my $ses = $c->session->param('foo');
803
804 Easy access to a CGI::Session object, so you can store user data
805 between requests. The session is not accessed or created until the
806 first call to session() in a given request. See
807 CGI::Application::Plugin::Session for more features and details.
808
809 cfg()
810
811 $c->cfg('root_uri');
812
813 Easy access to parameters loaded from a config file, which can be
814 stored in one of several formats, including YAML and Pure Perl. For
815 more features and details see CGI::Application::Plugin::ConfigAuto.
816
817 log()
818
819 $c->log->info('Information message');
820 $c->log->debug('Debug message');
821
822 Easy access to a Log::Dispatch logging object, allowing you to log to
823 different locations with different locations of severity. By adjusting
824 the logging level for your application, you make "debug" messages
825 appear or disappear from your logs without making pervasive code
826 changes. See CGI::Application::Plugin::LogDispatch for more features
827 and details.
828
829 check_rm()
830
831 my ($results, $err_page) = $c->check_rm('form_display','_form_profile');
832 return $err_page if $err_page;
833
834 Easy form validation with Data::FormValidator. If the validation fails,
835 we'll re-display the form for the user with their data pre-filled and
836 the errors highlighted. You'll have full control over the design of the
837 errors with HTML and CSS in your templates, although we provide some
838 intelligent defaults. See CGI::Application::Plugin::ValidateRM for
839 features and details.
840
841 fill_form()
842
843 # fill an HTML form with data in a hashref or from an object with with a param() method
844 my $filled_html = $self->fill_form($html, $data);
845
846 # ...or default to getting data from $self->query()
847 my $filled_html = $self->fill_form($html);
848
849 HTML::FillInForm is a useful when you want to fill in a web form with
850 default values from a database table. Like many CPAN modules, you can
851 use directly from CGI::Application without any special plugin. The
852 value of this plugin is that it defaults to finding values through
853 $self->query(). Besides that, it is just a bit of synatic sugar that
854 was mostly created work-around weaknesses in the HTML::FillInForm 1.x
855 interface, which were fixed with HTML::FillInForm 2.0 release. See
856 CGI::Application::Plugin::FillInForm for details.
857
858 error()
859
860 $c->error( title => '..', msg => '..' );
861
862 Provide quick error messages back to the user for exceptional cases.
863 You can provide your own custom designed template or use the default
864 one built-in. See CGI::Application::Plugin::ErrorPage.
865
866 stream_file()
867
868 $c->stream_file($file);
869
870 If your run mode is outputing an image or a spreadsheet instead of an
871 HTML page, you may want to stream the output. This method takes care of
872 the boring details of buffering, headers and MIME types. See
873 CGI::Application::Plugin::Stream for details.
874
875 prerun_mode()
876
877 $c->prerun_mode('new_run_mode');
878
879 The prerun_mode() method is an accessor/mutator which can be used
880 within your cgiapp_prerun() method to change the run mode which is
881 about to be executed. For example, consider:
882
883 # In WebApp.pm:
884 package WebApp;
885 use base 'Titanium';
886 sub cgiapp_prerun {
887 my $c = shift;
888
889 # Get the web user name, if any
890 my $q = $c->query();
891 my $user = $q->remote_user();
892
893 # Redirect to login, if necessary
894 unless ($user) {
895 $c->prerun_mode('login');
896 }
897 }
898
899 In this example, the web user will be forced into the "login" run mode
900 unless they have already logged in. The prerun_mode() method permits a
901 scalar text string to be set which overrides whatever the run mode
902 would otherwise be.
903
904 The prerun_mode() method should be used in cases where you want to use
905 Titanium's normal run mode switching facility, but you want to make
906 selective changes to the mode under specific conditions.
907
908 Note: The prerun_mode() method may ONLY be called in the context of a
909 cgiapp_prerun() method. Your application will die() if you call
910 prerun_mode() elsewhere, such as in setup() or a run mode method.
911
912 Dispatching Clean URIs to run modes
913 Modern web frameworks dispense with cruft in URIs, providing in clean
914 URIs instead. Instead of:
915
916 /cgi-bin/item.cgi?rm=view&id=15
917
918 A clean URI to describe the same resource might be:
919
920 /item/15/view
921
922 The process of mapping these URIs to run modes is called dispatching
923 and is handled by CGI::Application::Dispatch. Dispatching is not
924 required and is a layer you can fairly easily add to an application
925 later.
926
927 Offline website development
928 You can work on your Titanium project on your desktop or laptop without
929 installing a full-featured web-server like Apache. Instead, install
930 CGI::Application::Server from CPAN. After a few minutes of setup,
931 you'll have your own private application server up and running.
932
933 Automated Testing
934 There a couple of testing modules specifically made for Titanium.
935
936 Test::WWW::Mechanize::CGIApp allows functional testing of a
937 CGI::App-based project without starting a web server.
938 Test::WWW::Mechanize could be used to test the app through a real web
939 server.
940
941 Test::WWW::Selenium is similar, but uses Selenium for the testing,
942 meaning that a local web-browser would be used, allowing testing of
943 websites that contain JavaScript.
944
945 Direct testing is also easy. Titanium will normally print the output of
946 it's run modes directly to STDOUT. This can be surprised with an
947 enviroment variable, CGI_APP_RETURN_ONLY. For example:
948
949 $ENV{CGI_APP_RETURN_ONLY} = 1;
950 $output = $c->run;
951 like($output, qr/good/, "output is good");
952
953 Examples of this style can be seen in our own test suite.
954
956 Titanium has a plug-in architecture that is easy to use and easy to
957 develop new plug-ins for. Plugins made for CGI::Application are
958 directly compatible. The CGI::Application should be referenced for
959 those who wish to write plugins.
960
961 Select plugins are listed below. For a current complete list, please
962 consult CPAN:
963
964 http://search.cpan.org/search?m=dist&q=CGI%2DApplication%2DPlugin
965
966 • CGI::Application::Plugin::Apache - Use Apache::* modules without
967 interference
968
969 • CGI::Application::Plugin::AutoRunmode - Automatically register
970 runmodes
971
972 • CGI::Application::Plugin::CompressGzip - Add Gzip compression
973
974 • CGI::Application::Plugin::TT - Use Template::Toolkit as an
975 alternative to HTML::Template.
976
977 Consult each plug-in for the exact usage syntax.
978
980 Therese are primary resources available for those who wish to learn
981 more about Titanium and discuss it with others.
982
983 Wiki
984
985 This is a community built and maintained resource that anyone is
986 welcome to contribute to. It contains a number of articles of its own
987 and links to many other Titanium related pages. It is currently branded
988 as CGI::Application, but the code is the same.
989
990 <http://www.cgi-app.org>
991
992 Support Mailing List
993
994 If you have any questions, comments, bug reports or feature
995 suggestions, post them to the support mailing list! To join the
996 mailing list, simply send a blank message to
997 "cgiapp-subscribe@lists.erlbaum.net".
998
999 IRC
1000
1001 You can also drop by "#cgiapp" on "irc.perl.org" with a good chance of
1002 finding some people involved with the project there.
1003
1004 Source Code
1005
1006 This project is managed using the darcs source control system (
1007 http://www.darcs.net/ ). The darcs archive is here:
1008 http://mark.stosberg.com/darcs_hive/titanium
1009
1011 * I would like Titanium to be easier to install and get started with.
1012 Rather than depending on the large CPAN dependency chain being
1013 installed, I would like an option for users to download the full stack
1014 of dependencies, so that you can just unpack a single file and go.
1015
1016 * I'd like a plugin to cope with the URI-encoding that Dreamweaver does
1017 to templates that may just mean packing and releasing the following
1018 code as a plug-in:
1019
1020 CGI::Application->add_callback('load_tmpl',sub {
1021 my ($c, $ht_params, $tmpl_params, $tmpl_file) = @_;
1022
1023 require HTML::Template::Filter::URIdecode;
1024 import HTML::Template::Filter::URIdecode 'ht_uri_decode';
1025
1026 # If you already have a filter defined, don't do anything.
1027 # If you want to add more of your own filters later, be mindful
1028 # about whether you add to this arrayref, or replace it.
1029 unless ($ht_params->{filter}) {
1030 $ht_params->{filter} = [\&ht_uri_decode]
1031 }
1032 });
1033
1035 • CGI::Application
1036
1038 If you're interested in finding out more about Titanium, the following
1039 articles are available on Perl.com, providing context about the
1040 underlying CGI::Application framework
1041
1042 Using CGI::Application
1043 http://www.perl.com/pub/a/2001/06/05/cgi.html
1044
1045 Rapid Website Development with CGI::Application
1046 http://www.perl.com/pub/a/2006/10/19/cgi_application.html
1047
1048 Thanks to O'Reilly for publishing these articles, and for the
1049 incredible value they provide to the Perl community!
1050
1052 Many.
1053
1054 Mark Stosberg, "mark@summersault.com" published the original Titanium
1055 module, while many another contributed to CGI::Application and the
1056 related plugins.
1057
1059 Copyright (C) 2008, Mark Stosberg.
1060
1061 This module is free software; you can redistribute it and/or modify it
1062 under the terms of either:
1063
1064 a) the GNU General Public License as published by the Free Software
1065 Foundation; either version 1, or (at your option) any later version,
1066
1067 or
1068
1069 b) the "Artistic License".
1070
1071 This program is distributed in the hope that it will be useful, but
1072 WITHOUT ANY WARRANTY; without even the implied warranty of
1073 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See either the
1074 GNU General Public License or the Artistic License for more details.
1075
1076
1077
1078perl v5.36.0 2023-01-20 Titanium(3)