File Coverage

blib/lib/Redirx/Client.pm
Criterion Covered Total %
statement 67 100 67.0
branch 12 36 33.3
condition 1 3 33.3
subroutine 17 20 85.0
pod 0 4 0.0
total 97 163 59.5


line stmt bran cond sub pod time code
1              
2             package Redirx::Client;
3              
4 1     1   10519 use 5.006;
  1         4  
  1         45  
5 1     1   894 use fields qw(socket host port timeout debug);
  1         1973  
  1         6  
6 1     1   83 use strict;
  1         6  
  1         30  
7 1     1   4 use warnings;
  1         1  
  1         22  
8 1     1   4120 use IO::Socket ();
  1         36981  
  1         58  
9              
10             our $VERSION = '0.01';
11              
12 1     1   10 use constant DEFAULT_HOST => 'redirx.com';
  1         3  
  1         108  
13 1     1   5 use constant DEFAULT_PORT => 5313;
  1         2  
  1         48  
14 1     1   5 use constant DEFAULT_TIMEOUT => 5;
  1         1  
  1         38  
15              
16 1     1   5 use constant CMD_PING => 'PING';
  1         1  
  1         34  
17 1     1   7 use constant RES_PONG => 'PONG';
  1         1  
  1         48  
18              
19 1     1   8 use constant STATUS_ERROR => 'ERROR';
  1         2  
  1         265  
20 1     1   5 use constant STATUS_OK => 'OK';
  1         2  
  1         899  
21              
22             sub new {
23 2     2 0 1198 my $self = shift;
24 2         4 my $args = shift;
25              
26 2 50       17 $self = fields::new($self) unless ref $self;
27 2         5342 $self->{socket} = undef;
28 2         8 $self->{host} = DEFAULT_HOST;
29 2         4 $self->{port} = DEFAULT_PORT;
30 2         5 $self->{timeout} = DEFAULT_TIMEOUT;
31              
32 2         10 $self->connect($args);
33              
34 0         0 return $self;
35             }
36              
37             sub connect {
38 2     2 0 4 my $self = shift;
39 2         4 my $args = shift;
40              
41 2 50       8 if (! $self->ping()) {
42 2 50       5 if ($args) {
43 2 100       9 $self->{host} = $args->{Host} if $args->{Host};
44 2 50       6 $self->{port} = $args->{Port} if $args->{Port};
45 2 50       7 $self->{timeout} = $args->{Timeout} if $args->{Timeout};
46 2         6 $self->{debug} = $args->{Debug};
47             }
48              
49             # open the persistent connection
50 2         16 my $serverUrl =
51             sprintf("redirx://%s:%s", $self->{host}, $self->{port});
52              
53 2         5 eval {
54 2         10 $self->_debug("Connecting to: $serverUrl");
55 2         28 $self->{socket} =
56             IO::Socket::INET->new(PeerHost => $self->{host},
57             PeerPort => $self->{port},
58             Timeout => $self->{timeout});
59             };
60 2 50       10529572 if ($@) {
61 0         0 die "Unable to connect to $serverUrl: $@\n";
62             }
63 2 50       11 if (! $self->{socket}) {
64 2         48 die "No response from $serverUrl\n";
65             }
66              
67             # negotiate the protocol
68 0         0 my $proto = $self->_getline();
69 0         0 $self->_debug("Received protocol: $proto");
70 0 0       0 unless ($proto =~ /^REDIRXD V\d+.\d+$/) {
71 0         0 die "Bad protocol: $proto\n";
72             }
73             }
74              
75 0         0 return 1;
76             }
77              
78             sub ping {
79 2     2 0 3 my $self = shift;
80              
81 2 50       11 if ($self->_connected()) {
82             # send PING
83 0         0 $self->_debug(sprintf("Sending cmd: %s", CMD_PING));
84 0         0 $self->_print(CMD_PING);
85              
86             # receive PONG
87 0         0 my $res = $self->_getline();
88 0         0 $self->_debug("Received response: $res");
89 0         0 return $res eq RES_PONG;
90             }
91              
92 2         6 return undef;
93             }
94              
95             sub storeUrl {
96 0     0 0 0 my $self = shift;
97 0 0       0 my $url = shift or
98             die "No url to store\n";
99              
100 0         0 $self->connect();
101              
102             # send URL
103 0         0 $self->_debug("Sending URL $url");
104 0         0 $self->_print($url);
105              
106             # receive response
107 0         0 my $res = $self->_getline();
108 0         0 my ($status, $msg) = split /\s+/, $res;
109 0         0 $self->_debug("Received response: $status: $msg");
110 0 0       0 if ($status eq STATUS_ERROR) {
    0          
111 0         0 die "Error: $msg\n";
112             }
113             elsif ($status ne STATUS_OK) {
114 0         0 die "Bad response: status: $res";
115             }
116              
117 0         0 return $msg; # this is the redirx url
118             }
119              
120             sub _connected {
121 2     2   4 my $self = shift;
122              
123 2   33     13 return $self->{socket} && $self->{socket}->connected();
124             }
125              
126             sub _debug {
127 2     2   4 my $self = shift;
128 2 50       5 my $str = shift or
129             return undef;
130              
131 2 50       8 warn "$str\n" if $self->{debug};
132             }
133              
134             sub _getline {
135 0     0     my $self = shift;
136              
137 0 0         $self->{socket} or
138             die "Can't read from closed connection\n";
139 0           my $line = $self->{socket}->getline();
140 0           chomp $line;
141              
142 0           return $line;
143             }
144              
145             sub _print {
146 0     0     my $self = shift;
147 0 0         my $line = shift or
148             die "No line to print\n";
149              
150 0 0         $self->{socket} or
151             die "Can't print to closed connection\n";
152 0           $self->{socket}->print("$line\n");
153             }
154              
155             1;
156             __END__