Intro: using outside Models in Cat
[catagits/Catalyst-Runtime.git] / lib / Catalyst / Manual / Intro.pod
CommitLineData
fc7ec1d9 1=head1 NAME
2
3Catalyst::Manual::Intro - Introduction to Catalyst
4
5=head1 DESCRIPTION
6
129cfe74 7This is a brief overview of why and how to use Catalyst. It explains how
8Catalyst works and shows how to get a simple application up and running quickly.
fc7ec1d9 9
10=head2 What is Catalyst?
11
129cfe74 12Catalyst is an elegant web application framework, extremely flexible yet
13extremely simple. It's similar to Ruby on Rails, Spring (Java) and L<Maypole>,
14upon which it was originally based.
fc7ec1d9 15
16=head3 MVC
17
129cfe74 18Catalyst follows the Model-View-Controller (MVC) design pattern, allowing you to
19easily separate concerns, like content, presentation, and flow control, into
20separate modules. This separation allows you to modify code that handles one
21concern without affecting code that handles the others. Catalyst promotes the
22re-use of existing Perl modules that already handle common web application
23concerns well.
fc7ec1d9 24
129cfe74 25Here's how the M, V, and C map to those concerns, with examples of well-known
26Perl modules you may want to use for each.
fc7ec1d9 27
28=over 4
29
4a6895ce 30=item * B<Model>
fc7ec1d9 31
32Access and modify content (data). L<Class::DBI>, L<Plucene>, L<Net::LDAP>...
33
4a6895ce 34=item * B<View>
fc7ec1d9 35
129cfe74 36Present content to the user. L<Template Toolkit|Template>, L<Mason|HTML::Mason>,
37L<HTML::Template>...
fc7ec1d9 38
4a6895ce 39=item * B<Controller>
fc7ec1d9 40
129cfe74 41Control the whole request phase, check parameters, dispatch actions, flow
42control. Catalyst!
fc7ec1d9 43
44=back
45
129cfe74 46If you're unfamiliar with MVC and design patterns, you may want to check out the
47original book on the subject, I<Design Patterns>, by Gamma, Helm, Johson and
48Vlissides, also known as the Gang of Four (GoF). You can also just google it.
49Many, many web application frameworks are based on MVC, including all those
50listed above.
fc7ec1d9 51
52=head3 Flexibility
53
129cfe74 54Catalyst is much more flexible than many other frameworks. We'll talk more about
55this later, but rest assured you can use your favorite Perl modules with
56Catalyst.
fc7ec1d9 57
58=over 4
59
72d9bfc7 60=item * B<Multiple Models, Views, and Controllers>
fc7ec1d9 61
129cfe74 62To build a Catalyst application, you handle each type of concern inside special
63modules called L</Components>. Often this code will be very simple, just calling
64out to Perl modules like those listed above under L</MVC>. Catalyst handles
65these components in a very flexible way. Use as many Models, Views, and
66Controllers as you like, using as many different Perl modules as you like, all
67in the same application. Want to manipulate multiple databases, and retrieve
68some data via LDAP? No problem. Want to present data from the same Model using
69L<Template Toolkit|Template> and L<PDF::Template>? Easy.
fc7ec1d9 70
cda8d1ac 71=item * B<Reuseable Components>
fc7ec1d9 72
129cfe74 73Not only does Catalyst promote the re-use of already existing Perl modules, it
74also allows you to re-use your Catalyst components in multiple Catalyst
75applications.
fc7ec1d9 76
4a6895ce 77=item * B<Unrestrained URL-to-Action Dispatching>
fc7ec1d9 78
129cfe74 79Catalyst allows you to dispatch any URLs to any application L<Actions>, even
80through regular expressions! Unlike most other frameworks, it doesn't require
81mod_rewrite or class and method names in URLs.
fc7ec1d9 82
83With Catalyst you register your actions and address them directly. For example:
84
e3dc9d78 85 sub hello : Global {
fc7ec1d9 86 my ( $self, $context ) = @_;
87 $context->response->output('Hello World!');
5a8ed4fe 88 }
fc7ec1d9 89
90Now http://localhost:3000/hello prints "Hello World!".
91
4a6895ce 92=item * B<Support for CGI, mod_perl, Apache::Request>
fc7ec1d9 93
94Use L<Catalyst::Engine::Apache> or L<Catalyst::Engine::CGI>.
95
96=back
97
98=head3 Simplicity
99
129cfe74 100The best part is that Catalyst implements all this flexibility in a very simple
101way.
fc7ec1d9 102
6f4e1683 103=over 4
104
4a6895ce 105=item * B<Building Block Interface>
fc7ec1d9 106
129cfe74 107Components interoperate very smoothly. For example, Catalyst automatically makes
108a L<Context> object available to every component. Via the context, you can
109access the request object, share data between components, and control the flow
110of your application. Building a Catalyst application feels a lot like snapping
111together toy building blocks, and everything just works.
fc7ec1d9 112
4a6895ce 113=item * B<Component Auto-Discovery>
fc7ec1d9 114
129cfe74 115No need to C<use> all of your components. Catalyst automatically finds and loads
116them.
fc7ec1d9 117
4a6895ce 118=item * B<Pre-Built Components for Popular Modules>
fc7ec1d9 119
129cfe74 120See L<Catalyst::Model::CDBI> for L<Class::DBI>, or L<Catalyst::View::TT> for
121L<Template Toolkit|Template>. You can even get an instant web database front end
122with L<Catalyst::Model::CDBI::CRUD>.
fc7ec1d9 123
72d9bfc7 124=item * B<Built-in Test Framework>
fc7ec1d9 125
129cfe74 126Catalyst comes with a built-in, lightweight http server and test framework,
127making it easy to test applications from the command line.
fc7ec1d9 128
4a6895ce 129=item * B<Helper Scripts>
fc7ec1d9 130
129cfe74 131Catalyst provides helper scripts to quickly generate running starter code for
132components and unit tests.
fc7ec1d9 133
6f4e1683 134=back
135
fc7ec1d9 136=head2 Quickstart
137
129cfe74 138Here's how to install Catalyst and get a simple application up and running,
139using the helper scripts described above.
fc7ec1d9 140
141=head3 Install
142
143 $ perl -MCPAN -e 'install Bundle::Catalyst'
144
145=head3 Setup
146
2feb6632 147 $ catalyst.pl MyApp
b33ed88c 148 # output omitted
2feb6632 149 $ cd MyApp
ac4a0ae0 150 $ script/myapp_create.pl controller Library::Login
fc7ec1d9 151
152=head3 Run
153
b33ed88c 154 $ script/myapp_server.pl
fc7ec1d9 155
129cfe74 156Now visit these locations with your favorite browser or user agent to see
157Catalyst in action:
fc7ec1d9 158
159=over 4
160
161=item http://localhost:3000/
162
ac4a0ae0 163=item http://localhost:3000/library/login/
fc7ec1d9 164
165=back
166
167Dead easy!
168
169=head2 How It Works
170
129cfe74 171Let's see how Catalyst works, by taking a closer look at the components and
172other parts of a Catalyst application.
fc7ec1d9 173
174=head3 Application Class
175
129cfe74 176In addition to the Model, View, and Controller components, there's a single
177class that represents your application itself. This is where you configure your
178application, load plugins, define application-wide actions, and extend Catalyst.
fc7ec1d9 179
180 package MyApp;
181
182 use strict;
183 use Catalyst qw/-Debug/;
184
185 MyApp->config(
186 name => 'My Application',
187 root => '/home/joeuser/myapp/root',
188
b33ed88c 189 # You can put anything else you want in here:
190 my_configuration_variable => 'something',
fc7ec1d9 191 );
192
5a8ed4fe 193 sub default : Private {
fc7ec1d9 194 my ( $self, $context ) = @_;
195 $context->response->output('Catalyst rockz!');
5a8ed4fe 196 }
fc7ec1d9 197
198 1;
199
129cfe74 200For most applications, Catalyst requires you to define only two config
201parameters:
fc7ec1d9 202
203=over 4
204
4a6895ce 205=item * B<name>
fc7ec1d9 206
207Name of your application.
208
4a6895ce 209=item * B<root>
fc7ec1d9 210
72d9bfc7 211Path to additional files such as templates, images, or other static data.
fc7ec1d9 212
213=back
214
129cfe74 215However, you can define as many parameters as you want for plugins or whatever
216you need. You can access them anywhere in your application via
217C<$context-E<gt>config-E<gt>{$param_name}>.
fc7ec1d9 218
219=head3 Context
220
129cfe74 221Catalyst automatically blesses a Context object into your application class and
222makes it available everywhere in your application. Use the Context to directly
223interact with Catalyst and glue your L<Components> together. For example, if you
224need to use the Context from within a Template Toolkit template, it's already
225there:
c42f5bbf 226
227 <h1>Welcome to [% c.config.name %]!</h1>
fc7ec1d9 228
129cfe74 229As illustrated earlier in our URL-to-Action dispatching example, the Context is
230always the second method parameter, behind the Component object reference or
231class name itself. Previously we called it C<$context> for clarity, but most
232Catalyst developers just call it C<$c>:
fc7ec1d9 233
e3dc9d78 234 sub hello : Global {
fc7ec1d9 235 my ( $self, $c ) = @_;
236 $c->res->output('Hello World!');
5a8ed4fe 237 }
fc7ec1d9 238
239The Context contains several important objects:
240
241=over 4
242
243=item * L<Catalyst::Request>
244
245 $c->request
246 $c->req # alias
247
129cfe74 248The request object contains all kinds of request-specific information, like
249query parameters, cookies, uploads, headers, and more.
fc7ec1d9 250
251 $c->req->params->{foo};
252 $c->req->cookies->{sessionid};
253 $c->req->headers->content_type;
254 $c->req->base;
255
afdca3a3 256=item * L<Catalyst::Response>
fc7ec1d9 257
258 $c->response
259 $c->res # alias
260
129cfe74 261The response is like the request, but contains just response-specific
262information.
fc7ec1d9 263
264 $c->res->output('Hello World');
265 $c->res->status(404);
266 $c->res->redirect('http://oook.de');
267
268=item * L<Catalyst::Config>
269
270 $c->config
271
272 $c->config->root;
273 $c->config->name;
274
275=item * L<Catalyst::Log>
276
277 $c->log
278
279 $c->log->debug('Something happened');
280 $c->log->info('Something you should know');
281
4a6895ce 282=item * B<Stash>
fc7ec1d9 283
284 $c->stash
285
286 $c->stash->{foo} = 'bar';
287
288=back
289
129cfe74 290The last of these, the stash, is a universal hash for sharing data among
291application components. For an example, we return to our 'hello' action:
fc7ec1d9 292
e3dc9d78 293 sub hello : Global {
5a8ed4fe 294 my ( $self, $c ) = @_;
295 $c->stash->{message} = 'Hello World!';
4c6807d2 296 $c->forward('show_message');
5a8ed4fe 297 }
fc7ec1d9 298
4c6807d2 299 sub show_message : Private {
5a8ed4fe 300 my ( $self, $c ) = @_;
301 $c->res->output( $c->stash->{message} );
302 }
fc7ec1d9 303
129cfe74 304Note that the stash should be used only for passing data in an individual
305request cycle; it gets cleared at a new request. If you need to maintain more
306persistent data, use a session.
dd25a192 307
fc7ec1d9 308=head3 Actions
309
129cfe74 310A Catalyst controller is defined by its actions. An action is a sub with a
311special attribute. You've already seen some examples of actions in this
312document. The URL (for example http://localhost.3000/foo/bar) consists of two
313parts, the base (http://localhost:3000/ in this example) and the path (foo/bar).
314Please note that the trailing slash after the hostname[:port] always belongs to
315base and not to the action.
cda8d1ac 316
317Catalyst supports several types of actions:
fc7ec1d9 318
319=over 4
320
4a6895ce 321=item * B<Literal>
fc7ec1d9 322
f29c48dd 323 sub bar : Path('foo/bar') { }
fc7ec1d9 324
325Matches only http://localhost:3000/foo/bar.
326
4a6895ce 327=item * B<Regex>
fc7ec1d9 328
b33ed88c 329 sub bar : Regex('^item(\d+)/order(\d+)$') { }
fc7ec1d9 330
129cfe74 331Matches any URL that matches the pattern in the action key, e.g.
332http://localhost:3000/item23/order42. The '' around the regexp is optional, but
333perltidy likes it. :)
b33ed88c 334
129cfe74 335Regex matches act globally, i.e. without reference to the namespace from which
336it is called, so that a C<bar> method in the
337C<MyApp::Controller::Catalog::Order::Process> namespace won't match any form of
338C<bar>, C<Catalog>, C<Order>, or C<Process> unless you explicitly put this in
339the regex.
fc7ec1d9 340
129cfe74 341If you use capturing parentheses to extract values within the matching URL (23,
34242 in the above example), those values are available in the $c->req->snippets
343array. If you want to pass arguments at the end of your URL, you must use regex
344action keys. See L</URL Argument Handling> below.
fc7ec1d9 345
72d9bfc7 346=item * B<Top-level>
cda8d1ac 347
348 package MyApp;
349 sub foo : Global { }
350
b33ed88c 351Matches http://localhost:3000/foo. The function name is mapped directly
352to the application base.
cda8d1ac 353
4a6895ce 354=item * B<Namespace-Prefixed>
fc7ec1d9 355
2feb6632 356 package MyApp::C::My::Controller;
e3dc9d78 357 sub foo : Local { }
fc7ec1d9 358
cda8d1ac 359Matches http://localhost:3000/my/controller/foo.
fc7ec1d9 360
129cfe74 361This action type indicates that the matching URL must be prefixed with a
362modified form of the component's class (package) name. This modified class name
363excludes the parts that have a pre-defined meaning in Catalyst ("MyApp::C" in
364the above example), replaces "::" with "/", and converts the name to lower case.
365See L</Components> for a full explanation of the pre-defined meaning of Catalyst
366component class names.
fc7ec1d9 367
4a6895ce 368=item * B<Private>
fc7ec1d9 369
5a8ed4fe 370 sub foo : Private { }
fc7ec1d9 371
129cfe74 372Matches no URL, and cannot be executed by requesting a URL that corresponds to
373the action key. Private actions can be executed only inside a Catalyst
374application, by calling the C<forward> method:
fc7ec1d9 375
5a8ed4fe 376 $c->forward('foo');
fc7ec1d9 377
129cfe74 378See L</Flow Control> for a full explanation of C<forward>. Note that, as
fc9c8698 379discussed there, when forwarding from another component, you must use
380the absolute path to the method, so that a private C<bar> method in your
381C<MyApp::Controller::Catalog::Order::Process> controller must, if called
382from elsewhere, be reached with
383C<$c-E<gt>forward('/catalog/order/process/bar')>.
fc7ec1d9 384
385=back
386
b33ed88c 387B<Note:> After seeing these examples, you probably wonder what the point
388is of defining names for regex and path actions. Actually, every public
389action is also a private one, so you have one unified way of addressing
390components in your C<forward>s.
cda8d1ac 391
72d9bfc7 392=head4 Built-in Private Actions
fc7ec1d9 393
fc9c8698 394In response to specific application states, Catalyst will automatically
395call these built-in private actions in your application class:
fc7ec1d9 396
397=over 4
398
cda8d1ac 399=item * B<default : Private>
fc7ec1d9 400
fc9c8698 401Called when no other action matches. Could be used, for example, for
402displaying a generic frontpage for the main app, or an error page for
403individual controllers.
fc7ec1d9 404
cda8d1ac 405=item * B<begin : Private>
fc7ec1d9 406
fc9c8698 407Called at the beginning of a request, before any matching actions are
408called.
fc7ec1d9 409
cda8d1ac 410=item * B<end : Private>
4a6895ce 411
fc7ec1d9 412Called at the end of a request, after all matching actions are called.
413
fc9c8698 414=back
415
6b10c72b 416=head4 Built-in actions in controllers/autochaining
fc7ec1d9 417
cda8d1ac 418 Package MyApp::C::Foo;
419 sub begin : Private { }
5a8ed4fe 420 sub default : Private { }
eff5f524 421 sub auto : Private { }
fc7ec1d9 422
fc9c8698 423You can define built-in private actions within your controllers as
424well. The actions will override the ones in less-specific controllers,
425or your application class. In other words, for each of the three
426built-in private actions, only one will be run in any request
427cycle. Thus, if C<MyApp::C::Catalog::begin> exists, it will be run in
428place of C<MyApp::begin> if you're in the C<catalog> namespace, and
429C<MyApp::C::Catalog::Order::begin> would override this in turn.
430
eff5f524 431In addition to the normal built-in actions, you have a special action
432for making chains, C<auto>. Such C<auto> actions will be run after any
fc9c8698 433C<begin>, but before your action is processed. Unlike the other
eff5f524 434built-ins, C<auto> actions I<do not> override each other; they will be
435called in turn, starting with the application class and going through to
436the I<most> specific class. I<This is the reverse of the order in which
437the normal built-ins override each other>.
fc9c8698 438
439Here are some examples of the order in which the various built-ins
440would be called:
cda8d1ac 441
442=over 4
443
fc9c8698 444=item for a request for C</foo/foo>
cda8d1ac 445
446 MyApp::begin
80ef2e6d 447 MyApp::auto
fc9c8698 448 MyApp::C::Foo::default # in the absence of MyApp::C::Foo::Foo
cda8d1ac 449 MyApp::end
450
fc9c8698 451=item for a request for C</foo/bar/foo>
cda8d1ac 452
cda8d1ac 453 MyApp::C::Foo::Bar::begin
80ef2e6d 454 MyApp::auto
455 MyApp::C::Foo::auto
fc9c8698 456 MyApp::C::Foo::Bar::auto
457 MyApp::C::Foo::Bar::default # for MyApp::C::Foo::Bar::foo
cda8d1ac 458 MyApp::C::Foo::Bar::end
80ef2e6d 459
460=back
461
fc9c8698 462The C<auto> action is also distinguished by the fact that you can break
463out of the processing chain by returning 0. If an C<auto> action returns
4640, any remaining actions will be skipped, except for C<end>. So, for the
465request above, if the first auto returns false, the chain would look
466like this:
80ef2e6d 467
468=over 4
469
fc9c8698 470=item for a request for C</foo/bar/foo> where first C<auto> returns
471false
80ef2e6d 472
473 MyApp::C::Foo::Bar::begin
474 MyApp::auto
475 MyApp::C::Foo::Bar::end
cda8d1ac 476
477=back
4a6895ce 478
fc9c8698 479An example of why one might use this is an authentication action: you
480could set up a C<auto> action to handle authentication in your
481application class (which will always be called first), and if
482authentication fails, returning 0 would skip any remaining methods
483for that URL.
03805733 484
fc9c8698 485B<Note:> Looking at it another way, C<auto> actions have to return a
486true value to continue processing! You can also C<die> in the autochain
487action; in that case, the request will go straight to the finalize
488stage, without processing further actions.
03805733 489
6b10c72b 490=head4 URL Path Handling
4a6895ce 491
fc9c8698 492You can pass variable arguments as part of the URL path. In this case,
493you must use regex action keys with '^' and '$' anchors, and the
494arguments must be separated with forward slashes (/) in the URL. For
495example, suppose you want to handle C</foo/$bar/$baz>, where C<$bar> and
496C<$baz> may vary:
4a6895ce 497
cda8d1ac 498 sub foo : Regex('^foo$') { my ($self, $context, $bar, $baz) = @_; }
4a6895ce 499
fc9c8698 500But what if you also defined actions for C</foo/boo> and C</foo/boo/hoo>?
4a6895ce 501
f29c48dd 502 sub boo : Path('foo/boo') { .. }
503 sub hoo : Path('foo/boo/hoo') { .. }
4a6895ce 504
505Catalyst matches actions in most specific to least specific order:
506
507 /foo/boo/hoo
508 /foo/boo
fc9c8698 509 /foo # might be /foo/bar/baz but won't be /foo/boo/hoo
4a6895ce 510
fc9c8698 511So Catalyst would never mistakenly dispatch the first two URLs to the
512'^foo$' action.
fc7ec1d9 513
6b10c72b 514=head4 Parameter Processing
2ef2fb0f 515
fc9c8698 516Parameters passed in the URL query string are handled with methods in
517the L<Catalyst::Request> class. The C<param> method is functionally
518equivalent to the C<param> method of C<CGI.pm> and can be used in
519modules that require this.
2ef2fb0f 520
521 # http://localhost:3000/catalog/view/?category=hardware&page=3
522 my $category = $c->req->param('category');
523 my $current_page = $c->req->param('page') || 1;
524
525 # multiple values for single parameter name
526 my @values = $c->req->param('scrolling_list');
527
528 # DFV requires a CGI.pm-like input hash
529 my $results = Data::FormValidator->check($c->req->params, \%dfv_profile);
530
fc7ec1d9 531=head3 Flow Control
532
d08ced28 533You control the application flow with the C<forward> method, which
534accepts the key of an action to execute. This can be an action in the
535same or another Catalyst controller, or a Class name, optionally
536followed by a method name. After a C<forward>, the control flow will
537return to the method from which the C<forward> was issued.
538
539A C<forward> is similar to a method call. The main differences are that
540it wraps the call in an C<eval> to allow exception handling; it
541automatically passes along the context object (C<$c> or C<$context>);
542and it allows profiling of each call (displayed in the log with
543debugging enabled).
fc7ec1d9 544
e3dc9d78 545 sub hello : Global {
5a8ed4fe 546 my ( $self, $c ) = @_;
547 $c->stash->{message} = 'Hello World!';
d08ced28 548 $c->forward('check_message'); # $c is automatically included
5a8ed4fe 549 }
fc7ec1d9 550
4c6807d2 551 sub check_message : Private {
5a8ed4fe 552 my ( $self, $c ) = @_;
553 return unless $c->stash->{message};
4c6807d2 554 $c->forward('show_message');
5a8ed4fe 555 }
fc7ec1d9 556
4c6807d2 557 sub show_message : Private {
5a8ed4fe 558 my ( $self, $c ) = @_;
559 $c->res->output( $c->stash->{message} );
560 }
3323f920 561
d08ced28 562A C<forward> does not create a new request, so your request
563object (C<$c-E<gt>req>) will remain unchanged. This is a
564key difference between using C<forward> and issuing a
565redirect.
3323f920 566
d08ced28 567You can pass new arguments to a C<forward> by adding them
568in an anonymous array. In this case C<$c-E<gt>req-E<gt>args>
569will be changed for the duration of the C<forward> only; upon
570return, the original value of C<$c-E<gt>req-E<gt>args> will
571be reset.
3323f920 572
573 sub hello : Global {
574 my ( $self, $c ) = @_;
575 $c->stash->{message} = 'Hello World!';
d08ced28 576 $c->forward('check_message',[qw/test1/]);
577 # now $c->req->args is back to what it was before
3323f920 578 }
579
d08ced28 580 sub check_message : Private {
581 my ( $self, $c ) = @_;
582 my $first_argument = $c->req->args[0]; # now = 'test1'
583 # do something...
584 }
cda8d1ac 585
d08ced28 586As you can see from these examples, you can just use the method name as
587long as you are referring to methods in the same controller. If you want
588to forward to a method in another controller, or the main application,
589you will have to refer to the method by absolute path.
cda8d1ac 590
591 $c->forward('/my/controller/action');
d08ced28 592 $c->forward('/default'); # calls default in main application
fc7ec1d9 593
d08ced28 594Here are some examples of how to forward to classes and methods.
fc7ec1d9 595
e3dc9d78 596 sub hello : Global {
5a8ed4fe 597 my ( $self, $c ) = @_;
598 $c->forward(qw/MyApp::M::Hello say_hello/);
599 }
fc7ec1d9 600
e3dc9d78 601 sub bye : Global {
5a8ed4fe 602 my ( $self, $c ) = @_;
d08ced28 603 $c->forward('MyApp::M::Hello'); # no method: will try 'process'
5a8ed4fe 604 }
fc7ec1d9 605
606 package MyApp::M::Hello;
607
608 sub say_hello {
609 my ( $self, $c ) = @_;
610 $c->res->output('Hello World!');
611 }
612
613 sub process {
614 my ( $self, $c ) = @_;
615 $c->res->output('Goodbye World!');
616 }
617
d08ced28 618Note that C<forward> returns to the calling action and continues
13436c14 619processing after the action finishes. If you want all further processing
620in the calling action to stop, use C<detach> instead, which will execute
621the C<detach>ed action and not return to the calling sub. In both cases,
622Catalyst will automatically try to call process() if you omit the
623method.
fc7ec1d9 624
625=head3 Components
626
129cfe74 627Catalyst has an uncommonly flexible component system. You can define as many
628L<Models>, L<Views>, and L<Controllers> as you like.
fc7ec1d9 629
129cfe74 630All components must inherit from L<Catalyst::Base>, which provides a simple
631class structure and some common class methods like C<config> and C<new>
632(constructor).
fc7ec1d9 633
ac4a0ae0 634 package MyApp::C::Catalog;
fc7ec1d9 635
636 use strict;
637 use base 'Catalyst::Base';
638
639 __PACKAGE__->config( foo => 'bar' );
640
641 1;
642
6b10c72b 643You don't have to C<use> or otherwise register Models, Views, and
644Controllers. Catalyst automatically discovers and instantiates them
645when you call C<setup> in the main application. All you need to do is
646put them in directories named for each Component type. Notice that you
647can use some very terse aliases for each one.
fc7ec1d9 648
649=over 4
650
4a6895ce 651=item * B<MyApp/Model/>
fc7ec1d9 652
4a6895ce 653=item * B<MyApp/M/>
fc7ec1d9 654
4a6895ce 655=item * B<MyApp/View/>
fc7ec1d9 656
4a6895ce 657=item * B<MyApp/V/>
fc7ec1d9 658
4a6895ce 659=item * B<MyApp/Controller/>
fc7ec1d9 660
4a6895ce 661=item * B<MyApp/C/>
fc7ec1d9 662
663=back
664
665=head4 Views
666
129cfe74 667To show how to define views, we'll use an already-existing base class for the
668L<Template Toolkit|Template>, L<Catalyst::View::TT>. All we need to do is
669inherit from this class:
fc7ec1d9 670
671 package MyApp::V::TT;
672
673 use strict;
674 use base 'Catalyst::View::TT';
675
676 1;
677
b33ed88c 678(You can also generate this automatically by using the helper script:
679
680 script/myapp_create.pl view TT TT
681
682where the first C<TT> tells the script to create a Template Toolkit
683view, and the second tells the script that its name should be C<TT>.)
684
129cfe74 685This gives us a process() method and we can now just do
686$c->forward('MyApp::V::TT') to render our templates. The base class makes
687process() implicit, so we don't have to say C<$c-E<gt>forward(qw/MyApp::V::TT
688process/)>.
fc7ec1d9 689
e3dc9d78 690 sub hello : Global {
5a8ed4fe 691 my ( $self, $c ) = @_;
692 $c->stash->{template} = 'hello.tt';
693 }
fc7ec1d9 694
5a8ed4fe 695 sub end : Private {
696 my ( $self, $c ) = @_;
2feb6632 697 $c->forward('MyApp::V::TT');
5a8ed4fe 698 }
fc7ec1d9 699
6b10c72b 700You normally render templates at the end of a request, so it's a perfect
701use for the global C<end> action.
fc7ec1d9 702
129cfe74 703Also, be sure to put the template under the directory specified in
6b10c72b 704C<$c-E<gt>config-E<gt>{root}>, or you'll be forced to look at our
705eyecandy debug screen. ;)
fc7ec1d9 706
707=head4 Models
708
129cfe74 709To show how to define models, again we'll use an already-existing base class,
710this time for L<Class::DBI>: L<Catalyst::Model::CDBI>.
fc7ec1d9 711
712But first, we need a database.
713
714 -- myapp.sql
715 CREATE TABLE foo (
716 id INTEGER PRIMARY KEY,
717 data TEXT
718 );
719
720 CREATE TABLE bar (
721 id INTEGER PRIMARY KEY,
722 foo INTEGER REFERENCES foo,
723 data TEXT
724 );
725
726 INSERT INTO foo (data) VALUES ('TEST!');
727
728
729 % sqlite /tmp/myapp.db < myapp.sql
730
731Now we can create a CDBI component for this database.
732
733 package MyApp::M::CDBI;
734
735 use strict;
736 use base 'Catalyst::Model::CDBI';
737
738 __PACKAGE__->config(
739 dsn => 'dbi:SQLite:/tmp/myapp.db',
740 relationships => 1
741 );
742
743 1;
744
129cfe74 745Catalyst automatically loads table layouts and relationships. Use the stash to
746pass data to your templates.
fc7ec1d9 747
748 package MyApp;
749
750 use strict;
751 use Catalyst '-Debug';
752
753 __PACKAGE__->config(
754 name => 'My Application',
755 root => '/home/joeuser/myapp/root'
756 );
cda8d1ac 757
758 __PACKAGE__->setup;
fc7ec1d9 759
5a8ed4fe 760 sub end : Private {
761 my ( $self, $c ) = @_;
762 $c->stash->{template} ||= 'index.tt';
763 $c->forward('MyApp::V::TT');
764 }
fc7ec1d9 765
e3dc9d78 766 sub view : Global {
5a8ed4fe 767 my ( $self, $c, $id ) = @_;
768 $c->stash->{item} = MyApp::M::CDBI::Foo->retrieve($id);
769 }
fc7ec1d9 770
771 1;
772
6b10c72b 773 # Then, in a TT template:
fc7ec1d9 774 The id is [% item.data %]
775
6b10c72b 776Models do not have to be part of your Catalyst application; you
777can always call an outside module that serves as your Model:
778
779 # in a Controller
780 sub list : Local {
781 my ( $self, $c ) = @_;
782 $c->stash->{template} = 'list.tt';
783 use Some::Outside::CDBI::Module;
784 my @records = Some::Outside::CDBI::Module->retrieve_all;
785 $c->stash->{records} = \@records;
786 }
787
788But by using a Model that is part of your Catalyst application, you gain
789several things: you don't have to C<use> each component, Catalyst will
790find and load it automatically at compile-time; you can C<forward> to
791the module, which can only be done to Catalyst componenents; and only
792Catalyst components can be fetched with
793C<$c-E<gt>comp('MyApp::M::SomeModel')>.
794
795Happily, since many people have existing Model classes that they
796would like to use with Catalyst (or, conversely, they want to
797write Catalyst models that can be used outside of Catalyst, e.g.
798in a cron job), it's trivial to write a simple component in
799Catalyst that slurps in an outside Model:
800
801 package MyApp::M::Catalog;
802 use base qw/Catalyst::Base Some::Other::CDBI::Module::Catalog/;
803 1;
804
805and that's it! Now C<Some::Other::CDBI::Module::Catalog> is part of your
806Cat app as C<MyApp::M::Catalog>.
807
fc7ec1d9 808=head4 Controllers
809
129cfe74 810Multiple controllers are a good way to separate logical domains of your
811application.
fc7ec1d9 812
813 package MyApp::C::Login;
814
72d9bfc7 815 sign-in : Local { }
816 new-password : Local { }
817 sign-out : Local { }
fc7ec1d9 818
819 package MyApp::C::Catalog;
820
e3dc9d78 821 sub view : Local { }
822 sub list : Local { }
fc7ec1d9 823
824 package MyApp::C::Cart;
825
e3dc9d78 826 sub add : Local { }
827 sub update : Local { }
828 sub order : Local { }
fc7ec1d9 829
830=head3 Testing
831
129cfe74 832Catalyst has a built-in http server for testing! (Later, you can easily use a
833more powerful server, e.g. Apache/mod_perl, in a production environment.)
fc7ec1d9 834
835Start your application on the command line...
836
b33ed88c 837 script/myapp_server.pl
fc7ec1d9 838
839...then visit http://localhost:3000/ in a browser to view the output.
840
841You can also do it all from the command line:
842
b33ed88c 843 script/myapp_test.pl http://localhost/
fc7ec1d9 844
845Have fun!
846
3cb1db8c 847=head1 SUPPORT
848
849IRC:
850
851 Join #catalyst on irc.perl.org.
852
72d9bfc7 853Mailing-lists:
3cb1db8c 854
855 http://lists.rawmode.org/mailman/listinfo/catalyst
856 http://lists.rawmode.org/mailman/listinfo/catalyst-dev
857
fc7ec1d9 858=head1 AUTHOR
859
cda8d1ac 860Sebastian Riedel, C<sri@oook.de>
861David Naughton, C<naughton@umn.edu>
862Marcus Ramberg, C<mramberg@cpan.org>
f531dd37 863Jesse Sheidlower, C<jester@panix.com>
129cfe74 864Danijel Milicevic, C<me@danijel.de>
fc7ec1d9 865
866=head1 COPYRIGHT
867
868This program is free software, you can redistribute it and/or modify it under
869the same terms as Perl itself.