NAME
CatalystX::Controller::Sugar - Sugar for Catalyst controller
VERSION
0.0901
DESCRIPTION
This module is written to simplify the way controllers are written. I personally think that shifting off $c
and $self
in every action is tidious. I also wanted a simpler API to created chained actions, since I rarely use any other actions - except of "private".
SYNOPSIS
package MyApp::Controller::Root;
use CatalystX::Controller::Sugar;
__PACKAGE__->config->{'namespace'} = q();
# Private action
private authenticate => sub {
c->user_exists and return 1;
};
# Chain /
chain sub {
report debug => 'Someone tries to access %s', c->action;
};
# Endpioint /*
chain '' => sub {
res->body('not found');
};
# Endpoint /login
chain login => {
get => sub {}, # show template
post => sub {
forward 'authenticate' and go '';
},
};
# Chain /user/[id]/*
chain user => ['id'], sub {
stash user => c->model('DB::User')->find($_[0]);
};
# Endpoint /user/[id]/view/*
chain 'user:1' => view => sub {
res->body(
sprintf 'Person is called: %s', stash->{'user'}->name
);
};
Same with standard Catalyst syntax
package MyApp::Controller::Root;
use Moose;
BEGIN { extends 'Catalyst::Controller' }
__PACKAGE__->config->{'namespace'} = q();
# Private action
sub authenticate :Private {
my($self, $c) = @_;
$c->user_exists and return 1;
}
# Chain /
sub root :Chained("/") PathPart("") CaptureArgs(0) {
my($self, $c) = @_;
$c->log->debug(sprintf 'Someone tries to access %s', $c->action);
}
# Endpioint /*
sub default :Chained("/root") PathPart("") Args {
my($self, $c) = @_;
$c->res->body('not found');
}
# Endpoint /login
sub login :Chained("/root") PathPart Args {
my($self, $c) = @_;
if(lc $c->req->method eq 'get') {
return; # show template
}
elsif(lc $c->req->method eq 'post') {
$c->forward('authenticate') and go('');
}
}
# Chain /user/[id]/*
sub user :Chained("/root") PathPart CaptureArgs(1) {
my($self, $c, $id) = @_;
$c->stash->{'id'} = $id; # alternative to captured('id');
$c->stash->{'user'} = $c->model('DB::User')->find($id);
}
# Endpoint /user/[id]/view/*
sub user_view :Chained("/user") PathPart('view') Args {
my($self, $c) = @_;
$c->res->body(sprintf 'Person is called: %s', $c->stash->{'user'}->name);
}
NOTE
$self
and $c
is not part of the argument list inside a chain() or private() action. $c
is acquired by calling c(), and $self
is available by calling controller().
EXPORTED FUNCTIONS
chain
1. chain sub { };
2. chain $PathPart => sub { };
3. chain $PathPart => $Int, sub { };
4. chain $PathPart => \@CaptureArgs, sub { };
5. chain $Chained => $PathPart => sub { };
6. chain $Chained => $PathPart => $Int, sub { };
7. chain $Chained => $PathPart => \@CaptureArgs, sub { };
8. chain ..., \%method_map;
9. chain ANY => \%extra_args => sub { };
Same as:
1. sub root : Chained('/') PathPart('') CaptureArgs(0) { }
2. sub $PathPart : Chained('/root') Args { }
3. sub $PathPart : Chained('/root') Args($Int) { }
4. sub $PathPart : Chained('/root') CaptureArgs($Int) { }
5. sub $PathPart : Chained($Chained) Args { }
6. sub $PathPart : Chained($Chained) Args($Int) { }
7. sub $PathPart : Chained($Chained) CaptureArgs($Int) { }
8. Special case: See below
9. Special case: See below
@CaptureArgs
is a list of names of the captured arguments, which can be retrieved using captured().
$Int
is a number of Args to capture at the endpoint of a chain. These cannot be aquired using captured(), but is instead available in @_
.
%method_map
can be used if you want to dispatch to a specific method, for a certain HTTP method: (The HTTP method is in lowercase)
%method_map = (
post => sub { ... },
get => sub { ... },
delete => sub { ... },
default => sub { ... },
#...
);
%extra_args
can be used to override information. Example:
{ name => 'foo' }
Specifying "name" will replace the default name for this action, with "foo" (or something else).
private
private $name => sub {};
Same as:
sub $name :Private {}
forward
@Any = forward $action;
@Any = forward $action, \@arguments;
See Catalyst::forward().
go
go $action;
go $action, \@arguments;
See Catalyst::go().
c
$context_obj = c;
Returns the context object for this request, an instance of Catalyst.
controller
$controller_obj = controller;
Returns the current controller object.
req
$request_obj = req;
Returns the request object for this request, an instance of Catalyst::Request.
res
$response_obj = res;
Returns the response object for this request, an instance of Catalyst::Response.
captured
$value = captured($name);
Retrieve data captured in a chain, using the names set with chain().
chain '/' => 'user' => ['id'], sub {
res->body( captured('id') );
};
stash
$value = stash $key;
$hash_ref = stash $key => $value, ...;
$hash_ref = stash;
Set/get data from the stash. The $hash_ref
is a reference to what the stash is holding.
This will be the same as:
$c->stash->{$key} = $value;
session
$value = session $key;
$hash_ref == session $key => $value;
$hash_ref == session;
Set/get data from the session. The $hash_ref
is a reference to what the session is holding.
This function will only work if a session module/plugin is loaded into Catalyst.
report
report $level, $format, @args;
Almost the same as:
$c->log->$level(sprintf $format, @args);
But undef values from @args
are turned into "__UNDEF__", and objects and/or datastructructures are flatten, using Data::Dumper.
METHODS
init_meta
See Moose::Exporter.
BUGS
Please report any bugs or feature requests to bug-catalystx-controller-sugar at rt.cpan.org
. I will be notified, and then you'll automatically be notified of progress on your bug as I make changes.
COPYRIGHT & LICENSE
Copyright 2007 Jan Henning Thorsen, all rights reserved.
This program is free software; you can redistribute it and/or modify it under the same terms as Perl itself.
AUTHOR
Jan Henning Thorsen, <jhthorsen at cpan.org>