90c90ed83ce8e2b23094f3094b7f73d63648d748
[catagits/Web-Simple.git] / t / dispatch_misc.t
1 use strict;
2 use warnings FATAL => 'all';
3 no warnings::illegalproto;
4
5 use Test::More;
6
7 use HTTP::Request::Common qw(GET POST);
8 use Web::Dispatch;
9 use HTTP::Response;
10
11 my @dispatch;
12
13 {
14     use Web::Simple 'MiscTest';
15
16     package MiscTest;
17     sub dispatch_request { @dispatch }
18 }
19
20 my $app = MiscTest->new;
21 sub run_request { $app->run_test_request( @_ ); }
22
23 app_is_non_plack();
24 plack_app_return();
25 plack_streaming_app_return();
26 broken_route_def();
27 array_with_sub();
28 array_with_no_sub();
29 middleware_as_only_route();
30 route_returns_middleware_plus_extra();
31 route_returns_undef();
32
33 done_testing();
34
35 sub app_is_non_plack {
36
37     my $r = HTTP::Response->new( 999 );
38
39     my $d = Web::Dispatch->new( app => $r );
40     eval { $d->call };
41
42     like $@, qr/No idea how we got here with HTTP::Response/,
43       "Web::Dispatch dies when run with an app() that is a non-PSGI object";
44     undef $@;
45 }
46
47 sub plack_app_return {
48     {
49
50         package FauxPlackApp;
51         sub new { bless {}, $_[0] }
52
53         sub to_app {
54             return sub {
55                 [ 999, [], [""] ];
56             };
57         }
58     }
59
60     @dispatch = (
61         sub (/) {
62             FauxPlackApp->new;
63         }
64     );
65
66     my $get = run_request( GET => 'http://localhost/' );
67
68     cmp_ok $get->code, '==', 999,
69       "when a route returns a thing that look like a Plack app, the web app redispatches to that thing";
70 }
71
72 sub plack_streaming_app_return {
73     {
74
75         package FauxPlackStreamApp;
76         sub new { bless {}, $_[0] }
77
78         sub to_app {
79             return sub {
80                 return sub {
81                     my $responder = shift;
82                     $responder->([ 999, [], ["foo"] ]);
83                 };
84             };
85         }
86     }
87
88     @dispatch = (
89         sub (/) {
90             FauxPlackStreamApp->new;
91         }
92     );
93
94     my $get = run_request( GET => 'http://localhost/' );
95
96     cmp_ok $get->code, '==', 999,
97       "when a route returns a thing that look like a Plack Streaming app, the web app redispatches to that thing";
98 }
99
100 sub broken_route_def {
101
102     @dispatch = ( '/' => "" );
103
104     my $get = run_request( GET => 'http://localhost/' );
105
106     cmp_ok $get->code, '==', 500, "a route definition by hash that doesn't pair a sub with a route dies";
107     like $get->content, qr[No idea how we got here with /], "the error message points out the broken definition";
108 }
109
110 sub array_with_sub {
111     @dispatch = (
112         sub (/) {
113             [
114                 sub {
115                     [ 999, [], [""] ];
116                 },
117             ];
118         }
119     );
120
121     eval { run_request( GET => 'http://localhost/' ) };
122
123     like $@, qr/Can't call method "request" on an undefined value .*MockHTTP/,
124 "if a route returns an arrayref with a single sub in it, then that sub is returned as a response by WD, causing HTTP::Message::PSGI to choke";
125 }
126
127 sub array_with_no_sub {
128     @dispatch = (
129         sub (/) {
130             ["moo"];
131         }
132     );
133
134     eval { run_request( GET => 'http://localhost/' ) };
135
136     like $@, qr/Can't call method "request" on an undefined value .*MockHTTP/,
137 "if a route returns an arrayref with a scalar that is not a sub, then WD returns that array out of the PSGI app (and causes HTTP::Message::PSGI to choke)";
138     undef $@;
139 }
140
141 sub middleware_as_only_route {
142     @dispatch = ( bless {}, "Plack::Middleware" );
143
144     my $get = run_request( GET => 'http://localhost/' );
145
146     cmp_ok $get->code, '==', 500, "a route definition consisting of only a middleware causes a bail";
147     like $get->content, qr[Multiple results but first one is a middleware \(Plack::Middleware=],
148       "the error message mentions the middleware class";
149 }
150
151 sub route_returns_middleware_plus_extra {
152     @dispatch = (
153         sub (/) {
154             return ( bless( {}, "Plack::Middleware" ), "" );
155         }
156     );
157
158     my $get = run_request( GET => 'http://localhost/' );
159
160     cmp_ok $get->code, '==', 500, "a route returning a middleware and at least one other variable causes a bail";
161     like $get->content,
162       qr[Multiple results but first one is a middleware \(Plack::Middleware=],
163       "the error message mentions the middleware class";
164 }
165
166 sub route_returns_undef {
167     @dispatch = (
168         sub (/) {
169             (
170                 sub(/) {
171                     undef;
172                 },
173                 sub(/) {
174                     [ 900, [], [""] ];
175                 }
176             );
177         },
178         sub () {
179             [ 400, [], [""] ];
180         }
181     );
182
183     my $get = run_request( GET => 'http://localhost/' );
184
185     cmp_ok $get->code, '==', 900, "a route that returns undef causes WD to ignore it and resume dispatching";
186 }