支付宝App支付签名和验签
代码:
using CMS.Utility.ReturnResult;
using OAuthWebAPI.Package;
using Common;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Net;
using System.Net.Http;
using System.Web.Http;
using Ninject;
using System.Data;
using Aop.Api;
using Aop.Api.Request;
using Aop.Api.Response;
using System.Text;
using System.Web;
using System.Web.Script.Serialization;
using Aop.Api.Util; namespace ADT.TuDou.OAuthWebAPI.Controllers
{
public class TestAliPayController : ApiController
{
private static readonly log4net.ILog logger = log4net.LogManager.GetLogger(System.Reflection.MethodBase.GetCurrentMethod().DeclaringType); /// <summary>
/// 支付宝同步通知
/// AliPay/AliPayCallBack
/// </summary>
/// <param name="data"></param>
/// <returns></returns>
[AcceptVerbs("POST")]
[Authorize]
public HttpResponseMessage AliPayCallBack([FromBody]PostModel.AliPayCallBackModel data)
{
//参考:https://doc.open.alipay.com/docs/doc.htm?spm=a219a.7629140.0.0.o060pE&treeId=193&articleId=105302&docType=1
MessagesDataCodeModel json = new MessagesDataCodeModel(false, "无效参数", );
{
try
{
if (data.resultStatus == "")
{
json.Success = true;
json.Msg = "操作成功";
json.Code = ;
}
else if (data.resultStatus == "")
{
json.Success = false;
json.Msg = "正在处理中";
json.Code = ;
}
else if (data.resultStatus == "")
{
json.Success = false;
json.Msg = "订单支付失败";
json.Code = ;
}
else if (data.resultStatus == "")
{
json.Success = false;
json.Msg = "重复请求";
json.Code = ;
}
else if (data.resultStatus == "")
{
json.Success = false;
json.Msg = "用户中途取消";
json.Code = ;
}
else if (data.resultStatus == "")
{
json.Success = false;
json.Msg = "网络连接出错";
json.Code = ;
}
else if (data.resultStatus == "")
{
json.Success = false;
json.Msg = "支付结果未知";
json.Code = ;
}
else
{
json.Success = false;
json.Msg = "其他未知错误";
json.Code = ;
}
}
catch (Exception ex)
{
json.Success = false;
json.Msg = "服务器无响应";
json.Code = ;
json.Data = ex.Message;
logger.Error("AliPayController.AliPayCallBack", ex);
}
return ToJsonTran.ToJson(json);
}
} /// <summary>
/// 阿里异步通知
/// AliPay/Notify
/// </summary>
/// <returns></returns>
[AcceptVerbs("POST")]
public void Notify()
{
//验签(解决问题成功率90 %) issig为false,一般有几种可能:
//1、支付宝公鈅(特别是PHP编程语言,一定要用demo中的支付宝公钥文件)或者key有问题;
//2、参与验签的待签名字符串存在中文乱码,或者多了商户的自定义参数(异步通知地址带自定义参数;),或者少了一些异步通知参数;
//3、需要RSA验签,但是商户用MD5验签;
//4、验签的编码格式有问题(主要是java和c#);
//5、验签的代码逻辑有问题,强烈建议参考demo的 //[FromBody]PostModel.AliNotify data
//参考地址:https://doc.open.alipay.com/docs/doc.htm?spm=a219a.7629140.0.0.XZMUaR&treeId=204&articleId=105301&docType=1
//编码(101-登录无效,102-账号无效,200-成功,201-失败,202~299-其他原因1-99,300-无效提交方式,400-无效参数)
MessagesDataCodeModel json = new MessagesDataCodeModel(false, "无效参数", );
string result = "failed";
try
{
#region 验签
//获取所有通知参数,其中sign不要解码
IDictionary<string, string> dic = GetParas();
//string signContent = AlipaySignature.GetSignContent(dic);//验签字符串
//支付宝公钥
string publicKeyPem_Alipay = HttpContext.Current.Server.MapPath("~/alipay/rsa_public_key_alipay.pem");
//验签,公共类库下载地址:
bool ValidateSign = AlipaySignature.RSACheckV1(dic, publicKeyPem_Alipay, ConfigApi.AliPay_App_charset);
#endregion #region 处理订单
if (ValidateSign)
{
//处理订单的业务逻辑...
result = "success";
}
else
{
result = "RSACheckV1Error";
logger.Error("AliPayController.Notify【验签失败】");
}
#endregion
}
catch (Exception ex)
{
logger.Error("AliPay/Notify", ex);
result = "exception";
}
HttpContext.Current.Response.Write(result);
HttpContext.Current.Response.End();
} /// <summary>
/// RSA签名
/// AliPay/Sign
/// 系统平台 ios 、android
/// pro_type 商品类型 购买官方录音专辑=1,购买Vip会员=2,购买绘本=3,快乐英语=4,打赏优秀专家=5,打赏优秀机构=6,打赏优秀电台=7,
/// </summary>
/// <param name="data"></param>
/// <returns></returns>
[AcceptVerbs("POST")]
[Authorize]
public HttpResponseMessage Sign([FromBody]PostModel.biz_content data)
{
//编码(101-登录无效,102-账号无效,200-成功,201-失败,202~299-其他原因1-99,300-无效提交方式,400-无效参数)
MessagesDataCodeModel json = new MessagesDataCodeModel(false, "无效参数", ); try
{
if (data != null)
{
//生成签名之前,编写自己的验证逻辑... //订单编号
string out_trade_no = Guid.NewGuid().ToString().Replace("-", "");
double total_fee = 0.01;//费用 1分钱(测试) #region 生成签名
string publicKeyPem = HttpContext.Current.Server.MapPath("~/alipay/rsa_public_key.pem");//公钥
string privateKeyPem = HttpContext.Current.Server.MapPath("~/alipay/rsa_private_key.pem");//私钥
string app_id = ConfigApi.AliPay_App_app_id;//app支付,支付宝中该应用的ID
string seller_id = ConfigApi.AliPay_App_seller_id;//商户账户
string method = ConfigApi.AliPay_App_method;//alipay.trade.app.pay
string charset = ConfigApi.AliPay_App_charset;//utf-8
string timestamp = DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss");
string version = @"1.0";
string sign_type = @"RSA";
string timeout_express = "30m";
string notify_url = ConfigApi.AliPay_App_notify_url;
string body = data.body;
string subject = data.subject; //拼接签名使用的字符串【编码】
string app_id_encode = HttpUtility.UrlEncode(app_id, Encoding.GetEncoding(charset));//
string charset_encode = HttpUtility.UrlEncode(charset, Encoding.GetEncoding(charset));//
string method_encode = HttpUtility.UrlEncode(method, Encoding.GetEncoding(charset));//
string sign_type_encode = HttpUtility.UrlEncode(sign_type, Encoding.GetEncoding(charset));//
string timestamp_encode = HttpUtility.UrlEncode(timestamp, Encoding.GetEncoding(charset));//
string version_encode = HttpUtility.UrlEncode(version, Encoding.GetEncoding(charset));//
string notify_url_encode = HttpUtility.UrlEncode(ConfigApi.AliPay_App_notify_url, Encoding.GetEncoding(charset));//
string body_encode = HttpUtility.UrlEncode(data.body, Encoding.GetEncoding(charset));//
string subject_encode = HttpUtility.UrlEncode(data.subject, Encoding.GetEncoding(charset));//
//订单内容
string biz_content = "{\"body\":\"" + body + "\",\"subject\":\"" + subject + "\",\"out_trade_no\":\"" + out_trade_no + "\",\"timeout_express\":\"" + timeout_express + "\",\"total_amount\":\"" + total_fee + "\",\"seller_id\":\"" + seller_id + "\",\"product_code\":\"QUICK_MSECURITY_PAY\"}";
//将订单内容编码,必须和支付宝指定的编码一致 utf-8
string biz_content_encode = HttpUtility.UrlEncode(biz_content, Encoding.GetEncoding(charset));
//构建签名参数集合
IDictionary<string, string> dic = new Dictionary<string, string>();
dic.Add("app_id", app_id);
dic.Add("biz_content", biz_content);
dic.Add("charset", charset);
dic.Add("method", method);
dic.Add("notify_url", notify_url);
dic.Add("sign_type", sign_type);
dic.Add("timestamp", timestamp);
dic.Add("version", version);
//得到签名字符串
string result1 = Aop.Api.Util.AlipaySignature.RSASign(dic, privateKeyPem, charset, true, sign_type);
//把得到的签名字符串使用指定的格式编码(utf-8),返回给客户端再用utf-8解码就行了
string result = HttpUtility.UrlEncode(result1, Encoding.GetEncoding(charset));
string jsonStr = Aop.Api.Util.AlipaySignature.GetSignContent(dic);//得到签名原字符串,客户端要用(支付宝提供的方法)
//下面是我手动拼接的,其实阿里提供的有...
//@"app_id=" + app_id_encode + "&biz_content=" + biz_content_encode + "&charset=" + charset_encode + "&method=" + method_encode + "¬ify_url=" + notify_url_encode + "&sign_type=" + sign_type_encode + "×tamp=" + timestamp_encode + "&version=" + version_encode;
#endregion #region 生成订单,返回 out_trade_no
//生成订单的逻辑...
#endregion
json.Success = true;
json.Msg = "操作成功";
json.Code = ;
json.Data = new { TradeNo = out_trade_no, Sign = result, SignContent = jsonStr };
}
}
catch (Exception ex)
{
json.Success = false;
json.Msg = "服务器无响应";
json.Code = ;
json.Data = ex.Message;
logger.Error("AliPay/Sign", ex);
}
return ToJsonTran.ToJson(json);
}
public string GetPara(string ParaName)
{
string result = HttpContext.Current.Request[ParaName];
if (!string.IsNullOrEmpty(result))
{
return result;
}
return "";
}
public string GetPara_Decode(string ParaName)
{
string result = HttpContext.Current.Request[ParaName];
if (!string.IsNullOrEmpty(result))
{
return HttpUtility.UrlDecode(result, System.Text.Encoding.GetEncoding(ConfigApi.AliPay_App_charset));
}
return "";
}
public IDictionary<string, string> GetParas()
{
IDictionary<string, string> dic = new Dictionary<string, string>();
for (int i = ; i < HttpContext.Current.Request.Form.Keys.Count; i++)
{
string key = HttpContext.Current.Request.Form.Keys[i].ToString();
string value = "";
if (key != "sign")
{
value = GetPara_Decode(key);
}
else
{
value = GetPara(key);
}
if (!string.IsNullOrEmpty(value))
{
dic.Add(key, value);
}
}
return dic;
}
}
}
签名类:
#region 支付签名 实体类
public class biz_content
{
/// <summary>
/// 订单描述 [传入]
/// </summary>
public string body { get; set; }
/// <summary>
/// 订单标题 [传入]
/// </summary>
public string subject { get; set; }
/// <summary>
/// 付款总金额 [传入]
/// </summary>
public string total_amount { get; set; }
/// <summary>
/// 订单编号GUID
/// </summary>
public string out_trade_no { get; set; }
/// <summary>
/// 订单有效时限
/// </summary>
public string timeout_express { get; set; }
}
#endregion
文档:https://doc.open.alipay.com/docs/doc.htm?spm=a219a.7629140.0.0.9CZS6Q&treeId=193&articleId=105465&docType=1
主要看的有四篇:申请支付请求参数说明、客户端同步返回、支付结构异步通知、交易操作接口
服务端SDK下载:https://doc.open.alipay.com/docs/doc.htm?spm=a219a.7629140.0.0.huKVyy&treeId=54&articleId=103419&docType=1
支付宝App支付签名和验签的更多相关文章
- NodeJs支付宝移动支付签名及验签
非常感谢 :http://www.jianshu.com/p/8513e995ff3a?utm_campaign=hugo&utm_medium=reader_share&utm_co ...
- 微信,支付宝,支付异步通知验签,notify_url
在支付接口开发中 ,当用户支付完成之后,阿里或者微信会向我们服务器发送一个支付结果的通知,里边带有一系列参数:其中特殊的是签名类型,和签名(他们根据这些参数做出来的签名). 我们的得到这些参数之后要去 ...
- Delphi支付宝支付【支持SHA1WithRSA(RSA)和SHA256WithRSA(RSA2)签名与验签】
作者QQ:(648437169) 点击下载➨Delphi支付宝支付 支付宝支付api文档 [Delphi支付宝支付]支持条码支付.扫码支付.交易查询.交易退款.退款查询.交易撤 ...
- 支付宝app支付服务器签名代码(C#)
1,引入支付宝的sdk(AopSdk) 支付宝接口文档网站可下载,注意下载C#版本: 2,代码写的比较简单 public static string RSASign(string OrderNo,de ...
- 支付宝APP支付之Java后台生成签名具体步骤
/** *支付宝支付 * @param orderId 订单编号 * @param actualPay 实际支付金额 * @return */ private String getOrderInfoB ...
- Delphi微信支付【支持MD5和HMAC-SHA256签名与验签】
作者QQ:(648437169) 点击下载➨微信支付 微信支付api文档 [Delphi 微信支付]支持付款码支付.二维码支付.订单查询.申请退款.退款查询.撤销订单.关闭订单. ...
- 支付宝app支付java后台流程、原理分析(含nei wang chuan tou)
java版支付宝app支付流程及原理分析 本实例是基于springmvc框架编写 一.流程步骤 1.执行流程 当手机端app(就是你公司开发的app)在支付 ...
- 支付宝APP支付IOS手机端java后台版
版权声明:http://blog.csdn.net/u012131769/article/details/76639527#t8 转载:http://blog.csdn.net/u012131769/ ...
- .Net后台实现支付宝APP支付
前面讨论了微信支付,接下来聊聊支付宝的APP支付(新款支付宝支付).其实这些支付原理都一样,只不过具体到每个支付平台,所使用的支付配置参数不同,返回至支付端的下单参数也不同. 话不多说,直接上代码. ...
随机推荐
- FreeMark学习(二)
(1)用户定义指令 宏和变换器变量是两种不同类型的用户定义指令,它们之间的区别是宏是在模板中使用macro指令定义,而变换器是在模板外由程序定义,这里只介绍宏 基本用法 宏是和某个变量关联的模板片断, ...
- RunLoop的模式
RunLoop的模式有Default模式.Connection模式.Modal模式.Event tracking模式和Common模式. 1) NSDefaultRunLoopMode: 大多数工作中 ...
- cut命令
cut是一个选取命令,就是将一段数据经过分析,取出我们想要的.一般来说,选取信息通常是针对"行"来进行分析的,并不是整篇信息分析的. (1)其语法格式为:cut [-bn] [f ...
- java 静态代码块 构造块 构造方法
class className{ static{ }//静态代码块 { }//构造代码块 public className(){} //构造方法 }
- 高可用Hadoop平台-Flume NG实战图解篇
1.概述 今天补充一篇关于Flume的博客,前面在讲解高可用的Hadoop平台的时候遗漏了这篇,本篇博客为大家讲述以下内容: Flume NG简述 单点Flume NG搭建.运行 高可用Flume N ...
- Install Shield 打包教程
我的是已经下载过打包工具InstallShield2013LimitedEdition,没有下载的只有下面那个灰色的的图标,不过没关系选中灰色的点确定直接跳到下载页面了.下载完成后再重新添加安装和部署 ...
- linux 学习1
这里主要是听讲的一些东西的总结, thanks to lamp brother ____安装虚拟机 vmware 8.0.4, 因为高版本占用空间大,没必要 cent OS 6.3 linux 版本 ...
- EntityFramework+MySql 笔记1
最近需要使用mysql ,而之前用惯了EF,所以就尝试EntityFramework+MySql的方案. 首先上网搜了一大通资料后,这样开始: 安装mysql,我用的版本是5.6.25 ( windo ...
- 平板上的js和电脑上js的不同之处
一.事件 1.平板上没有:onmousedown,onmouseup,onmousemove等事件,由ontouchstart,ontouchmove,ontounchend替代 2.位置问题:平板上 ...
- Sublime Text 3 汉化小技巧
Sublime Text 3 简体中文汉化包使用方法 1.将下载的sublime_text3汉化包文件解压,得到的Default.sublime-package 文件.打开sublime text 3 ...