File Coverage

blib/lib/SMS/Send/IN/eSMS.pm
Criterion Covered Total %
statement 27 69 39.1
branch 3 30 10.0
condition 0 6 0.0
subroutine 8 13 61.5
pod 2 2 100.0
total 40 120 33.3


line stmt bran cond sub pod time code
1             package SMS::Send::IN::eSMS;
2              
3             # ABSTRACT: SMS::Send driver to send messages via eSMS ( http://api.esms.kerala.gov.in )
4              
5 3     3   17077 use 5.006;
  3         6  
6 3     3   9 use strict;
  3         3  
  3         52  
7 3     3   14 use warnings;
  3         3  
  3         57  
8 3     3   1609 use LWP::UserAgent;
  3         85242  
  3         78  
9 3     3   17 use URI::Escape;
  3         4  
  3         143  
10              
11 3     3   11 use base 'SMS::Send::Driver';
  3         4  
  3         1091  
12              
13             our $VERSION = '0.01'; # VERSION
14             our $AUTHORITY = 'cpan:INDRADG'; # AUTHORITY
15              
16             # setup error code lookup list for eSMS
17             our %eSMS_error_codes = ( "401", "Credentials Error, may be invalid username or password",
18             "402", "1 message submitted successfully",
19             "403", "Credits not available",
20             "404", "Internal Database Error",
21             "405", "Internal Networking Error",
22             "406", "Invalid or Duplicate numbers",
23             "407", "Network Error on SMSC",
24             "408", "Network Error on SMSC",
25             "409", "SMSC response timed out, message will be submitted",
26             "410", "Internal Limit Exceeded, Contact support",
27             "411", "Sender ID not approved.",
28             "412", "Sender ID not approved.",
29             "413", "Suspect Spam, we do not accept these messages.",
30             "414", "Rejected by varous reasons by the operator such as DND, SPAM etc" );
31            
32             sub new {
33 2     2 1 118 my ( $class, %args ) = @_;
34              
35             # check we have an username and password
36 2 50       6 die "Username needs to be passed as 'username'" unless ( $args{_login} );
37 2 50       6 die "Password needs to be passed as 'password'" unless ( $args{_password} );
38 2 50       5 die "SenderID needs to be passsed as 'senderid'" unless ( $args{_senderid} );
39              
40             # build the object
41 2         8 my $self = bless {
42             _endpoint => 'http://api.esms.kerala.gov.in/fastclient/SMSclient.php',
43             _debug => 0,
44             %args
45             }, $class;
46              
47             # get an LWP user agent ready
48 2         5 $self->{ua} = LWP::UserAgent->new;
49            
50 2         4066 return $self;
51             }
52              
53             sub _send_method {
54 0     0     my ( $self, @args ) = @_;
55              
56 0           my @params;
57 0           while (@args) {
58 0           my $key = shift @args;
59 0           my $val = shift @args;
60 0           push( @params, join( '=', uri_escape($key), uri_escape($val) ) );
61 0 0         print STDERR ">>> Arg $key = $val\n" if ( $self->{_debug} );
62             }
63 0           my $url = join( '?', $self->{_endpoint}, join( '&', @params ) );
64 0 0         print STDERR ">>> GET $url\n" if ( $self->{_debug} );
65              
66 0           my $res = $self->{ua}->get($url);
67              
68 0 0         printf STDERR "<<< Status: %s\n<<< Content: %s\n", $res->code, $res->content if ( $self->{_debug} );
69              
70 0           my $errorbroker = $self->_ERRORHANDLER ( $res, %eSMS_error_codes );
71              
72 0 0         die $res->status_line unless ( $res->is_success );
73              
74 0           return $res;
75             }
76              
77             sub send_sms {
78              
79 0     0 1   my ( $self, %args ) = @_;
80            
81             # check for message for 160 char limit
82 0           my $text = $self->_MESSAGETEXT ( $args{text} );
83            
84             # check destination number for well-formedness under NNP 2003 schema
85 0           my $to = $self->_TO ( $args{to} );
86              
87             $self->_send_method(
88             username => $self->{_login},
89             password => $self->{_password},
90             numbers => $args{to},
91             message => $args{text},
92             senderid => $self->{_senderid},
93 0           );
94             }
95              
96             # -----------------------------------------------------
97             # internal sanitization routines
98             # -----------------------------------------------------
99              
100             sub _MESSAGETEXT {
101 0     0     my ( $self, $text ) = @_;
102 3     3   14 use bytes;
  3         4  
  3         16  
103 0 0         die "Message length over limit. Max length is 160 characters" unless ( length($text) <= 160 );
104             } # check for 160 char length of message text
105              
106             # As per National Numbering Plan 2003, Indian mobile phone numbers have to be in
107             # [9|8|7]XXXXXXXXX format. So we need to sanitize our input. The driver expects
108             # number string in 91XXXXXXXXXX format
109              
110             sub _TO {
111 0     0     my ( $self, $dest ) = @_;
112              
113 0           my $checkseries;
114             my $countrycode;
115              
116             # strip out NaN characters
117 0           $dest =~ s/[^\d]//g;
118              
119             # strip leading zero as some have the habit of inputing numbers as 0XXXXXXXXXX
120 0           $dest =~ s/^0+//g;
121              
122             # check destination number length and format for well-formedness and fix common issues.
123 0 0 0       if ( length($dest) == 12 or length($dest) == 10 ) {
124 0 0         if ( length($dest) == 12 ) {
125 0           $countrycode = substr $dest, 0, 2;
126 0 0         die "Country code incorrect, needs to be 91 for India" unless ( $countrycode eq '91' );
127             }
128 0 0         if ( length($dest) == 10 ) {
129 0           $countrycode = "91";
130 0           $dest = $countrycode . $dest; #bring it up to 91XXXXXXXXXX
131             }
132              
133             # check for 9,8,7 series numbering under NNP 2003
134 0           $checkseries = substr $dest, 2, 1;
135 0 0         die "Invalid phone number as per National Numbering Plan 2003" unless ( $checkseries =~ /[9|8|7]/ );
136             } else {
137 0           die "Invalid phone number format";
138             }
139 0           return $dest;
140             }
141              
142             sub _ERRORHANDLER {
143 0     0     my ( $self, $res, %uecodes ) = @_;
144              
145 0           my $res_content = $res->content;
146              
147             # check for unique MID (message ID) signifying a successful transaction
148              
149 0 0 0       if ( $res_content =~ /^[0-9]+$/ and length( $res_content ) == 19 ) {
150 0           return "Successfully transmitted with MID $res_content\n";
151             } else {
152 0           my $ecode = substr $res_content, 0, 5;
153 0 0         if ( $uecodes{$ecode} ) {
154 0           die "eSMS error $ecode : $uecodes{$ecode}";
155             }
156             }
157             }
158              
159             1;
160              
161             __END__