=cut
use Moose;
-
+use Scalar::Util 'looks_like_number';
with 'MooseX::Emulate::Class::Accessor::Fast';
+use namespace::clean -except => 'meta';
has class => (is => 'rw');
has namespace => (is => 'rw');
has name => (is => 'rw');
has code => (is => 'rw');
-no Moose;
-
use overload (
# Stringify to reverse for debug output etc.
# Codulate to execute to invoke the encapsulated action coderef
'&{}' => sub { my $self = shift; sub { $self->execute(@_); }; },
+ # Which action takes precedence
+ 'cmp' => 'compare',
+ '<=>' => 'compare',
+
# Make general $stuff still work
fallback => 1,
return scalar( @{ $c->req->args } ) == $args;
}
+sub sort_order {
+ my $self = shift;
+
+ my ($args) = @{ $self->attributes->{Args} || [] };
+
+ return $args if looks_like_number($args);
+
+ return ~0;
+}
+
+sub compare {
+ my ($a1, $a2) = @_;
+
+ return $a1->sort_order <=> $a2->sort_order;
+}
+
__PACKAGE__->meta->make_immutable;
1;
use Text::SimpleTable;
use Catalyst::Utils;
use URI;
-use Scalar::Util ();
has _paths => (
is => 'rw',
if ( keys %{ $self->_paths } );
}
-sub _action_args_sort_order {
- my ( $self, $action ) = @_;
-
- my ($args) = @{ $action->attributes->{Args} || [] };
-
- return $args if Scalar::Util::looks_like_number($args);
-
- return ~0;
-}
-
=head2 $self->match( $c, $path )
For each action registered to this exact path, offers the action a chance to
$path = '/' if !defined $path || !length $path;
- # sort from least args to most
- my @actions = sort { $self->_action_args_sort_order($a) <=>
- $self->_action_args_sort_order($b) }
- @{ $self->_paths->{$path} || [] };
-
- foreach my $action ( @actions ) {
+ foreach my $action ( @{ $self->_paths->{$path} || [] } ) {
next unless $action->match($c);
$c->req->action($path);
$c->req->match($path);
unshift( @{ $self->_paths->{$path} ||= [] }, $action);
+ $self->_paths->{$path} = [ sort @{ $self->_paths->{$path} } ];
+
return 1;
}
BEGIN { $iters = $ENV{CAT_BENCH_ITERS} || 1; }
-use Test::More tests => 1*$iters;
+use Test::More tests => 3*$iters;
-use Catalyst::Test 'TestAppIndexActionName';
+use Catalyst::Test 'TestAppIndexDefault';
if ( $ENV{CAT_BENCHMARK} ) {
require Benchmark;
sub run_tests {
is(get('/indexchained'), 'index_chained', ':Chained overrides index');
+ is(get('/indexprivate'), 'index_private', 'index : Private still works');
+ is(get('/defaultandpath/path_one_arg'), 'path_one_arg',
+ 'Path overrides default');
}
-package TestAppIndexActionName;
+package TestAppIndexDefault;
use strict;
use warnings;
use Catalyst;
--- /dev/null
+package TestAppIndexDefault::Controller::DefaultAndPath;
+
+use base 'Catalyst::Controller';
+
+sub default : Private {
+ my ($self, $c) = @_;
+ $c->res->body('default');
+}
+
+sub path_one_arg : Path('/') Args(1) {
+ my ($self, $c) = @_;
+ $c->res->body('path_one_arg');
+}
+
+1;
-package TestAppIndexActionName::Controller::IndexChained;
+package TestAppIndexDefault::Controller::IndexChained;
use base 'Catalyst::Controller';
--- /dev/null
+package TestAppIndexDefault::Controller::IndexPrivate;
+
+use base 'Catalyst::Controller';
+
+sub index : Private {
+ my ($self, $c) = @_;
+ $c->res->body('index_private');
+}
+
+1;