File Coverage

blib/lib/Mojo/UserAgent/SecureServer.pm
Criterion Covered Total %
statement 31 31 100.0
branch 11 12 91.6
condition 1 2 50.0
subroutine 7 7 100.0
pod 3 3 100.0
total 53 55 96.3


line stmt bran cond sub pod time code
1             package Mojo::UserAgent::SecureServer;
2 3     3   1620132 use Mojo::Base 'Mojo::UserAgent::Server';
  3         27  
  3         20  
3              
4 3     3   550 use Net::SSLeay ();
  3         7  
  3         57  
5 3     3   17 use Scalar::Util qw(weaken);
  3         7  
  3         1934  
6              
7             our $VERSION = '0.02';
8              
9             has listen => sub { Mojo::URL->new('https://127.0.0.1') };
10              
11             sub from_ua {
12 5 100   5 1 53571 my $self = ref $_[0] ? shift : shift->new;
13 5         20 my $ua = shift;
14 5         15 my $server = $ua->server;
15              
16 5         54 $self->$_($server->$_) for qw(app ioloop);
17 5         141 $self->listen->query->param($_ => $ua->$_) for grep { $ua->$_ } qw(ca cert key);
  15         88  
18 5 100       916 $self->listen->query->param(verify => Net::SSLeay::VERIFY_PEER()) unless $ua->insecure;
19              
20 5         350 return $self;
21             }
22              
23 1     1 1 36080 sub nb_url { shift->_url(1, @_) }
24 2     2 1 2007 sub url { shift->_url(0, @_) }
25              
26             sub _url {
27 3     3   9 my ($self, $nb) = @_;
28              
29 3 100       13 my $port_key = $nb ? 'nb_port' : 'port';
30 3 50       12 unless ($self->{$port_key}) {
31 3 100       12 my $server_key = $nb ? 'nb_server' : 'server';
32 3         12 my $url = $self->listen->clone;
33 3         585 my @daemon_attrs = (silent => 1);
34 3 100       21 push @daemon_attrs, ioloop => $self->ioloop unless $nb;
35              
36 3         50 my $server = $self->{$server_key} = Mojo::Server::Daemon->new(@daemon_attrs);
37 3         99 weaken $server->app($self->app)->{app};
38 3   50     75 $url->port($self->{port} || undef);
39 3         26 $self->{$port_key} = $server->listen([$url->to_string])->start->ports->[0];
40             }
41              
42 3         7867 return Mojo::URL->new("https://127.0.0.1:$self->{$port_key}/");
43             }
44              
45             1;
46              
47             =encoding utf8
48              
49             =head1 NAME
50              
51             Mojo::UserAgent::SecureServer - Secure application server for Mojo::UserAgent
52              
53             =head1 SYNOPSIS
54              
55             # Construct from Mojo::UserAgent
56             my $ua = Mojo::UserAgent->new;
57             $ua->ca('ca.pem')->cert('cert.pem')->key('key.pem');
58             $ua->server(Mojo::UserAgent::SecureServer->from_ua($ua));
59              
60             # Construct manually
61             my $ua = Mojo::UserAgent->new;
62             my $server = Mojo::UserAgent::SecureServer->new;
63             $server->listen(Mojo::URL->new('https://127.0.0.1?cert=/x/server.crt&key=/y/server.key&ca=/z/ca.crt'));
64             $ua->server($server);
65              
66             # Test::Mojo
67             my $app = Mojolicious->new;
68             $app->routes->get('/' => sub {
69             my $c = shift;
70             my $handle = Mojo::IOLoop->stream($c->tx->connection)->handle;
71             $c->render(json => {cn => $handle->peer_certificate('cn')});
72             });
73              
74             my $t = Test::Mojo->new($app);
75             $t->ua->insecure(0);
76             $t->ua->ca('t/pki/certs/ca-chain.cert.pem')
77             ->cert('t/pki/mojo.example.com.cert.pem')
78             ->key('t/pki/mojo.example.com.key.pem');
79             $t->ua->server(Mojo::UserAgent::SecureServer->from_ua($t->ua));
80              
81             $t->get_ok('/')->status_is(200)->json_is('/cn', 'mojo.example.com');
82              
83             =head1 DESCRIPTION
84              
85             L allows you to test your L web
86             application with custom SSL/TLS key/cert/ca.
87              
88             =head1 ATTRIBUTES
89              
90             L inherits all attributes from
91             L and implements the following new ones.
92              
93             =head2 listen
94              
95             $url = $server->listen;
96             $server = $server->listen(Mojo::URL->new('https://127.0.0.1'));
97              
98             The base listen URL for L created by L and
99             L. The "port" will be discarded, while other
100             L parameters are kept.
101              
102             =head1 METHODS
103              
104             L inherits all methods from
105             L and implements the following new ones.
106              
107             =head2 from_ua
108              
109             $server = Mojo::UserAgent::SecureServer->from_ua($ua);
110             $server = $server->from_ua($ua);
111              
112             Used to construct a new object and/or copy attributes from a L
113             object. Here is the long version:
114              
115             $server->app($ua->server->app);
116             $server->ioloop($ua->server->ioloop);
117             $server->listen->query->param(ca => $ua->ca);
118             $server->listen->query->param(cert => $ua->cert);
119             $server->listen->query->param(key => $ua->key);
120             $server->listen->query->param(verify => Net::SSLeay::VERIFY_PEER()) unless $ua->insecure
121              
122             =head2 nb_url
123              
124             $url = $server->nb_url;
125              
126             Get absolute L object for server processing non-blocking requests
127             with L.
128              
129             =head2 url
130              
131             $url = $server->url;
132              
133             Get absolute L object for server processing non-blocking requests
134             with L.
135              
136             =head1 AUTHOR
137              
138             Jan Henning Thorsen
139              
140             =head1 COPYRIGHT AND LICENSE
141              
142             Copyright (C) Jan Henning Thorsen.
143              
144             This program is free software, you can redistribute it and/or modify it under
145             the terms of the Artistic License version 2.0.
146              
147             =head1 SEE ALSO
148              
149             L, L and L.
150              
151             =cut