支付宝使用即时到账接口收款

时间:2022-05-27 13:15:46

1.首先需要有支付宝企业账号


2.账号完成认证

支付宝使用即时到账接口收款

3.下载即时到账接口DEMO

http://aopsdkdownload.cn-hangzhou.alipay-pub.aliyun-inc.com/demo/alipaydirect.zip?spm=a219a.7629140.0.0.jBjnRi&file=alipaydirect.zip

4.打开支付宝配置文件AlipayConfig.java

package com.alipay.config;

/* *
*类名:AlipayConfig
*功能:基础配置类
*详细:设置帐户有关信息及返回路径
*版本:3.4
*修改日期:2016-03-08
*说明:
*以下代码只是为了方便商户测试而提供的样例代码,商户可以根据自己网站的需要,按照技术文档编写,并非一定要使用该代码。
*该代码仅供学习和研究支付宝接口使用,只是提供一个参考。
*/

public class AlipayConfig {

//↓↓↓↓↓↓↓↓↓↓请在这里配置您的基本信息↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓

// 合作身份者ID,签约账号,以2088开头由16位纯数字组成的字符串,查看地址:https://b.alipay.com/order/pidAndKey.htm
public static String partner = "";

// 收款支付宝账号,以2088开头由16位纯数字组成的字符串,一般情况下收款账号就是签约账号
public static String seller_id = partner;

//商户的私钥,需要PKCS8格式,RSA公私钥生成:https://doc.open.alipay.com/doc2/detail.htm?spm=a219a.7629140.0.0.nBDxfy&treeId=58&articleId=103242&docType=1
public static String private_key = "";

// 支付宝的公钥,查看地址:https://b.alipay.com/order/pidAndKey.htm
public static String alipay_public_key = "MIGfMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKBgQCnxj/9qwVfgoUh/y2W89L6BkRAFljhNhgPdyPuBV64bfQNN1PjbCzkIM6qRdKBoLPXmKKMiFYnkd6rAoprih3/PrQEB/VsW8OoM8fxn67UDYuyBTqA23MML9q1+ilIZwBC2AQ2UBVOrFXfFl75p6/B5KsiNG9zpgmLCUYuLkxpLQIDAQAB";

// 服务器异步通知页面路径 需http://格式的完整路径,不能加?id=123这类自定义参数,必须外网可以正常访问
public static String notify_url = "http://商户网址/create_direct_pay_by_user-JAVA-UTF-8/notify_url.jsp";

// 页面跳转同步通知页面路径 需http://格式的完整路径,不能加?id=123这类自定义参数,必须外网可以正常访问
public static String return_url = "http://商户网址/create_direct_pay_by_user-JAVA-UTF-8/return_url.jsp";

// 签名方式
public static String sign_type = "RSA";

// 调试用,创建TXT日志文件夹路径,见AlipayCore.java类中的logResult(String sWord)打印方法。
public static String log_path = "C:\\";

// 字符编码格式 目前支持 gbk 或 utf-8
public static String input_charset = "utf-8";

// 支付类型 ,无需修改
public static String payment_type = "1";

// 调用的接口名,无需修改
public static String service = "create_direct_pay_by_user";


//↑↑↑↑↑↑↑↑↑↑请在这里配置您的基本信息↑↑↑↑↑↑↑↑↑↑↑↑↑↑↑

//↓↓↓↓↓↓↓↓↓↓ 请在这里配置防钓鱼信息,如果没开通防钓鱼功能,为空即可 ↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓

// 防钓鱼时间戳 若要使用请调用类文件submit中的query_timestamp函数
public static String anti_phishing_key = "";

// 客户端的IP地址 非局域网的外网IP地址,如:221.0.0.1
public static String exter_invoke_ip = "";

//↑↑↑↑↑↑↑↑↑↑请在这里配置防钓鱼信息,如果没开通防钓鱼功能,为空即可 ↑↑↑↑↑↑↑↑↑↑↑↑↑↑↑

}
修改里面的信息。

4.使用RES签名

package com.alipay.sign;

import java.io.ByteArrayInputStream;
import java.io.ByteArrayOutputStream;
import java.io.InputStream;
import java.security.KeyFactory;
import java.security.PrivateKey;
import java.security.PublicKey;
import java.security.spec.PKCS8EncodedKeySpec;
import java.security.spec.X509EncodedKeySpec;

import javax.crypto.Cipher;

public class RSA{

public static final String SIGN_ALGORITHMS = "SHA1WithRSA";

/**
* RSA签名
* @param content 待签名数据
* @param privateKey 商户私钥
* @param input_charset 编码格式
* @return 签名值
*/
public static String sign(String content, String privateKey, String input_charset)
{
try
{
PKCS8EncodedKeySpec priPKCS8 = new PKCS8EncodedKeySpec( Base64.decode(privateKey) );
KeyFactory keyf = KeyFactory.getInstance("RSA");
PrivateKey priKey = keyf.generatePrivate(priPKCS8);

java.security.Signature signature = java.security.Signature
.getInstance(SIGN_ALGORITHMS);

signature.initSign(priKey);
signature.update( content.getBytes(input_charset) );

byte[] signed = signature.sign();

return Base64.encode(signed);
}
catch (Exception e)
{
e.printStackTrace();
}

return null;
}

/**
* RSA验签名检查
* @param content 待签名数据
* @param sign 签名值
* @param ali_public_key 支付宝公钥
* @param input_charset 编码格式
* @return 布尔值
*/
public static boolean verify(String content, String sign, String ali_public_key, String input_charset)
{
try
{
KeyFactory keyFactory = KeyFactory.getInstance("RSA");
byte[] encodedKey = Base64.decode(ali_public_key);
PublicKey pubKey = keyFactory.generatePublic(new X509EncodedKeySpec(encodedKey));


java.security.Signature signature = java.security.Signature
.getInstance(SIGN_ALGORITHMS);

signature.initVerify(pubKey);
signature.update( content.getBytes(input_charset) );

boolean bverify = signature.verify( Base64.decode(sign) );
return bverify;

}
catch (Exception e)
{
e.printStackTrace();
}

return false;
}

/**
* 解密
* @param content 密文
* @param private_key 商户私钥
* @param input_charset 编码格式
* @return 解密后的字符串
*/
public static String decrypt(String content, String private_key, String input_charset) throws Exception {
PrivateKey prikey = getPrivateKey(private_key);

Cipher cipher = Cipher.getInstance("RSA");
cipher.init(Cipher.DECRYPT_MODE, prikey);

InputStream ins = new ByteArrayInputStream(Base64.decode(content));
ByteArrayOutputStream writer = new ByteArrayOutputStream();
//rsa解密的字节大小最多是128,将需要解密的内容,按128位拆开解密
byte[] buf = new byte[128];
int bufl;

while ((bufl = ins.read(buf)) != -1) {
byte[] block = null;

if (buf.length == bufl) {
block = buf;
} else {
block = new byte[bufl];
for (int i = 0; i < bufl; i++) {
block[i] = buf[i];
}
}

writer.write(cipher.doFinal(block));
}

return new String(writer.toByteArray(), input_charset);
}


/**
* 得到私钥
* @param key 密钥字符串(经过base64编码)
* @throws Exception
*/
public static PrivateKey getPrivateKey(String key) throws Exception {

byte[] keyBytes;

keyBytes = Base64.decode(key);

PKCS8EncodedKeySpec keySpec = new PKCS8EncodedKeySpec(keyBytes);

KeyFactory keyFactory = KeyFactory.getInstance("RSA");

PrivateKey privateKey = keyFactory.generatePrivate(keySpec);

return privateKey;
}
}
5.Base64.java
/* * Copyright (C) 2010 The MobileSecurePay Project * All right reserved. * author: shiqun.shi@alipay.com */package com.alipay.sign;public final class Base64 {    static private final int     BASELENGTH           = 128;    static private final int     LOOKUPLENGTH         = 64;    static private final int     TWENTYFOURBITGROUP   = 24;    static private final int     EIGHTBIT             = 8;    static private final int     SIXTEENBIT           = 16;    static private final int     FOURBYTE             = 4;    static private final int     SIGN                 = -128;    static private final char    PAD                  = '=';    static private final boolean fDebug               = false;    static final private byte[]  base64Alphabet       = new byte[BASELENGTH];    static final private char[]  lookUpBase64Alphabet = new char[LOOKUPLENGTH];    static {        for (int i = 0; i < BASELENGTH; ++i) {            base64Alphabet[i] = -1;        }        for (int i = 'Z'; i >= 'A'; i--) {            base64Alphabet[i] = (byte) (i - 'A');        }        for (int i = 'z'; i >= 'a'; i--) {            base64Alphabet[i] = (byte) (i - 'a' + 26);        }        for (int i = '9'; i >= '0'; i--) {            base64Alphabet[i] = (byte) (i - '0' + 52);        }        base64Alphabet['+'] = 62;        base64Alphabet['/'] = 63;        for (int i = 0; i <= 25; i++) {            lookUpBase64Alphabet[i] = (char) ('A' + i);        }        for (int i = 26, j = 0; i <= 51; i++, j++) {            lookUpBase64Alphabet[i] = (char) ('a' + j);        }        for (int i = 52, j = 0; i <= 61; i++, j++) {            lookUpBase64Alphabet[i] = (char) ('0' + j);        }        lookUpBase64Alphabet[62] = (char) '+';        lookUpBase64Alphabet[63] = (char) '/';    }    private static boolean isWhiteSpace(char octect) {        return (octect == 0x20 || octect == 0xd || octect == 0xa || octect == 0x9);    }    private static boolean isPad(char octect) {        return (octect == PAD);    }    private static boolean isData(char octect) {        return (octect < BASELENGTH && base64Alphabet[octect] != -1);    }    /**     * Encodes hex octects into Base64     *     * @param binaryData Array containing binaryData     * @return Encoded Base64 array     */    public static String encode(byte[] binaryData) {        if (binaryData == null) {            return null;        }        int lengthDataBits = binaryData.length * EIGHTBIT;        if (lengthDataBits == 0) {            return "";        }        int fewerThan24bits = lengthDataBits % TWENTYFOURBITGROUP;        int numberTriplets = lengthDataBits / TWENTYFOURBITGROUP;        int numberQuartet = fewerThan24bits != 0 ? numberTriplets + 1 : numberTriplets;        char encodedData[] = null;        encodedData = new char[numberQuartet * 4];        byte k = 0, l = 0, b1 = 0, b2 = 0, b3 = 0;        int encodedIndex = 0;        int dataIndex = 0;        if (fDebug) {            System.out.println("number of triplets = " + numberTriplets);        }        for (int i = 0; i < numberTriplets; i++) {            b1 = binaryData[dataIndex++];            b2 = binaryData[dataIndex++];            b3 = binaryData[dataIndex++];            if (fDebug) {                System.out.println("b1= " + b1 + ", b2= " + b2 + ", b3= " + b3);            }            l = (byte) (b2 & 0x0f);            k = (byte) (b1 & 0x03);            byte val1 = ((b1 & SIGN) == 0) ? (byte) (b1 >> 2) : (byte) ((b1) >> 2 ^ 0xc0);            byte val2 = ((b2 & SIGN) == 0) ? (byte) (b2 >> 4) : (byte) ((b2) >> 4 ^ 0xf0);            byte val3 = ((b3 & SIGN) == 0) ? (byte) (b3 >> 6) : (byte) ((b3) >> 6 ^ 0xfc);            if (fDebug) {                System.out.println("val2 = " + val2);                System.out.println("k4   = " + (k << 4));                System.out.println("vak  = " + (val2 | (k << 4)));            }            encodedData[encodedIndex++] = lookUpBase64Alphabet[val1];            encodedData[encodedIndex++] = lookUpBase64Alphabet[val2 | (k << 4)];            encodedData[encodedIndex++] = lookUpBase64Alphabet[(l << 2) | val3];            encodedData[encodedIndex++] = lookUpBase64Alphabet[b3 & 0x3f];        }        // form integral number of 6-bit groups        if (fewerThan24bits == EIGHTBIT) {            b1 = binaryData[dataIndex];            k = (byte) (b1 & 0x03);            if (fDebug) {                System.out.println("b1=" + b1);                System.out.println("b1<<2 = " + (b1 >> 2));            }            byte val1 = ((b1 & SIGN) == 0) ? (byte) (b1 >> 2) : (byte) ((b1) >> 2 ^ 0xc0);            encodedData[encodedIndex++] = lookUpBase64Alphabet[val1];            encodedData[encodedIndex++] = lookUpBase64Alphabet[k << 4];            encodedData[encodedIndex++] = PAD;            encodedData[encodedIndex++] = PAD;        } else if (fewerThan24bits == SIXTEENBIT) {            b1 = binaryData[dataIndex];            b2 = binaryData[dataIndex + 1];            l = (byte) (b2 & 0x0f);            k = (byte) (b1 & 0x03);            byte val1 = ((b1 & SIGN) == 0) ? (byte) (b1 >> 2) : (byte) ((b1) >> 2 ^ 0xc0);            byte val2 = ((b2 & SIGN) == 0) ? (byte) (b2 >> 4) : (byte) ((b2) >> 4 ^ 0xf0);            encodedData[encodedIndex++] = lookUpBase64Alphabet[val1];            encodedData[encodedIndex++] = lookUpBase64Alphabet[val2 | (k << 4)];            encodedData[encodedIndex++] = lookUpBase64Alphabet[l << 2];            encodedData[encodedIndex++] = PAD;        }        return new String(encodedData);    }    /**     * Decodes Base64 data into octects     *     * @param encoded string containing Base64 data     * @return Array containind decoded data.     */    public static byte[] decode(String encoded) {        if (encoded == null) {            return null;        }        char[] base64Data = encoded.toCharArray();        // remove white spaces        int len = removeWhiteSpace(base64Data);        if (len % FOURBYTE != 0) {            return null;//should be divisible by four        }        int numberQuadruple = (len / FOURBYTE);        if (numberQuadruple == 0) {            return new byte[0];        }        byte decodedData[] = null;        byte b1 = 0, b2 = 0, b3 = 0, b4 = 0;        char d1 = 0, d2 = 0, d3 = 0, d4 = 0;        int i = 0;        int encodedIndex = 0;        int dataIndex = 0;        decodedData = new byte[(numberQuadruple) * 3];        for (; i < numberQuadruple - 1; i++) {            if (!isData((d1 = base64Data[dataIndex++])) || !isData((d2 = base64Data[dataIndex++]))                || !isData((d3 = base64Data[dataIndex++]))                || !isData((d4 = base64Data[dataIndex++]))) {                return null;            }//if found "no data" just return null            b1 = base64Alphabet[d1];            b2 = base64Alphabet[d2];            b3 = base64Alphabet[d3];            b4 = base64Alphabet[d4];            decodedData[encodedIndex++] = (byte) (b1 << 2 | b2 >> 4);            decodedData[encodedIndex++] = (byte) (((b2 & 0xf) << 4) | ((b3 >> 2) & 0xf));            decodedData[encodedIndex++] = (byte) (b3 << 6 | b4);        }        if (!isData((d1 = base64Data[dataIndex++])) || !isData((d2 = base64Data[dataIndex++]))) {            return null;//if found "no data" just return null        }        b1 = base64Alphabet[d1];        b2 = base64Alphabet[d2];        d3 = base64Data[dataIndex++];        d4 = base64Data[dataIndex++];        if (!isData((d3)) || !isData((d4))) {//Check if they are PAD characters            if (isPad(d3) && isPad(d4)) {                if ((b2 & 0xf) != 0)//last 4 bits should be zero                {                    return null;                }                byte[] tmp = new byte[i * 3 + 1];                System.arraycopy(decodedData, 0, tmp, 0, i * 3);                tmp[encodedIndex] = (byte) (b1 << 2 | b2 >> 4);                return tmp;            } else if (!isPad(d3) && isPad(d4)) {                b3 = base64Alphabet[d3];                if ((b3 & 0x3) != 0)//last 2 bits should be zero                {                    return null;                }                byte[] tmp = new byte[i * 3 + 2];                System.arraycopy(decodedData, 0, tmp, 0, i * 3);                tmp[encodedIndex++] = (byte) (b1 << 2 | b2 >> 4);                tmp[encodedIndex] = (byte) (((b2 & 0xf) << 4) | ((b3 >> 2) & 0xf));                return tmp;            } else {                return null;            }        } else { //No PAD e.g 3cQl            b3 = base64Alphabet[d3];            b4 = base64Alphabet[d4];            decodedData[encodedIndex++] = (byte) (b1 << 2 | b2 >> 4);            decodedData[encodedIndex++] = (byte) (((b2 & 0xf) << 4) | ((b3 >> 2) & 0xf));            decodedData[encodedIndex++] = (byte) (b3 << 6 | b4);        }        return decodedData;    }    /**     * remove WhiteSpace from MIME containing encoded Base64 data.     *     * @param data  the byte array of base64 data (with WS)     * @return      the new length     */    private static int removeWhiteSpace(char[] data) {        if (data == null) {            return 0;        }        // count characters that's not whitespace        int newSize = 0;        int len = data.length;        for (int i = 0; i < len; i++) {            if (!isWhiteSpace(data[i])) {                data[newSize++] = data[i];            }        }        return newSize;    }}

6.com.alipay.util

这里面的文件复制到项目中即可。这里我就不再帖出来了。

7.网页实现 接收订单信息的接口

<%
/* *
*功能:即时到账交易接口接入页
*版本:3.4
*修改日期:2016-03-08
*说明:
*以下代码只是为了方便商户测试而提供的样例代码,商户可以根据自己网站的需要,按照技术文档编写,并非一定要使用该代码。
*该代码仅供学习和研究支付宝接口使用,只是提供一个参考。

*************************注意*****************
*如果您在接口集成过程中遇到问题,可以按照下面的途径来解决
*1、开发文档中心(https://doc.open.alipay.com/doc2/detail.htm?spm=a219a.7629140.0.0.KvddfJ&treeId=62&articleId=103740&docType=1)
*2、商户帮助中心(https://cshall.alipay.com/enterprise/help_detail.htm?help_id=473888)
*3、支持中心(https://support.open.alipay.com/alipay/support/index.htm)
*如果不想使用扩展功能请把扩展功能参数赋空值。
**********************************************
*/
%>
<%@ page language="java" contentType="text/html; charset=UTF-8" pageEncoding="UTF-8"%>
<%@ page import="com.alipay.config.*"%>
<%@ page import="com.alipay.util.*"%>
<%@ page import="java.util.HashMap"%>
<%@ page import="java.util.Map"%>
<!DOCTYPE html>
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<title>支付宝即时到账交易接口</title>
</head>
<%
////////////////////////////////////请求参数//////////////////////////////////////

//商户订单号,商户网站订单系统中唯一订单号,必填
String out_trade_no = new String(request.getParameter("WIDout_trade_no").getBytes("ISO-8859-1"),"UTF-8");

//订单名称,必填
String subject = new String(request.getParameter("WIDsubject").getBytes("ISO-8859-1"),"UTF-8");

//付款金额,必填
String total_fee = new String(request.getParameter("WIDtotal_fee").getBytes("ISO-8859-1"),"UTF-8");

//商品描述,可空
String body = new String(request.getParameter("WIDbody").getBytes("ISO-8859-1"),"UTF-8");



//////////////////////////////////////////////////////////////////////////////////

//把请求参数打包成数组
Map<String, String> sParaTemp = new HashMap<String, String>();
sParaTemp.put("service", AlipayConfig.service);
sParaTemp.put("partner", AlipayConfig.partner);
sParaTemp.put("seller_id", AlipayConfig.seller_id);
sParaTemp.put("_input_charset", AlipayConfig.input_charset);
sParaTemp.put("payment_type", AlipayConfig.payment_type);
sParaTemp.put("notify_url", AlipayConfig.notify_url);
sParaTemp.put("return_url", AlipayConfig.return_url);
sParaTemp.put("anti_phishing_key", AlipayConfig.anti_phishing_key);
sParaTemp.put("exter_invoke_ip", AlipayConfig.exter_invoke_ip);
sParaTemp.put("out_trade_no", out_trade_no);
sParaTemp.put("subject", subject);
sParaTemp.put("total_fee", total_fee);
sParaTemp.put("body", body);
//其他业务参数根据在线开发文档,添加参数.文档地址:https://doc.open.alipay.com/doc2/detail.htm?spm=a219a.7629140.0.0.O9yorI&treeId=62&articleId=103740&docType=1
//如sParaTemp.put("参数名","参数值");

//建立请求
String sHtmlText = AlipaySubmit.buildRequest(sParaTemp,"get","确认");
out.println(sHtmlText);
%>
<body>
</body>
</html>

8.提交订单信息到刚才编写的接口

<%
/* *
*功能:支付宝即时到账交易接口调试入口页面
*版本:3.4
*日期:2016-03-08
*说明:
*以下代码只是为了方便商户测试而提供的样例代码,商户可以根据自己网站的需要,按照技术文档编写,并非一定要使用该代码。
**********************************************
*/
%>
<%@ page language="java" contentType="text/html; charset=UTF-8" pageEncoding="UTF-8"%>
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>支付宝即时到账交易接口</title>
</head>

<style>
html,body {
width:100%;
min-width:1200px;
height:auto;
padding:0;
margin:0;
font-family:"微软雅黑";
background-color:#242736
}
.header {
width:100%;
margin:0 auto;
height:230px;
background-color:#fff
}
.container {
width:100%;
min-width:100px;
height:auto
}
.black {
background-color:#242736
}
.blue {
background-color:#0ae
}
.qrcode {
width:1200px;
margin:0 auto;
height:30px;
background-color:#242736
}
.littlecode {
width:16px;
height:16px;
margin-top:6px;
cursor:pointer;
float:right
}
.showqrs {
top:30px;
position:absolute;
width:100px;
margin-left:-65px;
height:160px;
display:none
}
.shtoparrow {
width:0;
height:0;
margin-left:65px;
border-left:8px solid transparent;
border-right:8px solid transparent;
border-bottom:8px solid #e7e8eb;
margin-bottom:0;
font-size:0;
line-height:0
}
.guanzhuqr {
text-align:center;
background-color:#e7e8eb;
border:1px solid #e7e8eb
}
.guanzhuqr img {
margin-top:10px;
width:80px
}
.shmsg {
margin-left:10px;
width:80px;
height:16px;
line-height:16px;
font-size:12px;
color:#242323;
text-align:center
}
.nav {
width:1200px;
margin:0 auto;
height:70px;
}
.open,.logo {
display:block;
float:left;
height:40px;
width:85px;
margin-top:20px
}
.divier {
display:block;
float:left;
margin-left:20px;
margin-right:20px;
margin-top:23px;
width:1px;
height:24px;
background-color:#d3d3d3
}
.open {
line-height:30px;
font-size:20px;
text-decoration:none;
color:#1a1a1a
}
.navbar {
float:right;
width:200px;
height:40px;
margin-top:15px;
list-style:none
}
.navbar li {
float:left;
width:100px;
height:40px
}
.navbar li a {
display:inline-block;
width:100px;
height:40px;
line-height:40px;
font-size:16px;
color:#1a1a1a;
text-decoration:none;
text-align:center
}
.navbar li a:hover {
color:#00AAEE
}
.title {
width:1200px;
margin:0 auto;
height:80px;
line-height:80px;
font-size:20px;
color:#FFF
}
.content {
width:100%;
min-width:1200px;
height:660px;
background-color:#fff;
}
.alipayform {
width:800px;
margin:0 auto;
height:600px;
border:1px solid #0ae
}
.element {
width:600px;
height:80px;
margin-left:100px;
font-size:20px
}
.etitle,.einput {
float:left;
height:26px
}
.etitle {
width:150px;
line-height:26px;
text-align:right
}
.einput {
width:200px;
margin-left:20px
}
.einput input {
width:398px;
height:24px;
border:1px solid #0ae;
font-size:16px
}
.mark {
margin-top: 10px;
width:500px;
height:30px;
margin-left:80px;
line-height:30px;
font-size:12px;
color:#999
}
.legend {
margin-left:100px;
font-size:24px
}
.alisubmit {
width:400px;
height:40px;
border:0;
background-color:#0ae;
font-size:16px;
color:#FFF;
cursor:pointer;
margin-left:170px
}
.footer {
width:100%;
height:120px;
background-color:#242735
}
.footer-sub a,span {
color:#808080;
font-size:12px;
text-decoration:none
}
.footer-sub a:hover {
color:#00aeee
}
.footer-sub span {
margin:0 3px
}
.footer-sub {
padding-top:40px;
height:20px;
width:600px;
margin:0 auto;
text-align:center
}
</style>
<body>
<div class="header">
<div class="container black">
<div class="qrcode">
<div class="littlecode">
<img width="16px" src="img/little_qrcode.jpg" id="licode">
<div class="showqrs" id="showqrs">
<div class="shtoparrow"></div>
<div class="guanzhuqr">
<img src="img/guanzhu_qrcode.png" width="80">
<div class="shmsg" style="margin-top:5px;">
请扫码关注
</div>
<div class="shmsg" style="margin-bottom:5px;">
接收重要信息
</div>
</div>
</div>
</div>
</div>
</div>
<div class="container">
<div class="nav">
<a href="https://www.alipay.com/" class="logo"><img src="img/alipay_logo.png" height="30px"></a>
<span class="divier"></span>
<a href="http://open.alipay.com/platform/home.htm" class="open" target="_blank">开放平台</a>
<ul class="navbar">
<li><a href="https://doc.open.alipay.com/doc2/detail?treeId=62&articleId=103566&docType=1" target="_blank">在线文档</a></li>
<li><a href="https://cschannel.alipay.com/portal.htm?sourceId=213" target="_blank">技术支持</a></li>
</ul>
</div>
</div>
<div class="container blue">
<div class="title">支付宝即时到账(create_direct_pay_by_user)</div>
</div>
</div>
<div class="content">
<form action="alipayapi.jsp" class="alipayform" method="POST" target="_blank">
<div class="element" style="margin-top:60px;">
<div class="legend">支付宝即时到账交易接口快速通道 </div>
</div>
<div class="element">
<div class="etitle">商户订单号:</div>
<div class="einput"><input type="text" name="WIDout_trade_no" id="out_trade_no"></div>
<br>
<div class="mark">注意:商户订单号(out_trade_no).必填(建议是英文字母和数字,不能含有特殊字符)</div>
</div>

<div class="element">
<div class="etitle">商品名称:</div>
<div class="einput"><input type="text" name="WIDsubject" value="test商品123"></div>
<br>
<div class="mark">注意:产品名称(subject),必填(建议中文,英文,数字,不能含有特殊字符)</div>
</div>
<div class="element">
<div class="etitle">付款金额:</div>
<div class="einput"><input type="text" name="WIDtotal_fee" value="0.01"></div>
<br>
<div class="mark">注意:付款金额(total_fee),必填(格式如:1.00,请精确到分)</div>
</div>
<div class="element">
<div class="etitle">商品描述:</div>
<div class="einput"><input type="text" name="WIDbody" value="即时到账测试"></div>
<br>
<div class="mark">注意:商品描述(body),选填(建议中文,英文,数字,不能含有特殊字符)</div>
</div>
<div class="element">
<input type="submit" class="alisubmit" value ="确认支付">
</div>
</form>
</div>
<div class="footer">
<p class="footer-sub">
<a href="http://ab.alipay.com/i/index.htm" target="_blank">关于支付宝</a><span>|</span>
<a href="https://e.alipay.com/index.htm" target="_blank">商家中心</a><span>|</span>
<a href="https://job.alibaba.com/zhaopin/index.htm" target="_blank">诚征英才</a><span>|</span>
<a href="http://ab.alipay.com/i/lianxi.htm" target="_blank">联系我们</a><span>|</span>
<a href="#" id="international" target="_blank">International Business</a><span>|</span>
<a href="http://ab.alipay.com/i/jieshao.htm#en" target="_blank">About Alipay</a>
<br>
<span>支付宝版权所有</span>
<span class="footer-date">2004-2016</span>
<span><a href="http://fun.alipay.com/certificate/jyxkz.htm" target="_blank">ICP证:沪B2-20150087</a></span>
</p>


</div>
</body>
<script>

var even = document.getElementById("licode");
var showqrs = document.getElementById("showqrs");
even.onmouseover = function(){
showqrs.style.display = "block";
}
even.onmouseleave = function(){
showqrs.style.display = "none";
}

var out_trade_no = document.getElementById("out_trade_no");

//设定时间格式化函数
Date.prototype.format = function (format) {
var args = {
"M+": this.getMonth() + 1,
"d+": this.getDate(),
"h+": this.getHours(),
"m+": this.getMinutes(),
"s+": this.getSeconds(),
};
if (/(y+)/.test(format))
format = format.replace(RegExp.$1, (this.getFullYear() + "").substr(4 - RegExp.$1.length));
for (var i in args) {
var n = args[i];
if (new RegExp("(" + i + ")").test(format))
format = format.replace(RegExp.$1, RegExp.$1.length == 1 ? n : ("00" + n).substr(("" + n).length));
}
return format;
};

out_trade_no.value = 'test'+ new Date().format("yyyyMMddhhmmss");

</script>

</html>

9.异步回调接口
<%
/* *
功能:支付宝服务器异步通知页面
版本:3.3
日期:2012-08-17
说明:
以下代码只是为了方便商户测试而提供的样例代码,商户可以根据自己网站的需要,按照技术文档编写,并非一定要使用该代码。
该代码仅供学习和研究支付宝接口使用,只是提供一个参考。

//***********页面功能说明***********
创建该页面文件时,请留心该页面文件中无任何HTML代码及空格。
该页面不能在本机电脑测试,请到服务器上做测试。请确保外部可以访问该页面。
该页面调试工具请使用写文本函数logResult,该函数在com.alipay.util文件夹的AlipayNotify.java类文件中
如果没有收到该页面返回的 success 信息,支付宝会在24小时内按一定的时间策略重发通知
//********************************
* */
%>
<%@ page language="java" contentType="text/html; charset=UTF-8" pageEncoding="UTF-8"%>
<%@ page import="java.util.*"%>
<%@ page import="com.alipay.util.*"%>
<%@ page import="com.alipay.config.*"%>
<%
//获取支付宝POST过来反馈信息
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 out_trade_no = new String(request.getParameter("out_trade_no").getBytes("ISO-8859-1"),"UTF-8");

//支付宝交易号

String trade_no = new String(request.getParameter("trade_no").getBytes("ISO-8859-1"),"UTF-8");

//交易状态
String trade_status = new String(request.getParameter("trade_status").getBytes("ISO-8859-1"),"UTF-8");

//获取支付宝的通知返回参数,可参考技术文档中页面跳转同步通知参数列表(以上仅供参考)//

if(AlipayNotify.verify(params)){//验证成功
//////////////////////////////////////////////////////////////////////////////////////////
//请在这里加上商户的业务逻辑程序代码

//——请根据您的业务逻辑来编写程序(以下代码仅作参考)——

if(trade_status.equals("TRADE_FINISHED")){
//判断该笔订单是否在商户网站中已经做过处理
//如果没有做过处理,根据订单号(out_trade_no)在商户网站的订单系统中查到该笔订单的详细,并执行商户的业务程序
//请务必判断请求时的total_fee、seller_id与通知时获取的total_fee、seller_id为一致的
//如果有做过处理,不执行商户的业务程序

//注意:
//退款日期超过可退款期限后(如三个月可退款),支付宝系统发送该交易状态通知
} else if (trade_status.equals("TRADE_SUCCESS")){
//判断该笔订单是否在商户网站中已经做过处理
//如果没有做过处理,根据订单号(out_trade_no)在商户网站的订单系统中查到该笔订单的详细,并执行商户的业务程序
//请务必判断请求时的total_fee、seller_id与通知时获取的total_fee、seller_id为一致的
//如果有做过处理,不执行商户的业务程序

//注意:
//付款完成后,支付宝系统发送该交易状态通知
}

//——请根据您的业务逻辑来编写程序(以上代码仅作参考)——

out.print("success");//请不要修改或删除

//////////////////////////////////////////////////////////////////////////////////////////
}else{//验证失败
out.print("fail");
}
%>
这样就OK 了。RES签名必须使用支付宝提供的工具生成并上传公私到支付宝里面。