Add HTTP support
Wallace Reis [Thu, 9 Dec 2010 04:19:07 +0000 (04:19 +0000)]
Changes
Makefile.PL
lib/Catalyst/View/Component/SubInclude/HTTP.pm [new file with mode: 0644]
t/01-app.t [moved from t/01esi.t with 100% similarity]
t/author/http.t [new file with mode: 0644]
t/lib/ESITest/Controller/Root.pm
t/lib/ESITest/View/TTWithHTTP.pm [new file with mode: 0644]
t/lib/ESITest/root/http_cpan.tt [new file with mode: 0644]
t/lib/ESITest/root/http_github.tt [new file with mode: 0644]

diff --git a/Changes b/Changes
index eed5818..53ee257 100644 (file)
--- a/Changes
+++ b/Changes
@@ -1,5 +1,8 @@
 Revision history for Catalyst-View-Component-SubInclude
 
+0.10
+      - Add HTTP support (Wallace Reis)
+
 0.09  Thu 10 June 21:24:00 2010
       - Add SSI support (Vladimir Timofeev)
       - Additional documentation.
index fa12b05..0a3b6d9 100644 (file)
@@ -14,6 +14,9 @@ requires 'Moose::Role';
 requires 'MooseX::Types';
 requires 'Carp';
 requires 'namespace::clean';
+requires 'LWP::UserAgent';
+requires 'List::MoreUtils';
+requires 'URI';
 
 test_requires 'Test::More' => '0.88';
 test_requires 'Catalyst::View::TT';
diff --git a/lib/Catalyst/View/Component/SubInclude/HTTP.pm b/lib/Catalyst/View/Component/SubInclude/HTTP.pm
new file mode 100644 (file)
index 0000000..35beee5
--- /dev/null
@@ -0,0 +1,135 @@
+package Catalyst::View::Component::SubInclude::HTTP;
+
+use Moose;
+use namespace::clean -except => 'meta';
+use LWP::UserAgent;
+use List::MoreUtils 'firstval';
+use URI;
+
+our $VERSION = '0.01';
+$VERSION = eval $VERSION;
+
+has ua_timeout => (
+    isa => 'Int', is => 'ro', default => 60,
+);
+
+has http_method => (
+    isa => 'Str', is => 'ro', required => 1,
+);
+
+has base_uri => (
+    isa => 'Str', is => 'ro', required => 0,
+);
+
+has uri_map => (
+    isa => 'HashRef', is => 'ro', required => 0,
+);
+
+has user_agent => (
+    is => 'ro', lazy => 1, builder => '_build_user_agent',
+);
+
+sub _build_user_agent {
+    my $self = shift;
+    return LWP::UserAgent->new(
+        agent => ref($self),
+        timeout => $self->ua_timeout,
+    );
+}
+
+sub generate_subinclude {
+    my ($self, $c, $path, $args) = @_;
+    my $error_msg_prefix = "SubInclude for $path failed: ";
+    my $base_uri = $self->base_uri || $c->req->base;
+    my $uri_map = $self->uri_map || { q{/} => $base_uri };
+    $base_uri = $uri_map->{ firstval { $path =~ s/^$_// } keys %$uri_map };
+    $base_uri =~ s{/$}{};
+    my $uri = URI->new(join(q{/}, $base_uri, $path));
+    my $req_method = q{_} . lc $self->http_method . '_request';
+
+    my $response;
+    if ( $self->can($req_method) ) {
+        $response = $self->$req_method($uri, $args);
+    }
+    else {
+        confess $self->http_method . ' not supported';
+    }
+    if ($response->is_success) {
+        return $response->content;
+    }
+    else {
+        $c->log->info($error_msg_prefix . $response->status_line);
+        return undef;
+    }
+}
+
+sub _get_request {
+    my ( $self, $uri, $args) = @_;
+    $uri->query_form($args);
+    return $self->user_agent->get($uri);
+}
+
+sub _post_request {
+    my ( $self, $uri, $args ) = @_;
+    return $self->user_agent->post($uri, $args);
+}
+
+__PACKAGE__->meta->make_immutable;
+
+1;
+
+__END__
+
+=head1 NAME
+
+Catalyst::View::Component::SubInclude::HTTP - HTTP plugin for C::V::Component::SubInclude
+
+=head1 SYNOPSIS
+
+In your view class:
+
+    package MyApp::View::TT;
+    use Moose;
+
+    extends 'Catalyst::View::TT';
+    with 'Catalyst::View::Component::SubInclude';
+
+    __PACKAGE__->config(
+        subinclude_plugin => 'HTTP',
+        subinclude => {
+            HTTP => {
+                base_uri => 'http://www.foo.com/bar',
+            },
+        },
+    );
+
+Then, somewhere in your templates:
+
+    [% subinclude('/my/widget') %]
+
+=head1 DESCRIPTION
+
+=head1 METHODS
+
+=head2 C<generate_subinclude( $c, $path, @params )>
+
+=head1 SEE ALSO
+
+L<Catalyst::View::Component::SubInclude|Catalyst::View::Component::SubInclude>
+
+=head1 AUTHOR
+
+Wallace Reis C<< <wreis@cpan.org> >>
+
+=head1 SPONSORSHIP
+
+Development sponsored by Ionzero LLC L<http://www.ionzero.com/>.
+
+=head1 COPYRIGHT & LICENSE
+
+Copyright (c) 2010 Wallace Reis.
+
+This program is free software; you can redistribute it and/or modify it
+under the same terms as Perl itself.
+
+=cut
similarity index 100%
rename from t/01esi.t
rename to t/01-app.t
diff --git a/t/author/http.t b/t/author/http.t
new file mode 100644 (file)
index 0000000..4fd8c65
--- /dev/null
@@ -0,0 +1,16 @@
+use strict;
+use warnings;
+use FindBin qw/$Bin/;
+use lib "$Bin/../lib";
+use Test::More;
+use Catalyst::Test 'ESITest';
+
+my $res_content = get('/http_cpan');
+like $res_content, qr{CPAN Directory};
+like $res_content, qr{WREIS};
+
+$res_content = get('/http_github');
+like $res_content, qr{GitHub};
+like $res_content, qr{Wallace Reis};
+
+done_testing;
index 966a992..43881bf 100644 (file)
@@ -6,13 +6,15 @@ use base 'Catalyst::Controller';
 
 __PACKAGE__->config->{namespace} = '';
 
-sub index :Path Args(0) {
+sub auto : Private {
     my ( $self, $c ) = @_;
+    $c->stash->{'current_view'} = 'TT';
+    return 1;
 }
 
-sub base : Chained('/') PathPart('') CaptureArgs(0) {
-    my ( $self, $c ) = @_;
-}
+sub index :Path Args(0) {}
+
+sub base : Chained('/') PathPart('') CaptureArgs(0) {}
 
 sub time_include : Chained('base') PathPart('time') Args(0) {
     my ( $self, $c ) = @_;
@@ -106,6 +108,14 @@ sub time_args_no_chained : Path('time_args_no_chained') Args {
     $c->stash->{template} = 'time_include.tt';
 }
 
+sub http : Chained('base') PathPart('') CaptureArgs(0) {
+    pop->stash->{'current_view'} = 'TTWithHTTP';
+}
+
+sub http_cpan : Chained('http') Args(0) {}
+
+sub http_github : Chained('http') Args(0) {}
+
 sub end : ActionClass('RenderView') {}
 
 1;
diff --git a/t/lib/ESITest/View/TTWithHTTP.pm b/t/lib/ESITest/View/TTWithHTTP.pm
new file mode 100644 (file)
index 0000000..17f9b2f
--- /dev/null
@@ -0,0 +1,22 @@
+package ESITest::View::TTWithHTTP;
+use Moose;
+
+extends 'Catalyst::View::TT';
+with 'Catalyst::View::Component::SubInclude';
+
+__PACKAGE__->config(
+    TEMPLATE_EXTENSION => '.tt',
+    subinclude_plugin => 'HTTP::GET',
+    subinclude => {
+        'HTTP::GET' => {
+            class => 'HTTP',
+            http_method => 'GET',
+            uri_map => {
+                '/cpan/' => 'http://search.cpan.org/~',
+                '/github/' => 'http://github.com/',
+            },
+        },
+    },
+);
+
+1;
diff --git a/t/lib/ESITest/root/http_cpan.tt b/t/lib/ESITest/root/http_cpan.tt
new file mode 100644 (file)
index 0000000..2e07f3b
--- /dev/null
@@ -0,0 +1 @@
+[% subinclude('/cpan/wreis') %]
diff --git a/t/lib/ESITest/root/http_github.tt b/t/lib/ESITest/root/http_github.tt
new file mode 100644 (file)
index 0000000..5a127ba
--- /dev/null
@@ -0,0 +1 @@
+[% subinclude('/github/wreis') %]