实战 Spring MVC接入支付宝即时到账 (部分代码)

下面就拿我项目中的部分代码来实践一下.

支付请求

首先,是提交表单

fund.jsp(这里我表单只需要用户填交易金额,其他的订单号之类的全部后台生成)

<form id="deposit"  name= "alipaysubmit" method="post" target="_blank">
    <input type="hidden" name="user.id" value= "<shiro:principal property="id"/>" />
      <table cellpadding="10">
        <tr>
          <td>账户余额</td>
          <td class="balance" id="userBalance"></td>
        </tr>
        <tr>
          <td><i class="zfb"></i></td>
          <td style="padding-bottom: 0px;">亲爱的<span
            class="suppliment_user" id="suppliment_user"></span>,您可以使用支付宝充值积善分,请填写以下信息
          </td>
        </tr>
        <tr>
          <td></td>
          <td><label class="radio inline"> <input type="radio"
              name="amount" id="optionsRadios7" value="option7">自定义<input
              class="compliment_count" name="amount" placeholder="充值金额"></label></td>
        </tr>
        <tr>
          <td></td>
          <td class="warm_prompt">温馨提示:<br />1.采用支付宝充值,1元可以充值1积善值。<br />2.若出现已充值成功的提示,但积善值未到账,可能是网络或者系统繁忙导致,我们会在2个工作日内核对后为您充值<br />3在充值过程中如出现网页错误或打开缓慢时,请先查询支付宝的交易记录,检查扣款是否成功;然后查看积善之家账户是否成功充值。若没有确认,请不要反复刷新页面,以防止重复购买。
          </td>
        </tr>
        <tr>
          <td></td>
          <td><button class="affirm-donate" id="rechange">立即充值</button></td>
        </tr>
      </table>
</form>
 

fund.js

$('#rechange').click(function(e) {
    //$this = $("#deposit");
    e.preventDefault();
    var postData = $.toJSON(form2js('deposit', '.', true));
    console.log(postData);
    $.ajax({
      url : $CONFIG.base_url+ "/api/fund_detail/web/deposit",
      type : "POST",
      data : postData,
      contentType : "application/json",
      success : function(data) {
        
        data.total_fee = data.total_fee/100;//测试成功后请删除
        console.log(data);
        console.log(data.sHtmlText);
        $("#deposit").append(data.sHtmlText);//后台会返回一个新的交易表单,并自动提交。所以随便放一个地方就OK
      },
      error : function() {
      }
    });
  });

 

 

下面就是后台代码: 

AlipayController.java(里面的User FundDetail都是我自己定义的实体类,与支付本身没有关系)部分配置在AlipayConfig中,

@RequestMapping(value = "/web/deposit", method = RequestMethod.POST)
  public ResponseEntity<HttpEntity> deposit(@RequestBody FundDetail newfundDetail,Model model) {
    Date date = new Date();
    User user = new User();
    FundDetail fundDetail = new FundDetail();
    Map<String, String> sParaTemp = new HashMap<String, String>();
    // 支付类型
    // 必填,不能修改
    String payment_type = "1";
    // 服务器异步通知页面路径
    // 需http://格式的完整路径,不能加?id=123这类自定义参数
    String notify_url = "http://jishanjia.lanbaoo.com/api/alipay/async";
    // 页面跳转同步通知页面路径
    // 需http://格式的完整路径,不能加?id=123这类自定义参数,不能写成http://localhost/
    String return_url = "http://jishanjia.lanbaoo.com/alipay/return_url";
    // 商户订单号.
    // 商户网站订单系统中唯一订单号,必填
    //String out_trade_no = date.getTime() + "";
    // 订单名称
    // 必填
    String subject = "充值积善值";
    // 防钓鱼时间戳
    // 若要使用请调用类文件submit中的query_timestamp函数
    String anti_phishing_key = "";
    // 客户端的IP地址
    // 非局域网的外网IP地址,如:221.0.0.1
    String exter_invoke_ip = "";
    
    user = userService.getUser(newfundDetail.getUser().getId());
    fundDetail.setUser(user);
    fundDetail.setActionType(3);
    fundDetail.setTradeNo(date.getTime()+user.getId().toString());
    fundDetail.setAmount(newfundDetail.getAmount());
    fundDetailService.addFundDetail(fundDetail);
    
    Double total_fee = (double) (fundDetail.getAmount()/100d);//测试结束后删除
    sParaTemp.put("total_fee", total_fee.toString());
    sParaTemp.put("service", "create_direct_pay_by_user");
    sParaTemp.put("partner", AlipayConfig.partner);
    sParaTemp.put("_input_charset", AlipayConfig.input_charset);
    sParaTemp.put("payment_type", payment_type);
    sParaTemp.put("notify_url", notify_url);
    sParaTemp.put("return_url", return_url);
    sParaTemp.put("seller_id", AlipayConfig.seller_id);
    sParaTemp.put("out_trade_no", date.getTime()+user.getId().toString());
    sParaTemp.put("subject", subject);
    sParaTemp.put("anti_phishing_key", anti_phishing_key);
    sParaTemp.put("exter_invoke_ip", exter_invoke_ip);
    sParaTemp.put("key", AlipayConfig.key);
    
    String sHtmlText = AlipaySubmit.buildRequest(sParaTemp,"get","确认");
    
    model.addAttribute("sHtmlText", sHtmlText);
    model.addAttribute("fundDetail", fundDetail);
    
    return new ResponseEntity(model, HttpStatus.OK);
  }

 

 

到此一次交易就成功了

异步通知和跳转:

AlipayNotifyController.java(对应上面的notify_url)

@RequestMapping(value = "/async",method = RequestMethod.GET)
  @ResponseBody
  public String async(HttpServletRequest request){
    Map<String,String> params = new HashMap<String,String>();
    Map requestParams = request.getParameterMap();
    for (Iterator iter = requestParams.keySet().iterator(); iter.hasNext();) {
      String name = (String) iter.next();
      String[] values = (String[]) requestParams.get(name);
      String valueStr = "";
      for (int i = 0; i < values.length; i++) {
        valueStr = (i == values.length - 1) ? valueStr + values[i]: valueStr + values[i] + ",";
      }
      //乱码解决,这段代码在出现乱码时使用。如果mysign和sign不相等也可以使用这段代码转化
      //valueStr = new String(valueStr.getBytes("ISO-8859-1"), "gbk");
      params.put(name, valueStr);
    }
    String tradeNo = request.getParameter("out_trade_no");
    String tradeStatus = request.getParameter("trade_status");
    //String notifyId = request.getParameter("notify_id");
    if(AlipayNotify.verify(params)){//验证成功
      if(tradeStatus.equals("TRADE_FINISHED") || tradeStatus.equals("TRADE_SUCCESS")) {
        FundDetail fundDetail = new FundDetail();
        fundDetail = fundDetailService.getFundDetail(tradeNo);
        fundDetail.setActionType(1);
        fundDetailService.updateFundDetail(fundDetail);
        User user = new User();
        user = userService.getUser(fundDetail.getUser().getId());
        user.setFund(user.getFund() + fundDetail.getAmount());
        userService.updateUser(user);
        System.out.println(">>>>>充值成功" + tradeNo);
      }
      return "success";
    }else{//验证失败
      return "fail";
    }
  }

 

return_url跟notify_url差不多。在return_url控制交易成功后的跳转页面就可以了.

至此,一次支付宝即时到账交易就完成了

posted @ 2016-09-10 09:44  JokerJason  阅读(1367)  评论(0编辑  收藏  举报

It's not who you are underneath, it's what you do that defines you

Brick walls are there for a reason :they let us prove how badly we want things