3af0f151f677f318a863b412b9482e04597869c5
[catagits/Catalyst-Runtime.git] / lib / Catalyst / Test.pm
1 package Catalyst::Test;
2
3 use strict;
4 use warnings;
5
6 use Catalyst::Exception;
7 use Catalyst::Utils;
8 use UNIVERSAL::require;
9 use HTTP::Headers;
10
11 $ENV{CATALYST_ENGINE} = 'Test';
12
13 # Bypass a HTTP::Headers bug
14 {
15     no warnings 'redefine';
16
17     sub HTTP::Headers::new {
18         my $class = shift;
19         my $self = bless {}, $class;
20         if (@_) {
21             while ( my ( $field, $val ) = splice( @_, 0, 2 ) ) {
22                 $self->push_header( $field, $val );
23             }
24         }
25         return $self;
26     }
27 }
28
29 =head1 NAME
30
31 Catalyst::Test - Test Catalyst applications
32
33 =head1 SYNOPSIS
34
35     # Helper
36     script/test.pl
37
38     # Tests
39     use Catalyst::Test 'TestApp';
40     request('index.html');
41     get('index.html');
42
43     # Run tests against a remote server
44     CATALYST_SERVER='http://localhost:3000/' prove -r -l lib/ t/
45
46     # Tests with inline apps need to use Catalyst::Engine::Test
47     package TestApp;
48
49     use Catalyst qw[-Engine=Test];
50
51     sub foo : Global {
52             my ( $self, $c ) = @_;
53             $c->res->output('bar');
54     }
55
56     __PACKAGE__->setup();
57
58     package main;
59
60     use Test::More tests => 1;
61     use Catalyst::Test 'TestApp';
62
63     ok( get('/foo') =~ /bar/ );
64
65 =head1 DESCRIPTION
66
67 Test Catalyst applications.
68
69 =head2 METHODS
70
71 =over 4
72
73 =item get
74
75 Returns the content.
76
77     my $content = get('foo/bar?test=1');
78
79 =item request
80
81 Returns a C<HTTP::Response> object.
82
83     my $res = request('foo/bar?test=1');
84
85 =cut
86
87 sub import {
88     my $self  = shift;
89     my $class = shift;
90
91     my ( $get, $request );
92
93     if ( $ENV{CATALYST_SERVER} ) {
94         $request = sub { remote_request(@_) };
95         $get     = sub { remote_request(@_)->content };
96     }
97
98     else {
99         $class->require;
100         die if $@ && $@ !~ /^Can't locate /;
101         $class->import;
102
103         $request = sub { $class->run(@_) };
104         $get     = sub { $class->run(@_)->content };
105     }
106
107     no strict 'refs';
108     my $caller = caller(0);
109     *{"$caller\::request"} = $request;
110     *{"$caller\::get"}     = $get;
111 }
112
113 my $agent;
114
115 =item remote_request
116
117 Do an actual remote request using LWP.
118
119 =cut
120
121 sub remote_request {
122
123     require LWP::UserAgent;
124
125     my $request = Catalyst::Utils::request( shift(@_) );
126
127     my $server = URI->new( $ENV{CATALYST_SERVER} );
128
129     if ( $server->path =~ m|^(.+)?/$| ) {
130         $server->path("$1");    # need to be quoted
131     }
132
133     $request->uri->scheme( $server->scheme );
134     $request->uri->host( $server->host );
135     $request->uri->port( $server->port );
136     $request->uri->path( $server->path . $request->uri->path );
137
138     unless ($agent) {
139
140         $agent = LWP::UserAgent->new(
141             keep_alive   => 1,
142             max_redirect => 0,
143             timeout      => 60,
144         );
145
146         $agent->env_proxy;
147     }
148
149     return $agent->request($request);
150 }
151
152 =back 
153
154 =head1 SEE ALSO
155
156 L<Catalyst>.
157
158 =head1 AUTHOR
159
160 Sebastian Riedel, C<sri@cpan.org>
161
162 =head1 COPYRIGHT
163
164 This program is free software, you can redistribute it and/or modify it under
165 the same terms as Perl itself.
166
167 =cut
168
169 1;