From 3eb46286b7175a8b4129273e50deb7e7302423c9 Mon Sep 17 00:00:00 2001 From: Kyle M Hall Date: Wed, 29 Oct 2014 07:49:38 -0400 Subject: [PATCH] Bug 13159 - Enhancements to the SIP2 command line emulator I needed to be able to perform checkout operations for testing from the command line. I ended up reengineering the SIP2 command line tester quite a bit. Enhancements: * Moved message generation code to subroutines * Added checkout message support * Added command line switches for each supported message * Enabled use of Sip::Constants to keep code DRY and more understandable * Moved script from misc to C4/SIP * Designed with an eye towards possibly moving some code to CPAN in the future Test Plan: 1) Apply this patch 2) Look at help via ./C4/SIP/sip_cli_emulator.pl --help 3) Test patron status request and patron information, should work as before except you need to pass the command line switches to enable them 4) Test the new checkout option --checkout --- C4/SIP/sip_cli_emulator.pl | 325 ++++++++++++++++++++++++++++++++++++++++++++ misc/sip_cli_emulator.pl | 161 ---------------------- 2 files changed, 325 insertions(+), 161 deletions(-) create mode 100755 C4/SIP/sip_cli_emulator.pl delete mode 100755 misc/sip_cli_emulator.pl diff --git a/C4/SIP/sip_cli_emulator.pl b/C4/SIP/sip_cli_emulator.pl new file mode 100755 index 0000000..305a530 --- /dev/null +++ b/C4/SIP/sip_cli_emulator.pl @@ -0,0 +1,325 @@ +#!/usr/bin/perl + +# This file is part of Koha. +# +# Copyright (C) 2012-2013 ByWater Solutions +# +# Koha is free software; you can redistribute it and/or modify it +# under the terms of the GNU General Public License as published by +# the Free Software Foundation; either version 3 of the License, or +# (at your option) any later version. +# +# Koha is distributed in the hope that it will be useful, but +# WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with Koha; if not, see . + +use Modern::Perl; + +use Socket qw(:crlf); +use IO::Socket::INET; +use Getopt::Long; + +use Sip::Constants qw(:all); + +use constant { LANGUAGE => '001' }; + +my $help = 0; + +my $host; +my $port = '6001'; + +my $login_user_id; +my $login_password; +my $location_code; + +my $patron_identifier; +my $patron_password; + +my $terminator = q{}; + +my $patron_status_request; +my $patron_information; +my $checkout; + +GetOptions( + "a|address|host|hostaddress=s" => \$host, # sip server ip + "p|port=s" => \$port, # sip server port + "su|sip_user=s" => \$login_user_id, # sip user + "sp|sip_pass=s" => \$login_password, # sip password + "l|location|location_code=s" => \$location_code, # sip location code + + "patron=s" => \$patron_identifier, # patron cardnumber or login + "password=s" => \$patron_password, # patron's password + + "t|terminator=s" => \$terminator, + + "psr|patron-status-request" => \$patron_status_request, + "pi|patron-information" => \$patron_information, + "c|checkout=s" => \$checkout, + + 'h|help|?' => \$help +); + +if ( $help + || !$host + || !$login_user_id + || !$login_password + || !$location_code + || !$patron_identifier + || !$patron_password ) +{ + say &help(); + exit(); +} + +$terminator = ( $terminator eq 'CR' ) ? $CR : $CRLF; + +# Set perl to expect the same record terminator it is sending +$/ = $terminator; + +my ( $sec, $min, $hour, $day, $month, $year ) = localtime(time); +$year += 1900; +my $transaction_date = "$year$month$day $hour$min$sec"; + +my $terminal_password = $login_password; + +$| = 1; +print "Attempting socket connection to $host:$port..."; + +my $socket = IO::Socket::INET->new("$host:$port") + or die "failed! : $!\n"; +say "connected!"; + +my $login_command = get_login_command_message( + { + login_user_id => $login_user_id, + login_password => $login_password, + location_code => $location_code, + } +); + +say "OUTBOUND: $login_command"; +print $socket $login_command . $terminator; + +my $data = <$socket>; + +say " INBOUND: $data"; + +if ( $data =~ '^941' ) { ## we are logged in + + if ($patron_status_request) { + + say "Trying 'Patron Status Request'"; + my $patron_status_request = get_patron_status_request_command_message( + { + transaction_date => $transaction_date, + institution_id => $location_code, + patron_identifier => $patron_identifier, + terminal_password => $terminal_password, + patron_password => $patron_password, + } + ); + + say "OUTBOUND: $patron_status_request"; + print $socket $patron_status_request . $terminator; + + $data = <$socket>; + + say " INBOUND: $data"; + } + + if ($patron_information) { + + say "Trying 'Patron Information'"; + my $parton_status_request = get_patron_information_command_message( + { + transaction_date => $transaction_date, + institution_id => $location_code, + patron_identifier => $patron_identifier, + terminal_password => $terminal_password, + patron_password => $patron_password, + } + ); + + say "OUTBOUND: $patron_status_request"; + print $socket $patron_status_request . $terminator; + + $data = <$socket>; + + say " INBOUND: $data"; + } + + if ($checkout) { + + say "Trying 'Checkout'"; + my $checkout_message = get_checkout_command_message( + { + SC_renewal_policy => 'Y', + no_block => 'N', + transaction_date => $transaction_date, + nb_due_date => undef, + institution_id => $location_code, + patron_identifier => $patron_identifier, + item_identifier => $checkout, + terminal_password => $terminal_password, + item_properties => undef, + patron_password => $patron_password, + fee_acknowledged => undef, + cancel => undef, + } + ); + + say "OUTBOUND: $checkout_message"; + print $socket $checkout_message . $terminator; + + $data = <$socket>; + + say " INBOUND: $data"; + } + +} +else { + say "Login Failed!"; +} + +sub get_login_command_message { + my ($params) = @_; + + my $login_user_id = $params->{login_user_id}; + my $login_password = $params->{login_password}; + my $location_code = $params->{location_code}; + + return + LOGIN . "00" + . build_field( FID_LOGIN_UID, $login_user_id ) + . build_field( FID_LOGIN_PWD, $login_password ) + . build_field( FID_LOCATION_CODE, $location_code ); +} + +sub get_patron_status_request_command_message { + my ($params) = @_; + + my $transaction_date = $params->{transaction_date}; + my $institution_id = $params->{institution_id}; + my $patron_identifier = $params->{patron_identifier}; + my $terminal_password = $params->{terminal_password}; + my $patron_password = $params->{patron_password}; + + return + PATRON_STATUS_REQ + . LANGUAGE + . $transaction_date + . build_field( FID_INST_ID, $institution_id ) + . build_field( FID_PATRON_ID, $patron_identifier ) + . build_field( FID_TERMINAL_PWD, $terminal_password ) + . build_field( FID_PATRON_PWD, $patron_password ); +} + +sub get_patron_information_command_message { + my ($params) = @_; + + my $transaction_date = $params->{transaction_date}; + my $institution_id = $params->{institution_id}; + my $patron_identifier = $params->{patron_identifier}; + my $terminal_password = $params->{terminal_password}; + my $patron_password = $params->{patron_password}; + + my $summary = " "; + + return + PATRON_INFO + . LANGUAGE + . $transaction_date + . $summary + . build_field( FID_INST_ID, $institution_id ) + . build_field( FID_PATRON_ID, $patron_identifier ) + . build_field( FID_TERMINAL_PWD, $terminal_password ) + . build_field( FID_PATRON_PWD, $patron_password ); +} + +sub get_checkout_command_message { + my ($params) = @_; + + my $SC_renewal_policy = $params->{SC_renewal_policy}; + my $no_block = $params->{no_block}; + my $transaction_date = $params->{transaction_date}; + my $nb_due_date = $params->{nb_due_date}; + my $institution_id = $params->{institution_id}; + my $patron_identifier = $params->{patron_identifier}; + my $item_identifier = $params->{item_identifier}; + my $terminal_password = $params->{terminal_password}; + my $item_properties = $params->{item_properties}; + my $patron_password = $params->{patron_password}; + my $fee_acknowledged = $params->{fee_acknowledged}; + my $cancel = $params->{cancel}; + + $SC_renewal_policy = $SC_renewal_policy ? 'Y' : 'N'; + $no_block = $no_block ? 'Y' : 'N'; + $fee_acknowledged = $fee_acknowledged ? 'Y' : 'N'; + $cancel = $cancel ? 'Y' : 'N'; + + $nb_due_date ||= $transaction_date; + + return + CHECKOUT + . $SC_renewal_policy + . $no_block + . $transaction_date + . $nb_due_date + . build_field( FID_INST_ID, $institution_id ) + . build_field( FID_PATRON_ID, $patron_identifier ) + . build_field( FID_ITEM_ID, $item_identifier ) + . build_field( FID_TERMINAL_PWD, $terminal_password ) + . build_field( FID_ITEM_PROPS, $item_properties, { optional => 1 } ) + . build_field( FID_PATRON_PWD, $patron_password, { optional => 1 } ) + . build_field( FID_FEE_ACK, $fee_acknowledged, { optional => 1 } ) + . build_field( FID_CANCEL, $cancel, { optional => 1 } ); +} + +sub build_field { + my ( $field_identifier, $value, $params ) = @_; + + $params //= {}; + + return q{} if ( $params->{optional} && !$value ); + + return $field_identifier . $value . '|'; +} + +sub help { + say q/sip_cli_emulator.pl - SIP command line emulator + +Test a SIP2 service by sending patron status and patron +information requests. + +Usage: + sip_cli_emulator.pl [OPTIONS] + +Options: + --help display help message + + -a --address SIP server ip address or host name + -p --port SIP server port + + -su --sip_user SIP server login username + -sp --sip_pass SIP server login password + + -l --location SIP location code + + --patron ILS patron cardnumber or username + --password ILS patron password + + -t --terminator SIP2 message terminator, either CR, or CRLF + (defaults to CRLF) + + Implemented Messages: + -psr --patron-status-request + -pi --patron-information + -c --checkout + +/ +} diff --git a/misc/sip_cli_emulator.pl b/misc/sip_cli_emulator.pl deleted file mode 100755 index b6d7880..0000000 --- a/misc/sip_cli_emulator.pl +++ /dev/null @@ -1,161 +0,0 @@ -#!/usr/bin/perl - -# This file is part of Koha. -# -# Copyright (C) 2012-2013 ByWater Solutions -# -# Koha is free software; you can redistribute it and/or modify it -# under the terms of the GNU General Public License as published by -# the Free Software Foundation; either version 3 of the License, or -# (at your option) any later version. -# -# Koha is distributed in the hope that it will be useful, but -# WITHOUT ANY WARRANTY; without even the implied warranty of -# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -# GNU General Public License for more details. -# -# You should have received a copy of the GNU General Public License -# along with Koha; if not, see . - -use Modern::Perl; - -use Socket qw(:crlf); -use IO::Socket::INET; -use Getopt::Long; - -my $help = 0; - -my $host; -my $port = '6001'; - -my $login_user_id; -my $login_password; -my $location_code; - -my $patron_identifier; -my $patron_password; - -my $terminator = q{}; - -GetOptions( - "a|address|host|hostaddress=s" => \$host, # sip server ip - "p|port=s" => \$port, # sip server port - "su|sip_user=s" => \$login_user_id, # sip user - "sp|sip_pass=s" => \$login_password, # sip password - "l|location|location_code=s" => \$location_code, # sip location code - - "patron=s" => \$patron_identifier, # patron cardnumber or login - "password=s" => \$patron_password, # patron's password - - "t|terminator=s" => \$terminator, - - 'h|help|?' => \$help -); - -if ( $help - || !$host - || !$login_user_id - || !$login_password - || !$location_code - || !$patron_identifier - || !$patron_password ) -{ - print &help(); - exit(); -} - -$terminator = ( $terminator eq 'CR' ) ? $CR : $CRLF; - -# Set perl to expect the same record terminator it is sending -$/ = $terminator; - -my ( $sec, $min, $hour, $day, $month, $year ) = localtime(time); -$year += 1900; -my $transaction_date = "$year$month$day $hour$min$sec"; - -my $institution_id = $location_code; -my $terminal_password = $login_password; - -my $socket = IO::Socket::INET->new("$host:$port") - or die "ERROR in Socket Creation host=$host port=$port : $!\n"; - -my $login_command = "9300CN$login_user_id|CO$login_password|CP$location_code|"; - -print "\nOUTBOUND: $login_command\n"; -print $socket $login_command . $terminator; - -my $data = <$socket>; - -print "\nINBOUND: $data\n"; - -if ( $data =~ '^941' ) { ## we are logged in - - ## Patron Status Request - print "\nTrying 'Patron Status Request'\n"; - my $patron_status_request = "23001" - . $transaction_date - . "AO" . $institution_id - . "|AA" . $patron_identifier - . "|AC" . $terminal_password - . "|AD" . $patron_password; - - print "\nOUTBOUND: $patron_status_request\n"; - print $socket $patron_status_request . $terminator; - - $data = <$socket>; - - print "\nINBOUND: $data\n"; - - ## Patron Information - print "\nTrying 'Patron Information'\n"; - my $summary = " "; - $patron_status_request = "63001" - . $transaction_date - . $summary - . "AO" . $institution_id - . "|AA" . $patron_identifier - . "|AC" . $terminal_password - . "|AD" . $patron_password; - - print "\nOUTBOUND: $patron_status_request\n"; - print $socket $patron_status_request . $terminator; - - $data = <$socket>; - - print "\nINBOUND: $data\n"; - -} -else { - print "\nLogin Failed!\n"; -} - -sub help { - print -q/sip_cli_emulator.pl - SIP command line emulator - -Test a SIP2 service by sending patron status and patron -information requests. - -Usage: - sip_cli_emulator.pl [OPTIONS] - -Options: - --help display help message - - -a --address SIP server ip address or host name - -p --port SIP server port - - -su --sip_user SIP server login username - -sp --sip_pass SIP server login password - - -l --location SIP location code - - --patron ILS patron cardnumber or username - --password ILS patron password - - -t --terminator SIP2 message terminator, either CR, or CRLF - (defaults to CRLF) - -/ - -} -- 1.7.2.5