1 24 package org.ofbiz.shipment.thirdparty.usps; 25 26 import java.io.ByteArrayOutputStream ; 27 import java.io.FileOutputStream ; 28 import java.io.IOException ; 29 import java.io.OutputStream ; 30 import java.text.DecimalFormat ; 31 import java.util.ArrayList ; 32 import java.util.HashMap ; 33 import java.util.Iterator ; 34 import java.util.LinkedList ; 35 import java.util.List ; 36 import java.util.ListIterator ; 37 import java.util.Map ; 38 39 import javax.xml.parsers.ParserConfigurationException ; 40 41 import org.ofbiz.base.util.*; 42 import org.ofbiz.entity.GenericDelegator; 43 import org.ofbiz.entity.GenericEntityException; 44 import org.ofbiz.entity.GenericValue; 45 import org.ofbiz.entity.util.EntityUtil; 46 import org.ofbiz.product.store.ProductStoreWorker; 47 import org.ofbiz.service.DispatchContext; 48 import org.ofbiz.service.GenericServiceException; 49 import org.ofbiz.service.LocalDispatcher; 50 import org.ofbiz.service.ModelService; 51 import org.ofbiz.service.ServiceUtil; 52 53 import org.apache.xml.serialize.OutputFormat; 54 import org.apache.xml.serialize.XMLSerializer; 55 import org.w3c.dom.Document ; 56 import org.w3c.dom.Element ; 57 import org.xml.sax.SAXException ; 58 59 66 public class UspsServices { 67 68 public final static String module = UspsServices.class.getName(); 69 70 public static Map uspsRateInquire(DispatchContext dctx, Map context) { 71 72 GenericDelegator delegator = dctx.getDelegator(); 73 74 Double shippableWeight = (Double ) context.get("shippableWeight"); 76 if (shippableWeight.doubleValue() == 0) { 77 return ServiceUtil.returnError("shippableWeight must be greater than 0"); 79 } 80 81 String originationZip = null; 83 GenericValue productStore = ProductStoreWorker.getProductStore(((String ) context.get("productStoreId")), delegator); 84 if (productStore != null && productStore.get("inventoryFacilityId") != null) { 85 try { 86 List shipLocs = delegator.findByAnd("FacilityContactMechPurpose", 87 UtilMisc.toMap("facilityId", productStore.getString("inventoryFacilityId"), 88 "contactMechPurposeTypeId", "SHIP_ORIG_LOCATION"), UtilMisc.toList("-fromDate")); 89 if (UtilValidate.isNotEmpty(shipLocs)) { 90 shipLocs = EntityUtil.filterByDate(shipLocs); 91 GenericValue purp = EntityUtil.getFirst(shipLocs); 92 if (purp != null) { 93 GenericValue shipFromAddress = delegator.findByPrimaryKey("PostalAddress", 94 UtilMisc.toMap("contactMechId", purp.getString("contactMechId"))); 95 if (shipFromAddress != null) { 96 originationZip = shipFromAddress.getString("postalCode"); 97 } 98 } 99 } 100 } catch (GenericEntityException e) { 101 Debug.logError(e, module); 102 } 103 } 104 if (UtilValidate.isEmpty(originationZip)) { 105 return ServiceUtil.returnError("Unable to determine the origination ZIP"); 106 } 107 108 String destinationZip = null; 110 String shippingContactMechId = (String ) context.get("shippingContactMechId"); 111 if (UtilValidate.isNotEmpty(shippingContactMechId)) { 112 try { 113 GenericValue shipToAddress = delegator.findByPrimaryKey("PostalAddress", UtilMisc.toMap("contactMechId", shippingContactMechId)); 114 if (shipToAddress != null) { 115 destinationZip = shipToAddress.getString("postalCode"); 116 } 117 } catch (GenericEntityException e) { 118 Debug.logError(e, module); 119 } 120 } 121 if (UtilValidate.isEmpty(destinationZip)) { 122 return ServiceUtil.returnError("Unable to determine the destination ZIP"); 123 } 124 125 String serviceCode = null; 127 try { 128 GenericValue carrierShipmentMethod = delegator.findByPrimaryKey("CarrierShipmentMethod", 129 UtilMisc.toMap("shipmentMethodTypeId", (String ) context.get("shipmentMethodTypeId"), 130 "partyId", (String ) context.get("carrierPartyId"), "roleTypeId", (String ) context.get("carrierRoleTypeId"))); 131 if (carrierShipmentMethod != null) { 132 serviceCode = carrierShipmentMethod.getString("carrierServiceCode"); 133 } 134 } catch (GenericEntityException e) { 135 Debug.logError(e, module); 136 } 137 if (UtilValidate.isEmpty(serviceCode)) { 138 return ServiceUtil.returnError("Unable to determine the service code"); 139 } 140 141 Document requestDocument = createUspsRequestDocument("RateRequest"); 143 144 double maxWeight = 70; 146 String maxWeightStr = UtilProperties.getPropertyValue((String ) context.get("serviceConfigProps"), 147 "shipment.usps.max.estimate.weight", "70"); 148 try { 149 maxWeight = Double.parseDouble(maxWeightStr); 150 } catch (NumberFormatException e) { 151 Debug.logWarning("Error parsing max estimate weight string [" + maxWeightStr + "], using default instead", module); 152 maxWeight = 70; 153 } 154 155 List shippableItemInfo = (List ) context.get("shippableItemInfo"); 156 List packages = getPackageSplit(shippableItemInfo, maxWeight); 157 for (ListIterator li = packages.listIterator(); li.hasNext();) { 159 Map packageMap = (Map ) li.next(); 160 161 double packageWeight = calcPackageWeight(packageMap, shippableItemInfo, 0); 162 if (packageWeight == 0) { 163 continue; 164 } 165 166 Element packageElement = UtilXml.addChildElement(requestDocument.getDocumentElement(), "Package", requestDocument); 167 packageElement.setAttribute("ID", String.valueOf(li.nextIndex() - 1)); 169 UtilXml.addChildElementValue(packageElement, "Service", serviceCode, requestDocument); 170 UtilXml.addChildElementValue(packageElement, "ZipOrigination", originationZip, requestDocument); 171 UtilXml.addChildElementValue(packageElement, "ZipDestination", destinationZip, requestDocument); 172 173 double weightPounds = Math.floor(packageWeight); 174 UtilXml.addChildElementValue(packageElement, "Pounds", String.valueOf(weightPounds), requestDocument); 175 176 double weightOunces = Math.ceil(packageWeight % weightPounds * 16); 177 UtilXml.addChildElementValue(packageElement, "Ounces", String.valueOf(weightOunces), requestDocument); 178 179 UtilXml.addChildElementValue(packageElement, "Container", "None", requestDocument); 181 UtilXml.addChildElementValue(packageElement, "Size", "Regular", requestDocument); 182 UtilXml.addChildElementValue(packageElement, "Machinable", "False", requestDocument); 183 } 184 185 Document responseDocument = null; 187 try { 188 responseDocument = sendUspsRequest("Rate", requestDocument); 189 } catch (UspsRequestException e) { 190 Debug.log(e, module); 191 return ServiceUtil.returnError("Error sending request for USPS Domestic Rate Calculation service: " + e.getMessage()); 192 } 193 194 List rates = UtilXml.childElementList(responseDocument.getDocumentElement(), "Package"); 195 if (UtilValidate.isEmpty(rates)) { 196 return ServiceUtil.returnError("No rate available at this time"); 197 } 198 199 double estimateAmount = 0.00; 200 for (Iterator i = rates.iterator(); i.hasNext();) { 201 Element packageElement = (Element ) i.next(); 202 try { 203 double packageAmount = Double.parseDouble(UtilXml.childElementValue(packageElement, "Postage")); 204 estimateAmount += packageAmount; 205 } catch (NumberFormatException e) { 206 Debug.log(e, module); 207 } 208 } 209 210 Map result = ServiceUtil.returnSuccess(); 211 result.put("shippingEstimateAmount", new Double (estimateAmount)); 212 return result; 213 } 214 215 private static List getPackageSplit(List shippableItemInfo, double maxWeight) { 217 List packages = new LinkedList (); 219 220 if (shippableItemInfo != null) { 221 Iterator sii = shippableItemInfo.iterator(); 222 while (sii.hasNext()) { 223 Map itemInfo = (Map ) sii.next(); 224 long pieces = ((Long ) itemInfo.get("piecesIncluded")).longValue(); 225 double totalQuantity = ((Double ) itemInfo.get("quantity")).doubleValue(); 226 double totalWeight = ((Double ) itemInfo.get("weight")).doubleValue(); 227 String productId = (String ) itemInfo.get("productId"); 228 229 if (pieces < 1) { 231 pieces = 1; } 233 double weight = totalWeight / pieces; 234 235 for (int z = 1; z <= totalQuantity; z++) { 236 double partialQty = pieces > 1 ? 1.000 / pieces : 1; 237 for (long x = 0; x < pieces; x++) { 238 if (weight >= maxWeight) { 239 Map newPackage = new HashMap (); 240 newPackage.put(productId, new Double (partialQty)); 241 packages.add(newPackage); 242 } else if (totalWeight > 0) { 243 if (packages.size() == 0) { 245 packages.add(new HashMap ()); 246 } 247 248 int packageSize = packages.size(); 250 boolean addedToPackage = false; 251 for (int pi = 0; pi < packageSize; pi++) { 252 if (!addedToPackage) { 253 Map packageMap = (Map ) packages.get(pi); 254 double packageWeight = calcPackageWeight(packageMap, shippableItemInfo, weight); 255 if (packageWeight <= maxWeight) { 256 Double qtyD = (Double ) packageMap.get(productId); 257 double qty = qtyD == null ? 0 : qtyD.doubleValue(); 258 packageMap.put(productId, new Double (qty + partialQty)); 259 addedToPackage = true; 260 } 261 } 262 } 263 if (!addedToPackage) { 264 Map packageMap = new HashMap (); 265 packageMap.put(productId, new Double (partialQty)); 266 packages.add(packageMap); 267 } 268 } 269 } 270 } 271 } 272 } 273 return packages; 274 } 275 276 private static double calcPackageWeight(Map packageMap, List shippableItemInfo, double additionalWeight) { 278 double totalWeight = 0.00; 279 Iterator i = packageMap.keySet().iterator(); 280 while (i.hasNext()) { 281 String productId = (String ) i.next(); 282 Map productInfo = getProductItemInfo(shippableItemInfo, productId); 283 double productWeight = ((Double ) productInfo.get("weight")).doubleValue(); 284 double quantity = ((Double ) packageMap.get(productId)).doubleValue(); 285 totalWeight += (productWeight * quantity); 286 } 287 return totalWeight + additionalWeight; 288 } 289 290 private static Map getProductItemInfo(List shippableItemInfo, String productId) { 292 if (shippableItemInfo != null) { 293 Iterator i = shippableItemInfo.iterator(); 294 while (i.hasNext()) { 295 Map testMap = (Map ) i.next(); 296 String id = (String ) testMap.get("productId"); 297 if (productId.equals(id)) { 298 return testMap; 299 } 300 } 301 } 302 return null; 303 } 304 305 325 326 public static Map uspsTrackConfirm(DispatchContext dctx, Map context) { 327 328 Document requestDocument = createUspsRequestDocument("TrackRequest"); 329 330 Element trackingElement = UtilXml.addChildElement(requestDocument.getDocumentElement(), "TrackID", requestDocument); 331 trackingElement.setAttribute("ID", (String ) context.get("trackingId")); 332 333 Document responseDocument = null; 334 try { 335 responseDocument = sendUspsRequest("TrackV2", requestDocument); 336 } catch (UspsRequestException e) { 337 Debug.log(e, module); 338 return ServiceUtil.returnError("Error sending request for USPS Tracking service: " + e.getMessage()); 339 } 340 341 Element trackInfoElement = UtilXml.firstChildElement(responseDocument.getDocumentElement(), "TrackInfo"); 342 if (trackInfoElement == null) { 343 return ServiceUtil.returnError("Incomplete response from USPS Tracking service: no TrackInfo element found"); 344 } 345 346 Map result = ServiceUtil.returnSuccess(); 347 348 result.put("trackingSummary", UtilXml.childElementValue(trackInfoElement, "TrackSummary")); 349 350 List detailElementList = UtilXml.childElementList(trackInfoElement, "TrackDetail"); 351 if (UtilValidate.isNotEmpty(detailElementList)) { 352 List trackingDetailList = new ArrayList (); 353 for (Iterator iter = detailElementList.iterator(); iter.hasNext();) { 354 trackingDetailList.add(UtilXml.elementValue((Element ) iter.next())); 355 } 356 result.put("trackingDetailList", trackingDetailList); 357 } 358 359 return result; 360 } 361 362 395 396 public static Map uspsAddressValidation(DispatchContext dctx, Map context) { 397 398 Document requestDocument = createUspsRequestDocument("AddressValidateRequest"); 399 400 Element addressElement = UtilXml.addChildElement(requestDocument.getDocumentElement(), "Address", requestDocument); 401 addressElement.setAttribute("ID", "0"); 402 403 UtilXml.addChildElementValue(addressElement, "FirmName", (String ) context.get("firmName"), requestDocument); 405 UtilXml.addChildElementValue(addressElement, "Address1", (String ) context.get("address2"), requestDocument); 407 UtilXml.addChildElementValue(addressElement, "Address2", (String ) context.get("address1"), requestDocument); 409 UtilXml.addChildElementValue(addressElement, "City", (String ) context.get("city"), requestDocument); 411 412 UtilXml.addChildElementValue(addressElement, "State", (String ) context.get("state"), requestDocument); 413 UtilXml.addChildElementValue(addressElement, "Zip5", (String ) context.get("zip5"), requestDocument); 414 UtilXml.addChildElementValue(addressElement, "Zip4", (String ) context.get("zip4"), requestDocument); 415 416 Document responseDocument = null; 417 try { 418 responseDocument = sendUspsRequest("Verify", requestDocument); 419 } catch (UspsRequestException e) { 420 Debug.log(e, module); 421 return ServiceUtil.returnError("Error sending request for USPS Address Validation service: " + e.getMessage()); 422 } 423 424 Element respAddressElement = UtilXml.firstChildElement(responseDocument.getDocumentElement(), "Address"); 425 if (respAddressElement == null) { 426 return ServiceUtil.returnError("Incomplete response from USPS Address Validation service: no Address element found"); 427 } 428 429 Element respErrorElement = UtilXml.firstChildElement(respAddressElement, "Error"); 430 if (respErrorElement != null) { 431 return ServiceUtil.returnError("The following error was returned by the USPS Address Validation service: " + 432 UtilXml.childElementValue(respErrorElement, "Description")); 433 } 434 435 Map result = ServiceUtil.returnSuccess(); 436 437 String firmName = UtilXml.childElementValue(respAddressElement, "FirmName"); 439 if (UtilValidate.isNotEmpty(firmName)) { 440 result.put("firmName", firmName); 441 } 442 443 String address1 = UtilXml.childElementValue(respAddressElement, "Address1"); 445 if (UtilValidate.isNotEmpty(address1)) { 446 result.put("address2", address1); 447 } 448 449 result.put("address1", UtilXml.childElementValue(respAddressElement, "Address2")); 450 result.put("city", UtilXml.childElementValue(respAddressElement, "City")); 451 result.put("state", UtilXml.childElementValue(respAddressElement, "State")); 452 result.put("zip5", UtilXml.childElementValue(respAddressElement, "Zip5")); 453 result.put("zip4", UtilXml.childElementValue(respAddressElement, "Zip4")); 454 455 return result; 456 } 457 458 479 480 public static Map uspsCityStateLookup(DispatchContext dctx, Map context) { 481 482 Document requestDocument = createUspsRequestDocument("CityStateLookupRequest"); 483 484 Element zipCodeElement = UtilXml.addChildElement(requestDocument.getDocumentElement(), "ZipCode", requestDocument); 485 zipCodeElement.setAttribute("ID", "0"); 486 487 String zipCode = ((String ) context.get("zip5")).trim(); 489 UtilXml.addChildElementValue(zipCodeElement, "Zip5", zipCode, requestDocument); 491 492 Document responseDocument = null; 493 try { 494 responseDocument = sendUspsRequest("CityStateLookup", requestDocument); 495 } catch (UspsRequestException e) { 496 Debug.log(e, module); 497 return ServiceUtil.returnError("Error sending request for USPS City/State Lookup service: " + e.getMessage()); 498 } 499 500 Element respAddressElement = UtilXml.firstChildElement(responseDocument.getDocumentElement(), "ZipCode"); 501 if (respAddressElement == null) { 502 return ServiceUtil.returnError("Incomplete response from USPS City/State Lookup service: no ZipCode element found"); 503 } 504 505 Element respErrorElement = UtilXml.firstChildElement(respAddressElement, "Error"); 506 if (respErrorElement != null) { 507 return ServiceUtil.returnError("The following error was returned by the USPS City/State Lookup service: " + 508 UtilXml.childElementValue(respErrorElement, "Description")); 509 } 510 511 Map result = ServiceUtil.returnSuccess(); 512 513 String city = UtilXml.childElementValue(respAddressElement, "City"); 514 if (UtilValidate.isEmpty(city)) { 515 return ServiceUtil.returnError("Incomplete response from USPS City/State Lookup service: no City element found"); 516 } 517 result.put("city", city); 518 519 String state = UtilXml.childElementValue(respAddressElement, "State"); 520 if (UtilValidate.isEmpty(state)) { 521 return ServiceUtil.returnError("Incomplete response from USPS City/State Lookup service: no State element found"); 522 } 523 result.put("state", state); 524 525 return result; 526 } 527 528 568 569 public static Map uspsPriorityMailStandard(DispatchContext dctx, Map context) { 570 context.put("serviceType", "PriorityMail"); 571 return uspsServiceStandards(dctx, context); 572 } 573 574 public static Map uspsPackageServicesStandard(DispatchContext dctx, Map context) { 575 context.put("serviceType", "StandardB"); 576 return uspsServiceStandards(dctx, context); 577 } 578 579 private static Map uspsServiceStandards(DispatchContext dctx, Map context) { 580 581 String type = (String ) context.get("serviceType"); 582 if (!type.matches("PriorityMail|StandardB")) { 583 return ServiceUtil.returnError("Unsupported service type: " + type); 584 } 585 586 Document requestDocument = createUspsRequestDocument(type + "Request"); 587 588 UtilXml.addChildElementValue(requestDocument.getDocumentElement(), "OriginZip", 589 (String ) context.get("originZip"), requestDocument); 590 UtilXml.addChildElementValue(requestDocument.getDocumentElement(), "DestinationZip", 591 (String ) context.get("destinationZip"), requestDocument); 592 593 Document responseDocument = null; 594 try { 595 responseDocument = sendUspsRequest(type, requestDocument); 596 } catch (UspsRequestException e) { 597 Debug.log(e, module); 598 return ServiceUtil.returnError("Error sending request for USPS " + type + " Service Standards service: " + 599 e.getMessage()); 600 } 601 602 Map result = ServiceUtil.returnSuccess(); 603 604 String days = UtilXml.childElementValue(responseDocument.getDocumentElement(), "Days"); 605 if (UtilValidate.isEmpty(days)) { 606 return ServiceUtil.returnError("Incomplete response from USPS " + type + " Service Standards service: " + 607 "no Days element found"); 608 } 609 result.put("days", days); 610 611 return result; 612 } 613 614 615 616 660 661 public static Map uspsDomesticRate(DispatchContext dctx, Map context) { 662 663 Document requestDocument = createUspsRequestDocument("RateRequest"); 664 665 Element packageElement = UtilXml.addChildElement(requestDocument.getDocumentElement(), "Package", requestDocument); 666 packageElement.setAttribute("ID", "0"); 667 668 UtilXml.addChildElementValue(packageElement, "Service", (String ) context.get("service"), requestDocument); 669 UtilXml.addChildElementValue(packageElement, "ZipOrigination", (String ) context.get("originZip"), requestDocument); 670 UtilXml.addChildElementValue(packageElement, "ZipDestination", (String ) context.get("destinationZip"), requestDocument); 671 UtilXml.addChildElementValue(packageElement, "Pounds", (String ) context.get("pounds"), requestDocument); 672 UtilXml.addChildElementValue(packageElement, "Ounces", (String ) context.get("ounces"), requestDocument); 673 674 String container = (String ) context.get("container"); 675 if (UtilValidate.isEmpty(container)) { 676 container = "None"; 677 } 678 UtilXml.addChildElementValue(packageElement, "Container", container, requestDocument); 679 680 String size = (String ) context.get("size"); 681 if (UtilValidate.isEmpty(size)) { 682 size = "Regular"; 683 } 684 UtilXml.addChildElementValue(packageElement, "Size", size, requestDocument); 685 686 String machinable = (String ) context.get("machinable"); 687 if (UtilValidate.isEmpty(machinable)) { 688 machinable = "False"; 689 } 690 UtilXml.addChildElementValue(packageElement, "Machinable", machinable, requestDocument); 691 692 Document responseDocument = null; 693 try { 694 responseDocument = sendUspsRequest("Rate", requestDocument); 695 } catch (UspsRequestException e) { 696 Debug.log(e, module); 697 return ServiceUtil.returnError("Error sending request for USPS Domestic Rate Calculation service: " + e.getMessage()); 698 } 699 700 Element respPackageElement = UtilXml.firstChildElement(responseDocument.getDocumentElement(), "Package"); 701 if (respPackageElement == null) { 702 return ServiceUtil.returnError("Incomplete response from USPS Domestic Rate Calculation service: no Package element found"); 703 } 704 705 Element respErrorElement = UtilXml.firstChildElement(respPackageElement, "Error"); 706 if (respErrorElement != null) { 707 return ServiceUtil.returnError("The following error was returned by the USPS Domestic Rate Calculation service: " + 708 UtilXml.childElementValue(respErrorElement, "Description")); 709 } 710 711 Map result = ServiceUtil.returnSuccess(); 712 713 String zone = UtilXml.childElementValue(respPackageElement, "Zone"); 714 if (UtilValidate.isEmpty(zone)) { 715 return ServiceUtil.returnError("Incomplete response from USPS Domestic Rate Calculation service: no Zone element found"); 716 } 717 result.put("zone", zone); 718 719 String postage = UtilXml.childElementValue(respPackageElement, "Postage"); 720 if (UtilValidate.isEmpty(postage)) { 721 return ServiceUtil.returnError("Incomplete response from USPS Domestic Rate Calculation service: no Postage element found"); 722 } 723 result.put("postage", postage); 724 725 String restrictionCodes = UtilXml.childElementValue(respPackageElement, "RestrictionCodes"); 726 if (UtilValidate.isNotEmpty(restrictionCodes)) { 727 result.put("restrictionCodes", restrictionCodes); 728 } 729 730 String restrictionDesc = UtilXml.childElementValue(respPackageElement, "RestrictionDescription"); 731 if (UtilValidate.isNotEmpty(restrictionCodes)) { 732 result.put("restrictionDesc", restrictionDesc); 733 } 734 735 return result; 736 } 737 738 740 741 742 public static Map uspsUpdateShipmentRateInfo(DispatchContext dctx, Map context) { 743 744 GenericDelegator delegator = dctx.getDelegator(); 745 LocalDispatcher dispatcher = dctx.getDispatcher(); 746 747 String shipmentId = (String ) context.get("shipmentId"); 748 String shipmentRouteSegmentId = (String ) context.get("shipmentRouteSegmentId"); 749 750 String srsKeyString = "[" + shipmentId + "," + shipmentRouteSegmentId + "]"; 752 753 try { 754 GenericValue shipmentRouteSegment = delegator.findByPrimaryKey("ShipmentRouteSegment", 755 UtilMisc.toMap("shipmentId", shipmentId, "shipmentRouteSegmentId", shipmentRouteSegmentId)); 756 if (shipmentRouteSegment == null) { 757 return ServiceUtil.returnError("ShipmentRouteSegment " + srsKeyString + " not found"); 758 } 759 760 if (!"USPS".equals(shipmentRouteSegment.getString("carrierPartyId"))) { 762 return ServiceUtil.returnError("The Carrier for ShipmentRouteSegment " + srsKeyString + ", is not USPS"); 763 } 764 765 GenericValue originAddress = shipmentRouteSegment.getRelatedOne("OriginPostalAddress"); 767 if (originAddress == null) { 768 return ServiceUtil.returnError("OriginPostalAddress not found for ShipmentRouteSegment [" + 769 shipmentId + ":" + shipmentRouteSegmentId + "]"); 770 } 771 if (!"USA".equals(originAddress.getString("countryGeoId"))) { 772 return ServiceUtil.returnError("ShipmentRouteSeqment " + srsKeyString + " does not originate from a US address"); 773 } 774 String originZip = originAddress.getString("postalCode"); 775 if (UtilValidate.isEmpty(originZip)) { 776 return ServiceUtil.returnError("ZIP code is missing from the origin postal address" + 777 " (contactMechId " + originAddress.getString("contactMechId") + ")"); 778 } 779 780 GenericValue destinationAddress = shipmentRouteSegment.getRelatedOne("DestPostalAddress"); 782 if (destinationAddress == null) { 783 return ServiceUtil.returnError("DestPostalAddress not found for ShipmentRouteSegment " + srsKeyString); 784 } 785 if (!"USA".equals(destinationAddress.getString("countryGeoId"))) { 786 return ServiceUtil.returnError("ShipmentRouteSeqment " + srsKeyString + " is not destined for a US address"); 787 } 788 String destinationZip = destinationAddress.getString("postalCode"); 789 if (UtilValidate.isEmpty(destinationZip)) { 790 return ServiceUtil.returnError("ZIP code is missing from the destination postal address" + 791 " (contactMechId " + originAddress.getString("contactMechId") + ")"); 792 } 793 794 String shipmentMethodTypeId = shipmentRouteSegment.getString("shipmentMethodTypeId"); 796 String partyId = shipmentRouteSegment.getString("carrierPartyId"); 797 String csmKeystring = "[" + shipmentMethodTypeId + "," + partyId + ",CARRIER]"; 798 799 GenericValue carrierShipmentMethod = delegator.findByPrimaryKey("CarrierShipmentMethod", 800 UtilMisc.toMap("partyId", partyId, "roleTypeId", "CARRIER", "shipmentMethodTypeId", shipmentMethodTypeId)); 801 if (carrierShipmentMethod == null) { 802 return ServiceUtil.returnError("CarrierShipmentMethod " + csmKeystring + 803 " not found for ShipmentRouteSegment " + srsKeyString); 804 } 805 String serviceType = carrierShipmentMethod.getString("carrierServiceCode"); 806 if (UtilValidate.isEmpty(serviceType)) { 807 return ServiceUtil.returnError("carrierServiceCode not found for CarrierShipmentMethod" + csmKeystring); 808 } 809 810 List shipmentPackageRouteSegList = shipmentRouteSegment.getRelated("ShipmentPackageRouteSeg", null, 812 UtilMisc.toList("+shipmentPackageSeqId")); 813 if (UtilValidate.isEmpty(shipmentPackageRouteSegList)) { 814 return ServiceUtil.returnError("No packages found for ShipmentRouteSegment " + srsKeyString); 815 } 816 817 double actualTransportCost = 0; 818 819 String carrierDeliveryZone = null; 820 String carrierRestrictionCodes = null; 821 String carrierRestrictionDesc = null; 822 823 for (Iterator i = shipmentPackageRouteSegList.iterator(); i.hasNext();) { 825 826 GenericValue shipmentPackageRouteSeg = (GenericValue) i.next(); 827 String sprsKeyString = "[" + shipmentPackageRouteSeg.getString("shipmentId") + "," + 828 shipmentPackageRouteSeg.getString("shipmentPackageSeqId") + "," + 829 shipmentPackageRouteSeg.getString("shipmentRouteSegmentId") + "]"; 830 831 Document requestDocument = createUspsRequestDocument("RateRequest"); 832 833 Element packageElement = UtilXml.addChildElement(requestDocument.getDocumentElement(), "Package", requestDocument); 834 packageElement.setAttribute("ID", "0"); 835 836 UtilXml.addChildElementValue(packageElement, "Service", serviceType, requestDocument); 837 UtilXml.addChildElementValue(packageElement, "ZipOrigination", originZip, requestDocument); 838 UtilXml.addChildElementValue(packageElement, "ZipDestination", destinationZip, requestDocument); 839 840 GenericValue shipmentPackage = null; 841 shipmentPackage = shipmentPackageRouteSeg.getRelatedOne("ShipmentPackage"); 842 843 String spKeyString = "[" + shipmentPackage.getString("shipmentId") + "," + 844 shipmentPackage.getString("shipmentPackageSeqId") + "]"; 845 846 String weightStr = shipmentPackage.getString("weight"); 848 if (UtilValidate.isEmpty(weightStr)) { 849 return ServiceUtil.returnError("weight not found for ShipmentPackage " + spKeyString); 850 } 851 852 double weight = 0; 853 try { 854 weight = Double.parseDouble(weightStr); 855 } catch (NumberFormatException nfe) { 856 nfe.printStackTrace(); } 858 859 String weightUomId = shipmentPackage.getString("weightUomId"); 860 if (UtilValidate.isEmpty(weightUomId)) { 861 weightUomId = "WT_lb"; } 863 if (!"WT_lb".equals(weightUomId)) { 864 Map result = new HashMap (); 866 try { 867 result = dispatcher.runSync("convertUom", UtilMisc.toMap("uomId", weightUomId, "uomIdTo", "WT_lb", "originalValue", new Double (weight))); 868 } catch (GenericServiceException ex) { 869 return ServiceUtil.returnError(ex.getMessage()); 870 } 871 872 if (result.get(ModelService.RESPONSE_MESSAGE).equals(ModelService.RESPOND_SUCCESS)) { 873 weight *= ((Double ) result.get("convertedValue")).doubleValue(); 874 } else { 875 return ServiceUtil.returnError("Unsupported weightUom [" + weightUomId + "] for ShipmentPackage " + 876 spKeyString + ", could not find a conversion factor for WT_lb"); 877 } 878 879 } 880 881 double weightPounds = Math.floor(weight); 882 double weightOunces = Math.ceil(weight % weightPounds * 16); 883 884 DecimalFormat df = new DecimalFormat ("#"); 885 UtilXml.addChildElementValue(packageElement, "Pounds", df.format(weightPounds), requestDocument); 886 UtilXml.addChildElementValue(packageElement, "Ounces", df.format(weightOunces), requestDocument); 887 888 GenericValue carrierShipmentBoxType = null; 890 List carrierShipmentBoxTypes = null; 891 carrierShipmentBoxTypes = shipmentPackage.getRelated("CarrierShipmentBoxType", 892 UtilMisc.toMap("partyId", "USPS"), null); 893 894 if (carrierShipmentBoxTypes.size() > 0) { 895 carrierShipmentBoxType = (GenericValue) carrierShipmentBoxTypes.get(0); 896 } 897 898 if (carrierShipmentBoxType != null && 899 UtilValidate.isNotEmpty(carrierShipmentBoxType.getString("packagingTypeCode"))) { 900 UtilXml.addChildElementValue(packageElement, "Container", 901 carrierShipmentBoxType.getString("packagingTypeCode"), requestDocument); 902 } else { 903 UtilXml.addChildElementValue(packageElement, "Container", "None", requestDocument); 905 } 906 907 if (carrierShipmentBoxType != null && UtilValidate.isNotEmpty("oversizeCode")) { 909 UtilXml.addChildElementValue(packageElement, "Size", 910 carrierShipmentBoxType.getString("oversizeCode"), requestDocument); 911 } else { 912 UtilXml.addChildElementValue(packageElement, "Size", "Regular", requestDocument); 914 } 915 916 UtilXml.addChildElementValue(packageElement, "Machinable", "False", requestDocument); 918 919 Document responseDocument = null; 920 try { 921 responseDocument = sendUspsRequest("Rate", requestDocument); 922 } catch (UspsRequestException e) { 923 Debug.log(e, module); 924 return ServiceUtil.returnError("Error sending request for USPS Domestic Rate Calculation service: " + 925 e.getMessage()); 926 } 927 928 Element respPackageElement = UtilXml.firstChildElement(responseDocument.getDocumentElement(), "Package"); 929 if (respPackageElement == null) { 930 return ServiceUtil.returnError("Incomplete response from USPS Domestic Rate Calculation service: " + 931 "no Package element found"); 932 } 933 934 Element respErrorElement = UtilXml.firstChildElement(respPackageElement, "Error"); 935 if (respErrorElement != null) { 936 return ServiceUtil.returnError("The following error was returned by the USPS Domestic Rate Calculation " + 937 "service for ShipmentPackage " + spKeyString + ": " + 938 UtilXml.childElementValue(respErrorElement, "Description")); 939 } 940 941 String postageString = UtilXml.childElementValue(respPackageElement, "Postage"); 943 if (UtilValidate.isEmpty(postageString)) { 944 return ServiceUtil.returnError("Incomplete response from USPS Domestic Rate Calculation service: " + 945 "missing or empty Postage element"); 946 } 947 948 double postage = 0; 949 try { 950 postage = Double.parseDouble(postageString); 951 } catch (NumberFormatException nfe) { 952 nfe.printStackTrace(); } 954 actualTransportCost += postage; 955 956 shipmentPackageRouteSeg.setString("packageTransportCost", postageString); 957 shipmentPackageRouteSeg.store(); 958 959 if (!i.hasNext()) { 961 carrierDeliveryZone = UtilXml.childElementValue(respPackageElement, "Zone"); 962 carrierRestrictionCodes = UtilXml.childElementValue(respPackageElement, "RestrictionCodes"); 963 carrierRestrictionDesc = UtilXml.childElementValue(respPackageElement, "RestrictionDescription"); 964 } 965 } 966 967 shipmentRouteSegment.set("carrierDeliveryZone", carrierDeliveryZone); 969 shipmentRouteSegment.set("carrierRestrictionCodes", carrierRestrictionCodes); 970 shipmentRouteSegment.set("carrierRestrictionDesc", carrierRestrictionDesc); 971 shipmentRouteSegment.setString("actualTransportCost", String.valueOf(actualTransportCost)); 972 shipmentRouteSegment.store(); 973 974 } catch (GenericEntityException gee) { 975 Debug.log(gee, module); 976 return ServiceUtil.returnError("Error reading or writing shipment data for the USPS " + 977 "Domestic Rate Calculation service: " + gee.getMessage()); 978 } 979 980 return ServiceUtil.returnSuccess(); 981 } 982 983 1017 1018 public static Map uspsDeliveryConfirmation(DispatchContext dctx, Map context) { 1019 1020 GenericDelegator delegator = dctx.getDelegator(); 1021 1022 String shipmentId = (String ) context.get("shipmentId"); 1023 String shipmentRouteSegmentId = (String ) context.get("shipmentRouteSegmentId"); 1024 1025 String srsKeyString = "[" + shipmentId + "," + shipmentRouteSegmentId + "]"; 1027 1028 try { 1029 GenericValue shipment = delegator.findByPrimaryKey("Shipment", UtilMisc.toMap("shipmentId", shipmentId)); 1030 if (shipment == null) { 1031 return ServiceUtil.returnError("Shipment not found with ID " + shipmentId); 1032 } 1033 1034 GenericValue shipmentRouteSegment = delegator.findByPrimaryKey("ShipmentRouteSegment", 1035 UtilMisc.toMap("shipmentId", shipmentId, "shipmentRouteSegmentId", shipmentRouteSegmentId)); 1036 if (shipmentRouteSegment == null) { 1037 return ServiceUtil.returnError("ShipmentRouteSegment not found with shipmentId " + shipmentId + 1038 " and shipmentRouteSegmentId " + shipmentRouteSegmentId); 1039 } 1040 1041 if (!"USPS".equals(shipmentRouteSegment.getString("carrierPartyId"))) { 1043 return ServiceUtil.returnError("The Carrier for ShipmentRouteSegment " + srsKeyString + ", is not USPS"); 1044 } 1045 1046 GenericValue originAddress = shipmentRouteSegment.getRelatedOne("OriginPostalAddress"); 1048 if (originAddress == null) { 1049 return ServiceUtil.returnError("OriginPostalAddress not found for ShipmentRouteSegment [" + 1050 shipmentId + ":" + shipmentRouteSegmentId + "]"); 1051 } 1052 if (!"USA".equals(originAddress.getString("countryGeoId"))) { 1053 return ServiceUtil.returnError("ShipmentRouteSeqment " + srsKeyString + " does not originate from a US address"); 1054 } 1055 1056 GenericValue destinationAddress = shipmentRouteSegment.getRelatedOne("DestPostalAddress"); 1058 if (destinationAddress == null) { 1059 return ServiceUtil.returnError("DestPostalAddress not found for ShipmentRouteSegment " + srsKeyString); 1060 } 1061 if (!"USA".equals(destinationAddress.getString("countryGeoId"))) { 1062 return ServiceUtil.returnError("ShipmentRouteSeqment " + srsKeyString + " is not destined for a US address"); 1063 } 1064 1065 String shipmentMethodTypeId = shipmentRouteSegment.getString("shipmentMethodTypeId"); 1067 String partyId = shipmentRouteSegment.getString("carrierPartyId"); 1068 1069 String csmKeystring = "[" + shipmentMethodTypeId + "," + partyId + ",CARRIER]"; 1070 1071 GenericValue carrierShipmentMethod = delegator.findByPrimaryKey("CarrierShipmentMethod", 1072 UtilMisc.toMap("partyId", partyId, "roleTypeId", "CARRIER", "shipmentMethodTypeId", shipmentMethodTypeId)); 1073 if (carrierShipmentMethod == null) { 1074 return ServiceUtil.returnError("CarrierShipmentMethod " + csmKeystring + 1075 " not found for ShipmentRouteSegment " + srsKeyString); 1076 } 1077 String serviceType = carrierShipmentMethod.getString("carrierServiceCode"); 1078 if (UtilValidate.isEmpty(serviceType)) { 1079 return ServiceUtil.returnError("carrierServiceCode not found for CarrierShipmentMethod" + csmKeystring); 1080 } 1081 1082 List shipmentPackageRouteSegList = shipmentRouteSegment.getRelated("ShipmentPackageRouteSeg", null, 1084 UtilMisc.toList("+shipmentPackageSeqId")); 1085 if (UtilValidate.isEmpty(shipmentPackageRouteSegList)) { 1086 return ServiceUtil.returnError("No packages found for ShipmentRouteSegment " + srsKeyString); 1087 } 1088 1089 for (Iterator i = shipmentPackageRouteSegList.iterator(); i.hasNext();) { 1090 1091 Document requestDocument = createUspsRequestDocument("DeliveryConfirmationV2.0Request"); 1092 Element requestElement = requestDocument.getDocumentElement(); 1093 1094 UtilXml.addChildElementValue(requestElement, "Option", "3", requestDocument); 1095 UtilXml.addChildElement(requestElement, "ImageParameters", requestDocument); 1096 1097 if (UtilValidate.isNotEmpty(originAddress.getString("attnName"))) { 1099 UtilXml.addChildElementValue(requestElement, "FromName", originAddress.getString("attnName"), requestDocument); 1100 UtilXml.addChildElementValue(requestElement, "FromFirm", originAddress.getString("toName"), requestDocument); 1101 } else { 1102 UtilXml.addChildElementValue(requestElement, "FromName", originAddress.getString("toName"), requestDocument); 1103 } 1104 UtilXml.addChildElementValue(requestElement, "FromAddress1", originAddress.getString("address2"), requestDocument); 1106 UtilXml.addChildElementValue(requestElement, "FromAddress2", originAddress.getString("address1"), requestDocument); 1107 UtilXml.addChildElementValue(requestElement, "FromCity", originAddress.getString("city"), requestDocument); 1108 UtilXml.addChildElementValue(requestElement, "FromState", originAddress.getString("stateProvinceGeoId"), requestDocument); 1109 UtilXml.addChildElementValue(requestElement, "FromZip5", originAddress.getString("postalCode"), requestDocument); 1110 UtilXml.addChildElement(requestElement, "FromZip4", requestDocument); 1111 1112 if (UtilValidate.isNotEmpty(destinationAddress.getString("attnName"))) { 1114 UtilXml.addChildElementValue(requestElement, "ToName", destinationAddress.getString("attnName"), requestDocument); 1115 UtilXml.addChildElementValue(requestElement, "ToFirm", destinationAddress.getString("toName"), requestDocument); 1116 } else { 1117 UtilXml.addChildElementValue(requestElement, "ToName", destinationAddress.getString("toName"), requestDocument); 1118 } 1119 UtilXml.addChildElementValue(requestElement, "ToAddress1", destinationAddress.getString("address2"), requestDocument); 1121 UtilXml.addChildElementValue(requestElement, "ToAddress2", destinationAddress.getString("address1"), requestDocument); 1122 UtilXml.addChildElementValue(requestElement, "ToCity", destinationAddress.getString("city"), requestDocument); 1123 UtilXml.addChildElementValue(requestElement, "ToState", destinationAddress.getString("stateProvinceGeoId"), requestDocument); 1124 UtilXml.addChildElementValue(requestElement, "ToZip5", destinationAddress.getString("postalCode"), requestDocument); 1125 UtilXml.addChildElement(requestElement, "ToZip4", requestDocument); 1126 1127 GenericValue shipmentPackageRouteSeg = (GenericValue) i.next(); 1128 GenericValue shipmentPackage = shipmentPackageRouteSeg.getRelatedOne("ShipmentPackage"); 1129 String spKeyString = "[" + shipmentPackage.getString("shipmentId") + "," + 1130 shipmentPackage.getString("shipmentPackageSeqId") + "]"; 1131 1132 String weightStr = shipmentPackage.getString("weight"); 1134 if (UtilValidate.isEmpty(weightStr)) { 1135 return ServiceUtil.returnError("weight not found for ShipmentPackage " + spKeyString); 1136 } 1137 1138 double weight = 0; 1139 try { 1140 weight = Double.parseDouble(weightStr); 1141 } catch (NumberFormatException nfe) { 1142 nfe.printStackTrace(); } 1144 1145 String weightUomId = shipmentPackage.getString("weightUomId"); 1146 if (UtilValidate.isEmpty(weightUomId)) { 1147 weightUomId = "WT_lb"; 1149 } 1150 if (!"WT_oz".equals(weightUomId)) { 1151 GenericValue uomConversion = delegator.findByPrimaryKey("UomConversion", 1153 UtilMisc.toMap("uomId", weightUomId, "uomIdTo", "WT_oz")); 1154 if (uomConversion == null || UtilValidate.isEmpty(uomConversion.getString("conversionFactor"))) { 1155 return ServiceUtil.returnError("Unsupported weightUom [" + weightUomId + "] for ShipmentPackage " + 1156 spKeyString + ", could not find a conversion factor for WT_oz"); 1157 } 1158 weight *= uomConversion.getDouble("conversionFactor").doubleValue(); 1159 } 1160 1161 DecimalFormat df = new DecimalFormat ("#"); 1162 UtilXml.addChildElementValue(requestElement, "WeightInOunces", df.format(Math.ceil(weight)), requestDocument); 1163 1164 UtilXml.addChildElementValue(requestElement, "ServiceType", serviceType, requestDocument); 1165 UtilXml.addChildElementValue(requestElement, "ImageType", "TIF", requestDocument); 1166 UtilXml.addChildElementValue(requestElement, "AddressServiceRequested", "True", requestDocument); 1167 1168 Document responseDocument = null; 1169 try { 1170 responseDocument = sendUspsRequest("DeliveryConfirmationV2", requestDocument); 1171 } catch (UspsRequestException e) { 1172 Debug.log(e, module); 1173 return ServiceUtil.returnError("Error sending request for USPS Delivery Confirmation service: " + 1174 e.getMessage()); 1175 } 1176 Element responseElement = responseDocument.getDocumentElement(); 1177 1178 Element respErrorElement = UtilXml.firstChildElement(responseElement, "Error"); 1179 if (respErrorElement != null) { 1180 return ServiceUtil.returnError("The following error was returned by the USPS Delivery Confirmation " + 1181 "service for ShipmentPackage " + spKeyString + ": " + 1182 UtilXml.childElementValue(respErrorElement, "Description")); 1183 } 1184 1185 String labelImageString = UtilXml.childElementValue(responseElement, "DeliveryConfirmationLabel"); 1186 if (UtilValidate.isEmpty(labelImageString)) { 1187 return ServiceUtil.returnError("Incomplete response from the USPS Delivery Confirmation service: " + 1188 "missing or empty DeliveryConfirmationLabel element"); 1189 } 1190 shipmentPackageRouteSeg.setBytes("labelImage", Base64.base64Decode(labelImageString.getBytes())); 1191 String trackingCode = UtilXml.childElementValue(responseElement, "DeliveryConfirmationNumber"); 1192 if (UtilValidate.isEmpty(trackingCode)) { 1193 return ServiceUtil.returnError("Incomplete response from the USPS Delivery Confirmation service: " + 1194 "missing or empty DeliveryConfirmationNumber element"); 1195 } 1196 shipmentPackageRouteSeg.set("trackingCode", trackingCode); 1197 shipmentPackageRouteSeg.store(); 1198 } 1199 1200 } catch (GenericEntityException gee) { 1201 Debug.log(gee, module); 1202 return ServiceUtil.returnError("Error reading or writing shipment data for the USPS " + 1203 "Delivery Confirmation service: " + gee.getMessage()); 1204 } 1205 1206 return ServiceUtil.returnSuccess(); 1207 } 1208 1209 1210 1211 public static Map uspsDumpShipmentLabelImages(DispatchContext dctx, Map context) { 1213 1214 GenericDelegator delegator = dctx.getDelegator(); 1215 1216 try { 1217 1218 String shipmentId = (String ) context.get("shipmentId"); 1219 String shipmentRouteSegmentId = (String ) context.get("shipmentRouteSegmentId"); 1220 1221 GenericValue shipmentRouteSegment = delegator.findByPrimaryKey("ShipmentRouteSegment", 1222 UtilMisc.toMap("shipmentId", shipmentId, "shipmentRouteSegmentId", shipmentRouteSegmentId)); 1223 1224 List shipmentPackageRouteSegList = shipmentRouteSegment.getRelated("ShipmentPackageRouteSeg", null, 1225 UtilMisc.toList("+shipmentPackageSeqId")); 1226 1227 for (Iterator i = shipmentPackageRouteSegList.iterator(); i.hasNext();) { 1228 GenericValue shipmentPackageRouteSeg = (GenericValue) i.next(); 1229 1230 byte[] labelImageBytes = shipmentPackageRouteSeg.getBytes("labelImage"); 1231 1232 String outFileName = "UspsLabelImage" + shipmentRouteSegment.getString("shipmentId") + "_" + 1233 shipmentRouteSegment.getString("shipmentRouteSegmentId") + "_" + 1234 shipmentPackageRouteSeg.getString("shipmentPackageSeqId") + ".gif"; 1235 1236 FileOutputStream fileOut = new FileOutputStream (outFileName); 1237 fileOut.write(labelImageBytes); 1238 fileOut.flush(); 1239 fileOut.close(); 1240 } 1241 1242 } catch (GenericEntityException e) { 1243 Debug.log(e, module); 1244 return ServiceUtil.returnError(e.getMessage()); 1245 } catch (IOException e) { 1246 Debug.log(e, module); 1247 return ServiceUtil.returnError(e.getMessage()); 1248 } 1249 1250 return ServiceUtil.returnSuccess(); 1251 } 1252 1253 private static Document createUspsRequestDocument(String rootElement) { 1254 1255 Document requestDocument = UtilXml.makeEmptyXmlDocument(rootElement); 1256 1257 Element requestElement = requestDocument.getDocumentElement(); 1258 requestElement.setAttribute("USERID", 1259 UtilProperties.getPropertyValue("shipment.properties", "shipment.usps.access.userid")); 1260 requestElement.setAttribute("PASSWORD", 1261 UtilProperties.getPropertyValue("shipment.properties", "shipment.usps.access.password")); 1262 1263 return requestDocument; 1264 } 1265 1266 private static Document sendUspsRequest(String requestType, Document requestDocument) throws UspsRequestException { 1267 String conUrl = UtilProperties.getPropertyValue("shipment.properties", "shipment.usps.connect.url"); 1268 if (UtilValidate.isEmpty(conUrl)) { 1269 throw new UspsRequestException("Connection URL not specified; please check your configuration"); 1270 } 1271 1272 OutputStream os = new ByteArrayOutputStream (); 1273 1274 OutputFormat format = new OutputFormat(requestDocument); 1275 format.setOmitDocumentType(true); 1276 format.setOmitXMLDeclaration(true); 1277 format.setIndenting(false); 1278 1279 XMLSerializer serializer = new XMLSerializer(os, format); 1280 try { 1281 serializer.asDOMSerializer(); 1282 serializer.serialize(requestDocument.getDocumentElement()); 1283 } catch (IOException e) { 1284 throw new UspsRequestException("Error serializing requestDocument: " + e.getMessage()); 1285 } 1286 1287 String xmlString = os.toString(); 1288 1289 Debug.logInfo("USPS XML request string: " + xmlString, module); 1290 1291 String timeOutStr = UtilProperties.getPropertyValue("shipment.properties", "shipment.usps.connect.timeout", "60"); 1292 int timeout = 60; 1293 try { 1294 timeout = Integer.parseInt(timeOutStr); 1295 } catch (NumberFormatException e) { 1296 Debug.logError(e, "Unable to set timeout to " + timeOutStr + " using default " + timeout); 1297 } 1298 1299 HttpClient http = new HttpClient(conUrl); 1300 http.setTimeout(timeout * 1000); 1301 http.setParameter("API", requestType); 1302 http.setParameter("XML", xmlString); 1303 1304 String responseString = null; 1305 try { 1306 responseString = http.post(); 1307 } catch (HttpClientException e) { 1308 throw new UspsRequestException("Problem connecting with USPS server", e); 1309 } 1310 1311 Debug.logInfo("USPS response: " + responseString, module); 1312 1313 Document responseDocument = null; 1314 try { 1315 responseDocument = UtilXml.readXmlDocument(responseString, false); 1316 } catch (SAXException se) { 1317 throw new UspsRequestException("Error reading request Document from a String: " + se.getMessage()); 1318 } catch (ParserConfigurationException pce) { 1319 throw new UspsRequestException("Error reading request Document from a String: " + pce.getMessage()); 1320 } catch (IOException xmlReadException) { 1321 throw new UspsRequestException("Error reading request Document from a String: " + xmlReadException.getMessage()); 1322 } 1323 1324 Element responseElement = responseDocument.getDocumentElement(); 1327 if ("Error".equals(responseElement.getNodeName())) { 1328 throw new UspsRequestException(UtilXml.childElementValue(responseElement, "Description")); 1329 } 1330 1331 return responseDocument; 1332 } 1333 1334} 1335 1336class UspsRequestException extends GeneralException { 1337 UspsRequestException() { 1338 super(); 1339 } 1340 1341 UspsRequestException(String msg) { 1342 super(msg); 1343 } 1344 1345 UspsRequestException(Throwable t) { 1346 super(t); 1347 } 1348 1349 UspsRequestException(String msg, Throwable t) { 1350 super(msg, t); 1351 } 1352} 1353 | Popular Tags |