[open-ils-commits] r15208 - in trunk/Open-ILS/web: css/skin/default js/dojo/openils js/dojo/openils/circ/nls js/ui/default/circ/selfcheck templates/default/circ/selfcheck (erickson)

svn at svn.open-ils.org svn at svn.open-ils.org
Mon Dec 21 11:33:26 EST 2009


Author: erickson
Date: 2009-12-21 11:33:23 -0500 (Mon, 21 Dec 2009)
New Revision: 15208

Added:
   trunk/Open-ILS/web/templates/default/circ/selfcheck/payment.tt2
Modified:
   trunk/Open-ILS/web/css/skin/default/selfcheck.css
   trunk/Open-ILS/web/js/dojo/openils/Event.js
   trunk/Open-ILS/web/js/dojo/openils/circ/nls/selfcheck.js
   trunk/Open-ILS/web/js/ui/default/circ/selfcheck/selfcheck.js
   trunk/Open-ILS/web/templates/default/circ/selfcheck/circ_page.tt2
   trunk/Open-ILS/web/templates/default/circ/selfcheck/main.tt2
   trunk/Open-ILS/web/templates/default/circ/selfcheck/summary.tt2
Log:
initial support for credit card payments via selfcheck.  2 caveats.  1) the code does not (yet) support cherry-picking transactions to pay, it instead pays the oldest transactions first if the payment amount is less than the total owed.  2) it does not differentiate between transactions that started at (or having billings at) locations that do not support credit card payments.  Until (and if) support for differentiation is added, if the current location supports CC payments, all transactions are fair game for payment

Modified: trunk/Open-ILS/web/css/skin/default/selfcheck.css
===================================================================
--- trunk/Open-ILS/web/css/skin/default/selfcheck.css	2009-12-21 16:21:48 UTC (rev 15207)
+++ trunk/Open-ILS/web/css/skin/default/selfcheck.css	2009-12-21 16:33:23 UTC (rev 15208)
@@ -79,6 +79,9 @@
     text-align: right;
     width: 100%;
 }
+#oils-selfck-content-header span {
+    padding-left: 5px;
+}
 
 #oils-selfck-info-nav {
     margin: 15px 10px 15px 10px;
@@ -86,9 +89,11 @@
     border-bottom: 1px dashed #888;
 }
 
+#oils-selfck-circ-info-div span {
+    padding-right: 8px;
+}
 #oils-selfck-info-nav span {
     padding-left: 8px;
-    padding-right: 8px;
 }
 
 #oils-selfck-info-nav span.selected {
@@ -118,4 +123,13 @@
     color: red;
 }
 
+#oils-selfck-cc-payment-summary {
+    font-weight:bold;
+    padding: 30px;
+}
 
+#oils-selfck-cc-payment-table td {
+    padding: 5px;
+}
+
+

Modified: trunk/Open-ILS/web/js/dojo/openils/Event.js
===================================================================
--- trunk/Open-ILS/web/js/dojo/openils/Event.js	2009-12-21 16:21:48 UTC (rev 15207)
+++ trunk/Open-ILS/web/js/dojo/openils/Event.js	2009-12-21 16:33:23 UTC (rev 15208)
@@ -29,12 +29,15 @@
             this.servertime = kwargs.servertime;
             this.ilsperm = kwargs.ilsperm;
             this.ilspermloc = kwargs.ilspermloc;
+            this.note = kwargs.note;
         },
 
         toString : function() {
             var s = 'Event: ' + (this.code || '') + ':' + this.textcode + ' -> ' + new String(this.desc);
             if(this.ilsperm)
                 s += ' ' + this.ilsperm + '@' + this.ilspermloc;
+            if(this.note)
+                s += '\n' + this.note;
             return s;
         }
     });

Modified: trunk/Open-ILS/web/js/dojo/openils/circ/nls/selfcheck.js
===================================================================
--- trunk/Open-ILS/web/js/dojo/openils/circ/nls/selfcheck.js	2009-12-21 16:21:48 UTC (rev 15207)
+++ trunk/Open-ILS/web/js/dojo/openils/circ/nls/selfcheck.js	2009-12-21 16:33:23 UTC (rev 15208)
@@ -16,6 +16,7 @@
     'MAX_RENEWALS' : 'No more renewals allowed for item ${0}',
     'ITEM_NOT_CATALOGED' : 'Item ${0} was not found in the system.  Try re-scanning the item.',
     'WORKSTATION_REQUIRED' : 'A workstation is required to log in to selfcheck.  You can set the  workstation name with URL param "ws".  \n\nWould you like to register a new workstation for this self-check interface?',
-    'WORKSTATION_EXISTS' : 'This workstation has already been registered.  Would you like to use it for this self-check station?'
+    'WORKSTATION_EXISTS' : 'This workstation has already been registered.  Would you like to use it for this self-check station?',
+    'CC_PAYABLE_BALANCE' : 'You have \$${0} in fines payable by credit card.'
 }
 

Modified: trunk/Open-ILS/web/js/ui/default/circ/selfcheck/selfcheck.js
===================================================================
--- trunk/Open-ILS/web/js/ui/default/circ/selfcheck/selfcheck.js	2009-12-21 16:21:48 UTC (rev 15207)
+++ trunk/Open-ILS/web/js/ui/default/circ/selfcheck/selfcheck.js	2009-12-21 16:33:23 UTC (rev 15208)
@@ -1,5 +1,7 @@
 dojo.require('dojo.date.locale');
 dojo.require('dojo.date.stamp');
+dojo.require('dijit.form.CheckBox');
+dojo.require('dijit.form.NumberSpinner');
 dojo.require('openils.CGI');
 dojo.require('openils.Util');
 dojo.require('openils.User');
@@ -19,6 +21,7 @@
 const SET_WORKSTATION_REQUIRED = 'circ.selfcheck.workstation_required';
 const SET_ALERT_POPUP = 'circ.selfcheck.alert.popup';
 const SET_ALERT_SOUND = 'circ.selfcheck.alert.sound';
+const SET_CC_PAYMENT_ALLOWED = 'credit.payments.allow';
 
 function SelfCheckManager() {
 
@@ -94,7 +97,8 @@
     // connect onclick handlers to the various navigation links
     var linkHandlers = {
         'oils-selfck-hold-details-link' : function() { self.drawHoldsPage(); },
-        'oils-selfck-pay-fines-link' : function() { self.drawFinesPage(); },
+        'oils-selfck-view-fines-link' : function() { self.drawFinesPage(); },
+        'oils-selfck-pay-fines-link' : function() { self.drawPayFinesPage(); },
         'oils-selfck-nav-home' : function() { self.drawCircPage(); },
         'oils-selfck-nav-logout' : function() { self.logoutPatron(); },
         'oils-selfck-nav-logout-print' : function() { self.logoutPatron(true); },
@@ -190,7 +194,8 @@
             SET_AUTO_OVERRIDE_EVENTS,
             SET_PATRON_PASSWORD_REQUIRED,
             SET_AUTO_RENEW_INTERVAL,
-            SET_WORKSTATION_REQUIRED
+            SET_WORKSTATION_REQUIRED,
+            SET_CC_PAYMENT_ALLOWED
         ]
     );
 
@@ -364,35 +369,45 @@
     if(!this.circTemplate)
         this.circTemplate = this.circTbody.removeChild(dojo.byId('oils-selfck-circ-row'));
 
-    // items out, holds, and fines summaries
+    // fines summary
+    this.updateFinesSummary();
 
+    // holds summary
+    this.updateHoldsSummary();
+
+    // items out summary
+    this.updateCircSummary();
+
+    // render mock checkouts for debugging?
+    if(this.mockCheckouts) {
+        for(var i in [1,2,3]) 
+            this.displayCheckout(this.mockCheckout, 'checkout');
+    }
+}
+
+
+SelfCheckManager.prototype.updateFinesSummary = function() {
+    var self = this; 
+
     // fines summary
     fieldmapper.standardRequest(
         ['open-ils.actor', 'open-ils.actor.user.fines.summary'],
         {   async : true,
             params : [this.authtoken, this.patron.id()],
             oncomplete : function(r) {
+
                 var summary = openils.Util.readResponse(r);
+
                 dojo.byId('oils-selfck-fines-total').innerHTML = 
                     dojo.string.substitute(
                         localeStrings.TOTAL_FINES_ACCOUNT, 
                         [summary.balance_owed()]
                     );
+
+                self.creditPayableBalance = summary.balance_owed();
             }
         }
     );
-
-    // holds summary
-    this.updateHoldsSummary();
-
-    // items out summary
-    this.updateCircSummary();
-
-    // render mock checkouts for debugging?
-    if(this.mockCheckouts) {
-        for(var i in [1,2,3]) 
-            this.displayCheckout(this.mockCheckout, 'checkout');
-    }
 }
 
 
@@ -446,9 +461,11 @@
 SelfCheckManager.prototype.goToTab = function(name) {
     this.tabName = name;
 
+    openils.Util.hide('oils-selfck-fines-page');
     openils.Util.hide('oils-selfck-payment-page');
     openils.Util.hide('oils-selfck-holds-page');
     openils.Util.hide('oils-selfck-circ-page');
+    openils.Util.hide('oils-selfck-pay-fines-link');
     
     switch(name) {
         case 'checkout':
@@ -461,6 +478,9 @@
             openils.Util.show('oils-selfck-holds-page');
             break;
         case 'fines':
+            openils.Util.show('oils-selfck-fines-page');
+            break;
+        case 'payment':
             openils.Util.show('oils-selfck-payment-page');
             break;
     }
@@ -645,6 +665,117 @@
 }
 
 
+SelfCheckManager.prototype.drawPayFinesPage = function() {
+    this.goToTab('payment');
+
+    dojo.byId('oils-selfck-cc-payment-summary').innerHTML = 
+        dojo.string.substitute(
+            localeStrings.CC_PAYABLE_BALANCE,
+            [this.creditPayableBalance]
+        );
+
+    oilsSelfckCCNumber.attr('value', '');
+    oilsSelfckCCMonth.attr('value', '01');
+    oilsSelfckCCAmount.attr('value', this.creditPayableBalance);
+    oilsSelfckCCYear.attr('value', new Date().getFullYear());
+    oilsSelfckCCFName.attr('value', this.patron.first_given_name());
+    oilsSelfckCCLName.attr('value', this.patron.family_name());
+    var addr = this.patron.billing_address() || this.patron.mailing_address();
+
+    if(addr) {
+        oilsSelfckCCStreet.attr('value', addr.street1()+' '+addr.street2());
+        oilsSelfckCCCity.attr('value', addr.city());
+        oilsSelfckCCState.attr('value', addr.state());
+        oilsSelfckCCZip.attr('value', addr.post_code());
+    }
+
+    dojo.connect(oilsSelfckEditDetails, 'onChange', 
+        function(newVal) {
+            dojo.forEach(
+                [   oilsSelfckCCFName, 
+                    oilsSelfckCCLName, 
+                    oilsSelfckCCStreet, 
+                    oilsSelfckCCCity, 
+                    oilsSelfckCCState, 
+                    oilsSelfckCCZip
+                ],
+                function(dij) { dij.attr('disabled', !newVal); }
+            );
+        }
+    );
+
+
+    var self = this;
+    dojo.connect(oilsSelfckCCSubmit, 'onClick',
+        function() {
+            progressDialog.show(true);
+            self.sendCCPayment();
+        }
+    );
+}
+
+
+// In this form, this code only supports global on/off credit card 
+// payments and does not dissallow payments to transactions that started
+// at remote locations or transactions that have accumulated billings at 
+// remote locations that dissalow credit card payments.
+// TODO add per-transaction blocks for orgs that do not support CC payments
+
+SelfCheckManager.prototype.sendCCPayment = function() {
+
+    var args = {
+        userid : this.patron.id(),
+        payment_type : 'credit_card_payment',
+        payments : [],
+        cc_args : {
+            where_process : 1,
+            number : oilsSelfckCCNumber.attr('value'),
+            expire_year : oilsSelfckCCYear.attr('value'),
+            expire_month : oilsSelfckCCMonth.attr('value'),
+            billing_first : oilsSelfckCCFName.attr('value'),
+            billing_last : oilsSelfckCCLName.attr('value'),
+            billing_address : oilsSelfckCCStreet.attr('value'),
+            billing_city : oilsSelfckCCCity.attr('value'),
+            billing_state : oilsSelfckCCState.attr('value'),
+            billing_zip : oilsSelfckCCZip.attr('value')
+        }
+    }
+
+    var funds = oilsSelfckCCAmount.attr('value');
+
+    xacts = this.finesData.sort(
+        function(a, b) {
+            if(a.transaction.xact_start() < b.transaction.xact_start()) 
+                return -1;
+            return 1;
+        }
+    );
+
+    for(var i in xacts) {
+        var xact = xacts[i].transaction;
+        var paying = Math.min(funds, xact.balance_owed());
+        args.payments.push([xact.id(), paying]);
+        funds -= paying;
+        if(funds <= 0) break;
+    }
+
+    var resp = fieldmapper.standardRequest(
+        ['open-ils.circ', 'open-ils.circ.money.payment'],
+        {params : [this.authtoken, args]}
+    );
+
+    progressDialog.hide();
+
+    var evt = openils.Event.parse(resp);
+    if(evt) {
+        alert(evt);
+    } else {
+        this.updateFinesSummary();
+        this.drawFinesPage();
+    }
+}
+
+
 SelfCheckManager.prototype.drawFinesPage = function() {
 
     // TODO add option to hid scanBox
@@ -653,6 +784,10 @@
     this.goToTab('fines');
     progressDialog.show(true);
 
+    if(this.creditPayableBalance > 0 && this.orgSettings[SET_CC_PAYMENT_ALLOWED]) {
+        openils.Util.show('oils-selfck-pay-fines-link', 'inline');
+    }
+
     this.finesTbody = dojo.byId('oils-selfck-fines-tbody');
     if(!this.finesTemplate)
         this.finesTemplate = this.finesTbody.removeChild(dojo.byId('oils-selfck-fines-row'));
@@ -662,6 +797,7 @@
     var self = this;
     var handler = function(dataList) {
         self.finesCount = dataList.length;
+        self.finesData = dataList;
         for(var i in dataList) {
             var data = dataList[i];
             var row = self.finesTemplate.cloneNode(true);

Modified: trunk/Open-ILS/web/templates/default/circ/selfcheck/circ_page.tt2
===================================================================
--- trunk/Open-ILS/web/templates/default/circ/selfcheck/circ_page.tt2	2009-12-21 16:21:48 UTC (rev 15207)
+++ trunk/Open-ILS/web/templates/default/circ/selfcheck/circ_page.tt2	2009-12-21 16:33:23 UTC (rev 15208)
@@ -7,7 +7,7 @@
                 <td>Title</td>
                 <td>Author</td>
                 <td>Due Date</td>
-                <td>Renewals Left</td>
+                <td class='hidden'>Renewals Left</td>
                 <td>Type</td>
             </tr>
         </thead>
@@ -18,7 +18,7 @@
                 <td name='title'></td>
                 <td name='author'></td>
                 <td name='due_date'></td>
-                <td name='remaining'></td>
+                <td  class='hidden' name='remaining'></td>
                 <td>
                     <div name='checkout' class='hidden'>Checkout</div>
                     <div name='renew' class='hidden'>Renewal</div>

Modified: trunk/Open-ILS/web/templates/default/circ/selfcheck/main.tt2
===================================================================
--- trunk/Open-ILS/web/templates/default/circ/selfcheck/main.tt2	2009-12-21 16:21:48 UTC (rev 15207)
+++ trunk/Open-ILS/web/templates/default/circ/selfcheck/main.tt2	2009-12-21 16:33:23 UTC (rev 15208)
@@ -10,7 +10,8 @@
 <div id='oils-selfck-bottom-div'>
     <div id='oils-selfck-content-div'>
         <div id='oils-selfck-content-header'>
-            <a id='oils-selfck-print-list-link' href='javascript:void(0);'>Print List</a>
+            <span><a class='hidden' href='javascript:void(0);' id='oils-selfck-pay-fines-link'>Pay Fines</a></span>
+            <span><a id='oils-selfck-print-list-link' href='javascript:void(0);'>Print List</a></span>
         </div>
         <div id='oils-selfck-circ-page' class='hidden'>
             <!-- Checkout / renewal and items out interface -->
@@ -20,10 +21,14 @@
             <!-- Patron holds interface -->
             [% INCLUDE 'default/circ/selfcheck/holds_page.tt2' %]
         </div>
-        <div id='oils-selfck-payment-page' class='hidden'>
-            <!-- Fines and credit card payments interface -->
+        <div id='oils-selfck-fines-page' class='hidden'>
+            <!-- Fines and interface -->
             [% INCLUDE 'default/circ/selfcheck/fines.tt2' %]
         </div>
+        <div id='oils-selfck-payment-page' class='hidden'>
+            <!-- credit card payments interface -->
+            [% INCLUDE 'default/circ/selfcheck/payment.tt2' %]
+        </div>
     </div>
     <div id='oils-selfck-summary-div'>
         [% INCLUDE 'default/circ/selfcheck/summary.tt2' %]

Added: trunk/Open-ILS/web/templates/default/circ/selfcheck/payment.tt2
===================================================================
--- trunk/Open-ILS/web/templates/default/circ/selfcheck/payment.tt2	                        (rev 0)
+++ trunk/Open-ILS/web/templates/default/circ/selfcheck/payment.tt2	2009-12-21 16:33:23 UTC (rev 15208)
@@ -0,0 +1,69 @@
+<div id='oils-selfck-cc-payment-summary'> </div>
+<table id='oils-selfck-cc-payment-table'>
+    <tbody>
+        <tr>
+            <td>Amount</td>
+            <td><input dojoType='dijit.form.TextBox' jsId='oilsSelfckCCAmount' required='true'/></td>
+        </tr>
+        <tr>
+            <td>Credit Card #</td>
+            <td><input dojoType='dijit.form.TextBox' jsId='oilsSelfckCCNumber' required='true'/></td>
+        </tr>
+        <tr>
+            <td>Exipration Month</td>
+            <td>
+                <select dojoType='dijit.form.FilteringSelect' jsId='oilsSelfckCCMonth' required='true'>
+                    <option value='01' selected='selected'>Jan</option>
+                    <option value='02'>Feb</option>
+                    <option value='03'>Mar</option>
+                    <option value='04'>April</option>
+                    <option value='05'>May</option>
+                    <option value='06'>June</option>
+                    <option value='07'>July</option>
+                    <option value='08'>Aug</option>
+                    <option value='09'>Sept</option>
+                    <option value='10'>Oct</option>
+                    <option value='11'>Nov</option>
+                    <option value='12'>Dec</option>
+                </select>
+            </td>
+        </tr>
+        <tr>
+            <td>Expiration Year</td>
+            <td><input dojoType='dijit.form.NumberSpinner' constraints='{pattern:"0000", places:0, maxlength:4}' jsId='oilsSelfckCCYear' required='true'/></td>
+        </tr>
+        <tr>
+            <td>Edit Billing Details</td>
+            <td><input dojoType='dijit.form.CheckBox' jsId='oilsSelfckEditDetails'/></td>
+        </tr>
+        <tr>
+            <td>First Name</td>
+            <td><input dojoType='dijit.form.TextBox' jsId='oilsSelfckCCFName' disabled='disabled' required='true'/></td>
+        </tr>
+        <tr>
+            <td>Last Name</td>
+            <td><input dojoType='dijit.form.TextBox' jsId='oilsSelfckCCLName' disabled='disabled' required='true'/></td>
+        </tr>
+        <tr>
+            <td>Street Address</td>
+            <td><input dojoType='dijit.form.TextBox' jsId='oilsSelfckCCStreet' disabled='disabled' required='true'/></td>
+        </tr>
+        <tr>
+            <td>City</td>
+            <td><input dojoType='dijit.form.TextBox' jsId='oilsSelfckCCCity' disabled='disabled' required='true'/></td>
+        </tr>
+        <tr>
+            <td>State or Province</td>
+            <td><input dojoType='dijit.form.TextBox' jsId='oilsSelfckCCState' disabled='disabled' required='true'/></td>
+        </tr>
+        <tr>
+            <td>ZIP or Postal Code</td>
+            <td><input dojoType='dijit.form.TextBox' jsId='oilsSelfckCCZip' disabled='disabled' required='true'/></td>
+        </tr>
+        <tr>
+            <td colspan='2' align='center'>
+                <button dojoType='dijit.form.Button' jsId='oilsSelfckCCSubmit'>Submit Payment</button>
+            </td>
+        </tr>
+    </tbody>
+</table>

Modified: trunk/Open-ILS/web/templates/default/circ/selfcheck/summary.tt2
===================================================================
--- trunk/Open-ILS/web/templates/default/circ/selfcheck/summary.tt2	2009-12-21 16:21:48 UTC (rev 15207)
+++ trunk/Open-ILS/web/templates/default/circ/selfcheck/summary.tt2	2009-12-21 16:33:23 UTC (rev 15208)
@@ -19,7 +19,9 @@
     <fieldset>
         <legend>Fines</legend>
         <div id='oils-selfck-fines-total'></div>
-        <div><a href='javascript:void(0);' id='oils-selfck-pay-fines-link'>View Fines</a></div>
+        <div>
+            <span><a href='javascript:void(0);' id='oils-selfck-view-fines-link'>View Details</a></span>
+        </div>
     </fieldset>
 </div>
 



More information about the open-ils-commits mailing list