LP#1749795 Test that adjust-to-zero closes rebilled circ
authorRemington Steed <rjs7@calvin.edu>
Mon, 30 Apr 2018 15:04:44 +0000 (11:04 -0400)
committerDan Wells <dbw2@calvin.edu>
Mon, 30 Apr 2018 16:35:44 +0000 (12:35 -0400)
Current code fails when rebilling to exactly zero.

Signed-off-by: Remington Steed <rjs7@calvin.edu>
Signed-off-by: Dan Wells <dbw2@calvin.edu>
Open-ILS/src/perlmods/live_t/27-lp1749795_adjust_to_zero_closes_circ.t [new file with mode: 0644]

diff --git a/Open-ILS/src/perlmods/live_t/27-lp1749795_adjust_to_zero_closes_circ.t b/Open-ILS/src/perlmods/live_t/27-lp1749795_adjust_to_zero_closes_circ.t
new file mode 100644 (file)
index 0000000..fd93df7
--- /dev/null
@@ -0,0 +1,295 @@
+#!perl
+
+use Test::More tests => 22;
+
+diag("Test that adjust-to-zero closes a checked-in lost circ when rebilling to zero");
+
+use constant WORKSTATION_NAME => 'BR4-test-27-lp1749795_adjust_to_zero_closes_circ.t';
+use constant WORKSTATION_LIB => 7;
+
+use strict; use warnings;
+
+use DateTime;
+use DateTime::Format::ISO8601;
+use OpenSRF::Utils qw/cleanse_ISO8601/;
+use OpenILS::Utils::TestUtils;
+my $script = OpenILS::Utils::TestUtils->new();
+use Data::Dumper;
+
+our $apputils   = "OpenILS::Application::AppUtils";
+
+my $user_obj;
+my $storage_ses = $script->session('open-ils.storage');
+
+### Setup a patron
+my $patron_id = 52;
+my $patron_usrname = '99999306663';
+
+### Setup an item
+my $item_id = 310;
+my $item_barcode = 'CONC70000345';
+
+
+## HELPER FUNCTIONS
+
+sub retrieve_patron {
+    my $patron_id = shift;
+
+    my $user_req = $storage_ses->request('open-ils.storage.direct.actor.user.retrieve', $patron_id);
+    if (my $user_resp = $user_req->recv) {
+        if (my $patron_obj = $user_resp->content) {
+            return $patron_obj;
+        }
+    }
+    return 0;
+}
+
+sub fetch_billable_xact_summary {
+    my $xact_id = shift;
+    my $ses = $script->session('open-ils.cstore');
+    my $req = $ses->request(
+        'open-ils.cstore.direct.money.billable_transaction_summary.retrieve',
+        $xact_id);
+
+    if (my $resp = $req->recv) {
+        return $resp->content;
+    } else {
+        return 0;
+    }
+}
+
+sub pay_bills {
+    my $payment_blob = shift;
+    my $resp = $apputils->simplereq(
+        'open-ils.circ',
+        'open-ils.circ.money.payment',
+        $script->authtoken,
+        $payment_blob,
+        $user_obj->last_xact_id
+    );
+
+    #refetch user_obj to get latest last_xact_id
+    $user_obj = retrieve_patron($patron_id)
+        or die 'Could not refetch patron';
+
+    return $resp;
+}
+
+#----------------------------------------------------------------
+# The tests...  assumes stock sample data, full-auto install by
+# eg_wheezy_installer.sh, etc.
+#----------------------------------------------------------------
+
+# Connect to Evergreen
+$script->authenticate({
+    username => 'admin',
+    password => 'demo123',
+    type => 'staff'});
+ok( $script->authtoken, 'Have an authtoken');
+
+my $ws = $script->register_workstation(WORKSTATION_NAME,WORKSTATION_LIB);
+ok( ! ref $ws, 'Registered a new workstation');
+
+$script->logout();
+$script->authenticate({
+    username => 'admin',
+    password => 'demo123',
+    type => 'staff',
+    workstation => WORKSTATION_NAME});
+ok( $script->authtoken, 'Have an authtoken associated with the workstation');
+
+
+### Setup Org Unit Settings that apply to all test cases
+
+my $org_id = 1; #CONS
+my $settings = {
+    'circ.max_item_price' => 50,
+    'circ.min_item_price' => 50,
+    'circ.void_lost_on_checkin' => 1,
+    'circ.lost.xact_open_on_zero' => 0 #Leave transaction open when lost balance equals zero? NO
+};
+
+$apputils->simplereq(
+    'open-ils.actor',
+    'open-ils.actor.org_unit.settings.update',
+    $script->authtoken,
+    $org_id,
+    $settings
+);
+
+# Look up the patron
+if ($user_obj = retrieve_patron($patron_id)) {
+    is(
+        ref $user_obj,
+        'Fieldmapper::actor::user',
+        'open-ils.storage.direct.actor.user.retrieve returned aou object'
+    );
+    is(
+        $user_obj->usrname,
+        $patron_usrname,
+        'Patron with id = ' . $patron_id . ' has username ' . $patron_usrname
+    );
+}
+
+
+# TEST OVERVIEW
+#1. check out an item
+#2. mark it lost
+#-- check that bill is $50
+#3. make full payment
+#-- check that circ and bill are closed
+#4. check in the item
+#-- check that negative balance appears
+#5. adjust to zero
+#-- check that bill is gone
+#-- check that circ is closed
+
+# Check copy out to patron at BR4.
+my $checkout = $script->do_checkout(
+    {copy_id => $item_id, patron_id => $patron_id}
+);
+is(ref($checkout), 'HASH', 'Got checkout event');
+is($checkout->{textcode}, 'SUCCESS', 'Checkout succeeded');
+
+# Check copy status.
+my $copy = $apputils->simplereq(
+    'open-ils.pcrud',
+    'open-ils.pcrud.retrieve.acp',
+    $script->authtoken,
+    $item_id
+);
+is($copy->status(), 1, 'Copy is checked out');
+
+### Mark item LOST
+my $response = $apputils->simplereq(
+    'open-ils.circ',
+    'open-ils.circ.circulation.set_lost',
+    $script->authtoken,
+    {barcode => $item_barcode}
+);
+
+# verify that checkout returned a circ object
+ok(
+    $checkout->{payload}{circ},
+    'Response has a "circ" object'
+);
+my $xact_id;
+if ($checkout->{payload}{circ}) {
+    my $xact = $checkout->{payload}{circ};
+    $xact_id = $xact->id();
+}
+
+
+my $summary = fetch_billable_xact_summary($xact_id);
+ok( $summary, 'Found the transaction summary');
+is(
+    $summary->balance_owed,
+    '50.00',
+    'Balance owed is 50.00 for lost item'
+);
+
+### pay the whole bill
+my $payment_blob = {
+    userid => $patron_id,
+    note => 'XX-lp1749795_adjust_to_zero_closes_circ.t',
+    payment_type => 'cash_payment',
+    patron_credit => '0.00',
+    payments => [ [ $xact_id, '50.00' ] ]
+};
+my $pay_resp = pay_bills($payment_blob);
+
+is(
+    scalar( @{ $pay_resp->{payments} } ),
+    1,
+    'Payment response included one payment id'
+);
+
+$summary = fetch_billable_xact_summary($xact_id);
+is(
+    $summary->balance_owed,
+    '0.00',
+    'Remaining balance of 0.00 after payment'
+);
+
+# check that circ and bill are closed
+ok(
+    $summary->xact_finish,
+    'Transaction is closed'
+);
+
+### check-in the copy
+
+my $item_req = $storage_ses->request('open-ils.storage.direct.asset.copy.retrieve', $item_id);
+if (my $item_resp = $item_req->recv) {
+    if (my $item = $item_resp->content) {
+        is(
+            ref $item,
+            'Fieldmapper::asset::copy',
+            'open-ils.storage.direct.asset.copy.retrieve returned acp object'
+        );
+        is(
+            $item->status,
+            3,
+            'Item with id = ' . $item_id . ' has status of LOST'
+        );
+    }
+}
+
+### verify checkin succeeded
+my $checkin_resp = $script->do_checkin_override({
+    barcode => $item_barcode});
+is(
+    $checkin_resp->{ilsevent},
+    0,
+    'Checkin returned a SUCCESS event'
+);
+
+### verify item status
+$item_req = $storage_ses->request('open-ils.storage.direct.asset.copy.retrieve', $item_id);
+if (my $item_resp = $item_req->recv) {
+    if (my $item = $item_resp->content) {
+        ok(
+            $item->status == 7 || $item->status == 0,
+            'Item with id = ' . $item_id . ' has status of Reshelving or Available after fresh Storage request'
+        );
+    }
+}
+
+### verify negative balance
+$summary = fetch_billable_xact_summary($xact_id);
+is(
+    $summary->balance_owed,
+    '-50.00',
+    'Patron has a negative balance (credit) of 50.00 due to overpayment'
+);
+
+
+# Adjust to zero
+
+# returns array of IDs for each transaction updated, Event on error.
+my $adjust_resp = $apputils->simplereq(
+    'open-ils.circ',
+    'open-ils.circ.money.billable_xact.adjust_to_zero',
+    $script->authtoken,
+    [$xact_id]
+);
+is(
+    $adjust_resp->[0],
+    $xact_id,
+    'Adjust-to-zero succeeded'
+);
+
+### verify account has zero balance
+$summary = fetch_billable_xact_summary($xact_id);
+is(
+    $summary->balance_owed,
+    '0.00',
+    'Patron has 0.00 balance'
+);
+### verify xact is closed
+ok(
+    $summary->xact_finish,
+    'Transaction is closed'
+);
+
+