View Javadoc
1   package org.kuali.ole.service;
2   
3   import org.apache.commons.lang.StringUtils;
4   import org.kuali.ole.deliver.bo.OleDeliverRequestBo;
5   import org.kuali.ole.deliver.bo.OleLoanDocument;
6   import org.kuali.ole.deliver.bo.FeeType;
7   import org.kuali.ole.deliver.bo.PatronBillPayment;
8   import org.kuali.ole.deliver.bo.OleAddressBo;
9   import org.kuali.ole.deliver.bo.OlePatronDocument;
10  import org.kuali.ole.deliver.bo.OleProxyPatronDocument;
11  import org.kuali.ole.deliver.processor.LoanProcessor;
12  import org.kuali.ole.sys.context.SpringContext;
13  import org.kuali.rice.kim.impl.identity.entity.EntityBo;
14  import org.kuali.rice.krad.service.KRADServiceLocator;
15  import org.kuali.ole.docstore.common.document.content.instance.Item;
16  
17  import java.sql.Timestamp;
18  import java.util.*;
19  import java.util.concurrent.TimeUnit;
20  import java.util.regex.Matcher;
21  import java.util.regex.Pattern;
22  
23  /**
24   * Created with IntelliJ IDEA.
25   * User: Bala.km
26   * Date: 7/2/12
27   * Time: 2:04 PM
28   * Service class to provide input to the krms rule engine for loans circulation policy
29   */
30  public class OleCirculationPolicyServiceImpl implements OleCirculationPolicyService {
31      private static final org.apache.log4j.Logger LOG = org.apache.log4j.Logger.getLogger(OleLocationServiceImpl.class);
32      private LoanProcessor loanProcessor;
33  
34      private LoanProcessor getLoanProcessor() {
35          if (loanProcessor == null) {
36              loanProcessor = SpringContext.getBean(LoanProcessor.class);
37          }
38          return loanProcessor;
39      }
40  
41      public void setLoanProcessor(LoanProcessor loanProcessor) {
42          this.loanProcessor = loanProcessor;
43      }
44  
45      /**
46       *  This method checks valid barcode using barcode.
47       *
48       * @param barcode
49       * @return boolean
50       */
51      @Override
52      public boolean isValidBarcode(String barcode, String pattern) {
53          boolean valid = false;
54          //"^[0-9]{1}(([0-9]*-[0-9]*)*|([0-9]* [0-9]*)*|[0-9]*)[0-9]{1}$"
55          if(pattern!=null && barcode!=null){
56              Pattern p = Pattern.compile(pattern);
57              Matcher m = p.matcher(barcode);
58              boolean result = m.matches();
59  
60              if (!result) {
61                  valid = true;
62              }
63          }
64          return valid;
65      }
66  
67      /**
68       *  This method returns MembershipExpireDate using patronBarcode.
69       * @param patronBarcode
70       * @return Date
71       */
72      @Override
73      public Date getPatronMembershipExpireDate(String patronBarcode) {
74          Date expirationDate=null;
75          try{
76              Map<String, String> criteria = new HashMap<String, String>();
77              criteria.put("barcode", patronBarcode);
78              List<OlePatronDocument> olePatronDocument = (List<OlePatronDocument>)  KRADServiceLocator.getBusinessObjectService().findMatching(OlePatronDocument.class,criteria);
79              if(olePatronDocument.size()==1) {
80                  expirationDate = olePatronDocument.get(0).getExpirationDate();
81              }
82          }catch(Exception e){
83              LOG.error(e.getMessage());
84          }
85          return expirationDate;
86      }
87  
88      /**
89       *  This method returns number of items loaned for a particular patron id.
90       * @param olePatronId
91       * @return int
92       */
93      @Override
94      public int getNoOfItemsLoaned(String olePatronId,boolean renewalFlag) {
95          Map<String, String> criteria = new HashMap<String, String>();
96          Collection<OleLoanDocument> oleLoanDocuments=null;
97          try{
98              criteria.put("patronId", olePatronId);
99              oleLoanDocuments = KRADServiceLocator.getBusinessObjectService().findMatching(OleLoanDocument.class,criteria);
100         }catch(Exception e){
101             LOG.error(e.getMessage());
102         }
103         int loanedItems = 0;
104         if(oleLoanDocuments!=null){
105             loanedItems = renewalFlag ?oleLoanDocuments.size() : oleLoanDocuments.size()+1;
106         }
107         return loanedItems;
108     }
109 
110     /**
111      *  This method returns loan due date using loan period.
112      * @param loanPeriod
113      * @return  Timestamp
114      */
115     @Override
116     public Timestamp calculateLoanDueDate(String loanPeriod) {
117         String loanPeriodType[]=null;
118         Timestamp dueDate = null;
119         Calendar calendar = Calendar.getInstance();
120         if(loanPeriod != null && loanPeriod.trim().length()>0){
121             loanPeriodType =  loanPeriod.split("-");
122             int loanPeriodValue =  Integer.parseInt(loanPeriodType[0].toString());
123             String loanPeriodTypeValue =  loanPeriodType[1].toString();
124             if(loanPeriodTypeValue.equalsIgnoreCase("MINUTE")){
125                 calendar.add(Calendar.MINUTE, loanPeriodValue);
126             } else if(loanPeriodTypeValue.equalsIgnoreCase("HOUR")) {
127                 calendar.add(Calendar.HOUR, loanPeriodValue);
128             } else if(loanPeriodTypeValue.equalsIgnoreCase("WEEK")) {
129                 calendar.add(Calendar.WEEK_OF_MONTH, loanPeriodValue);
130             } else {
131                 calendar.add(Calendar.DATE, loanPeriodValue);
132             }
133             dueDate =  new Timestamp(calendar.getTime().getTime());
134         }
135         return dueDate;
136     }
137     public List<FeeType> getPatronBillPayment(String patronId){
138         List<FeeType> feeTypeList = new ArrayList<FeeType>();
139         Map<String, String> criteria = new HashMap<String, String>();
140         criteria.put("patronId",patronId);
141         List<PatronBillPayment> patronBillPayments =  (List<PatronBillPayment>)KRADServiceLocator.getBusinessObjectService().findMatching(PatronBillPayment.class,criteria);
142         for(PatronBillPayment patronBillPayment : patronBillPayments){
143             feeTypeList.addAll(patronBillPayment.getFeeType());
144         }
145         return feeTypeList;
146     }
147 
148     @Override
149     public HashMap getNumberOfOverdueItemsCheckedOut(String patronId) {
150         int count = 0;
151         HashMap overdueItems = new HashMap();
152 
153         List<OleLoanDocument> overdueLoanedItem = new ArrayList<OleLoanDocument>();
154         Map<String, String> criteria = new HashMap<String, String>();
155         criteria.put("patronId", patronId);
156         List<OleLoanDocument> oleLoanDocuments= (List<OleLoanDocument>)KRADServiceLocator.getBusinessObjectService().findMatching(OleLoanDocument.class,criteria);
157         oleLoanDocuments = oleLoanDocuments!=null?oleLoanDocuments:new ArrayList<OleLoanDocument>();
158         for(OleLoanDocument oleLoanDocument : oleLoanDocuments){
159             Integer numberOfOverdueNoticesSent = new Integer(oleLoanDocument.getNumberOfOverdueNoticesSent()!=null?oleLoanDocument.getNumberOfOverdueNoticesSent():"0");
160             if(numberOfOverdueNoticesSent>0){
161                 overdueLoanedItem.add(oleLoanDocument);
162                 count++;
163             }
164         }
165         overdueItems.put("count",count);
166         overdueItems.put("oleLoanDocumentList",overdueLoanedItem);
167         return overdueItems;
168     }
169 
170     @Override
171     public HashMap getRecalledOverdueItemsCheckedOut(List<OleLoanDocument> oleLoanDocuments) {
172         int count = 0;
173         List<Integer> listOfRecalledOverdueDays = new ArrayList<Integer>();
174         HashMap recalledOverdueItems = new HashMap();
175         List<OleLoanDocument> recallOverdueLoanedItem = new ArrayList<OleLoanDocument>();
176         oleLoanDocuments = oleLoanDocuments!=null?oleLoanDocuments:new ArrayList<OleLoanDocument>();
177         for(OleLoanDocument oleLoanDocument : oleLoanDocuments){
178             Map<String, String> criteria = new HashMap<String, String>();
179             criteria.put("itemId", oleLoanDocument.getItemId());
180             List<OleDeliverRequestBo> oleDeliverRequestBoList =(List<OleDeliverRequestBo>)KRADServiceLocator.getBusinessObjectService().findMatching(OleDeliverRequestBo.class,criteria);
181             for(OleDeliverRequestBo oleDeliverRequestBo : oleDeliverRequestBoList){
182                 if(oleDeliverRequestBo.getOleDeliverRequestType().getRequestTypeCode().contains("recall")){
183                     count ++;
184                     recallOverdueLoanedItem.add(oleLoanDocument);
185                     if(oleLoanDocument!=null && oleLoanDocument.getLoanDueDate()!=null && oleLoanDocument.getLoanDueDate().compareTo(new Date())<=0){
186                         listOfRecalledOverdueDays.add(new Integer(getTimeDiff(oleLoanDocument.getLoanDueDate(),new Date())));
187                     }
188                     break;
189                 }
190             }
191         }
192         recalledOverdueItems.put("count",count);
193         recalledOverdueItems.put("oleLoanDocumentList",recallOverdueLoanedItem);
194         recalledOverdueItems.put("listOfRecalledOverdueDays",listOfRecalledOverdueDays);
195         return recalledOverdueItems;
196     }
197 
198     @Override
199     public List<Integer> getNumberOfOverdueDays(String patronId) {
200         List<Integer> listOfOverdueDays = new ArrayList<Integer>();
201         Map<String, String> criteria = new HashMap<String, String>();
202         criteria.put("patronId", patronId);
203         OleLoanDocument oleLoanDocument=KRADServiceLocator.getBusinessObjectService().findByPrimaryKey(OleLoanDocument.class,criteria);
204         if(oleLoanDocument!=null && oleLoanDocument.getLoanDueDate()!=null && oleLoanDocument.getLoanDueDate().compareTo(new Date())<=0){
205             listOfOverdueDays.add(new Integer(getTimeDiff(oleLoanDocument.getLoanDueDate(),new Date())));
206         }
207         return listOfOverdueDays;
208     }
209     public String getTimeDiff(Date dateOne, Date dateTwo) {
210         String diff = "";
211         long timeDiff = Math.abs(dateOne.getTime() - dateTwo.getTime());
212         diff = String.format("%d",TimeUnit.MILLISECONDS.toDays(timeDiff),
213                 -TimeUnit.HOURS.toDays(timeDiff));
214         return diff;
215     }
216     @Override
217     public int getNumberOfClaimsReturned(String patronId) {
218         int count = 0;
219         Map<String, String> criteria = new HashMap<String, String>();
220         criteria.put("patronId", patronId);
221         List<OleLoanDocument> oleLoanDocuments= (List<OleLoanDocument>)KRADServiceLocator.getBusinessObjectService().findMatching(OleLoanDocument.class,criteria);
222         oleLoanDocuments = oleLoanDocuments!=null?oleLoanDocuments:new ArrayList<OleLoanDocument>();
223         for(OleLoanDocument oleLoanDocument : oleLoanDocuments){
224             try {
225                 String itemXmlContent = getLoanProcessor().getItemXML(oleLoanDocument.getItemUuid());
226                 Item oleItem = getLoanProcessor().getItemPojo(itemXmlContent);
227                 if (oleItem.isClaimsReturnedFlag()) {
228                     count++;
229                 }
230             } catch (Exception e) {
231                 throw new RuntimeException(e);
232             }
233         }
234         return count;
235     }
236 
237     public Integer getHoursDiff(Date dateOne, Date dateTwo) {
238         if(dateOne!=null && dateTwo!=null && dateOne.compareTo(dateTwo)<=0){
239             String diff = "";
240             long timeDiff = Math.abs(dateOne.getTime() - dateTwo.getTime());
241             diff = String.format("%d",TimeUnit.MILLISECONDS.toHours(timeDiff),
242                     -TimeUnit.HOURS.toMinutes(timeDiff));
243             return new Integer(diff);
244         }
245         return 0;
246     }
247 
248     public List<OlePatronDocument> isProxyPatron(String partonId) throws Exception{
249         List realPatron = new ArrayList();
250         Map<String, String> criteria = new HashMap<String, String>();
251         Map<String, String> proxyCriteria = new HashMap<String, String>();
252         criteria.put("proxyPatronId", partonId);
253         List<OleProxyPatronDocument> oleProxyPatronDocuments = (List<OleProxyPatronDocument>)KRADServiceLocator.getBusinessObjectService().findMatching(OleProxyPatronDocument.class,criteria);
254         if(oleProxyPatronDocuments != null && oleProxyPatronDocuments.size() >0){
255             for(int proxyPatron=0;proxyPatron<oleProxyPatronDocuments.size();proxyPatron++){
256                 proxyCriteria.put("olePatronId", oleProxyPatronDocuments.get(proxyPatron).getOlePatronId());
257                 List<OlePatronDocument> olePatronDocument = (List<OlePatronDocument>)  KRADServiceLocator.getBusinessObjectService().findMatching(OlePatronDocument.class,proxyCriteria);
258                 if(olePatronDocument!=null && olePatronDocument.size()>0)
259                     realPatron.add(olePatronDocument.get(0));
260                 // realPatron.add(oleProxyPatronDocuments.get(proxyPatron));
261             }
262             // return realPatron;
263         }
264         return realPatron;
265     }
266 
267     public List<OlePatronDocument> isProxyPatron(OlePatronDocument olePatronDocument) throws Exception{
268         List realPatron = new ArrayList();
269         List<OleProxyPatronDocument> oleProxyPatronDocuments = olePatronDocument.getOleProxyPatronDocumentList();
270         for(OleProxyPatronDocument oleProxyPatronDocument : oleProxyPatronDocuments){
271            realPatron.add(oleProxyPatronDocument.getOlePatronDocument());
272         }
273         return realPatron;
274     }
275 
276     public boolean isAddressVerified(String patronId) throws Exception{
277         int count =0;
278         Map<String, String> criteria = new HashMap<String, String>();
279         Map<String, String> addressCriteria = new HashMap<String, String>();
280         criteria.put("olePatronId", patronId);
281         List<OlePatronDocument> olePatronDocument = (List<OlePatronDocument>)  KRADServiceLocator.getBusinessObjectService().findMatching(OlePatronDocument.class,criteria);
282         if(olePatronDocument != null && olePatronDocument.size() >0){
283             EntityBo entityBo = olePatronDocument.get(0).getEntity();
284             if(entityBo.getEntityTypeContactInfos().get(0).getAddresses() != null && entityBo.getEntityTypeContactInfos().get(0).getAddresses().size() >0){
285                 for(int address=0;address<entityBo.getEntityTypeContactInfos().get(0).getAddresses().size();address ++ ){
286                     addressCriteria.put("id",entityBo.getEntityTypeContactInfos().get(0).getAddresses().get(address).getId());
287                     List<OleAddressBo> oleAddressBos = (List<OleAddressBo>)  KRADServiceLocator.getBusinessObjectService().findMatching(OleAddressBo.class,addressCriteria);
288                     if(oleAddressBos != null && oleAddressBos.size() > 0 && oleAddressBos.get(0).isAddressVerified()){
289                         count ++;
290                     }
291                 }
292                 if(count == entityBo.getEntityTypeContactInfos().get(0).getAddresses().size()){
293                     return true;
294                 }
295             }
296 
297         }
298         return false;
299     }
300 
301 
302     public boolean isAddressVerified(OlePatronDocument olePatronDocument,String patronId) throws Exception{
303         if (olePatronDocument == null){
304             return isAddressVerified(patronId);
305         }
306        // int count =0;
307         Map<String, String> addressCriteria = new HashMap<String, String>();
308         EntityBo entityBo = olePatronDocument.getEntity();
309             if(entityBo.getEntityTypeContactInfos().get(0).getAddresses() != null && entityBo.getEntityTypeContactInfos().get(0).getAddresses().size() >0){
310                 for(int address=0;address<entityBo.getEntityTypeContactInfos().get(0).getAddresses().size();address ++ ){
311                     addressCriteria.put("id",entityBo.getEntityTypeContactInfos().get(0).getAddresses().get(address).getId());
312                     List<OleAddressBo> oleAddressBos = (List<OleAddressBo>)  KRADServiceLocator.getBusinessObjectService().findMatching(OleAddressBo.class,addressCriteria);
313                     if(oleAddressBos != null && oleAddressBos.size() > 0 && entityBo.getEntityTypeContactInfos().get(0).getAddresses().get(address).isDefaultValue() && oleAddressBos.get(0).isAddressVerified()){
314                        return true;
315                     }
316                     /*if(oleAddressBos != null && oleAddressBos.size() > 0 && oleAddressBos.get(0).isAddressVerified()){
317                         count ++;
318                     }*/
319                 }
320                 /*if(count == entityBo.getEntityTypeContactInfos().get(0).getAddresses().size()){
321                     return true;
322                 }*/
323             }
324         return false;
325     }
326 
327     public HashMap getLoanedKeyMap(String patronId,boolean renewalFlag){
328         Long begin = System.currentTimeMillis();
329         // Initializing  variables
330         OlePatronDocument olePatronDocument;
331         int recallCount = 0;
332         int overdueCount=0;
333         int loanedItems=0;
334         List<Integer> listOfRecalledOverdueDays = new ArrayList<Integer>();
335         HashMap keyMap = new HashMap();
336         List<OleLoanDocument> recallOverdueLoanedItem = new ArrayList<OleLoanDocument>();
337         List<OleLoanDocument> overdueLoanedItem = new ArrayList<OleLoanDocument>();
338 
339         List<Integer> listOfOverdueDays = new ArrayList<Integer>();
340         Map<String, String> criteria = new HashMap<String, String>();
341         criteria.put("patronId", patronId);
342         List<OleLoanDocument> oleLoanDocuments= (List<OleLoanDocument>)KRADServiceLocator.getBusinessObjectService().findMatching(OleLoanDocument.class,criteria);
343         oleLoanDocuments = oleLoanDocuments!=null?oleLoanDocuments:new ArrayList<OleLoanDocument>();
344         olePatronDocument = oleLoanDocuments!=null &&  oleLoanDocuments.size()>0 ? oleLoanDocuments.get(0).getOlePatron() : null;
345         for(OleLoanDocument oleLoanDocument : oleLoanDocuments){
346             //checking overdue
347             Integer numberOfOverdueNoticesSent = new Integer(oleLoanDocument.getNumberOfOverdueNoticesSent()!=null?oleLoanDocument.getNumberOfOverdueNoticesSent():"0");
348             if(numberOfOverdueNoticesSent>0){
349                 //checking recall if overdue only
350                 overdueLoanedItem.add(oleLoanDocument);
351                 criteria.clear();
352                 criteria.put("itemId", oleLoanDocument.getItemId());
353                 List<OleDeliverRequestBo> oleDeliverRequestBoList =(List<OleDeliverRequestBo>)KRADServiceLocator.getBusinessObjectService().findMatching(OleDeliverRequestBo.class,criteria);
354                 for(OleDeliverRequestBo oleDeliverRequestBo : oleDeliverRequestBoList){
355                     if(oleDeliverRequestBo.getOleDeliverRequestType().getRequestTypeCode().contains("recall")){
356                         recallCount ++;
357                         recallOverdueLoanedItem.add(oleLoanDocument);
358                         if(oleLoanDocument!=null && oleLoanDocument.getLoanDueDate()!=null && oleLoanDocument.getLoanDueDate().compareTo(new Date())<=0){
359                             listOfRecalledOverdueDays.add(new Integer(getTimeDiff(oleLoanDocument.getLoanDueDate(),new Date())));
360                         }
361                         break;
362                     }
363                 }
364                 overdueCount++;
365             }
366 
367             // no of over
368             if(oleLoanDocument!=null && oleLoanDocument.getLoanDueDate()!=null && oleLoanDocument.getLoanDueDate().compareTo(new Date())<=0){
369                 listOfOverdueDays.add(new Integer(getTimeDiff(oleLoanDocument.getLoanDueDate(),new Date())));
370             }
371         }
372         if(oleLoanDocuments!=null){
373             loanedItems = renewalFlag ?oleLoanDocuments.size() : oleLoanDocuments.size()+1;
374         }
375         int claimsCount = 0;
376         HashMap<String,Integer> itemTypeMap = new HashMap<>();
377         for(OleLoanDocument oleLoanDocument : oleLoanDocuments){
378             if(StringUtils.isNotBlank(oleLoanDocument.getItemUuid())) {
379                 String itemXmlContent = null;
380                 Item oleItem = null;
381                 try {
382                     itemXmlContent = getLoanProcessor().getItemXML(oleLoanDocument.getItemUuid());
383                     oleItem = getLoanProcessor().getItemPojo(itemXmlContent);
384                 } catch (Exception e) {
385                     LOG.error("Item Parse Exception in CirculationPolicyServiceImpl getLoanedKeyMap");
386                 }
387 
388                 if (oleItem != null && oleItem.isClaimsReturnedFlag()) {
389                     claimsCount++;
390                 }
391             }
392 
393             if(itemTypeMap.containsKey(oleLoanDocument.getItemType())){
394                 Integer count = itemTypeMap.get(oleLoanDocument.getItemType());
395                 count++;
396                 itemTypeMap.put(oleLoanDocument.getItemType(),count);
397             }else{
398                 itemTypeMap.put(oleLoanDocument.getItemType(),1);
399             }
400         }
401         //total loaned item count
402         keyMap.put("loanedItemCount",loanedItems);
403         keyMap.put("recallCount", recallCount);
404         keyMap.put("oleLoanDocumentList", recallOverdueLoanedItem);
405         keyMap.put("listOfRecalledOverdueDays", listOfRecalledOverdueDays);
406         //overdue Item
407         keyMap.put("overdueCount",overdueCount);
408         keyMap.put("oleLoanDocumentList",overdueLoanedItem);
409         keyMap.put("listOfOverdueDays",listOfOverdueDays);
410 
411         keyMap.put("patronDetails",olePatronDocument);
412         keyMap.put("itemTypeMap",itemTypeMap);
413         keyMap.put("claimsCount",claimsCount);
414         Long end = System.currentTimeMillis();
415         Long timeTaken = end-begin;
416         LOG.info("The Time Taken for getLoanedKeyMap in Add Item"+timeTaken);
417         return keyMap;
418     }
419 
420 }