28b8a27d9305726926aef1280dad0b13b62a3985
[catagits/Catalyst-Runtime.git] / lib / Catalyst.pm
1 package Catalyst;
2
3 use MRO::Compat;
4 use mro 'c3';
5 use Moose;
6 extends 'Catalyst::Component';
7 use bytes;
8 use Catalyst::Exception;
9 use Catalyst::Log;
10 use Catalyst::Request;
11 use Catalyst::Request::Upload;
12 use Catalyst::Response;
13 use Catalyst::Utils;
14 use Catalyst::Controller;
15 use Devel::InnerPackage ();
16 use File::stat;
17 use Module::Pluggable::Object ();
18 use Text::SimpleTable ();
19 use Path::Class::Dir ();
20 use Path::Class::File ();
21 use Time::HiRes qw/gettimeofday tv_interval/;
22 use URI ();
23 use URI::http;
24 use URI::https;
25 use Scalar::Util qw/weaken blessed/;
26 use Tree::Simple qw/use_weak_refs/;
27 use Tree::Simple::Visitor::FindByUID;
28 use attributes;
29 use utf8;
30 use Carp qw/croak carp/;
31
32 BEGIN { require 5.008001; }
33
34 has stack => (is => 'rw', default => sub { [] });
35 has stash => (is => 'rw', default => sub { {} });
36 has state => (is => 'rw', default => 0);
37 has stats => (is => 'rw');
38 has action => (is => 'rw');
39 has counter => (is => 'rw', default => sub { {} });
40 has request => (is => 'rw', default => sub { $_[0]->request_class->new({}) }, required => 1, lazy => 1);
41 has response => (is => 'rw', default => sub { $_[0]->response_class->new({}) }, required => 1, lazy => 1);
42 has namespace => (is => 'rw');
43
44 no Moose;
45
46 attributes->import( __PACKAGE__, \&namespace, 'lvalue' );
47
48 sub depth { scalar @{ shift->stack || [] }; }
49 sub comp { shift->component(@_) }
50
51 sub req {
52     # carp "the use of req() is deprecated in favour of request()";
53     my $self = shift; return $self->request(@_);
54 }
55 sub res {
56     # carp "the use of res() is deprecated in favour of response()";
57     my $self = shift; return $self->response(@_);
58 }
59
60 # For backwards compatibility
61 sub finalize_output { shift->finalize_body(@_) };
62
63 # For statistics
64 our $COUNT     = 1;
65 our $START     = time;
66 our $RECURSION = 1000;
67 our $DETACH    = "catalyst_detach\n";
68
69 #I imagine that very few of these really need to be class variables. if any.
70 #maybe we should just make them attributes with a default?
71 __PACKAGE__->mk_classdata($_)
72   for qw/components arguments dispatcher engine log dispatcher_class
73   engine_class context_class request_class response_class stats_class 
74   setup_finished/;
75
76 __PACKAGE__->dispatcher_class('Catalyst::Dispatcher');
77 __PACKAGE__->engine_class('Catalyst::Engine::CGI');
78 __PACKAGE__->request_class('Catalyst::Request');
79 __PACKAGE__->response_class('Catalyst::Response');
80 __PACKAGE__->stats_class('Catalyst::Stats');
81
82 # Remember to update this in Catalyst::Runtime as well!
83
84 our $VERSION = '5.7013';
85
86 sub import {
87     my ( $class, @arguments ) = @_;
88
89     # We have to limit $class to Catalyst to avoid pushing Catalyst upon every
90     # callers @ISA.
91     return unless $class eq 'Catalyst';
92
93     my $caller = caller();
94     return if $caller eq 'main';
95     my $meta = Moose::Meta::Class->initialize($caller);
96     #Moose->import({ into => $caller }); #do we want to do this?
97
98     unless ( $caller->isa('Catalyst') ) {
99         my @superclasses = ($meta->superclasses, $class, 'Catalyst::Controller');
100         $meta->superclasses(@superclasses);
101     }
102     unless( $meta->has_method('meta') ){
103         $meta->add_method(meta => sub { Moose::Meta::Class->initialize("${caller}") } );
104     }
105
106     $caller->arguments( [@arguments] );
107     $caller->setup_home;
108 }
109
110 =head1 NAME
111
112 Catalyst - The Elegant MVC Web Application Framework
113
114 =head1 SYNOPSIS
115
116 See the L<Catalyst::Manual> distribution for comprehensive
117 documentation and tutorials.
118
119     # Install Catalyst::Devel for helpers and other development tools
120     # use the helper to create a new application
121     catalyst.pl MyApp
122
123     # add models, views, controllers
124     script/myapp_create.pl model MyDatabase DBIC::Schema create=dynamic dbi:SQLite:/path/to/db
125     script/myapp_create.pl view MyTemplate TT
126     script/myapp_create.pl controller Search
127
128     # built in testserver -- use -r to restart automatically on changes
129     # --help to see all available options
130     script/myapp_server.pl
131
132     # command line testing interface
133     script/myapp_test.pl /yada
134
135     ### in lib/MyApp.pm
136     use Catalyst qw/-Debug/; # include plugins here as well
137     
138     ### In lib/MyApp/Controller/Root.pm (autocreated)
139     sub foo : Global { # called for /foo, /foo/1, /foo/1/2, etc.
140         my ( $self, $c, @args ) = @_; # args are qw/1 2/ for /foo/1/2
141         $c->stash->{template} = 'foo.tt'; # set the template
142         # lookup something from db -- stash vars are passed to TT
143         $c->stash->{data} = 
144           $c->model('Database::Foo')->search( { country => $args[0] } );
145         if ( $c->req->params->{bar} ) { # access GET or POST parameters
146             $c->forward( 'bar' ); # process another action
147             # do something else after forward returns            
148         }
149     }
150     
151     # The foo.tt TT template can use the stash data from the database
152     [% WHILE (item = data.next) %]
153         [% item.foo %]
154     [% END %]
155     
156     # called for /bar/of/soap, /bar/of/soap/10, etc.
157     sub bar : Path('/bar/of/soap') { ... }
158
159     # called for all actions, from the top-most controller downwards
160     sub auto : Private { 
161         my ( $self, $c ) = @_;
162         if ( !$c->user_exists ) { # Catalyst::Plugin::Authentication
163             $c->res->redirect( '/login' ); # require login
164             return 0; # abort request and go immediately to end()
165         }
166         return 1; # success; carry on to next action
167     }
168     
169     # called after all actions are finished
170     sub end : Private { 
171         my ( $self, $c ) = @_;
172         if ( scalar @{ $c->error } ) { ... } # handle errors
173         return if $c->res->body; # already have a response
174         $c->forward( 'MyApp::View::TT' ); # render template
175     }
176
177     ### in MyApp/Controller/Foo.pm
178     # called for /foo/bar
179     sub bar : Local { ... }
180     
181     # called for /blargle
182     sub blargle : Global { ... }
183     
184     # an index action matches /foo, but not /foo/1, etc.
185     sub index : Private { ... }
186     
187     ### in MyApp/Controller/Foo/Bar.pm
188     # called for /foo/bar/baz
189     sub baz : Local { ... }
190     
191     # first Root auto is called, then Foo auto, then this
192     sub auto : Private { ... }
193     
194     # powerful regular expression paths are also possible
195     sub details : Regex('^product/(\w+)/details$') {
196         my ( $self, $c ) = @_;
197         # extract the (\w+) from the URI
198         my $product = $c->req->captures->[0];
199     }
200
201 See L<Catalyst::Manual::Intro> for additional information.
202
203 =head1 DESCRIPTION
204
205 Catalyst is a modern framework for making web applications without the
206 pain usually associated with this process. This document is a reference
207 to the main Catalyst application. If you are a new user, we suggest you
208 start with L<Catalyst::Manual::Tutorial> or L<Catalyst::Manual::Intro>.
209
210 See L<Catalyst::Manual> for more documentation.
211
212 Catalyst plugins can be loaded by naming them as arguments to the "use
213 Catalyst" statement. Omit the C<Catalyst::Plugin::> prefix from the
214 plugin name, i.e., C<Catalyst::Plugin::My::Module> becomes
215 C<My::Module>.
216
217     use Catalyst qw/My::Module/;
218
219 If your plugin starts with a name other than C<Catalyst::Plugin::>, you can
220 fully qualify the name by using a unary plus:
221
222     use Catalyst qw/
223         My::Module
224         +Fully::Qualified::Plugin::Name
225     /;
226
227 Special flags like C<-Debug> and C<-Engine> can also be specified as
228 arguments when Catalyst is loaded:
229
230     use Catalyst qw/-Debug My::Module/;
231
232 The position of plugins and flags in the chain is important, because
233 they are loaded in the order in which they appear.
234
235 The following flags are supported:
236
237 =head2 -Debug
238
239 Enables debug output. You can also force this setting from the system
240 environment with CATALYST_DEBUG or <MYAPP>_DEBUG. The environment
241 settings override the application, with <MYAPP>_DEBUG having the highest
242 priority.
243
244 =head2 -Engine
245
246 Forces Catalyst to use a specific engine. Omit the
247 C<Catalyst::Engine::> prefix of the engine name, i.e.:
248
249     use Catalyst qw/-Engine=CGI/;
250
251 =head2 -Home
252
253 Forces Catalyst to use a specific home directory, e.g.:
254
255     use Catalyst qw[-Home=/usr/mst];
256
257 This can also be done in the shell environment by setting either the
258 C<CATALYST_HOME> environment variable or C<MYAPP_HOME>; where C<MYAPP>
259 is replaced with the uppercased name of your application, any "::" in
260 the name will be replaced with underscores, e.g. MyApp::Web should use
261 MYAPP_WEB_HOME. If both variables are set, the MYAPP_HOME one will be used.
262
263 =head2 -Log
264
265 Specifies log level.
266
267 =head2 -Stats
268
269 Enables statistics collection and reporting. You can also force this setting
270 from the system environment with CATALYST_STATS or <MYAPP>_STATS. The
271 environment settings override the application, with <MYAPP>_STATS having the
272 highest priority.
273
274 e.g. 
275
276    use Catalyst qw/-Stats=1/
277
278 =head1 METHODS
279
280 =head2 INFORMATION ABOUT THE CURRENT REQUEST
281
282 =head2 $c->action
283
284 Returns a L<Catalyst::Action> object for the current action, which
285 stringifies to the action name. See L<Catalyst::Action>.
286
287 =head2 $c->namespace
288
289 Returns the namespace of the current action, i.e., the URI prefix
290 corresponding to the controller of the current action. For example:
291
292     # in Controller::Foo::Bar
293     $c->namespace; # returns 'foo/bar';
294
295 =head2 $c->request
296
297 =head2 $c->req
298
299 Returns the current L<Catalyst::Request> object, giving access to
300 information about the current client request (including parameters,
301 cookies, HTTP headers, etc.). See L<Catalyst::Request>.
302
303 =head2 REQUEST FLOW HANDLING
304
305 =head2 $c->forward( $action [, \@arguments ] )
306
307 =head2 $c->forward( $class, $method, [, \@arguments ] )
308
309 Forwards processing to another action, by its private name. If you give a
310 class name but no method, C<process()> is called. You may also optionally
311 pass arguments in an arrayref. The action will receive the arguments in
312 C<@_> and C<< $c->req->args >>. Upon returning from the function,
313 C<< $c->req->args >> will be restored to the previous values.
314
315 Any data C<return>ed from the action forwarded to, will be returned by the
316 call to forward.
317
318     my $foodata = $c->forward('/foo');
319     $c->forward('index');
320     $c->forward(qw/MyApp::Model::DBIC::Foo do_stuff/);
321     $c->forward('MyApp::View::TT');
322
323 Note that forward implies an C<<eval { }>> around the call (actually
324 C<execute> does), thus de-fatalizing all 'dies' within the called
325 action. If you want C<die> to propagate you need to do something like:
326
327     $c->forward('foo');
328     die $c->error if $c->error;
329
330 Or make sure to always return true values from your actions and write
331 your code like this:
332
333     $c->forward('foo') || return;
334
335 =cut
336
337 sub forward { my $c = shift; no warnings 'recursion'; $c->dispatcher->forward( $c, @_ ) }
338
339 =head2 $c->detach( $action [, \@arguments ] )
340
341 =head2 $c->detach( $class, $method, [, \@arguments ] )
342
343 =head2 $c->detach()
344
345 The same as C<forward>, but doesn't return to the previous action when 
346 processing is finished. 
347
348 When called with no arguments it escapes the processing chain entirely.
349
350 =cut
351
352 sub detach { my $c = shift; $c->dispatcher->detach( $c, @_ ) }
353
354 =head2 $c->response
355
356 =head2 $c->res
357
358 Returns the current L<Catalyst::Response> object, see there for details.
359
360 =head2 $c->stash
361
362 Returns a hashref to the stash, which may be used to store data and pass
363 it between components during a request. You can also set hash keys by
364 passing arguments. The stash is automatically sent to the view. The
365 stash is cleared at the end of a request; it cannot be used for
366 persistent storage (for this you must use a session; see
367 L<Catalyst::Plugin::Session> for a complete system integrated with
368 Catalyst).
369
370     $c->stash->{foo} = $bar;
371     $c->stash( { moose => 'majestic', qux => 0 } );
372     $c->stash( bar => 1, gorch => 2 ); # equivalent to passing a hashref
373     
374     # stash is automatically passed to the view for use in a template
375     $c->forward( 'MyApp::View::TT' );
376
377 =cut
378
379 sub stash {
380     my $c = shift;
381     if (@_) {
382         my $stash = @_ > 1 ? {@_} : $_[0];
383         croak('stash takes a hash or hashref') unless ref $stash;
384         foreach my $key ( keys %$stash ) {
385             #shouldn't we hold this in a var and save ourselves the subcall?
386             $c->next::method->{$key} = $stash->{$key};
387         }
388     }
389
390     return $c->next::method;
391 }
392
393
394 =head2 $c->error
395
396 =head2 $c->error($error, ...)
397
398 =head2 $c->error($arrayref)
399
400 Returns an arrayref containing error messages.  If Catalyst encounters an
401 error while processing a request, it stores the error in $c->error.  This
402 method should only be used to store fatal error messages.
403
404     my @error = @{ $c->error };
405
406 Add a new error.
407
408     $c->error('Something bad happened');
409
410 =cut
411
412 sub error {
413     my $c = shift;
414     if ( $_[0] ) {
415         my $error = ref $_[0] eq 'ARRAY' ? $_[0] : [@_];
416         croak @$error unless ref $c;
417         push @{ $c->{error} }, @$error;
418     }
419     elsif ( defined $_[0] ) { $c->{error} = undef }
420     return $c->{error} || [];
421 }
422
423
424 =head2 $c->state
425
426 Contains the return value of the last executed action.
427
428 =head2 $c->clear_errors
429
430 Clear errors.  You probably don't want to clear the errors unless you are
431 implementing a custom error screen.
432
433 This is equivalent to running
434
435     $c->error(0);
436
437 =cut
438
439 sub clear_errors {
440     my $c = shift;
441     $c->error(0);
442 }
443
444
445 # search via regex
446 sub _comp_search {
447     my ( $c, @names ) = @_;
448
449     foreach my $name (@names) {
450         foreach my $component ( keys %{ $c->components } ) {
451             return $c->components->{$component} if $component =~ /$name/i;
452         }
453     }
454
455     return undef;
456 }
457
458 # try explicit component names
459 sub _comp_explicit {
460     my ( $c, @names ) = @_;
461
462     foreach my $try (@names) {
463         return $c->components->{$try} if ( exists $c->components->{$try} );
464     }
465
466     return undef;
467 }
468
469 # like component, but try just these prefixes before regex searching,
470 #  and do not try to return "sort keys %{ $c->components }"
471 sub _comp_prefixes {
472     my ( $c, $name, @prefixes ) = @_;
473
474     my $appclass = ref $c || $c;
475
476     my @names = map { "${appclass}::${_}::${name}" } @prefixes;
477
478     my $comp = $c->_comp_explicit(@names);
479     return $comp if defined($comp);
480     $comp = $c->_comp_search($name);
481     return $comp;
482 }
483
484 # Find possible names for a prefix 
485
486 sub _comp_names {
487     my ( $c, @prefixes ) = @_;
488
489     my $appclass = ref $c || $c;
490
491     my @pre = map { "${appclass}::${_}::" } @prefixes;
492
493     my @names;
494
495     COMPONENT: foreach my $comp ($c->component) {
496         foreach my $p (@pre) {
497             if ($comp =~ s/^$p//) {
498                 push(@names, $comp);
499                 next COMPONENT;
500             }
501         }
502     }
503
504     return @names;
505 }
506
507 # Return a component if only one matches.
508 sub _comp_singular {
509     my ( $c, @prefixes ) = @_;
510
511     my $appclass = ref $c || $c;
512
513     my ( $comp, $rest ) =
514       map { $c->_comp_search("^${appclass}::${_}::") } @prefixes;
515     return $comp unless $rest;
516 }
517
518 # Filter a component before returning by calling ACCEPT_CONTEXT if available
519 sub _filter_component {
520     my ( $c, $comp, @args ) = @_;
521     if ( eval { $comp->can('ACCEPT_CONTEXT'); } ) {
522         return $comp->ACCEPT_CONTEXT( $c, @args );
523     }
524     else { return $comp }
525 }
526
527 =head2 COMPONENT ACCESSORS
528
529 =head2 $c->controller($name)
530
531 Gets a L<Catalyst::Controller> instance by name.
532
533     $c->controller('Foo')->do_stuff;
534
535 If the name is omitted, will return the controller for the dispatched
536 action.
537
538 =cut
539
540 sub controller {
541     my ( $c, $name, @args ) = @_;
542     return $c->_filter_component( $c->_comp_prefixes( $name, qw/Controller C/ ),
543         @args )
544       if ($name);
545     return $c->component( $c->action->class );
546 }
547
548 =head2 $c->model($name)
549
550 Gets a L<Catalyst::Model> instance by name.
551
552     $c->model('Foo')->do_stuff;
553
554 Any extra arguments are directly passed to ACCEPT_CONTEXT.
555
556 If the name is omitted, it will look for 
557  - a model object in $c->stash{current_model_instance}, then
558  - a model name in $c->stash->{current_model}, then
559  - a config setting 'default_model', or
560  - check if there is only one model, and return it if that's the case.
561
562 =cut
563
564 sub model {
565     my ( $c, $name, @args ) = @_;
566     return $c->_filter_component( $c->_comp_prefixes( $name, qw/Model M/ ),
567         @args )
568       if $name;
569     if (ref $c) {
570         return $c->stash->{current_model_instance} 
571           if $c->stash->{current_model_instance};
572         return $c->model( $c->stash->{current_model} )
573           if $c->stash->{current_model};
574     }
575     return $c->model( $c->config->{default_model} )
576       if $c->config->{default_model};
577     return $c->_filter_component( $c->_comp_singular(qw/Model M/) );
578
579 }
580
581 =head2 $c->controllers
582
583 Returns the available names which can be passed to $c->controller
584
585 =cut
586
587 sub controllers {
588     my ( $c ) = @_;
589     return $c->_comp_names(qw/Controller C/);
590 }
591
592
593 =head2 $c->view($name)
594
595 Gets a L<Catalyst::View> instance by name.
596
597     $c->view('Foo')->do_stuff;
598
599 Any extra arguments are directly passed to ACCEPT_CONTEXT.
600
601 If the name is omitted, it will look for 
602  - a view object in $c->stash{current_view_instance}, then
603  - a view name in $c->stash->{current_view}, then
604  - a config setting 'default_view', or
605  - check if there is only one view, and return it if that's the case.
606
607 =cut
608
609 sub view {
610     my ( $c, $name, @args ) = @_;
611     return $c->_filter_component( $c->_comp_prefixes( $name, qw/View V/ ),
612         @args )
613       if $name;
614     if (ref $c) {
615         return $c->stash->{current_view_instance} 
616           if $c->stash->{current_view_instance};
617         return $c->view( $c->stash->{current_view} )
618           if $c->stash->{current_view};
619     }
620     return $c->view( $c->config->{default_view} )
621       if $c->config->{default_view};
622     return $c->_filter_component( $c->_comp_singular(qw/View V/) );
623 }
624
625 =head2 $c->models
626
627 Returns the available names which can be passed to $c->model
628
629 =cut
630
631 sub models {
632     my ( $c ) = @_;
633     return $c->_comp_names(qw/Model M/);
634 }
635
636
637 =head2 $c->views
638
639 Returns the available names which can be passed to $c->view
640
641 =cut
642
643 sub views {
644     my ( $c ) = @_;
645     return $c->_comp_names(qw/View V/);
646 }
647
648 =head2 $c->comp($name)
649
650 =head2 $c->component($name)
651
652 Gets a component object by name. This method is not recommended,
653 unless you want to get a specific component by full
654 class. C<< $c->controller >>, C<< $c->model >>, and C<< $c->view >>
655 should be used instead.
656
657 =cut
658
659 sub component {
660     my $c = shift;
661
662     if (@_) {
663
664         my $name = shift;
665
666         my $appclass = ref $c || $c;
667
668         my @names = (
669             $name, "${appclass}::${name}",
670             map { "${appclass}::${_}::${name}" }
671               qw/Model M Controller C View V/
672         );
673
674         my $comp = $c->_comp_explicit(@names);
675         return $c->_filter_component( $comp, @_ ) if defined($comp);
676
677         $comp = $c->_comp_search($name);
678         return $c->_filter_component( $comp, @_ ) if defined($comp);
679     }
680
681     return sort keys %{ $c->components };
682 }
683
684
685
686 =head2 CLASS DATA AND HELPER CLASSES
687
688 =head2 $c->config
689
690 Returns or takes a hashref containing the application's configuration.
691
692     __PACKAGE__->config( { db => 'dsn:SQLite:foo.db' } );
693
694 You can also use a C<YAML>, C<XML> or C<Config::General> config file
695 like myapp.yml in your applications home directory. See
696 L<Catalyst::Plugin::ConfigLoader>.
697
698     ---
699     db: dsn:SQLite:foo.db
700
701
702 =cut
703
704 sub config {
705     my $c = shift;
706
707     $c->log->warn("Setting config after setup has been run is not a good idea.")
708       if ( @_ and $c->setup_finished );
709
710     $c->next::method(@_);
711 }
712
713 =head2 $c->log
714
715 Returns the logging object instance. Unless it is already set, Catalyst
716 sets this up with a L<Catalyst::Log> object. To use your own log class,
717 set the logger with the C<< __PACKAGE__->log >> method prior to calling
718 C<< __PACKAGE__->setup >>.
719
720  __PACKAGE__->log( MyLogger->new );
721  __PACKAGE__->setup;
722
723 And later:
724
725     $c->log->info( 'Now logging with my own logger!' );
726
727 Your log class should implement the methods described in
728 L<Catalyst::Log>.
729
730
731 =head2 $c->debug
732
733 Overload to enable debug messages (same as -Debug option).
734
735 Note that this is a static method, not an accessor and should be overloaded
736 by declaring "sub debug { 1 }" in your MyApp.pm, not by calling $c->debug(1).
737
738 =cut
739
740 sub debug { 0 }
741
742 =head2 $c->dispatcher
743
744 Returns the dispatcher instance. Stringifies to class name. See
745 L<Catalyst::Dispatcher>.
746
747 =head2 $c->engine
748
749 Returns the engine instance. Stringifies to the class name. See
750 L<Catalyst::Engine>.
751
752
753 =head2 UTILITY METHODS
754
755 =head2 $c->path_to(@path)
756
757 Merges C<@path> with C<< $c->config->{home} >> and returns a
758 L<Path::Class::Dir> object.
759
760 For example:
761
762     $c->path_to( 'db', 'sqlite.db' );
763
764 =cut
765
766 sub path_to {
767     my ( $c, @path ) = @_;
768     my $path = Path::Class::Dir->new( $c->config->{home}, @path );
769     if ( -d $path ) { return $path }
770     else { return Path::Class::File->new( $c->config->{home}, @path ) }
771 }
772
773 =head2 $c->plugin( $name, $class, @args )
774
775 Helper method for plugins. It creates a classdata accessor/mutator and
776 loads and instantiates the given class.
777
778     MyApp->plugin( 'prototype', 'HTML::Prototype' );
779
780     $c->prototype->define_javascript_functions;
781
782 =cut
783
784 sub plugin {
785     my ( $class, $name, $plugin, @args ) = @_;
786     $class->_register_plugin( $plugin, 1 );
787
788     eval { $plugin->import };
789     $class->mk_classdata($name);
790     my $obj;
791     eval { $obj = $plugin->new(@args) };
792
793     if ($@) {
794         Catalyst::Exception->throw( message =>
795               qq/Couldn't instantiate instant plugin "$plugin", "$@"/ );
796     }
797
798     $class->$name($obj);
799     $class->log->debug(qq/Initialized instant plugin "$plugin" as "$name"/)
800       if $class->debug;
801 }
802
803 =head2 MyApp->setup
804
805 Initializes the dispatcher and engine, loads any plugins, and loads the
806 model, view, and controller components. You may also specify an array
807 of plugins to load here, if you choose to not load them in the C<use
808 Catalyst> line.
809
810     MyApp->setup;
811     MyApp->setup( qw/-Debug/ );
812
813 =cut
814
815 sub setup {
816     my ( $class, @arguments ) = @_;
817     Class::C3::initialize;
818     $class->log->warn("Running setup twice is not a good idea.")
819       if ( $class->setup_finished );
820
821     unless ( $class->isa('Catalyst') ) {
822
823         Catalyst::Exception->throw(
824             message => qq/'$class' does not inherit from Catalyst/ );
825     }
826
827     if ( $class->arguments ) {
828         @arguments = ( @arguments, @{ $class->arguments } );
829     }
830
831     # Process options
832     my $flags = {};
833
834     foreach (@arguments) {
835
836         if (/^-Debug$/) {
837             $flags->{log} =
838               ( $flags->{log} ) ? 'debug,' . $flags->{log} : 'debug';
839         }
840         elsif (/^-(\w+)=?(.*)$/) {
841             $flags->{ lc $1 } = $2;
842         }
843         else {
844             push @{ $flags->{plugins} }, $_;
845         }
846     }
847
848     $class->setup_home( delete $flags->{home} );
849
850     $class->setup_log( delete $flags->{log} );
851     $class->setup_plugins( delete $flags->{plugins} );
852     $class->setup_dispatcher( delete $flags->{dispatcher} );
853     $class->setup_engine( delete $flags->{engine} );
854     $class->setup_stats( delete $flags->{stats} );
855
856     for my $flag ( sort keys %{$flags} ) {
857
858         if ( my $code = $class->can( 'setup_' . $flag ) ) {
859             &$code( $class, delete $flags->{$flag} );
860         }
861         else {
862             $class->log->warn(qq/Unknown flag "$flag"/);
863         }
864     }
865
866     eval { require Catalyst::Devel; };
867     if( !$@ && $ENV{CATALYST_SCRIPT_GEN} && ( $ENV{CATALYST_SCRIPT_GEN} < $Catalyst::Devel::CATALYST_SCRIPT_GEN ) ) {
868         $class->log->warn(<<"EOF");
869 You are running an old script!
870
871   Please update by running (this will overwrite existing files):
872     catalyst.pl -force -scripts $class
873
874   or (this will not overwrite existing files):
875     catalyst.pl -scripts $class
876
877 EOF
878     }
879     
880     if ( $class->debug ) {
881         my @plugins = map { "$_  " . ( $_->VERSION || '' ) } $class->registered_plugins;
882
883         if (@plugins) {
884             my $t = Text::SimpleTable->new(74);
885             $t->row($_) for @plugins;
886             $class->log->debug( "Loaded plugins:\n" . $t->draw . "\n" );
887         }
888
889         my $dispatcher = $class->dispatcher;
890         my $engine     = $class->engine;
891         my $home       = $class->config->{home};
892
893         $class->log->debug(qq/Loaded dispatcher "$dispatcher"/);
894         $class->log->debug(qq/Loaded engine "$engine"/);
895
896         $home
897           ? ( -d $home )
898           ? $class->log->debug(qq/Found home "$home"/)
899           : $class->log->debug(qq/Home "$home" doesn't exist/)
900           : $class->log->debug(q/Couldn't find home/);
901     }
902
903     # Call plugins setup
904     {
905         no warnings qw/redefine/;
906         local *setup = sub { };
907         $class->setup;
908     }
909
910     # Initialize our data structure
911     $class->components( {} );
912
913     $class->setup_components;
914
915     if ( $class->debug ) {
916         my $t = Text::SimpleTable->new( [ 63, 'Class' ], [ 8, 'Type' ] );
917         for my $comp ( sort keys %{ $class->components } ) {
918             my $type = ref $class->components->{$comp} ? 'instance' : 'class';
919             $t->row( $comp, $type );
920         }
921         $class->log->debug( "Loaded components:\n" . $t->draw . "\n" )
922           if ( keys %{ $class->components } );
923     }
924
925     # Add our self to components, since we are also a component
926     if( $class->isa('Catalyst::Controller') ){
927       $class->components->{$class} = $class;
928     }
929
930     $class->setup_actions;
931
932     if ( $class->debug ) {
933         my $name = $class->config->{name} || 'Application';
934         $class->log->info("$name powered by Catalyst $Catalyst::VERSION");
935     }
936     $class->log->_flush() if $class->log->can('_flush');
937
938     $class->setup_finished(1);
939     Class::C3::initialize;
940 }
941
942 =head2 $c->uri_for( $path, @args?, \%query_values? )
943
944 Merges path with C<< $c->request->base >> for absolute URIs and with
945 C<< $c->namespace >> for relative URIs, then returns a normalized L<URI>
946 object. If any args are passed, they are added at the end of the path.
947 If the last argument to C<uri_for> is a hash reference, it is assumed to
948 contain GET parameter key/value pairs, which will be appended to the URI
949 in standard fashion.
950
951 Note that uri_for is destructive to the passed hashref.  Subsequent calls
952 with the same hashref may have unintended results.
953
954 Instead of C<$path>, you can also optionally pass a C<$action> object
955 which will be resolved to a path using
956 C<< $c->dispatcher->uri_for_action >>; if the first element of
957 C<@args> is an arrayref it is treated as a list of captures to be passed
958 to C<uri_for_action>.
959
960 =cut
961
962 sub uri_for {
963     my ( $c, $path, @args ) = @_;
964
965     if ( Scalar::Util::blessed($path) ) { # action object
966         my $captures = ( scalar @args && ref $args[0] eq 'ARRAY'
967                          ? shift(@args)
968                          : [] );
969         $path = $c->dispatcher->uri_for_action($path, $captures);
970         return undef unless defined($path);
971         $path = '/' if $path eq '';
972     }
973
974     undef($path) if (defined $path && $path eq '');
975
976     my $params =
977       ( scalar @args && ref $args[$#args] eq 'HASH' ? pop @args : {} );
978
979     carp "uri_for called with undef argument" if grep { ! defined $_ } @args;
980     s/([^$URI::uric])/$URI::Escape::escapes{$1}/go for @args;
981
982     unshift(@args, $path);
983
984     unless (defined $path && $path =~ s!^/!!) { # in-place strip
985         my $namespace = $c->namespace;
986         if (defined $path) { # cheesy hack to handle path '../foo'
987            $namespace =~ s{(?:^|/)[^/]+$}{} while $args[0] =~ s{^\.\./}{};
988         }
989         unshift(@args, $namespace || '');
990     }
991     
992     # join args with '/', or a blank string
993     my $args = join('/', grep { defined($_) } @args);
994     $args =~ s/\?/%3F/g; # STUPID STUPID SPECIAL CASE
995     $args =~ s!^/!!;
996     my $base = $c->req->base;
997     my $class = ref($base);
998     $base =~ s{(?<!/)$}{/};
999
1000     my $query = '';
1001
1002     if (my @keys = keys %$params) {
1003       # somewhat lifted from URI::_query's query_form
1004       $query = '?'.join('&', map {
1005           s/([;\/?:@&=+,\$\[\]%])/$URI::Escape::escapes{$1}/go;
1006           s/ /+/g;
1007           my $key = $_;
1008           my $val = $params->{$_};
1009           $val = '' unless defined $val;
1010           (map {
1011               $_ = "$_";
1012               utf8::encode( $_ ) if utf8::is_utf8($_);
1013               # using the URI::Escape pattern here so utf8 chars survive
1014               s/([^A-Za-z0-9\-_.!~*'() ])/$URI::Escape::escapes{$1}/go;
1015               s/ /+/g;
1016               "${key}=$_"; } ( ref $val eq 'ARRAY' ? @$val : $val ));
1017       } @keys);
1018     }
1019
1020     my $res = bless(\"${base}${args}${query}", $class);
1021     $res;
1022 }
1023
1024 =head2 $c->welcome_message
1025
1026 Returns the Catalyst welcome HTML page.
1027
1028 =cut
1029
1030 sub welcome_message {
1031     my $c      = shift;
1032     my $name   = $c->config->{name};
1033     my $logo   = $c->uri_for('/static/images/catalyst_logo.png');
1034     my $prefix = Catalyst::Utils::appprefix( ref $c );
1035     $c->response->content_type('text/html; charset=utf-8');
1036     return <<"EOF";
1037 <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
1038     "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
1039 <html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">
1040     <head>
1041     <meta http-equiv="Content-Language" content="en" />
1042     <meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
1043         <title>$name on Catalyst $VERSION</title>
1044         <style type="text/css">
1045             body {
1046                 color: #000;
1047                 background-color: #eee;
1048             }
1049             div#content {
1050                 width: 640px;
1051                 margin-left: auto;
1052                 margin-right: auto;
1053                 margin-top: 10px;
1054                 margin-bottom: 10px;
1055                 text-align: left;
1056                 background-color: #ccc;
1057                 border: 1px solid #aaa;
1058             }
1059             p, h1, h2 {
1060                 margin-left: 20px;
1061                 margin-right: 20px;
1062                 font-family: verdana, tahoma, sans-serif;
1063             }
1064             a {
1065                 font-family: verdana, tahoma, sans-serif;
1066             }
1067             :link, :visited {
1068                     text-decoration: none;
1069                     color: #b00;
1070                     border-bottom: 1px dotted #bbb;
1071             }
1072             :link:hover, :visited:hover {
1073                     color: #555;
1074             }
1075             div#topbar {
1076                 margin: 0px;
1077             }
1078             pre {
1079                 margin: 10px;
1080                 padding: 8px;
1081             }
1082             div#answers {
1083                 padding: 8px;
1084                 margin: 10px;
1085                 background-color: #fff;
1086                 border: 1px solid #aaa;
1087             }
1088             h1 {
1089                 font-size: 0.9em;
1090                 font-weight: normal;
1091                 text-align: center;
1092             }
1093             h2 {
1094                 font-size: 1.0em;
1095             }
1096             p {
1097                 font-size: 0.9em;
1098             }
1099             p img {
1100                 float: right;
1101                 margin-left: 10px;
1102             }
1103             span#appname {
1104                 font-weight: bold;
1105                 font-size: 1.6em;
1106             }
1107         </style>
1108     </head>
1109     <body>
1110         <div id="content">
1111             <div id="topbar">
1112                 <h1><span id="appname">$name</span> on <a href="http://catalyst.perl.org">Catalyst</a>
1113                     $VERSION</h1>
1114              </div>
1115              <div id="answers">
1116                  <p>
1117                  <img src="$logo" alt="Catalyst Logo" />
1118                  </p>
1119                  <p>Welcome to the  world of Catalyst.
1120                     This <a href="http://en.wikipedia.org/wiki/MVC">MVC</a>
1121                     framework will make web development something you had
1122                     never expected it to be: Fun, rewarding, and quick.</p>
1123                  <h2>What to do now?</h2>
1124                  <p>That really depends  on what <b>you</b> want to do.
1125                     We do, however, provide you with a few starting points.</p>
1126                  <p>If you want to jump right into web development with Catalyst
1127                     you might want want to start with a tutorial.</p>
1128 <pre>perldoc <a href="http://cpansearch.perl.org/dist/Catalyst-Manual/lib/Catalyst/Manual/Tutorial.pod">Catalyst::Manual::Tutorial</a></code>
1129 </pre>
1130 <p>Afterwards you can go on to check out a more complete look at our features.</p>
1131 <pre>
1132 <code>perldoc <a href="http://cpansearch.perl.org/dist/Catalyst-Manual/lib/Catalyst/Manual/Intro.pod">Catalyst::Manual::Intro</a>
1133 <!-- Something else should go here, but the Catalyst::Manual link seems unhelpful -->
1134 </code></pre>
1135                  <h2>What to do next?</h2>
1136                  <p>Next it's time to write an actual application. Use the
1137                     helper scripts to generate <a href="http://cpansearch.perl.org/search?query=Catalyst%3A%3AController%3A%3A&amp;mode=all">controllers</a>,
1138                     <a href="http://cpansearch.perl.org/search?query=Catalyst%3A%3AModel%3A%3A&amp;mode=all">models</a>, and
1139                     <a href="http://cpansearch.perl.org/search?query=Catalyst%3A%3AView%3A%3A&amp;mode=all">views</a>;
1140                     they can save you a lot of work.</p>
1141                     <pre><code>script/${prefix}_create.pl -help</code></pre>
1142                     <p>Also, be sure to check out the vast and growing
1143                     collection of <a href="http://cpansearch.perl.org/search?query=Catalyst%3A%3APlugin%3A%3A&amp;mode=all">plugins for Catalyst on CPAN</a>;
1144                     you are likely to find what you need there.
1145                     </p>
1146
1147                  <h2>Need help?</h2>
1148                  <p>Catalyst has a very active community. Here are the main places to
1149                     get in touch with us.</p>
1150                  <ul>
1151                      <li>
1152                          <a href="http://dev.catalyst.perl.org">Wiki</a>
1153                      </li>
1154                      <li>
1155                          <a href="http://lists.rawmode.org/mailman/listinfo/catalyst">Mailing-List</a>
1156                      </li>
1157                      <li>
1158                          <a href="irc://irc.perl.org/catalyst">IRC channel #catalyst on irc.perl.org</a>
1159                      </li>
1160                  </ul>
1161                  <h2>In conclusion</h2>
1162                  <p>The Catalyst team hopes you will enjoy using Catalyst as much 
1163                     as we enjoyed making it. Please contact us if you have ideas
1164                     for improvement or other feedback.</p>
1165              </div>
1166          </div>
1167     </body>
1168 </html>
1169 EOF
1170 }
1171
1172 =head1 INTERNAL METHODS
1173
1174 These methods are not meant to be used by end users.
1175
1176 =head2 $c->components
1177
1178 Returns a hash of components.
1179
1180 =head2 $c->context_class
1181
1182 Returns or sets the context class.
1183
1184 =head2 $c->counter
1185
1186 Returns a hashref containing coderefs and execution counts (needed for
1187 deep recursion detection).
1188
1189 =head2 $c->depth
1190
1191 Returns the number of actions on the current internal execution stack.
1192
1193 =head2 $c->dispatch
1194
1195 Dispatches a request to actions.
1196
1197 =cut
1198
1199 sub dispatch { my $c = shift; $c->dispatcher->dispatch( $c, @_ ) }
1200
1201 =head2 $c->dispatcher_class
1202
1203 Returns or sets the dispatcher class.
1204
1205 =head2 $c->dump_these
1206
1207 Returns a list of 2-element array references (name, structure) pairs
1208 that will be dumped on the error page in debug mode.
1209
1210 =cut
1211
1212 sub dump_these {
1213     my $c = shift;
1214     [ Request => $c->req ], 
1215     [ Response => $c->res ], 
1216     [ Stash => $c->stash ],
1217     [ Config => $c->config ];
1218 }
1219
1220 =head2 $c->engine_class
1221
1222 Returns or sets the engine class.
1223
1224 =head2 $c->execute( $class, $coderef )
1225
1226 Execute a coderef in given class and catch exceptions. Errors are available
1227 via $c->error.
1228
1229 =cut
1230
1231 sub execute {
1232     my ( $c, $class, $code ) = @_;
1233     $class = $c->component($class) || $class;
1234     $c->state(0);
1235
1236     if ( $c->depth >= $RECURSION ) {
1237         my $action = $code->reverse();
1238         $action = "/$action" unless $action =~ /->/;
1239         my $error = qq/Deep recursion detected calling "${action}"/;
1240         $c->log->error($error);
1241         $c->error($error);
1242         $c->state(0);
1243         return $c->state;
1244     }
1245
1246     my $stats_info = $c->_stats_start_execute( $code ) if $c->use_stats;
1247
1248     push( @{ $c->stack }, $code );
1249     
1250     eval { $c->state( $code->execute( $class, $c, @{ $c->req->args } ) || 0 ) };
1251
1252     $c->_stats_finish_execute( $stats_info ) if $c->use_stats and $stats_info;
1253     
1254     my $last = pop( @{ $c->stack } );
1255
1256     if ( my $error = $@ ) {
1257         if ( !ref($error) and $error eq $DETACH ) { die $DETACH if $c->depth > 1 }
1258         else {
1259             unless ( ref $error ) {
1260                 no warnings 'uninitialized';
1261                 chomp $error;
1262                 my $class = $last->class;
1263                 my $name  = $last->name;
1264                 $error = qq/Caught exception in $class->$name "$error"/;
1265             }
1266             $c->error($error);
1267             $c->state(0);
1268         }
1269     }
1270     return $c->state;
1271 }
1272
1273 sub _stats_start_execute {
1274     my ( $c, $code ) = @_;
1275
1276     return if ( ( $code->name =~ /^_.*/ )
1277         && ( !$c->config->{show_internal_actions} ) );
1278
1279     my $action_name = $code->reverse();
1280     $c->counter->{$action_name}++;
1281
1282     my $action = $action_name;
1283     $action = "/$action" unless $action =~ /->/;
1284
1285     # determine if the call was the result of a forward
1286     # this is done by walking up the call stack and looking for a calling
1287     # sub of Catalyst::forward before the eval
1288     my $callsub = q{};
1289     for my $index ( 2 .. 11 ) {
1290         last
1291         if ( ( caller($index) )[0] eq 'Catalyst'
1292             && ( caller($index) )[3] eq '(eval)' );
1293
1294         if ( ( caller($index) )[3] =~ /forward$/ ) {
1295             $callsub = ( caller($index) )[3];
1296             $action  = "-> $action";
1297             last;
1298         }
1299     }
1300
1301     my $uid = $action_name . $c->counter->{$action_name};
1302
1303     # is this a root-level call or a forwarded call?
1304     if ( $callsub =~ /forward$/ ) {
1305
1306         # forward, locate the caller
1307         if ( my $parent = $c->stack->[-1] ) {
1308             $c->stats->profile(
1309                 begin  => $action, 
1310                 parent => "$parent" . $c->counter->{"$parent"},
1311                 uid    => $uid,
1312             );
1313         }
1314         else {
1315
1316             # forward with no caller may come from a plugin
1317             $c->stats->profile(
1318                 begin => $action,
1319                 uid   => $uid,
1320             );
1321         }
1322     }
1323     else {
1324         
1325         # root-level call
1326         $c->stats->profile(
1327             begin => $action,
1328             uid   => $uid,
1329         );
1330     }
1331     return $action;
1332
1333 }
1334
1335 sub _stats_finish_execute {
1336     my ( $c, $info ) = @_;
1337     $c->stats->profile( end => $info );
1338 }
1339
1340 =head2 $c->_localize_fields( sub { }, \%keys );
1341
1342 =cut
1343
1344 #Why does this exist? This is no longer safe and WILL NOT WORK.
1345 # it doesnt seem to be used anywhere. can we remove it?
1346 sub _localize_fields {
1347     my ( $c, $localized, $code ) = ( @_ );
1348
1349     my $request = delete $localized->{request} || {};
1350     my $response = delete $localized->{response} || {};
1351     
1352     local @{ $c }{ keys %$localized } = values %$localized;
1353     local @{ $c->request }{ keys %$request } = values %$request;
1354     local @{ $c->response }{ keys %$response } = values %$response;
1355
1356     $code->();
1357 }
1358
1359 =head2 $c->finalize
1360
1361 Finalizes the request.
1362
1363 =cut
1364
1365 sub finalize {
1366     my $c = shift;
1367
1368     for my $error ( @{ $c->error } ) {
1369         $c->log->error($error);
1370     }
1371
1372     # Allow engine to handle finalize flow (for POE)
1373     my $engine = $c->engine;
1374     if ( my $code = $engine->can('finalize') ) {
1375         $engine->$code($c);
1376     }
1377     else {
1378
1379         $c->finalize_uploads;
1380
1381         # Error
1382         if ( $#{ $c->error } >= 0 ) {
1383             $c->finalize_error;
1384         }
1385
1386         $c->finalize_headers;
1387
1388         # HEAD request
1389         if ( $c->request->method eq 'HEAD' ) {
1390             $c->response->body('');
1391         }
1392
1393         $c->finalize_body;
1394     }
1395     
1396     if ($c->use_stats) {        
1397         my $elapsed = sprintf '%f', $c->stats->elapsed;
1398         my $av = $elapsed == 0 ? '??' : sprintf '%.3f', 1 / $elapsed;
1399         $c->log->info(
1400             "Request took ${elapsed}s ($av/s)\n" . $c->stats->report . "\n" );        
1401     }
1402
1403     return $c->response->status;
1404 }
1405
1406 =head2 $c->finalize_body
1407
1408 Finalizes body.
1409
1410 =cut
1411
1412 sub finalize_body { my $c = shift; $c->engine->finalize_body( $c, @_ ) }
1413
1414 =head2 $c->finalize_cookies
1415
1416 Finalizes cookies.
1417
1418 =cut
1419
1420 sub finalize_cookies { my $c = shift; $c->engine->finalize_cookies( $c, @_ ) }
1421
1422 =head2 $c->finalize_error
1423
1424 Finalizes error.
1425
1426 =cut
1427
1428 sub finalize_error { my $c = shift; $c->engine->finalize_error( $c, @_ ) }
1429
1430 =head2 $c->finalize_headers
1431
1432 Finalizes headers.
1433
1434 =cut
1435
1436 sub finalize_headers {
1437     my $c = shift;
1438
1439     my $response = $c->response; #accessor calls can add up?
1440
1441     # Check if we already finalized headers
1442     return if $response->finalized_headers;
1443
1444     # Handle redirects
1445     if ( my $location = $response->redirect ) {
1446         $c->log->debug(qq/Redirecting to "$location"/) if $c->debug;
1447         $response->header( Location => $location );
1448
1449         #Moose TODO: we should probably be using a predicate method here ?
1450         if ( !$response->body ) {
1451             # Add a default body if none is already present
1452             $response->body(
1453                 qq{<html><body><p>This item has moved <a href="$location">here</a>.</p></body></html>}
1454             );
1455         }
1456     }
1457
1458     # Content-Length
1459     if ( $response->body && !$response->content_length ) {
1460
1461         # get the length from a filehandle
1462         if ( blessed( $response->body ) && $response->body->can('read') )
1463         {
1464             my $stat = stat $response->body;
1465             if ( $stat && $stat->size > 0 ) {
1466                 $response->content_length( $stat->size );
1467             }
1468             else {
1469                 $c->log->warn('Serving filehandle without a content-length');
1470             }
1471         }
1472         else {
1473             # everything should be bytes at this point, but just in case
1474             $response->content_length( bytes::length( $response->body ) );
1475         }
1476     }
1477
1478     # Errors
1479     if ( $response->status =~ /^(1\d\d|[23]04)$/ ) {
1480         $response->headers->remove_header("Content-Length");
1481         $response->body('');
1482     }
1483
1484     $c->finalize_cookies;
1485
1486     $c->engine->finalize_headers( $c, @_ );
1487
1488     # Done
1489     $response->finalized_headers(1);
1490 }
1491
1492 =head2 $c->finalize_output
1493
1494 An alias for finalize_body.
1495
1496 =head2 $c->finalize_read
1497
1498 Finalizes the input after reading is complete.
1499
1500 =cut
1501
1502 sub finalize_read { my $c = shift; $c->engine->finalize_read( $c, @_ ) }
1503
1504 =head2 $c->finalize_uploads
1505
1506 Finalizes uploads. Cleans up any temporary files.
1507
1508 =cut
1509
1510 sub finalize_uploads { my $c = shift; $c->engine->finalize_uploads( $c, @_ ) }
1511
1512 =head2 $c->get_action( $action, $namespace )
1513
1514 Gets an action in a given namespace.
1515
1516 =cut
1517
1518 sub get_action { my $c = shift; $c->dispatcher->get_action(@_) }
1519
1520 =head2 $c->get_actions( $action, $namespace )
1521
1522 Gets all actions of a given name in a namespace and all parent
1523 namespaces.
1524
1525 =cut
1526
1527 sub get_actions { my $c = shift; $c->dispatcher->get_actions( $c, @_ ) }
1528
1529 =head2 $c->handle_request( $class, @arguments )
1530
1531 Called to handle each HTTP request.
1532
1533 =cut
1534
1535 sub handle_request {
1536     my ( $class, @arguments ) = @_;
1537
1538     # Always expect worst case!
1539     my $status = -1;
1540     eval {
1541         if ($class->debug) {
1542             my $secs = time - $START || 1;
1543             my $av = sprintf '%.3f', $COUNT / $secs;
1544             my $time = localtime time;
1545             $class->log->info("*** Request $COUNT ($av/s) [$$] [$time] ***");
1546         }
1547
1548         my $c = $class->prepare(@arguments);
1549         $c->dispatch;
1550         $status = $c->finalize;   
1551     };
1552
1553     if ( my $error = $@ ) {
1554         chomp $error;
1555         $class->log->error(qq/Caught exception in engine "$error"/);
1556     }
1557
1558     $COUNT++;
1559     
1560     if(my $coderef = $class->log->can('_flush')){
1561         $class->log->$coderef();
1562     }
1563     return $status;
1564 }
1565
1566 =head2 $c->prepare( @arguments )
1567
1568 Creates a Catalyst context from an engine-specific request (Apache, CGI,
1569 etc.).
1570
1571 =cut
1572
1573 sub prepare {
1574     my ( $class, @arguments ) = @_;
1575
1576     # XXX
1577     # After the app/ctxt split, this should become an attribute based on something passed
1578     # into the application.
1579     $class->context_class( ref $class || $class ) unless $class->context_class;
1580    
1581     my $c = $class->context_class->new({});
1582
1583     # For on-demand data
1584     $c->request->_context($c);
1585     $c->response->_context($c);
1586
1587     #surely this is not the most efficient way to do things...
1588     $c->stats($class->stats_class->new)->enable($c->use_stats);
1589     if ( $c->debug ) {
1590         $c->res->headers->header( 'X-Catalyst' => $Catalyst::VERSION );            
1591     }
1592
1593     #XXX reuse coderef from can
1594     # Allow engine to direct the prepare flow (for POE)
1595     if ( $c->engine->can('prepare') ) {
1596         $c->engine->prepare( $c, @arguments );
1597     }
1598     else {
1599         $c->prepare_request(@arguments);
1600         $c->prepare_connection;
1601         $c->prepare_query_parameters;
1602         $c->prepare_headers;
1603         $c->prepare_cookies;
1604         $c->prepare_path;
1605
1606         # Prepare the body for reading, either by prepare_body
1607         # or the user, if they are using $c->read
1608         $c->prepare_read;
1609         
1610         # Parse the body unless the user wants it on-demand
1611         unless ( $c->config->{parse_on_demand} ) {
1612             $c->prepare_body;
1613         }
1614     }
1615
1616     my $method  = $c->req->method  || '';
1617     my $path    = $c->req->path    || '/';
1618     my $address = $c->req->address || '';
1619
1620     $c->log->debug(qq/"$method" request for "$path" from "$address"/)
1621       if $c->debug;
1622
1623     $c->prepare_action;
1624
1625     return $c;
1626 }
1627
1628 =head2 $c->prepare_action
1629
1630 Prepares action. See L<Catalyst::Dispatcher>.
1631
1632 =cut
1633
1634 sub prepare_action { my $c = shift; $c->dispatcher->prepare_action( $c, @_ ) }
1635
1636 =head2 $c->prepare_body
1637
1638 Prepares message body.
1639
1640 =cut
1641
1642 sub prepare_body {
1643     my $c = shift;
1644
1645     #Moose TODO: what is  _body ??
1646     # Do we run for the first time?
1647     return if defined $c->request->{_body};
1648
1649     # Initialize on-demand data
1650     $c->engine->prepare_body( $c, @_ );
1651     $c->prepare_parameters;
1652     $c->prepare_uploads;
1653
1654     if ( $c->debug && keys %{ $c->req->body_parameters } ) {
1655         my $t = Text::SimpleTable->new( [ 35, 'Parameter' ], [ 36, 'Value' ] );
1656         for my $key ( sort keys %{ $c->req->body_parameters } ) {
1657             my $param = $c->req->body_parameters->{$key};
1658             my $value = defined($param) ? $param : '';
1659             $t->row( $key,
1660                 ref $value eq 'ARRAY' ? ( join ', ', @$value ) : $value );
1661         }
1662         $c->log->debug( "Body Parameters are:\n" . $t->draw );
1663     }
1664 }
1665
1666 =head2 $c->prepare_body_chunk( $chunk )
1667
1668 Prepares a chunk of data before sending it to L<HTTP::Body>.
1669
1670 See L<Catalyst::Engine>.
1671
1672 =cut
1673
1674 sub prepare_body_chunk {
1675     my $c = shift;
1676     $c->engine->prepare_body_chunk( $c, @_ );
1677 }
1678
1679 =head2 $c->prepare_body_parameters
1680
1681 Prepares body parameters.
1682
1683 =cut
1684
1685 sub prepare_body_parameters {
1686     my $c = shift;
1687     $c->engine->prepare_body_parameters( $c, @_ );
1688 }
1689
1690 =head2 $c->prepare_connection
1691
1692 Prepares connection.
1693
1694 =cut
1695
1696 sub prepare_connection {
1697     my $c = shift;
1698     $c->engine->prepare_connection( $c, @_ );
1699 }
1700
1701 =head2 $c->prepare_cookies
1702
1703 Prepares cookies.
1704
1705 =cut
1706
1707 sub prepare_cookies { my $c = shift; $c->engine->prepare_cookies( $c, @_ ) }
1708
1709 =head2 $c->prepare_headers
1710
1711 Prepares headers.
1712
1713 =cut
1714
1715 sub prepare_headers { my $c = shift; $c->engine->prepare_headers( $c, @_ ) }
1716
1717 =head2 $c->prepare_parameters
1718
1719 Prepares parameters.
1720
1721 =cut
1722
1723 sub prepare_parameters {
1724     my $c = shift;
1725     $c->prepare_body_parameters;
1726     $c->engine->prepare_parameters( $c, @_ );
1727 }
1728
1729 =head2 $c->prepare_path
1730
1731 Prepares path and base.
1732
1733 =cut
1734
1735 sub prepare_path { my $c = shift; $c->engine->prepare_path( $c, @_ ) }
1736
1737 =head2 $c->prepare_query_parameters
1738
1739 Prepares query parameters.
1740
1741 =cut
1742
1743 sub prepare_query_parameters {
1744     my $c = shift;
1745
1746     $c->engine->prepare_query_parameters( $c, @_ );
1747
1748     if ( $c->debug && keys %{ $c->request->query_parameters } ) {
1749         my $t = Text::SimpleTable->new( [ 35, 'Parameter' ], [ 36, 'Value' ] );
1750         for my $key ( sort keys %{ $c->req->query_parameters } ) {
1751             my $param = $c->req->query_parameters->{$key};
1752             my $value = defined($param) ? $param : '';
1753             $t->row( $key,
1754                 ref $value eq 'ARRAY' ? ( join ', ', @$value ) : $value );
1755         }
1756         $c->log->debug( "Query Parameters are:\n" . $t->draw );
1757     }
1758 }
1759
1760 =head2 $c->prepare_read
1761
1762 Prepares the input for reading.
1763
1764 =cut
1765
1766 sub prepare_read { my $c = shift; $c->engine->prepare_read( $c, @_ ) }
1767
1768 =head2 $c->prepare_request
1769
1770 Prepares the engine request.
1771
1772 =cut
1773
1774 sub prepare_request { my $c = shift; $c->engine->prepare_request( $c, @_ ) }
1775
1776 =head2 $c->prepare_uploads
1777
1778 Prepares uploads.
1779
1780 =cut
1781
1782 sub prepare_uploads {
1783     my $c = shift;
1784
1785     $c->engine->prepare_uploads( $c, @_ );
1786
1787     if ( $c->debug && keys %{ $c->request->uploads } ) {
1788         my $t = Text::SimpleTable->new(
1789             [ 12, 'Parameter' ],
1790             [ 26, 'Filename' ],
1791             [ 18, 'Type' ],
1792             [ 9,  'Size' ]
1793         );
1794         for my $key ( sort keys %{ $c->request->uploads } ) {
1795             my $upload = $c->request->uploads->{$key};
1796             for my $u ( ref $upload eq 'ARRAY' ? @{$upload} : ($upload) ) {
1797                 $t->row( $key, $u->filename, $u->type, $u->size );
1798             }
1799         }
1800         $c->log->debug( "File Uploads are:\n" . $t->draw );
1801     }
1802 }
1803
1804 =head2 $c->prepare_write
1805
1806 Prepares the output for writing.
1807
1808 =cut
1809
1810 sub prepare_write { my $c = shift; $c->engine->prepare_write( $c, @_ ) }
1811
1812 =head2 $c->request_class
1813
1814 Returns or sets the request class.
1815
1816 =head2 $c->response_class
1817
1818 Returns or sets the response class.
1819
1820 =head2 $c->read( [$maxlength] )
1821
1822 Reads a chunk of data from the request body. This method is designed to
1823 be used in a while loop, reading C<$maxlength> bytes on every call.
1824 C<$maxlength> defaults to the size of the request if not specified.
1825
1826 You have to set C<< MyApp->config->{parse_on_demand} >> to use this
1827 directly.
1828
1829 Warning: If you use read(), Catalyst will not process the body,
1830 so you will not be able to access POST parameters or file uploads via
1831 $c->request.  You must handle all body parsing yourself.
1832
1833 =cut
1834
1835 sub read { my $c = shift; return $c->engine->read( $c, @_ ) }
1836
1837 =head2 $c->run
1838
1839 Starts the engine.
1840
1841 =cut
1842
1843 sub run { my $c = shift; return $c->engine->run( $c, @_ ) }
1844
1845 =head2 $c->set_action( $action, $code, $namespace, $attrs )
1846
1847 Sets an action in a given namespace.
1848
1849 =cut
1850
1851 sub set_action { my $c = shift; $c->dispatcher->set_action( $c, @_ ) }
1852
1853 =head2 $c->setup_actions($component)
1854
1855 Sets up actions for a component.
1856
1857 =cut
1858
1859 sub setup_actions { my $c = shift; $c->dispatcher->setup_actions( $c, @_ ) }
1860
1861 =head2 $c->setup_components
1862
1863 Sets up components. Specify a C<setup_components> config option to pass
1864 additional options directly to L<Module::Pluggable>. To add additional
1865 search paths, specify a key named C<search_extra> as an array
1866 reference. Items in the array beginning with C<::> will have the
1867 application class name prepended to them.
1868
1869 =cut
1870
1871 sub setup_components {
1872     my $class = shift;
1873
1874     my @paths   = qw( ::Controller ::C ::Model ::M ::View ::V );
1875     my $config  = $class->config->{ setup_components };
1876     my $extra   = delete $config->{ search_extra } || [];
1877     
1878     push @paths, @$extra;
1879         
1880     my $locator = Module::Pluggable::Object->new(
1881         search_path => [ map { s/^(?=::)/$class/; $_; } @paths ],
1882         %$config
1883     );
1884
1885     my @comps = sort { length $a <=> length $b } $locator->plugins;
1886     my %comps = map { $_ => 1 } @comps;
1887     
1888     for my $component ( @comps ) {
1889
1890         # We pass ignore_loaded here so that overlay files for (e.g.)
1891         # Model::DBI::Schema sub-classes are loaded - if it's in @comps
1892         # we know M::P::O found a file on disk so this is safe
1893
1894         Catalyst::Utils::ensure_class_loaded( $component, { ignore_loaded => 1 } );
1895         #Class::MOP::load_class($component);
1896
1897         my $module  = $class->setup_component( $component );
1898         my %modules = (
1899             $component => $module,
1900             map {
1901                 $_ => $class->setup_component( $_ )
1902             } grep { 
1903               not exists $comps{$_}
1904             } Devel::InnerPackage::list_packages( $component )
1905         );
1906         
1907         for my $key ( keys %modules ) {
1908             $class->components->{ $key } = $modules{ $key };
1909         }
1910     }
1911 }
1912
1913 =head2 $c->setup_component
1914
1915 =cut
1916
1917 sub setup_component {
1918     my( $class, $component ) = @_;
1919
1920     unless ( $component->can( 'COMPONENT' ) ) {
1921         return $component;
1922     }
1923
1924     my $suffix = Catalyst::Utils::class2classsuffix( $component );
1925     my $config = $class->config->{ $suffix } || {};
1926
1927     my $instance = eval { $component->COMPONENT( $class, $config ); };
1928
1929     if ( my $error = $@ ) {
1930         chomp $error;
1931         Catalyst::Exception->throw(
1932             message => qq/Couldn't instantiate component "$component", "$error"/
1933         );
1934     }
1935
1936     Catalyst::Exception->throw(
1937         message =>
1938         qq/Couldn't instantiate component "$component", "COMPONENT() didn't return an object-like value"/
1939     ) unless blessed($instance);
1940
1941     return $instance;
1942 }
1943
1944 =head2 $c->setup_dispatcher
1945
1946 Sets up dispatcher.
1947
1948 =cut
1949
1950 sub setup_dispatcher {
1951     my ( $class, $dispatcher ) = @_;
1952
1953     if ($dispatcher) {
1954         $dispatcher = 'Catalyst::Dispatcher::' . $dispatcher;
1955     }
1956
1957     if ( my $env = Catalyst::Utils::env_value( $class, 'DISPATCHER' ) ) {
1958         $dispatcher = 'Catalyst::Dispatcher::' . $env;
1959     }
1960
1961     unless ($dispatcher) {
1962         $dispatcher = $class->dispatcher_class;
1963     }
1964
1965     Class::MOP::load_class($dispatcher);
1966
1967     # dispatcher instance
1968     $class->dispatcher( $dispatcher->new );
1969 }
1970
1971 =head2 $c->setup_engine
1972
1973 Sets up engine.
1974
1975 =cut
1976
1977 sub setup_engine {
1978     my ( $class, $engine ) = @_;
1979
1980     if ($engine) {
1981         $engine = 'Catalyst::Engine::' . $engine;
1982     }
1983
1984     if ( my $env = Catalyst::Utils::env_value( $class, 'ENGINE' ) ) {
1985         $engine = 'Catalyst::Engine::' . $env;
1986     }
1987
1988     if ( $ENV{MOD_PERL} ) {
1989
1990         # create the apache method
1991         $class->meta->add_method('apache' => sub { shift->engine->apache });
1992
1993         my ( $software, $version ) =
1994           $ENV{MOD_PERL} =~ /^(\S+)\/(\d+(?:[\.\_]\d+)+)/;
1995
1996         $version =~ s/_//g;
1997         $version =~ s/(\.[^.]+)\./$1/g;
1998
1999         if ( $software eq 'mod_perl' ) {
2000
2001             if ( !$engine ) {
2002
2003                 if ( $version >= 1.99922 ) {
2004                     $engine = 'Catalyst::Engine::Apache2::MP20';
2005                 }
2006
2007                 elsif ( $version >= 1.9901 ) {
2008                     $engine = 'Catalyst::Engine::Apache2::MP19';
2009                 }
2010
2011                 elsif ( $version >= 1.24 ) {
2012                     $engine = 'Catalyst::Engine::Apache::MP13';
2013                 }
2014
2015                 else {
2016                     Catalyst::Exception->throw( message =>
2017                           qq/Unsupported mod_perl version: $ENV{MOD_PERL}/ );
2018                 }
2019
2020             }
2021
2022             # install the correct mod_perl handler
2023             if ( $version >= 1.9901 ) {
2024                 *handler = sub  : method {
2025                     shift->handle_request(@_);
2026                 };
2027             }
2028             else {
2029                 *handler = sub ($$) { shift->handle_request(@_) };
2030             }
2031
2032         }
2033
2034         elsif ( $software eq 'Zeus-Perl' ) {
2035             $engine = 'Catalyst::Engine::Zeus';
2036         }
2037
2038         else {
2039             Catalyst::Exception->throw(
2040                 message => qq/Unsupported mod_perl: $ENV{MOD_PERL}/ );
2041         }
2042     }
2043
2044     unless ($engine) {
2045         $engine = $class->engine_class;
2046     }
2047
2048     Class::MOP::load_class($engine);
2049     #unless (Class::Inspector->loaded($engine)) {
2050     #    require Class::Inspector->filename($engine);
2051     #}
2052
2053     # check for old engines that are no longer compatible
2054     my $old_engine;
2055     if ( $engine->isa('Catalyst::Engine::Apache')
2056         && !Catalyst::Engine::Apache->VERSION )
2057     {
2058         $old_engine = 1;
2059     }
2060
2061     elsif ( $engine->isa('Catalyst::Engine::Server::Base')
2062         && Catalyst::Engine::Server->VERSION le '0.02' )
2063     {
2064         $old_engine = 1;
2065     }
2066
2067     elsif ($engine->isa('Catalyst::Engine::HTTP::POE')
2068         && $engine->VERSION eq '0.01' )
2069     {
2070         $old_engine = 1;
2071     }
2072
2073     elsif ($engine->isa('Catalyst::Engine::Zeus')
2074         && $engine->VERSION eq '0.01' )
2075     {
2076         $old_engine = 1;
2077     }
2078
2079     if ($old_engine) {
2080         Catalyst::Exception->throw( message =>
2081               qq/Engine "$engine" is not supported by this version of Catalyst/
2082         );
2083     }
2084
2085     # engine instance
2086     $class->engine( $engine->new );
2087 }
2088
2089 =head2 $c->setup_home
2090
2091 Sets up the home directory.
2092
2093 =cut
2094
2095 sub setup_home {
2096     my ( $class, $home ) = @_;
2097
2098     if ( my $env = Catalyst::Utils::env_value( $class, 'HOME' ) ) {
2099         $home = $env;
2100     }
2101
2102     $home ||= Catalyst::Utils::home($class);
2103
2104     if ($home) {
2105         #I remember recently being scolded for assigning config values like this
2106         $class->config->{home} ||= $home;
2107         $class->config->{root} ||= Path::Class::Dir->new($home)->subdir('root');
2108     }
2109 }
2110
2111 =head2 $c->setup_log
2112
2113 Sets up log.
2114
2115 =cut
2116
2117 sub setup_log {
2118     my ( $class, $debug ) = @_;
2119
2120     unless ( $class->log ) {
2121         $class->log( Catalyst::Log->new );
2122     }
2123
2124     my $env_debug = Catalyst::Utils::env_value( $class, 'DEBUG' );
2125     if ( defined($env_debug) ? $env_debug : $debug ) {
2126         $class->meta->add_method('debug' => sub { 1 });
2127         $class->log->debug('Debug messages enabled');
2128     }
2129 }
2130
2131 =head2 $c->setup_plugins
2132
2133 Sets up plugins.
2134
2135 =cut
2136
2137 =head2 $c->setup_stats
2138
2139 Sets up timing statistics class.
2140
2141 =cut
2142
2143 sub setup_stats {
2144     my ( $class, $stats ) = @_;
2145
2146     Catalyst::Utils::ensure_class_loaded($class->stats_class);
2147
2148     my $env = Catalyst::Utils::env_value( $class, 'STATS' );
2149     if ( defined($env) ? $env : ($stats || $class->debug ) ) {
2150         $class->meta->add_method('use_stats' => sub { 1 });
2151         $class->log->debug('Statistics enabled');
2152     }
2153 }
2154
2155
2156 =head2 $c->registered_plugins 
2157
2158 Returns a sorted list of the plugins which have either been stated in the
2159 import list or which have been added via C<< MyApp->plugin(@args); >>.
2160
2161 If passed a given plugin name, it will report a boolean value indicating
2162 whether or not that plugin is loaded.  A fully qualified name is required if
2163 the plugin name does not begin with C<Catalyst::Plugin::>.
2164
2165  if ($c->registered_plugins('Some::Plugin')) {
2166      ...
2167  }
2168
2169 =cut
2170
2171 {
2172
2173     sub registered_plugins {
2174         my $proto = shift;
2175         return sort keys %{ $proto->_plugins } unless @_;
2176         my $plugin = shift;
2177         return 1 if exists $proto->_plugins->{$plugin};
2178         return exists $proto->_plugins->{"Catalyst::Plugin::$plugin"};
2179     }
2180
2181     sub _register_plugin {
2182         my ( $proto, $plugin, $instant ) = @_;
2183         my $class = ref $proto || $proto;
2184
2185         # no ignore_loaded here, the plugin may already have been
2186         # defined in memory and we don't want to error on "no file" if so
2187
2188         Class::MOP::load_class( $plugin );
2189
2190         $proto->_plugins->{$plugin} = 1;
2191         unless ($instant) {
2192             no strict 'refs';
2193             if( $class->can('meta') ){
2194               my @superclasses = ($plugin, $class->meta->superclasses );
2195               $class->meta->superclasses(@superclasses);
2196             } else {
2197               unshift @{"$class\::ISA"}, $plugin;
2198             }
2199         }
2200         return $class;
2201     }
2202
2203     sub setup_plugins {
2204         my ( $class, $plugins ) = @_;
2205
2206         $class->_plugins( {} ) unless $class->_plugins;
2207         $plugins ||= [];
2208         for my $plugin ( reverse @$plugins ) {
2209
2210             unless ( $plugin =~ s/\A\+// ) {
2211                 $plugin = "Catalyst::Plugin::$plugin";
2212             }
2213
2214             $class->_register_plugin($plugin);
2215         }
2216     }
2217 }
2218
2219 =head2 $c->stack
2220
2221 Returns an arrayref of the internal execution stack (actions that are
2222 currently executing).
2223
2224 =head2 $c->stats_class
2225
2226 Returns or sets the stats (timing statistics) class.
2227
2228 =head2 $c->use_stats
2229
2230 Returns 1 when stats collection is enabled.  Stats collection is enabled
2231 when the -Stats options is set, debug is on or when the <MYAPP>_STATS
2232 environment variable is set.
2233
2234 Note that this is a static method, not an accessor and should be overloaded
2235 by declaring "sub use_stats { 1 }" in your MyApp.pm, not by calling $c->use_stats(1).
2236
2237 =cut
2238
2239 sub use_stats { 0 }
2240
2241
2242 =head2 $c->write( $data )
2243
2244 Writes $data to the output stream. When using this method directly, you
2245 will need to manually set the C<Content-Length> header to the length of
2246 your output data, if known.
2247
2248 =cut
2249
2250 sub write {
2251     my $c = shift;
2252
2253     # Finalize headers if someone manually writes output
2254     $c->finalize_headers;
2255
2256     return $c->engine->write( $c, @_ );
2257 }
2258
2259 =head2 version
2260
2261 Returns the Catalyst version number. Mostly useful for "powered by"
2262 messages in template systems.
2263
2264 =cut
2265
2266 sub version { return $Catalyst::VERSION }
2267
2268 =head1 INTERNAL ACTIONS
2269
2270 Catalyst uses internal actions like C<_DISPATCH>, C<_BEGIN>, C<_AUTO>,
2271 C<_ACTION>, and C<_END>. These are by default not shown in the private
2272 action table, but you can make them visible with a config parameter.
2273
2274     MyApp->config->{show_internal_actions} = 1;
2275
2276 =head1 CASE SENSITIVITY
2277
2278 By default Catalyst is not case sensitive, so C<MyApp::C::FOO::Bar> is
2279 mapped to C</foo/bar>. You can activate case sensitivity with a config
2280 parameter.
2281
2282     MyApp->config->{case_sensitive} = 1;
2283
2284 This causes C<MyApp::C::Foo::Bar> to map to C</Foo/Bar>.
2285
2286 =head1 ON-DEMAND PARSER
2287
2288 The request body is usually parsed at the beginning of a request,
2289 but if you want to handle input yourself, you can enable on-demand
2290 parsing with a config parameter.
2291
2292     MyApp->config->{parse_on_demand} = 1;
2293     
2294 =head1 PROXY SUPPORT
2295
2296 Many production servers operate using the common double-server approach,
2297 with a lightweight frontend web server passing requests to a larger
2298 backend server. An application running on the backend server must deal
2299 with two problems: the remote user always appears to be C<127.0.0.1> and
2300 the server's hostname will appear to be C<localhost> regardless of the
2301 virtual host that the user connected through.
2302
2303 Catalyst will automatically detect this situation when you are running
2304 the frontend and backend servers on the same machine. The following
2305 changes are made to the request.
2306
2307     $c->req->address is set to the user's real IP address, as read from 
2308     the HTTP X-Forwarded-For header.
2309     
2310     The host value for $c->req->base and $c->req->uri is set to the real
2311     host, as read from the HTTP X-Forwarded-Host header.
2312
2313 Obviously, your web server must support these headers for this to work.
2314
2315 In a more complex server farm environment where you may have your
2316 frontend proxy server(s) on different machines, you will need to set a
2317 configuration option to tell Catalyst to read the proxied data from the
2318 headers.
2319
2320     MyApp->config->{using_frontend_proxy} = 1;
2321     
2322 If you do not wish to use the proxy support at all, you may set:
2323
2324     MyApp->config->{ignore_frontend_proxy} = 1;
2325
2326 =head1 THREAD SAFETY
2327
2328 Catalyst has been tested under Apache 2's threading C<mpm_worker>,
2329 C<mpm_winnt>, and the standalone forking HTTP server on Windows. We
2330 believe the Catalyst core to be thread-safe.
2331
2332 If you plan to operate in a threaded environment, remember that all other
2333 modules you are using must also be thread-safe. Some modules, most notably
2334 L<DBD::SQLite>, are not thread-safe.
2335
2336 =head1 SUPPORT
2337
2338 IRC:
2339
2340     Join #catalyst on irc.perl.org.
2341
2342 Mailing Lists:
2343
2344     http://lists.rawmode.org/mailman/listinfo/catalyst
2345     http://lists.rawmode.org/mailman/listinfo/catalyst-dev
2346
2347 Web:
2348
2349     http://catalyst.perl.org
2350
2351 Wiki:
2352
2353     http://dev.catalyst.perl.org
2354
2355 =head1 SEE ALSO
2356
2357 =head2 L<Task::Catalyst> - All you need to start with Catalyst
2358
2359 =head2 L<Catalyst::Manual> - The Catalyst Manual
2360
2361 =head2 L<Catalyst::Component>, L<Catalyst::Base> - Base classes for components
2362
2363 =head2 L<Catalyst::Engine> - Core engine
2364
2365 =head2 L<Catalyst::Log> - Log class.
2366
2367 =head2 L<Catalyst::Request> - Request object
2368
2369 =head2 L<Catalyst::Response> - Response object
2370
2371 =head2 L<Catalyst::Test> - The test suite.
2372
2373 =head1 CREDITS
2374
2375 Andy Grundman
2376
2377 Andy Wardley
2378
2379 Andreas Marienborg
2380
2381 Andrew Bramble
2382
2383 Andrew Ford
2384
2385 Andrew Ruthven
2386
2387 Arthur Bergman
2388
2389 Autrijus Tang
2390
2391 Brian Cassidy
2392
2393 Carl Franks
2394
2395 Christian Hansen
2396
2397 Christopher Hicks
2398
2399 Dan Sully
2400
2401 Danijel Milicevic
2402
2403 David Kamholz
2404
2405 David Naughton
2406
2407 Drew Taylor
2408
2409 Gary Ashton Jones
2410
2411 Geoff Richards
2412
2413 Jesse Sheidlower
2414
2415 Jesse Vincent
2416
2417 Jody Belka
2418
2419 Johan Lindstrom
2420
2421 Juan Camacho
2422
2423 Leon Brocard
2424
2425 Marcus Ramberg
2426
2427 Matt S Trout
2428
2429 Robert Sedlacek
2430
2431 Sam Vilain
2432
2433 Sascha Kiefer
2434
2435 Sebastian Willert
2436
2437 Tatsuhiko Miyagawa
2438
2439 Ulf Edvinsson
2440
2441 Yuval Kogman
2442
2443 =head1 AUTHOR
2444
2445 Sebastian Riedel, C<sri@oook.de>
2446
2447 =head1 LICENSE
2448
2449 This library is free software, you can redistribute it and/or modify it under
2450 the same terms as Perl itself.
2451
2452 =cut
2453
2454 1;