网找了好久没有找到相关的资料,都是提问的没有回答,在这里发一下,做为笔记吧!
第一步:准备资料
开通汇付天下后,需要从http://mas.chinapnr.com/gam 下需二个签名验签DLL文件(ChinaPnr.dll,pnrpay.dll),这个是用来做RSA加解密的.
另外分别是两个Key文件,分别提公钥与私钥文件.例如:PgPubk.key与MerPrK510010.key.
第二步:官方推荐是在服务器上注册DLL文件
例如你将DLL文件放在C:/DLL文件夹下面。则在“开始”-“运行”中输入regsvr32 C:\DLL\ChinaPnr.dll,个人不推荐这样做,特别有的朋友是用虚拟机的,先不说提供商是否愿意,从安全角度来说也是有一定的风险性的.
我的方法是,DllImport使用非托管的方式来调用,msdn关于DllImport属性类的链接:
http://msdn.microsoft.com/zh-cn/library/system.runtime.interopservices.dllimportattribute(v=VS.100).aspx
//将两个DLL放在Web站点的Bin目录下
[DllImport("pnrpay.dll", EntryPoint = "SignMsg")]
public static extern int SignMsg(string MerId, string MerPubFile, string MsgData, int MsgLen, StringBuilder chkVal);
[DllImport("pnrpay.dll", EntryPoint = "VeriSignMsg")]
public static extern int VeriSignMsg(string MerKeyFile, string MsgData, int MsgLen, string chkVal);
第三步:创建支付订单
参数说明,就请自己参考文档了.
string msgData = Version + CmdId + MerId + OrdId + OrdAmt + CurCode + Pid + RetUrl + MerPriv + GateId + UsrMp + DivDetails + PayUsrId + BgRetUrl;
string chkVal = string.Empty;
//私钥文件的位置(这里是放在了站点的根目录下)
string pubPath = AppDomain.CurrentDomain.BaseDirectory + "MerPrK510010.key";
StringBuilder outchkVal = new StringBuilder(256);
//需要指定提交字符串的长度,汇付天下没有指定编码的功能,他们只接受GBK的数据,而且开发文档里面也不说明这个.
int len = Encoding.GetEncoding(936).GetBytes(msgData).Length;
int flag = SignMsg(this.MerId, pubPath, msgData, len, outchkVal);
this.ChkVal = outchkVal.ToString();
//填充为POST提交就OK啦!
最后:再写一个检验的方法
//我的站点是UTF8的.一开始,怎么都无法检验正确,后来联系了汇付才知道,他们的POST都是GBK的.在处理长度时需要注意.
public int CheckSignMsg(string msgData, string chkVal)
{
string pubPath = AppDomain.CurrentDomain.BaseDirectory + "PgPubk.key";
int len = Encoding.GetEncoding(936).GetBytes(msgData).Length; //需要取得GBK编码时的长度.
return VeriSignMsg(pubPath, msgData, len, chkVal);
}
注意:
如果你发现UTF8站点不做转码也可以正常验证,那是因为返回的字符串是全英文和数字的.做退款异步通知时,他的POST数据中就有中文,需要注意.如果你的站点也是GBK的那么就不用处理了.