View Javadoc
1   /*
2    * Copyright 2007 The Kuali Foundation
3    *
4    * Licensed under the Educational Community License, Version 2.0 (the "License");
5    * you may not use this file except in compliance with the License.
6    * You may obtain a copy of the License at
7    *
8    * http://www.opensource.org/licenses/ecl2.php
9    *
10   * Unless required by applicable law or agreed to in writing, software
11   * distributed under the License is distributed on an "AS IS" BASIS,
12   * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13   * See the License for the specific language governing permissions and
14   * limitations under the License.
15   */
16  package org.kuali.ole.module.purap.edi;
17  
18  import com.lowagie.text.DocumentException;
19  import org.apache.commons.logging.Log;
20  import org.apache.commons.logging.LogFactory;
21  import org.kuali.ole.module.purap.PurapConstants;
22  import org.kuali.ole.module.purap.businessobject.PurApItem;
23  import org.kuali.ole.module.purap.document.PurchaseOrderDocument;
24  import org.kuali.ole.module.purap.exception.PurError;
25  import org.kuali.ole.module.purap.util.PurApDateFormatUtils;
26  import org.kuali.ole.select.businessobject.OlePurchaseOrderItem;
27  import org.kuali.ole.select.lookup.DocLookupSearch;
28  import org.kuali.ole.select.lookup.DocLookupServiceImpl;
29  import org.kuali.ole.sys.context.SpringContext;
30  import org.kuali.rice.core.api.datetime.DateTimeService;
31  import org.kuali.rice.core.api.util.RiceConstants;
32  import org.kuali.rice.krad.util.ObjectUtils;
33  
34  import java.io.*;
35  import java.text.SimpleDateFormat;
36  import java.util.*;
37  
38  /**
39   * Base class to handle Edi for purchase order documents.
40   */
41  public class PurchaseOrderEdi {
42      private static Log LOG = LogFactory.getLog(PurchaseOrderEdi.class);
43  
44      private DateTimeService dateTimeService;
45  
46  
47      public PurchaseOrderEdi() {
48      }
49  
50  
51      /**
52       * Invokes the createEdiFile method to create a EDI document and saves it into a file
53       * which name and location are specified in the file.
54       *
55       * @param po           The PurchaseOrderDocument to be used to create the EDI.
56       * @param file         The file containing some of the parameters information needed by the EDI for example, the EDI file name and EDI file location, purchasing director name, etc.
57       * @param isRetransmit The boolean to indicate whether this is for a retransmit purchase order document.
58       * @param environment  The current environment used (e.g. DEV if it is a development environment).
59       */
60      public boolean saveEdi(PurchaseOrderDocument po, PurApItem item, String file) {
61          if (LOG.isInfoEnabled()) {
62              LOG.info("saveEdi() started for po number " + po.getPurapDocumentIdentifier());
63          }
64  
65          try {
66              createEdiFile(po, item, file);
67              if (LOG.isDebugEnabled()) {
68                  LOG.debug("saveEdi() completed for po number " + po.getPurapDocumentIdentifier());
69              }
70          } catch (DocumentException de) {
71              LOG.error("saveEdi() DocumentException: " + de.getMessage(), de);
72              throw new PurError("Document Exception when trying to save a Purchase Order EDI", de);
73          } catch (FileNotFoundException f) {
74              LOG.error("saveEdi() FileNotFoundException: " + f.getMessage(), f);
75              throw new PurError("FileNotFound Exception when trying to save a Purchase Order EDI", f);
76          } catch (IOException i) {
77              LOG.error("saveEdi() IOException: " + i.getMessage(), i);
78              throw new PurError("IO Exception when trying to save a Purchase Order EDI", i);
79          } catch (Exception t) {
80              LOG.error("saveEdi() EXCEPTION: " + t.getMessage(), t);
81              throw new PurError("Exception when trying to save a Purchase Order EDI", t);
82          }
83          return true;
84      }
85  
86  
87      /**
88       * This method is for generate a unique reference number for a PO
89       *
90       * @return String
91       * @throws Exception
92       */
93      private String generateReferenceNumber() throws Exception {
94          UUID referenceNumber = UUID.randomUUID();
95          return referenceNumber.toString();
96      }
97  
98  
99      /**
100      * Create an EDI file using the given input parameters.
101      *
102      * @param po   The PurchaseOrderDocument to be used to create the EDI.
103      * @param file The EDI document whose margins have already been set.
104      * @throws Exception
105      */
106     private void createEdiFile(PurchaseOrderDocument po, PurApItem item, String file) throws Exception {
107         Writer writer = null;
108         StringBuffer text = new StringBuffer();
109         try {
110 
111             LOG.debug("EDI File creation started");
112             List<OlePurchaseOrderItem> purchaseOrderItemList = new ArrayList<OlePurchaseOrderItem>();
113             String itemIdentifier = item.getItemIdentifier().toString();
114             Map map = new HashMap();
115             map.put("itemIdentifier", itemIdentifier);
116             DocLookupServiceImpl impl = SpringContext.getBean(DocLookupServiceImpl.class, "docLookupService");
117             OlePurchaseOrderItem olePurchaseOrderItem = null;
118             impl.setLookupDao(new DocLookupSearch());
119             try {
120                 List<OlePurchaseOrderItem> searchResults = (List) impl.findCollectionBySearchHelper(OlePurchaseOrderItem.class, map, true);
121                 for (OlePurchaseOrderItem poItem : searchResults) {
122                     purchaseOrderItemList.add(poItem);
123                 }
124                 olePurchaseOrderItem = purchaseOrderItemList.get(0);
125             } catch (Exception exception) {
126                 LOG.error("*****Exception in createEdiFile()******: No matching data found in the docstore " + exception.getMessage());
127             }
128 
129             int lineCount = 0;
130             String uniqueRefNumber = generateReferenceNumber();
131             text.append("UNH+" + uniqueRefNumber + "ORDERS:D:96A:UN:EAN008'");
132             text.append(System.getProperty("line.separator"));
133             lineCount++;
134             String statusCode = "220";
135             if (po.getApplicationDocumentStatus() != null && po.getApplicationDocumentStatus().equalsIgnoreCase(PurapConstants.PurchaseOrderStatuses.APPDOC_RETIRED_VERSION)) {
136                 statusCode = "230";
137             }
138             text.append("BGM+" + statusCode + "+" + po.getPurapDocumentIdentifier().toString() + "+9'");
139             text.append(System.getProperty("line.separator"));
140             lineCount++;
141             String orderDate = "";
142 
143             SimpleDateFormat sdf = new SimpleDateFormat(RiceConstants.SIMPLE_DATE_FORMAT_FOR_DATE, Locale.getDefault());
144             if (po.getPurchaseOrderInitialOpenTimestamp() != null) {
145                 orderDate = sdf.format(po.getPurchaseOrderInitialOpenTimestamp());
146             } else {
147                 // This date isn't set until the first time this document is printed, so will be null the first time; use today's date.
148                 orderDate = sdf.format(getDateTimeService().getCurrentSqlDate());
149             }
150 
151             SimpleDateFormat formatter = new SimpleDateFormat(RiceConstants.SIMPLE_DATE_FORMAT_FOR_DATE);
152             Date date = formatter.parse(orderDate);
153             String formattedDate = formatter.format(date);
154 
155             Date newDate = formatter.parse(formattedDate);
156             formatter = new SimpleDateFormat("yyMMdd");
157             formattedDate = formatter.format(newDate);
158 
159             Calendar calendar = Calendar.getInstance();
160             calendar.setTime(date);
161             int century = (calendar.get(Calendar.YEAR) / 100) + 1;
162 
163             text.append("DTM+137:" + century + formattedDate + ":102'");
164             text.append(System.getProperty("line.separator"));
165             lineCount++;
166             text.append("NAD+SU+++" + getSupplierDetails(po) + "'");
167             text.append(System.getProperty("line.separator"));
168             lineCount++;
169             text.append("NAD+BY+++" + getBillingDetails(po) + "'");
170             text.append(System.getProperty("line.separator"));
171             lineCount++;
172             text.append("NAD+DP+++" + getDeliveryDetails(po) + "'");
173             text.append(System.getProperty("line.separator"));
174             lineCount++;
175             if (po.getVendorCustomerNumber() != null && po.getVendorCustomerNumber().length() > 0) {
176                 text.append("RFF+API:" + po.getVendorCustomerNumber() + "'");
177                 text.append(System.getProperty("line.separator"));
178                 lineCount++;
179             }
180 
181             //text.append("CUX+2:"+"USD"+":9'");
182             //text.append(System.getProperty("line.separator"));
183             text.append("LIN+" + "1'");
184             text.append(System.getProperty("line.separator"));
185             lineCount++;
186             text.append("PIA+5+" + "9781444334609" + ":IB'");
187             text.append(System.getProperty("line.separator"));
188             lineCount++;
189             if (olePurchaseOrderItem != null && olePurchaseOrderItem.getDocData() != null) {
190                 if (olePurchaseOrderItem.getDocData().getTitle() != null && olePurchaseOrderItem.getDocData().getTitle().length() > 0) {
191                     text.append("IMD+L+050+:::" + olePurchaseOrderItem.getDocData().getTitle() + "'");
192                     text.append(System.getProperty("line.separator"));
193                     lineCount++;
194                 }
195                 if (olePurchaseOrderItem.getDocData().getPlaceOfPublication() != null && olePurchaseOrderItem.getDocData().getPlaceOfPublication().length() > 0) {
196                     text.append("IMD+L+110+:::" + olePurchaseOrderItem.getDocData().getPlaceOfPublication() + "'");
197                     text.append(System.getProperty("line.separator"));
198                     lineCount++;
199                 }
200                 if (olePurchaseOrderItem.getDocData().getAuthor() != null && olePurchaseOrderItem.getDocData().getAuthor().length() > 0) {
201                     text.append("IMD+L+009+:::" + olePurchaseOrderItem.getDocData().getAuthor() + "'");
202                     text.append(System.getProperty("line.separator"));
203                     lineCount++;
204                 }
205                 if (olePurchaseOrderItem.getDocData().getPublicationDate() != null && olePurchaseOrderItem.getDocData().getPublicationDate().length() > 0) {
206                     text.append("IMD+L+170+:::" + olePurchaseOrderItem.getDocData().getPublicationDate() + "'");
207                     text.append(System.getProperty("line.separator"));
208                     lineCount++;
209                 }
210                 if (olePurchaseOrderItem.getDocData().getPublisher() != null && olePurchaseOrderItem.getDocData().getPublisher().length() > 0) {
211                     text.append("IMD+L+109+:::" + olePurchaseOrderItem.getDocData().getPublisher() + "'");
212                     text.append(System.getProperty("line.separator"));
213                     lineCount++;
214                 }
215             }
216 
217             text.append("QTY+21:" + item.getItemQuantity() + "'");
218             text.append(System.getProperty("line.separator"));
219             lineCount++;
220             text.append("PRI+AAE:" + "33" + ":SRP'");
221             text.append(System.getProperty("line.separator"));
222             lineCount++;
223             text.append("UNS+S'");
224             text.append(System.getProperty("line.separator"));
225             lineCount++;
226             text.append("CNT+2:1'");
227             text.append(System.getProperty("line.separator"));
228             lineCount++;
229             lineCount++;
230             text.append("UNT+" + lineCount + "+" + uniqueRefNumber + ":'");
231 
232             File filePath = new File(file);
233             writer = new BufferedWriter(new FileWriter(filePath));
234             writer.write(text.toString());
235             LOG.debug("EDI File created");
236         } finally {
237             try {
238                 if (writer != null) {
239                     writer.close();
240                 }
241             } catch (IOException e) {
242                 e.printStackTrace();
243             }
244         }
245 
246     }
247 
248 
249     /**
250      * This method is to get the Supplier details
251      *
252      * @param po
253      * @return String
254      */
255     public String getSupplierDetails(PurchaseOrderDocument po) {
256         String str = (po.getVendorName() != null && po.getVendorName().length() > 0 ? po.getVendorName() + "+" : "") +
257                 (po.getVendorAttentionName() != null && po.getVendorAttentionName().length() > 0 ? "ATTN: " + po.getVendorAttentionName() + "+" : "") +
258                 (po.getVendorLine1Address() != null && po.getVendorLine1Address().length() > 0 ? po.getVendorLine1Address() + "+" : "") +
259                 (po.getVendorCityName() != null && po.getVendorCityName().length() > 0 ? po.getVendorCityName() + "+" : "") +
260                 (po.getVendorStateCode() != null && po.getVendorStateCode().length() > 0 ? po.getVendorStateCode() + "+" : "") +
261                 (po.getVendorPostalCode() != null && po.getVendorPostalCode().length() > 0 ? po.getVendorPostalCode() + "+" : "") +
262                 (po.getVendorCountryCode() != null && po.getVendorCountryCode().length() > 0 ? po.getVendorCountryCode() : "");
263         return str;
264 
265     }
266 
267 
268     /**
269      * This method is to get the billing details
270      *
271      * @param po
272      * @return String
273      */
274     public String getBillingDetails(PurchaseOrderDocument po) {
275         String str = (po.getBillingName() != null && po.getBillingName().length() > 0 ? po.getBillingName() + "+" : "") +
276                 (po.getBillingLine1Address() != null && po.getBillingLine1Address().length() > 0 ? po.getBillingLine1Address() + "+" : "") +
277                 (po.getBillingLine2Address() != null && po.getBillingLine2Address().length() > 0 ? po.getBillingLine2Address() + "+" : "") +
278                 (po.getBillingCityName() != null && po.getBillingCityName().length() > 0 ? po.getBillingCityName() + "+" : "") +
279                 (po.getBillingStateCode() != null && po.getBillingStateCode().length() > 0 ? po.getBillingStateCode() + "+" : "") +
280                 (po.getBillingPhoneNumber() != null && po.getBillingPhoneNumber().length() > 0 ? po.getBillingPhoneNumber() + "+" : "") +
281                 (po.getBillingPostalCode() != null && po.getBillingPostalCode().length() > 0 ? po.getBillingPostalCode() + "+" : "") +
282                 (po.getBillingCountryCode() != null && po.getBillingCountryCode().length() > 0 ? po.getBillingCountryCode() : "");
283         return str;
284 
285     }
286 
287 
288     /**
289      * This method is to get the delivery details
290      *
291      * @param po
292      * @return String
293      */
294     public String getDeliveryDetails(PurchaseOrderDocument po) {
295         String str = (po.getDeliveryToName() != null && po.getDeliveryToName().length() > 0 ? po.getDeliveryToName() + "+" : "") +
296                 (po.getDeliveryBuildingRoomNumber() != null && po.getDeliveryBuildingRoomNumber().length() > 0 ? "Room # " + po.getDeliveryBuildingRoomNumber() + "+" : "") +
297                 (po.getDeliveryBuildingLine1Address() != null && po.getDeliveryBuildingLine1Address().length() > 0 ? po.getDeliveryBuildingLine1Address() + "+" : "") +
298                 (po.getDeliveryCityName() != null && po.getDeliveryCityName().length() > 0 ? po.getDeliveryCityName() + "+" : "") +
299                 (po.getDeliveryStateCode() != null && po.getDeliveryStateCode().length() > 0 ? po.getDeliveryStateCode() + "+" : "") +
300                 (po.getDeliveryPostalCode() != null && po.getDeliveryPostalCode().length() > 0 ? po.getDeliveryPostalCode() + "+" : "") +
301                 (po.getDeliveryCountryCode() != null && po.getDeliveryCountryCode().length() > 0 ? po.getDeliveryCountryCode() : "");
302         return str;
303 
304     }
305 
306 
307     public DateTimeService getDateTimeService() {
308         if (ObjectUtils.isNull(dateTimeService)) {
309             this.dateTimeService = SpringContext.getBean(DateTimeService.class);
310         }
311         return this.dateTimeService;
312     }
313 
314 }