第三方支付接口技术对接实现及样例讲解.docx
《第三方支付接口技术对接实现及样例讲解.docx》由会员分享,可在线阅读,更多相关《第三方支付接口技术对接实现及样例讲解.docx(31页珍藏版)》请在冰豆网上搜索。
第三方支付接口技术对接实现及样例讲解
B2B网站对接支付宝接口
网站转接支付宝解决方案
大型网上购物系统除了能让会员选择货到付款结账方式外,还应该提供一些更方便快捷的网上支付方式。
如果网上商店没有足够的实力提供会员直接在网站中
建立现金账户的功能,就可以将订单信息转接到支付宝,让会员从支付宝付款。
当然就算会员可以在网站上建立自己的现金账户,提供支付宝支付功能也不失为另一种方便快捷的支付方式,这可以给客户提供更多可选的支付方式。
首先,网上购物系统必须与支付宝公司签订合作协议,以确保从本购物网站上传到
支付宝网站上的订单信息能被正确接收。
当会员于购物网站上买下一系列商品并选择支付宝付款方式后,购物系统即将会员购物的订单信息转发到支付宝,网站页面也会转到支付宝的付款页面。
此时,支付宝页面会发送一个验证信息到本网站以确认支付宝正确收到订单信息。
会员于支付宝网站付款完成后,网站页面会重新跳回本购物网站,同时支付宝会将已付款的订单信息发回本网站以便对本购物网站的数据库进行必要的修改操
作。
另外本网站还需要向支付宝网站发送一个返回信息,告知支付宝本系统已正确收到付款完毕的订单信息并且已经完成对数据的处理操作。
向支付宝网站传送订单信息时主要参数的含义:
gateway:
支付接口
service:
识别是何接口实现何功能的表示
seller_email:
商家签约时的支付宝账号,即收款的支付宝账号
key:
安全校验码,与partner是一组
partner:
商户ID,合作伙伴ID
sign_type:
加密类型
_input_charset:
编码类型
show_url:
展示地址,即在支付宝页面时商品名称旁边的“详情”的链接地址
out_trade_no:
会员订单编号,订单编号必须在本系统中保持唯一
subject:
商品名称,也可称为订单名称,该接口并不是单一的只能买一样东西,可把一次支付当作一次下订单
body:
商品描述,即备注
total_fee:
商品价格,也可称为订单的总金额
源码分析(C#):
首先必须建立一个通知页面(Notify.aspx)和一个返回页面(Return.aspx)以接受并验证从支付宝返回的信息并对数据库中相应的订单信息做修改处理操作。
Notify.aspx.cs
代码
usingSystem;
usingSystem.Data;
usingSystem.Configuration;
usingSystem.Collections;
usingSystem.Web;
usingSystem.Web.Security;
usingSystem.Web.UI;
usingSystem.Web.UI.WebControls;
usingSystem.Web.UI.WebControls.WebParts;
usingSystem.Web.UI.HtmlControls;
usingSystem.Text;
usingSystem.Collections.Specialized;
usingSystem.IO;
usingGateway;
///
///创建该页面文件时,请留心该页面文件中无任何HTML代码及空格。
///该页面称作“通知页”,是异步被支付宝服务器所调用。
///当支付宝的订单状态改变时,支付宝服务器则会自动调用此页面,因此请做好自身网站订单信息与支付宝上的订单的同步工作
publicpartialclassAlipay_Notify:
System.Web.UI.Page{
protected
voidPage_Load(objectsender,EventArgse)
{
stringalipayNotifyURL=
"
//stringalipayNotifyURL=
"此路径是在上面链
;
接地址无法起作用时替换使用。
string
partner=
"";
//partner
合作伙伴
id
(必须填写)
stringkey="";//partner的对应交易安全校验码(必须填写)
string_input_charset="utf-8";//编码类型,完全根据客户自身的
项目的编码格式而定,千万不要填错。
否则极其容易造成MD5加密错误。
alipayNotifyURL=alipayNotifyURL+
"&partner="
+partner+
"¬ify_id="
+Request.Form["notify_id"
];
//获取支付宝ATN返回结果,true是正确的订单信息,false是无效的
stringresponseTxt=AliPay.Get_Http(alipayNotifyURL,
120000);
//*******加密签名程序开始*******
inti;
NameValueCollectioncoll;
//LoadFormvariablesintoNameValueCollectionvariable.
coll=Request.Form;
//Getnamesofallformsintoastringarray.String[]requestarr=coll.AllKeys;
//进行排序;
string[]Sortedstr=AliPay.BubbleSort(requestarr);
//构造待md5摘要字符串;
StringBuilderprestr=newStringBuilder();
for(i=0;i{if(Request.Form[Sortedstr[i]]!=""&&Sortedstr[i]!="sign"&&Sortedstr[i]!="sign_type"){if(i==Sortedstr.Length-1){prestr.Append(Sortedstr[i]+"="+Request.Form[Sortedstr[i]]);}else{prestr.Append(Sortedstr[i]+"="+Request.Form[Sortedstr[i]]+"&"); }}} prestr.Append(key); stringmysign=AliPay.GetMD5(prestr.ToString(),_input_charset);//*******加密签名程序结束******* stringsign=Request.Form["sign"]; if(mysign==sign&&responseTxt=="true")//验证支付发过来的消息,签名是否正确,只要成功进如这个判断里,则表示该页面已被支付宝服务器成功调用//但判断内出现自身编写的程序相关错误导致通知给支付宝并不是发送success的消息或没有更新客户自身的数据库的情况,请自身程序编写好应对措施,否则查明原因时困难之极{if(Request.Form["trade_status"]=="WAIT_BUYER_PAY")//判断支付状态_等待买家付款(文档中有枚举表可以参考){//更新自己数据库的订单语句,请自己填写一下stringstrOrderNO=Request.Form["out_trade_no"];//订单号stringstrPrice=Request.Form["total_fee"];//金额如果你申请了商家购物卷功能,在返回信息里面请不要做金额的判断,否则会校验通过不了。 } elseif(Request.Form["trade_status"]=="TRADE_FINISHED"||Request.Form["trade_status"]=="TRADE_SUCCESS")//判断支付状态_交易成功结束(文档中有枚举表可以参考){//更新自己数据库的订单语句,请自己填写一下stringstrOrderNO=Request.Form["out_trade_no"];//订单号stringstrPrice=Request.Form["total_fee"];//金额 } else{ //更新自己数据库的订单语句,请自己填写一下 } Response.Write( "success");//返回给支付宝消息,成功,请不要改写这个success//success与fail及其他字符的区别在于,支付宝的服务器若遇到success时,则不再发送请求通知(即不再调用该页面,让该页面再次运行起来),//若不是success,则支付宝默认没有收到成功的信息,则会反复不停地调用该页面直到失效,有效调用时间是24小时以内。 //最好写TXT文件,以记录下是否异步返回记录。 ////写文本,纪录支付宝返回消息,比对md5计算结果(如网站不支持写txt文件,可改成写数据库)//stringTOEXCELLR="MD5结果:mysign="+mysign+",sign="+sign+",responseTxt="+responseTxt;//StreamWriterfs=newStreamWriter(Server.MapPath("Notify_DATA/"+DateTime.Now.ToString().Replace(":",""))+".txt",false,System.Text.Encoding.Default);//fs.Write(TOEXCELLR);//fs.Close();}else{Response.Write("fail"); //最好写TXT文件,以记录下是否异步返回记录。 //写文本,纪录支付宝返回消息,比对md5计算结果(如网站不支持写txt文件,可改成写数据库)stringTOEXCELLR="MD5结果:mysign="+mysign+",sign="+sign+",responseTxt="+responseTxt;StreamWriterfs=newStreamWriter(Server.MapPath("Notify_DATA/"+DateTime.Now.ToString().Replace(":"""))+".txt"falseSystem.Text.Encoding.Default);fs.Write(TOEXCELLR);fs.Close();}}} Return.aspx.cs 代码usingSystem;usingSystem.Data;usingSystem.Configuration;usingSystem.Collections;usingSystem.Web;usingSystem.Web.Security;usingSystem.Web.UI;usingSystem.Web.UI.WebControls;usingSystem.Web.UI.WebControls.WebParts;usingSystem.Web.UI.HtmlControls;usingSystem.Text;usingSystem.Collections.Specialized;usingSystem.IO;usingGateway; //////创建该页面文件时,请留心该页面文件是可以对其进行美工处理的,原因在于支付完成以后,当前窗口会从支付宝的页面跳转回这个页面。 ///该页面称作“返回页”,是同步被支付宝服务器所调用,可当作是支付完成后的提示信息页,如“您的某某某订单,多少金额已支付成功”。///publicpartialclassAlipay_Return:System.Web.UI.Page{ protectedvoidPage_Load(objectsender,EventArgse){stringalipayNotifyURL=";//stringalipayNotifyURL="此路径是在上面链接地址无法起作用时替换使用。stringkey="";//partner的对应交易安全校验码(必须填写)stringpartner="";//partner合作伙伴id(必须填写)string_input_charset="utf-8";//编码类型,完全根据客户自身的项目的编码格式而定,千万不要填错。否则极其容易造成MD5加密错误。 alipayNotifyURL=alipayNotifyURL+"&partner="+partner+"¬ify_id="+Request.QueryString["notify_id"]; //获取支付宝ATN返回结果,true是正确的订单信息,false是无效的stringresponseTxt=AliPay.Get_Http(alipayNotifyURL,120000); //*******加密签名程序开始//*******inti;NameValueCollectioncoll;//LoadFormvariablesintoNameValueCollectionvariable.coll=Request.QueryString; //Getnamesofallformsintoastringarray.String[]requestarr=coll.AllKeys; //进行排序;string[]Sortedstr=AliPay.BubbleSort(requestarr); //构造待md5摘要字符串; StringBuilderprestr=newStringBuilder(); for(i=0;i{ "sign"if(Request.Form[Sortedstr[i]]!=&&Sortedstr[i]!="sign_type"){""&&Sortedstr[i]!=if(i==Sortedstr.Length-1){prestr.Append(Sortedstr[i]+"="+Request.QueryString[Sortedstr[i]]);}else{prestr.Append(Sortedstr[i]+"="+Request.QueryString[Sortedstr[i]]+"&"); }}} prestr.Append(key); //生成Md5摘要;stringmysign=AliPay.GetMD5(prestr.ToString(),_input_charset); //******* string 加密签名程序结束*******sign=Request.QueryString[ "sign"]; //Response.Write(prestr.ToString());//调试用,支付宝服务器返回时的完整路径。 if(mysign==sign&&responseTxt=="true")//验证支付发过来的消息,签名是否正确{ //更新自己数据库的订单语句,请自己填写一下stringstrOrderNO=Request.QueryString["out_trade_no"];//订单号stringstrPrice=Request.QueryString["total_fee"];//金额stringstrTradeStatus=Request.QueryString["TRADE_STATUS"];//订单状态 Response.Write( "订单号:"+strOrderNO+"金额:"+strPrice);//成功,可美化该页面,提示信息}else{ Response.Write("------------------------------------------");Response.Write("Result:responseTxt="+responseTxt);Response.Write("Result:mysign="+mysign);Response.Write("Result:sign="+sign);Response.Write("支付失败");//支付失败,提示信息} }} 除此之外在Notify.aspx页面和Return.aspx页面公用的一些方法,可以提取出来放在一个公共的类里面(Alipay.cs) Alipay.cs 代码usingSystem.Web;usingSystem.Text;usingSystem.Security.Cryptography;usingSystem.IO;usingSystem.Net;usingSystem; //////NewInterfaceforAliPay///namespaceGateway{publicclassAliPay{//////与ASP兼容的MD5加密算法///publicstaticstringGetMD5(strings,string_input_charset){MD5md5=newMD5CryptoServiceProvider();byte[]t= md5.ComputeHash(Encoding.GetEncoding(_input_charset).GetBytes(s));StringBuildersb=newStringBuilder(32);for(inti=0;i {sb.Append(t[i].ToString("x").PadLeft(2,'0'));}returnsb.ToString();} //////冒泡排序法///按照字母序列从a到z的顺序排列///publicstaticstring[]BubbleSort(string[]r){inti,j;//交换标志stringtemp; boolexchange; for(i=0;i//最多做R.Length-1趟排序{exchange=false;//本趟排序开始前,交换标志应为假for(j=r.Length-2;j>=i;j--){//交换条件0)if(System.String.CompareOrdinal(r[j+1],r[j])<{temp=r[j+1];r[j+1]=r[j];r[j]=temp; exchange =true;//发生了交换,故将交换标志置为真}} if(!exchange)//本趟排序未发生交换,提前终止算法{break;}}returnr;} //////生成URL链接或加密结果//////参数加密数组///编码格式///加密类型///安全校验码///字符
if(Request.Form[Sortedstr[i]]!
=""&&Sortedstr[i]!
=
"sign"&&Sortedstr[i]!
="sign_type")
if(i==Sortedstr.Length-1)
prestr.Append(Sortedstr[i]+"="+
Request.Form[Sortedstr[i]]);
}
else
Request.Form[Sortedstr[i]]+"&");
prestr.Append(key);
stringmysign=AliPay.GetMD5(prestr.ToString(),_input_charset);
//*******
加密签名程序结束
*******
sign=Request.Form[
"sign"];
if(mysign==sign&&responseTxt=="true")//验证支付发过来的消息,
签名是否正确,只要成功进如这个判断里,则表示该页面已被支付宝服务器成功调用
//但判断内出现自身编写的程序相关错误导致通知给支付宝并不是发
送success的消息或没有更新客户自身的数据库的情况,请自身程序编写好应对措施,否则查明原因时困难之极
if(Request.Form["trade_status"]=="WAIT_BUYER_PAY")//
判断支付状态_等待买家付款(文档中有枚举表可以参考)
//更新自己数据库的订单语句,请自己填写一下
strOrderNO=Request.Form[
"out_trade_no"
];//订
单号
strPrice=Request.Form[
"total_fee"
];//金额
如果你申请了商家购物卷功能,在返回信息里面请不要做金额的判断,否则会校验通过不了。
elseif(Request.Form["trade_status"]=="TRADE_FINISHED"||
Request.Form["trade_status"]=="TRADE_SUCCESS")//判断支付状态_交易
成功结束(文档中有枚举表可以参考)
Response.Write(
"success");//返回给支付宝消息,成功,请不要改写这个success
//success与fail及其他字符的区别在于,支付宝的服务器若遇
到success时,则不再发送请求通知(即不再调用该页面,让该页面再次运行起来),
//若不是success,则支付宝默认没有收到成功的信息,则会反复
不停地调用该页面直到失效,有效调用时间是24小时以内。
//最好写TXT文件,以记录下是否异步返回记录。
////写文本,纪录支付宝返回消息,比对md5计算结果(如网站不支持写txt文件,可改成写数据库)
//stringTOEXCELLR="MD5结果:
mysign="+mysign+",sign="+sign+",responseTxt="+responseTxt;
//StreamWriterfs=newStreamWriter(Server.MapPath("Notify_DATA/"+DateTime.Now.ToString().Replace(":
",""))+".txt",false,System.Text.Encoding.Default);
//fs.Write(TOEXCELLR);
//fs.Close();
Response.Write("fail");
//写文本,纪录支付宝返回消息,比对md5计算结果(如网站不支持写txt文件,可改成写数据库)
TOEXCELLR="MD5结果:
mysign="
+mysign+
",sign="
+
sign+
",responseTxt="
+responseTxt;
StreamWriterfs=
new
StreamWriter(Server.MapPath(
"Notify_DATA/"
DateTime.Now.ToString().Replace(
":
""))+
".txt"
false
System.Text.Encoding.Default);
fs.Write(TOEXCELLR);
fs.Close();
Return.aspx.cs
///创建该页面文件时,请留心该页面文件是可以对其进行美工处理的,原因在于支付完成以后,当前窗口会从支付宝的页面跳转回这个页面。
///该页面称作“返回页”,是同步被支付宝服务器所调用,可当作是支付完成后的提示信息页,如“您的某某某订单,多少金额已支付成功”。
publicpartialclassAlipay_Return:
protectedvoidPage_Load(objectsender,EventArgse)
";
stringpartner="";//partner合作伙伴id(必须填写)
alipayNotifyURL=alipayNotifyURL+"&partner="+partner+
"¬ify_id="+Request.QueryString["notify_id"];
//*******加密签名程序开始//*******
coll=Request.QueryString;
for(i=0;i{ "sign"if(Request.Form[Sortedstr[i]]!=&&Sortedstr[i]!="sign_type"){""&&Sortedstr[i]!=if(i==Sortedstr.Length-1){prestr.Append(Sortedstr[i]+"="+Request.QueryString[Sortedstr[i]]);}else{prestr.Append(Sortedstr[i]+"="+Request.QueryString[Sortedstr[i]]+"&"); }}} prestr.Append(key); //生成Md5摘要;stringmysign=AliPay.GetMD5(prestr.ToString(),_input_charset); //******* string 加密签名程序结束*******sign=Request.QueryString[ "sign"]; //Response.Write(prestr.ToString());//调试用,支付宝服务器返回时的完整路径。 if(mysign==sign&&responseTxt=="true")//验证支付发过来的消息,签名是否正确{ //更新自己数据库的订单语句,请自己填写一下stringstrOrderNO=Request.QueryString["out_trade_no"];//订单号stringstrPrice=Request.QueryString["total_fee"];//金额stringstrTradeStatus=Request.QueryString["TRADE_STATUS"];//订单状态 Response.Write( "订单号:"+strOrderNO+"金额:"+strPrice);//成功,可美化该页面,提示信息}else{ Response.Write("------------------------------------------");Response.Write("Result:responseTxt="+responseTxt);Response.Write("Result:mysign="+mysign);Response.Write("Result:sign="+sign);Response.Write("支付失败");//支付失败,提示信息} }} 除此之外在Notify.aspx页面和Return.aspx页面公用的一些方法,可以提取出来放在一个公共的类里面(Alipay.cs) Alipay.cs 代码usingSystem.Web;usingSystem.Text;usingSystem.Security.Cryptography;usingSystem.IO;usingSystem.Net;usingSystem; //////NewInterfaceforAliPay///namespaceGateway{publicclassAliPay{//////与ASP兼容的MD5加密算法///publicstaticstringGetMD5(strings,string_input_charset){MD5md5=newMD5CryptoServiceProvider();byte[]t= md5.ComputeHash(Encoding.GetEncoding(_input_charset).GetBytes(s));StringBuildersb=newStringBuilder(32);for(inti=0;i {sb.Append(t[i].ToString("x").PadLeft(2,'0'));}returnsb.ToString();} //////冒泡排序法///按照字母序列从a到z的顺序排列///publicstaticstring[]BubbleSort(string[]r){inti,j;//交换标志stringtemp; boolexchange; for(i=0;i//最多做R.Length-1趟排序{exchange=false;//本趟排序开始前,交换标志应为假for(j=r.Length-2;j>=i;j--){//交换条件0)if(System.String.CompareOrdinal(r[j+1],r[j])<{temp=r[j+1];r[j+1]=r[j];r[j]=temp; exchange =true;//发生了交换,故将交换标志置为真}} if(!exchange)//本趟排序未发生交换,提前终止算法{break;}}returnr;} //////生成URL链接或加密结果//////参数加密数组///编码格式///加密类型///安全校验码///字符
"sign"
=&&Sortedstr[i]!
="sign_type"){
""&&Sortedstr[i]!
if(i==Sortedstr.Length-
1)
prestr.Append(Sortedstr[i]+
"="
Request.QueryString[Sortedstr[i]]);
Request.QueryString[Sortedstr[i]]+
"&");
//生成Md5摘要;
加密签名程序结束*******sign=Request.QueryString[
//Response.Write(prestr.ToString());//调试用,支付宝服务器返回时的
完整路径。
if(mysign==sign&&responseTxt=="true")//验证支付发过
来的消息,签名是否正确
strOrderNO
=Request.QueryString[
];//
订单号
strPrice=Request.QueryString[
strTradeStatus=
Request.QueryString[
"TRADE_STATUS"];//订单状态
"订单号:
"+strOrderNO+
"金额:
"+strPrice);
//成功,可美化
该页面,提示信息
Response.Write("------------------------------------------");
Response.Write("Result:
responseTxt="+responseTxt);
mysign="+mysign);
sign="+sign);
Response.Write("支付失败");
//支付失败,提示信息
除此之外在Notify.aspx页面和Return.aspx页面公用的一些方法,可以提取出来放在一个公共的类里面(Alipay.cs)
Alipay.cs
usingSystem.Security.Cryptography;
usingSystem.Net;
///NewInterfaceforAliPay
///namespaceGateway
publicclassAliPay
///与ASP兼容的MD5加密算法
publicstaticstringGetMD5(strings,string_input_charset)
MD5md5=newMD5CryptoServiceProvider();byte[]t=
md5.ComputeHash(Encoding.GetEncoding(_input_charset).GetBytes(s));
StringBuildersb=
newStringBuilder(
32);
for(inti=
0;i {sb.Append(t[i].ToString("x").PadLeft(2,'0'));}returnsb.ToString();} //////冒泡排序法///按照字母序列从a到z的顺序排列///publicstaticstring[]BubbleSort(string[]r){inti,j;//交换标志stringtemp; boolexchange; for(i=0;i//最多做R.Length-1趟排序{exchange=false;//本趟排序开始前,交换标志应为假for(j=r.Length-2;j>=i;j--){//交换条件0)if(System.String.CompareOrdinal(r[j+1],r[j])<{temp=r[j+1];r[j+1]=r[j];r[j]=temp; exchange =true;//发生了交换,故将交换标志置为真}} if(!exchange)//本趟排序未发生交换,提前终止算法{break;}}returnr;} //////生成URL链接或加密结果//////参数加密数组///编码格式///加密类型///安全校验码///字符
sb.Append(t[i].ToString("x").PadLeft(2,'0'));
returnsb.ToString();
///冒泡排序法
///按照字母序列从a到z的顺序排列
publicstaticstring[]BubbleSort(string[]r)
inti,j;//交换标志
stringtemp;
boolexchange;
for(i=
0;i//最多做R.Length-1趟排序{exchange=false;//本趟排序开始前,交换标志应为假for(j=r.Length-2;j>=i;j--){//交换条件0)if(System.String.CompareOrdinal(r[j+1],r[j])<{temp=r[j+1];r[j+1]=r[j];r[j]=temp; exchange =true;//发生了交换,故将交换标志置为真}} if(!exchange)//本趟排序未发生交换,提前终止算法{break;}}returnr;} //////生成URL链接或加密结果//////参数加密数组///编码格式///加密类型///安全校验码///字符
//
最多做R.Length-1
趟排序
exchange=
false;
//本趟排序开始前,交换标志应为假
for(j=r.Length-
2;j>=i;j--)
//交换条件
0)
if(System.String.CompareOrdinal(r[j+
1],r[j])<
temp=r[j+
1];
r[j+
1]=r[j];
r[j]=temp;
exchange
=true;//发生了交换,故将交换标志置为真
if(!
exchange)//本趟排序未发生交换,提前终止算法
break;
returnr;
///生成URL链接或加密结果
///参数加密数组
///编码格式
///加密类型
///安全校验码
///字符
copyright@ 2008-2022 冰豆网网站版权所有
经营许可证编号:鄂ICP备2022015515号-1