一 支付宝/银联:
0 TD_MARCHANT(ID NUMBER NAME PASSWORD EMAIL URL STATUS CREATEBY CREATEDATE LADTEDITBY LASTEDITDATE DELETEBY DELETEDATE) 当前商户/支付宝商户/银联商户
0 TD_ORDER(ID ORDERNUM MARCHANTID COURSEID USERID PAYMETHOD PAYSTATUS CREATEDATE) PAYSTATUS 支付状态 W Y Z
1 创建商户表/订单表
1 设置传递参数/回调参数的model
1 后台商户管理(DIDAO/支付宝/银联)
0 判断课程是否可用,如果可学,就不需要再支付
1 获得请求(COURSEID)
2 设置传入参数(通过 获得课程信息/商户信息/第三方信息即秘钥)
3 设置sign
3 插入订单表TD_ORDER(未支付)
4 调用接口传入所需参数
5 获得接口回调的参数
6 计算sign
7 判断回传sign和计算的sign是否相等
8 如果相等,更新TD_ORDER状态和插入TD_USERCOURSE
9 调转到该课程所在的章节列表
注意:
md5加密必须是utf-8的二进制转小写
购买该课程之前,需要先检查是该课程已经可用,如果可用,不需要购买
二 支付宝支付:
支付宝模拟器 http://paytest.rupeng.cn/
流程参考《实物商品交易服务集成技术文档2.0.pdf》
网关地址http://paytest.rupeng.cn/AliPay/PayGate.ashx
网关参数说明:
partner:商户编号
return_url:回调商户地址(通过商户网站的哪个页面来通知支付成功!)
subject:商品名称
body:商品描述
out_trade_no:订单号!!!(由商户网站生成,支付宝不确保正确性,只负责转发。)
total_fee:总金额
seller_email:卖家邮箱
sign:数字签名。为按顺序连接 总金额、 商户编号、订单号、商品名称、商户密钥的MD5值。
回调商户接口地址参数说明:
out_trade_no:订单号。给PayGate.ashx传过去的out_trade_no再传回来
returncode:返回码,字符串。ok为支付成功,error为支付失败。
total_fee:支付金额
sign:数字签名。为按顺序连接 订单号、返回码、支付金额、商户密钥为新字符串的MD5值。
三 银联支付:
流程参考《网银在线支付B2C系统商户接口文档.zip》
网关地址http://paytest.rupeng.cn/ChinaBank/PayGate.ashx
网关参数说明:
v_mid:商户编号
v_oid:订单号
v_amount:总金额
v_moneytype:币种。0为人民币,1为外币。
v_url:回调商户地址
v_md5info:数字签名。为按顺序连接 总金额、币种、订单号、商户编号、商户密钥为新字符串的MD5值。
style:网关模式:0(普通列表),2(银行列表中带外卡)
remark1:备注1。可空。
remark2:备注2。可空。
回调商户接口地址参数说明:
v_oid:订单号
v_pmode:支付银行。目前值衡为0.
v_pstatus:支付结果。20为成功,30为支付失败
v_amount:总金额
v_moneytype:币种。0为人民币,1为外币。
remark1:传递的备注1。
remark2:传递的备注1。
v_md5str:数字签名。为按顺序连接 订单号、支付结果、总金额、币种、商户密钥为新字符串的MD5值。
四 实例(支付宝支付/银联支付):
#region 支付 public void paymethod(HttpContext context) { #region 支付方式 string courseidStr = context.Request["courseid"]; int courseid = VolidHelper.CheckStrToInt(courseidStr); #region 如果可用,就不用购买 #region 获得该课程 object obj = new MyORM_BLL().SelectModelById(typeof(TD_COURSE), 1, courseid); if (obj == null) { RazorHelper.RazorParse(context, "~/error.cshtml", new { Msg = "未查询到该课程:courseid=" + courseid }); return; } TD_COURSE course = obj as TD_COURSE; #endregion #region 获得当前用户ID long? carrid = LoginHelper.GetSessionID(context); if (carrid == null) { context.Response.Redirect("/Login/LoginController.ashx?action=index"); return; } long currid = Convert.ToInt64(carrid); #endregion bool flag = new CourseBLL().CheckCourseIsLearn(course, currid); if (flag) { context.Response.Redirect("/Course/CourseController_chapter" + courseid + ".ashx"); return; } #endregion RazorHelper.RazorParse(context, "~/Course/PayMethod.cshtml", new { courseid = courseid }); #endregion } public void alipaycome(HttpContext context) { #region 支付宝 传参数 #region 逻辑 //1 获得请求(COURSEID MARCHANTID) //2 设置传入参数(获得课程信息 和商户信息) //3 设置sign //3 插入订单表TD_ORDER(未支付) //4 调用接口传入所需参数 #endregion //获得请求(COURSEID MARCHANTID) string courseidStr = context.Request["courseid"]; int courseid = VolidHelper.CheckStrToInt(courseidStr); #region 获得该课程 object obj = new MyORM_BLL().SelectModelById(typeof(TD_COURSE), 1, courseid); if (obj == null) { RazorHelper.RazorParse(context, "~/error.cshtml", new { Msg = "未查询到该课程:Courseid=" + courseid }); return; } TD_COURSE course = obj as TD_COURSE; #endregion #region 获得当前商户 object objMarchant = new MyORM_BLL().SelectModelById(typeof(TD_MARCHANT), 1, 1); //id=1 表示当前商户为DIDAO if (objMarchant == null) { RazorHelper.RazorParse(context, "~/error.cshtml", new { Msg = "未查询到当前商户:MarchantID=1" }); return; } TD_MARCHANT curriMarchant = objMarchant as TD_MARCHANT; #endregion #region 获得当前支付第三方信息(约定的秘钥) object objAlipay = new MyORM_BLL().SelectModelById(typeof(TD_MARCHANT), 1, 2); //id=2 表示当前商户为支付宝 if (objAlipay == null) { RazorHelper.RazorParse(context, "~/error.cshtml", new { Msg = "未查询到当前支付第三方信息:MarchantID=2" }); return; } TD_MARCHANT alipay = objAlipay as TD_MARCHANT; #endregion //设置传入参数(获得课程信息 和商户信息) TD_Alipay_ParaCome apc = new TD_Alipay_ParaCome(); #region 实例化 apc apc.body = course.NAME + "很不错"; apc.out_trade_no = Guid.NewGuid().ToString(); apc.partner = curriMarchant.NUM; apc.return_url = curriMarchant.URL + "Course/CourseController.ashx?action=alipayresult"; apc.seller_email = curriMarchant.EMAIL; apc.subject = course.NAME; apc.total_fee = course.PRICE.ToString(); #endregion apc.sign = CommonHelper.Md5EncodeByUTF8(apc.total_fee + apc.partner + apc.out_trade_no + apc.subject + alipay.PASSWORD).ToLower(); //插入订单表TD_ORDER(未支付) #region 获得当前用户ID long? carrid = LoginHelper.GetSessionID(context); if (carrid == null) { context.Response.Redirect("/Login/LoginController.ashx?action=index"); return; } long currid = Convert.ToInt64(carrid); #endregion TD_ORDER order = new TD_ORDER(); #region 实例化 order order.COURSEID = courseid; order.CREATEDATE = DateTime.Now; order.MARCHANTID = curriMarchant.ID; order.ORDERNUM = apc.out_trade_no; order.PAYMETHOD = "Z"; order.PAYSTATUS = "W"; order.USERID = currid; #endregion bool flag = new MyORM_BLL().InsertModel(order, "SE_TD_ORDER"); context.Response.Redirect("http://paytest.rupeng.cn/AliPay/PayGate.ashx?partner=" + apc.partner + "&return_url=" + apc.return_url + "&subject=" + apc.subject + "&body=" + apc.body + "&out_trade_no=" + apc.out_trade_no + "&total_fee=" + apc.total_fee + "&seller_email=" + apc.seller_email + "&sign=" + apc.sign); #endregion } public void alipayresult(HttpContext context) { #region 支付宝 回传结果 #region /获得接口回调的参数 验证 TD_Alipay_ParaResult apr = new TD_Alipay_ParaResult(); apr.out_trade_no = context.Request["out_trade_no"]; apr.returncode = context.Request["returncode"]; apr.total_fee = context.Request["total_fee"]; apr.sign = context.Request["sign"]; #endregion #region 获得当前支付第三方信息(约定的秘钥) object objAlipay = new MyORM_BLL().SelectModelById(typeof(TD_MARCHANT), 1, 2); //当前商户 if (objAlipay == null) { RazorHelper.RazorParse(context, "~/error.cshtml", new { Msg = "未查询到当前支付第三方信息:MarchantID=2" }); return; } TD_MARCHANT alipay = objAlipay as TD_MARCHANT; #endregion //判断回传sign和计算的sign是否相等 string signinner = CommonHelper.Md5EncodeByUTF8(apr.out_trade_no + apr.returncode + apr.total_fee + alipay.PASSWORD).ToLower(); if (string.IsNullOrWhiteSpace(apr.sign) || signinner != apr.sign) { RazorHelper.RazorParse(context, "~/error.cshtml", new { Msg = "支付返回失败:签名错误" }); return; } //如果相等,更新TD_ORDER状态和插入TD_USERCOURSE bool flag = new MyORM_BLL().UpdateFieldByField(typeof(TD_ORDER), "PAYSTATUS='Y'", "ORDERNUM='" + apr.out_trade_no + "'"); if (!flag) { RazorHelper.RazorParse(context, "~/error.cshtml", new { Msg = "支付返回时:更新数据库订单失败" }); return; } #region 根君订单号查询订单 List<object> list = new MyORM_BLL().SelectModelByField(typeof(TD_ORDER), "ORDERNUM='" + apr.out_trade_no + "'"); if (list.Count < 1) { RazorHelper.RazorParse(context, "~/error.cshtml", new { Msg = "支付返回时:未查询到数据库中订单 ORDERNUM=" + apr.out_trade_no }); return; } else if (list.Count > 1) { RazorHelper.RazorParse(context, "~/error.cshtml", new { Msg = "支付返回时:数据库异常,查询到重复的订单 ORDERNUM=" + apr.out_trade_no }); return; } TD_ORDER order = list[0] as TD_ORDER; #endregion #region 获得当前用户ID long? carrid = LoginHelper.GetSessionID(context); if (carrid == null) { context.Response.Redirect("/Login/LoginController.ashx?action=index"); return; } long currid = Convert.ToInt64(carrid); #endregion TD_USERCOURSE uc = new TD_USERCOURSE(); #region 实例化 uc uc.ACTIVEDATE = DateTime.Now; uc.COURSEID = order.COURSEID; uc.EXPIREDATE = DateTime.Now.AddDays(30); uc.USERID = currid; #endregion bool flagUC = new MyORM_BLL().InsertModel(uc, "SE_TD_USERCOURSE"); RazorHelper.RazorParse(context, "~/Course/PayResult.cshtml", new { courseid = order.COURSEID, msg = "支付宝支付成功,点击查看该课程列表" }); #endregion } public void ebankcome(HttpContext context) { #region 银联支付 传参 #region 逻辑 //1 获得请求(COURSEID) //2 设置传入参数(通过 获得课程信息/商户信息/第三方信息即秘钥) //3 设置sign //3 插入订单表TD_ORDER(未支付) //4 调用接口传入所需参数 #endregion //获得请求(COURSEID MARCHANTID) string courseidStr = context.Request["courseid"]; int courseid = VolidHelper.CheckStrToInt(courseidStr); #region 获得该课程 object obj = new MyORM_BLL().SelectModelById(typeof(TD_COURSE), 1, courseid); if (obj == null) { RazorHelper.RazorParse(context, "~/error.cshtml", new { Msg = "未查询到该课程:Courseid=" + courseid }); return; } TD_COURSE course = obj as TD_COURSE; #endregion #region 获得当前商户 object objMarchant = new MyORM_BLL().SelectModelById(typeof(TD_MARCHANT), 1, 1); //id=1 表示当前商户为DIDAO if (objMarchant == null) { RazorHelper.RazorParse(context, "~/error.cshtml", new { Msg = "未查询到当前商户:MarchantID=1" }); return; } TD_MARCHANT curriMarchant = objMarchant as TD_MARCHANT; #endregion #region 获得当前支付第三方信息(约定的秘钥) object objEbank = new MyORM_BLL().SelectModelById(typeof(TD_MARCHANT), 1, 3); //id=3 表示当前商户为银联 if (objEbank == null) { RazorHelper.RazorParse(context, "~/error.cshtml", new { Msg = "未查询到当前支付第三方信息:MarchantID=3" }); return; } TD_MARCHANT ebank = objEbank as TD_MARCHANT; #endregion //设置传入参数(通过 获得课程信息/商户信息/第三方信息即秘钥) TD_Ebankcome ebc = new TD_Ebankcome(); #region 实例化 ebc ebc.style = "0"; ebc.v_amount = course.PRICE.ToString(); ebc.v_mid = curriMarchant.NUM; ebc.v_moneytype = "0"; ebc.v_oid = Guid.NewGuid().ToString(); ebc.v_url = curriMarchant.URL + "Course/CourseController.ashx?action=ebankresult"; ebc.v_md5info = CommonHelper.Md5EncodeByUTF8(ebc.v_amount + ebc.v_moneytype + ebc.v_oid + ebc.v_mid + ebank.PASSWORD).ToLower(); #endregion //插入订单表TD_ORDER(未支付) #region 获得当前用户ID long? carrid = LoginHelper.GetSessionID(context); if (carrid == null) { context.Response.Redirect("/Login/LoginController.ashx?action=index"); return; } long currid = Convert.ToInt64(carrid); #endregion TD_ORDER order = new TD_ORDER(); #region 实例化 order order.COURSEID = courseid; order.CREATEDATE = DateTime.Now; order.MARCHANTID = curriMarchant.ID; order.ORDERNUM = ebc.v_oid; order.PAYMETHOD = "Y"; order.PAYSTATUS = "W"; order.USERID = currid; #endregion bool flag = new MyORM_BLL().InsertModel(order, "SE_TD_ORDER"); //调用接口传入所需参数 context.Response.Redirect("http://paytest.rupeng.cn/ChinaBank/PayGate.ashx?v_mid=" + ebc.v_mid + "&v_oid=" + ebc.v_oid + "&v_amount=" + ebc.v_amount + "&v_moneytype=" + ebc.v_moneytype + "&v_url=" + ebc.v_url + "&v_md5info=" + ebc.v_md5info + "&style=" + ebc.style); #endregion } public void ebankresult(HttpContext context) { #region 银联支付 回传结果 #region 逻辑 //5 获得接口回调的参数 //6 计算sign //7 判断回传sign和计算的sign是否相等 //8 如果相等,更新TD_ORDER状态和插入TD_USERCOURSE //9 调转到该课程所在的章节列表 #endregion //获得接口回调的参数 验证 TD_EbankResult ebr = new TD_EbankResult(); #region 实例化 ebr ebr.v_oid = context.Request["v_oid"]; ebr.v_pmode = context.Request["v_pmode"]; ebr.v_pstatus = context.Request["v_pstatus"]; ebr.v_amount = context.Request["v_amount"]; ebr.v_moneytype = context.Request["v_moneytype"]; ebr.v_md5str = context.Request["v_md5str"]; #endregion #region 获得当前支付第三方信息(约定的秘钥) object objEbank = new MyORM_BLL().SelectModelById(typeof(TD_MARCHANT), 1, 3); //id=3 表示第三方银联 if (objEbank == null) { RazorHelper.RazorParse(context, "~/error.cshtml", new { Msg = "未查询到当前支付第三方信息:MarchantID=3" }); return; } TD_MARCHANT ebank = objEbank as TD_MARCHANT; #endregion //判断回传sign和计算的sign是否相等 string signinner = CommonHelper.Md5EncodeByUTF8(ebr.v_oid + ebr.v_pstatus + ebr.v_amount + ebr.v_moneytype + ebank.PASSWORD).ToLower(); if (string.IsNullOrWhiteSpace(ebr.v_md5str) || signinner != ebr.v_md5str) { RazorHelper.RazorParse(context, "~/error.cshtml", new { Msg = "支付返回失败:签名错误" }); return; } //如果相等,更新TD_ORDER状态和插入TD_USERCOURSE bool flag = new MyORM_BLL().UpdateFieldByField(typeof(TD_ORDER), "PAYSTATUS='Y'", "ORDERNUM='" + ebr.v_oid + "'"); if (!flag) { RazorHelper.RazorParse(context, "~/error.cshtml", new { Msg = "支付返回时:更新数据库订单失败" }); return; } #region 根君订单号查询订单 List<object> list = new MyORM_BLL().SelectModelByField(typeof(TD_ORDER), "ORDERNUM='" + ebr.v_oid + "'"); if (list.Count < 1) { RazorHelper.RazorParse(context, "~/error.cshtml", new { Msg = "支付返回时:未查询到数据库中订单 ORDERNUM=" + ebr.v_oid }); return; } else if (list.Count > 1) { RazorHelper.RazorParse(context, "~/error.cshtml", new { Msg = "支付返回时:数据库异常,查询到重复的订单 ORDERNUM=" + ebr.v_oid }); return; } TD_ORDER order = list[0] as TD_ORDER; #endregion #region 获得当前用户ID long? carrid = LoginHelper.GetSessionID(context); if (carrid == null) { context.Response.Redirect("/Login/LoginController.ashx?action=index"); return; } long currid = Convert.ToInt64(carrid); #endregion TD_USERCOURSE uc = new TD_USERCOURSE(); #region 实例化 uc uc.ACTIVEDATE = DateTime.Now; uc.COURSEID = order.COURSEID; uc.EXPIREDATE = DateTime.Now.AddDays(30); uc.USERID = currid; #endregion bool flagUC = new MyORM_BLL().InsertModel(uc, "SE_TD_USERCOURSE"); RazorHelper.RazorParse(context, "~/Course/PayResult.cshtml", new { courseid = order.COURSEID, msg = "银联支付成功,点击查看该课程列表" }); #endregion } #endregion