涉及接口 hotel.order.create、hotel.order.detail
demo语言: Java
开发环境:
前端 jQuery类库、layui、 bootstrap
后端 jdk1.7以上、 tomcat8以上、 springmvc + spring + mybatis
下单前rp相关数据校验之后创建订单,本地保存订单数据,之后调用订单详情接口回显订单数据
注意
1. 艺龙下单接口的超时时间为30s,建议代理也设置为30s,不然如果这边返回时间较长,代理接收为null
2. 代理不能通过接收结果为null或空字符串判断下单失败,应该根据返回码是否错误判断
3. 如果返回null,则应该隔30秒左右重新用相同参数下单,最多重试5次即可,如果之前下单成功,则返回之前的订单。
请求url
下单页面,选择rateplan和房间数量、填写联系人,手机号等参数
var createUrl = "/api/order/createOrder"; // 下单请求controller var createReq = { "userName": $('#inputUser').val(), "arrivalDate": arrivalDate, "departureDate": $("#inputDepartureDate").val(), "hotelId": $("#inputHotelId").val(), "roomTypeId": $("#inputRoomTypeId").val(), "ratePlanId": $("#inputRatePlanId").val(), "earliestArrivalTime": (nextHour.substring(0,1) == "0" ? arrivalNextDate: arrivalDate) + " " + nextHour + ":00", "latestArrivalTime": ($('#btnArrivalTime').attr("value").substring(0,1) == "0" ? arrivalNextDate: arrivalDate) + " " + $('#btnArrivalTime').attr("value"), "paymentType": $('#inputPaymentType').val(), "numberOfRooms": $("#btnRoomNum").attr("value"), "currencyCode": $('#inputTotalRate').attr("currencyCode"), "totalPrice": parseFloat($('#inputTotalRate').val()), "needInvoice": needInvoice, "invoice": invoice, "customerType": $('#inputCustomerType').val(), "customers": customerString, "contactName": $('#inputContactName').val(), "contactPhone": $('#inputContactPhone').val() };
js请求后端
提交后端后返回下单结果,如果下单成功,调整到订单详情页面,如果显示失败原因
// 请求下单参数 var createResult = ajaxCommonForJson(createUrl, "POST", createReq); // 处理下单结果 if (createResult != null) { if (createResult.success) { window.location.href = '/view/order/detail?user=' + $('#inputUser').val() + '&orderId=' + createResult.orderId; } else { alert(createResult.errorMessage); } }
创建订单
后端通过http协议调用艺龙的hotel.order.create接口
public class HotelOrderCreateApi { private static double version = 1.50; private static EnumLocal locale = EnumLocal.zh_CN; private static boolean isHttps = true; // 测试环境换为false ... ... /** * 通过http工具类调用艺龙接口,将前端参数拼接为URL */ public OrderCreateResult createOrder(CreateOrderCondition condition, String userName, String appKey, String secretKey) { OrderCreateResult result = new OrderCreateResult(); String url = ""; String responseData = ""; try{ //产生签名 Long epoch = System.currentTimeMillis()/1000; if (condition.getCreditCard() != null) { condition.getCreditCard().setNumber(CipherUtil.desEncrypt(epoch.toString() +"#"+condition.getCreditCard().getNumber(), appKey.substring(appKey.length()-8))); } BaseRequest<CreateOrderCondition> req = new BaseRequest<CreateOrderCondition>(); req.Version = version; req.Local = locale; req.Request = condition; //请求参数转换为Json字符串 String str = JsonUtil.entity2Json(req); String sig = Tool.md5(epoch + Tool.md5(str + appKey) + secretKey); //产生请求链接 url = "http"+(this.isHttps ? "s": "")+ "://" + serverHost + "/rest?format=json&method=hotel.order.create"; url += "&user="+ userName +"×tamp="; url += epoch; url += "&signature="; url += sig; url += "&data=" + Tool.encodeUri(str); log.info(url); //发送请求 responseData = HttpUtil.Send("GET", url, "", "application/json"); //返回值处理 result = JsonUtil.jsonToObject(responseData, OrderCreateResult.class); } catch (Exception e) { log.info("[HotelOrderCreateApi] 异常: " + e); log.info("发送的url: " + url); log.info("返回值: " + responseData); } return result; } ... ... }
保存订单信息
下单成功后,将订单保存到数据库中, 数据库表见sdk
// 创建数据库插入对象 OrderDo orderDo = new OrderDo(); orderDo.setOrderId(createResult.getResult().getOrderId()); orderDo.setAffiliateConfirmationId(affiliateConfirmationId); orderDo.setUserId(request.getUserName()); orderDo.setBookingTime(new Date()); orderDo.setHotelId(request.getHotelId()); orderDo.setRoomTypeId(request.getRoomTypeId()); orderDo.setRatePlanId(request.getRatePlanId()); ... ... // 需要请求订单详情才能得知的信息 // 获取订单详情 OrderIdCondition orderIdCondition = new OrderIdCondition(); orderIdCondition.setOrderId(createResult.getResult().getOrderId()); try { OrderInfoResult orderInfoResult = hotelOrderDetailApi.Invoke(orderIdCondition); if (orderInfoResult != null) { if (orderInfoResult.getCode().equals("0")) { OrderDetailResult orderDetail = orderInfoResult.getResult(); orderDo.setStatus(orderDetail.getStatus()); orderDo.setShowStatus(orderDetail.getShowStatus()); orderDo.setHotelName(orderDetail.getHotelName()); orderDo.setRoomName(orderDetail.getRoomTypeName()); orderDo.setRatePlanName(orderDetail.getRatePlanName()); orderDo.setCancelTime(orderDetail.getCancelTime()); } else { logger.error(orderInfoResult.getCode()); } } else { logger.error("请求订单详情超时或网络错误"); } } catch (Exception e) { // 捕获异常,以免影响正常的数据库操作 logger.error(e); } ... ... // 调用dao对象将数据存入数据库 try { if (orderDao.addOrder(orderDo) < 1) { logger.error("【数据库操作失败,订单信息:】" + JsonUtil.entity2Json(orderDo)); } } catch (Exception e) { // 捕获异常,以免影响正常的返回操作 logger.error("【数据库操作异常,订单信息:】" + JsonUtil.entity2Json(orderDo)); } ...
订单详情
后端通过http协议调用艺龙的hotel.order.detail接口,进行订单详情回显
public class HotelOrderDetailApi { private static double version = 1.50; private static EnumLocal locale = EnumLocal.zh_CN; private static boolean isHttps = true; // 测试环境换为false ... ... /** * 通过http工具类调用艺龙接口,将前端参数拼接为URL */ public HotelOrderDetailResult getOrderDetail(OrderIdCondition condition, String userName, String appKey, String secretKey) { HotelOrderDetailResult result = new HotelOrderDetailResult(); String url = ""; String responseData = ""; try{ BaseRequest<OrderIdCondition> req = new BaseRequest<OrderIdCondition>(); req.Version = version; req.Local = locale; req.Request = condition; //请求参数转换为Json字符串 String str = JsonUtil.entity2Json(req); //产生签名 long epoch = System.currentTimeMillis()/1000; String sig = Tool.md5(epoch + Tool.md5(str + appKey) + secretKey); //产生请求链接 url = "http"+(this.isHttps ? "s": "")+ "://" + serverHost + "/rest?format=json&method=hotel.order.detail"; url += "&user="+ userName +"×tamp="; url += epoch; url += "&signature="; url += sig; url += "&data=" + Tool.encodeUri(str); //发送请求 responseData = HttpUtil.Send("GET", url, "", "application/json"); //返回值处理 result = JsonUtil.jsonToObject(responseData, HotelOrderDetailResult.class); } catch (Exception e) { log.info("[HotelOrderDetailNgApi] 异常: " + e); log.info("发送的url: " + url); log.info("返回值: " + responseData); } return result; } ... ... }
效果展示
下单成功后,跳转到订单详情页面
