[dw-free] Need a way to cleanly call controllers from tests
[commit: http://hg.dwscoalition.org/dw-free/rev/37f7a2c8953c]
http://bugs.dwscoalition.org/show_bug.cgi?id=3547
Limit the methods that are supported by controllers to GET/POST/HEAD.
Controllers can override to allow other methods.
Patch by
exor674.
Files modified:
http://bugs.dwscoalition.org/show_bug.cgi?id=3547
Limit the methods that are supported by controllers to GET/POST/HEAD.
Controllers can override to allow other methods.
Patch by
Files modified:
- cgi-bin/DW/Controller/Interface/S2.pm
- cgi-bin/DW/Request/Standard.pm
- cgi-bin/DW/Routing.pm
- cgi-bin/DW/Routing/CallInfo.pm
- t/routing.t
--------------------------------------------------------------------------------
diff -r b7d1369e7005 -r 37f7a2c8953c cgi-bin/DW/Controller/Interface/S2.pm
--- a/cgi-bin/DW/Controller/Interface/S2.pm Mon Feb 28 16:33:50 2011 +0800
+++ b/cgi-bin/DW/Controller/Interface/S2.pm Mon Feb 28 18:44:54 2011 +0800
@@ -21,7 +21,7 @@ use DW::Routing;
use DW::Routing;
# handle, even with no id, so that we can present an informative error message
-DW::Routing->register_regex( '^/interface/s2(?:/(\d+)?)?$', \&interface_handler, app => 1, format => 'plain' );
+DW::Routing->register_regex( '^/interface/s2(?:/(\d+)?)?$', \&interface_handler, app => 1, format => 'plain', methods => { GET => 1, PUT => 1 } );
# handles menu nav pages
sub interface_handler {
@@ -101,10 +101,6 @@ sub interface_handler {
return $r->OK;
}
- } else {
- # Return 'method not allowed' so that we can add methods in future
- # and clients will get a sensible error from old servers.
- return error( $r, $r->HTTP_METHOD_NOT_ALLOWED, 'Method Not Allowed', 'Only GET and PUT are supported for this resource' );
}
}
diff -r b7d1369e7005 -r 37f7a2c8953c cgi-bin/DW/Request/Standard.pm
--- a/cgi-bin/DW/Request/Standard.pm Mon Feb 28 16:33:50 2011 +0800
+++ b/cgi-bin/DW/Request/Standard.pm Mon Feb 28 18:44:54 2011 +0800
@@ -291,10 +291,14 @@ sub OK { return 200; }
sub OK { return 200; }
sub HTTP_CREATED { return 201; }
sub REDIRECT { return 302; }
+sub NOT_FOUND { return 404; }
+sub SERVER_ERROR { return 500; }
+sub HTTP_UNAUTHORIZED { return 401; }
sub HTTP_BAD_REQUEST { return 400; }
-sub HTTP_UNAUTHORIZED { return 403; }
-sub NOT_FOUND { return 404; }
+sub HTTP_UNSUPPORTED_MEDIA_TYPE { return 415; }
sub HTTP_SERVER_ERROR { return 500; }
+sub HTTP_METHOD_NOT_ALLOWED { return 405; }
+sub FORBIDDEN { return 403; }
# spawn a process for an external program
sub spawn {
diff -r b7d1369e7005 -r 37f7a2c8953c cgi-bin/DW/Routing.pm
--- a/cgi-bin/DW/Routing.pm Mon Feb 28 16:33:50 2011 +0800
+++ b/cgi-bin/DW/Routing.pm Mon Feb 28 18:44:54 2011 +0800
@@ -157,6 +157,10 @@ sub _call_hash {
my $opts = $r->pnote('routing_opts');
$opts->prepare_for_call;
+
+ # check method
+ my $method = uc( $r->method );
+ return $r->HTTP_METHOD_NOT_ALLOWED unless $opts->method_valid( $method );
my $format = $opts->format;
# check for format validity
@@ -370,7 +374,7 @@ sub _apply_defaults {
sub _apply_defaults {
my ( $opts, $hash ) = @_;
- $hash ||= 0;
+ $hash ||= {};
$opts->{app} = 1 if ! defined $opts->{app} && !$opts->{user};
$hash->{args} = $opts->{args};
$hash->{ssl} = $opts->{ssl} || 0;
@@ -382,6 +386,7 @@ sub _apply_defaults {
$formats = { map { ( $_, 1 ) } @$formats } if ( ref($formats) eq 'ARRAY' );
$hash->{formats} = $formats;
+ $hash->{methods} = $opts->{methods} || { GET => 1, POST => 1, HEAD => 1 };
return $hash;
}
diff -r b7d1369e7005 -r 37f7a2c8953c cgi-bin/DW/Routing/CallInfo.pm
--- a/cgi-bin/DW/Routing/CallInfo.pm Mon Feb 28 16:33:50 2011 +0800
+++ b/cgi-bin/DW/Routing/CallInfo.pm Mon Feb 28 18:44:54 2011 +0800
@@ -114,6 +114,18 @@ sub format_valid {
return $formats->{$_[0]->format} || 0;
}
+=head2 C<< $self->method_valid( $method ) >>
+
+Returns if the method is valid for the callinfo
+
+=cut
+
+sub method_valid {
+ my $methods = $_[0]->{__hash}->{methods};
+ return 1 if $methods == 1;
+ return $methods->{$_[1]} || 0;
+}
+
=head2 C<< $self->role >>
Current mode: 'app' or 'user' or 'ssl'
diff -r b7d1369e7005 -r 37f7a2c8953c t/routing.t
--- a/t/routing.t Mon Feb 28 16:33:50 2011 +0800
+++ b/t/routing.t Mon Feb 28 18:44:54 2011 +0800
@@ -14,7 +14,7 @@
# 'perldoc perlartistic' or 'perldoc perlgpl'.
#
use strict;
-use Test::More tests => 203;
+use Test::More tests => 238;
use lib "$ENV{LJHOME}/cgi-bin";
# don't let DW::Routing load DW::Controller subclasses
@@ -251,7 +251,6 @@ handle_redirect( '/xx3', '/xx3/' );
handle_redirect( '/xx3', '/xx3/' );
# 194
-
# test dying
DW::Routing->register_string( "/test/die/all_format", \&died_handler, app => 1, formats => 1 );
@@ -259,6 +258,32 @@ handle_server_error( "/test die .json fo
handle_server_error( "/test die .json format (app)", "/test/die/all_format.json", "json" ); # 2 tests
handle_server_error( "/test die .html format (app)", "/test/die/all_format.html", "html" ); # 2 tests
handle_server_error( "/test die .blah format (app)", "/test/die/all_format.blah", "blah" ); # 2 tests
+# 203 ( I know this doesn't add up. )
+
+DW::Routing->register_string( "/test/method/normal", \&handler, app => 1 );
+
+handle_request( "Method GET - okay", "/test/method/normal", 1, undef, method => 'GET' ); # 3 tests
+handle_request( "Method POST - okay", "/test/method/normal", 1, undef, method => 'POST' );
+handle_request( "Method HEAD - okay", "/test/method/normal", 1, undef, method => 'HEAD' );
+handle_request( "Method PUT - !ok", "/test/method/normal", 1, undef, method => 'PUT', expected_error => 405 ); # 1 test
+# 213
+
+DW::Routing->register_string( "/test/method/all", \&handler, app => 1, methods => 1 );
+
+handle_request( "Method GET - okay", "/test/method/all", 1, undef, method => 'GET' ); # 3 tests
+handle_request( "Method POST - okay", "/test/method/all", 1, undef, method => 'POST' );
+handle_request( "Method HEAD - okay", "/test/method/all", 1, undef, method => 'HEAD' );
+handle_request( "Method PUT - okay", "/test/method/all", 1, undef, method => 'PUT' );
+handle_request( "Method FOO - okay", "/test/method/all", 1, undef, method => 'FOO' );
+# 228
+
+DW::Routing->register_string( "/test/method/no_post", \&handler, app => 1, methods => { GET => 1, HEAD => 1, PUT => 1 } );
+
+handle_request( "Method GET - okay", "/test/method/no_post", 1, undef, method => 'GET' ); # 3 tests
+handle_request( "Method POST - !ok", "/test/method/no_post", 1, undef, method => 'POST', expected_error => 405 ); # 1 test
+handle_request( "Method HEAD - okay", "/test/method/no_post", 1, undef, method => 'HEAD' ); # 3 tests
+handle_request( "Method PUT - okay", "/test/method/no_post", 1, undef, method => 'PUT' ); # 3 test
+# 238
sub handle_redirect {
@@ -286,7 +311,9 @@ sub handle_request {
$DW::Request::determined = 0;
$DW::Request::cur_req = undef;
- my $req = HTTP::Request->new(GET=>"$uri");
+ my $method = $opts{method} || 'GET';
+
+ my $req = HTTP::Request->new($method=>"$uri");
my $r = DW::Request::Standard->new($req);
$result = undef;
--------------------------------------------------------------------------------
