代码:

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 + "&notify_url=" + notify_url_encode + "&sign_type=" + sign_type_encode + "&timestamp=" + 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支付签名和验签的更多相关文章

  1. NodeJs支付宝移动支付签名及验签

    非常感谢 :http://www.jianshu.com/p/8513e995ff3a?utm_campaign=hugo&utm_medium=reader_share&utm_co ...

  2. 微信,支付宝,支付异步通知验签,notify_url

    在支付接口开发中 ,当用户支付完成之后,阿里或者微信会向我们服务器发送一个支付结果的通知,里边带有一系列参数:其中特殊的是签名类型,和签名(他们根据这些参数做出来的签名). 我们的得到这些参数之后要去 ...

  3. Delphi支付宝支付【支持SHA1WithRSA(RSA)和SHA256WithRSA(RSA2)签名与验签】

    作者QQ:(648437169) 点击下载➨Delphi支付宝支付             支付宝支付api文档 [Delphi支付宝支付]支持条码支付.扫码支付.交易查询.交易退款.退款查询.交易撤 ...

  4. 支付宝app支付服务器签名代码(C#)

    1,引入支付宝的sdk(AopSdk) 支付宝接口文档网站可下载,注意下载C#版本: 2,代码写的比较简单 public static string RSASign(string OrderNo,de ...

  5. 支付宝APP支付之Java后台生成签名具体步骤

    /** *支付宝支付 * @param orderId 订单编号 * @param actualPay 实际支付金额 * @return */ private String getOrderInfoB ...

  6. Delphi微信支付【支持MD5和HMAC-SHA256签名与验签】

    作者QQ:(648437169) 点击下载➨微信支付            微信支付api文档 [Delphi 微信支付]支持付款码支付.二维码支付.订单查询.申请退款.退款查询.撤销订单.关闭订单. ...

  7. 支付宝app支付java后台流程、原理分析(含nei wang chuan tou)

    java版支付宝app支付流程及原理分析 本实例是基于springmvc框架编写     一.流程步骤         1.执行流程           当手机端app(就是你公司开发的app)在支付 ...

  8. 支付宝APP支付IOS手机端java后台版

    版权声明:http://blog.csdn.net/u012131769/article/details/76639527#t8 转载:http://blog.csdn.net/u012131769/ ...

  9. .Net后台实现支付宝APP支付

    前面讨论了微信支付,接下来聊聊支付宝的APP支付(新款支付宝支付).其实这些支付原理都一样,只不过具体到每个支付平台,所使用的支付配置参数不同,返回至支付端的下单参数也不同. 话不多说,直接上代码. ...

随机推荐

  1. 在大于32GB或64GB容量的SD卡上使用NOOB安装树莓派 - Using NOOB on SD cards larger than 32GB or 64GB for Raspberry Pi

    在树莓派上玩了一小段时间了,因为装的软件包越来越多,所以越来越感觉16G的SD卡没办法长期使用下去.于是采购了几张64G的SD卡,打算周末装上系统.可是按照一般的流程,在Windows下用SD For ...

  2. LVS+keepalived负载均衡实战

    1 首先安装虚拟机 安装系统 这里 配置两台虚拟机 1:192.168.137.102   2:192.168.137.103 分别安装tomcat 默认80端口,同时都是开启状态 配置192.168 ...

  3. Life cycle of plist in Lockdown changes dramatically in iOS 10

    We could take advantage of plist to bypass Trust Relationship so as to extract data from a iDevice. ...

  4. MySQL 第八天(核心优化二)

    一.昨天内容回顾 存储引擎 保存数据的格式(技术),不同格式体现特性不一样 myisam ① 结构.数据.索引 文件单独存储 ② 存入数据顺序(不考虑主键顺序) ,写入数据速度快 ③ 并发性,低,锁整 ...

  5. xhprof学习笔记

    一.简介 XHProf 是一个轻量级的分层性能测量分析器. 在数据收集阶段,它跟踪调用次数与测量数据,展示程序动态调用的弧线图. 它在报告.后期处理阶段计算了独占的性能度量,例如运行经过的时间.CPU ...

  6. MYSQL 中 update set from where 问题

    MySQL 和 SQLSERVER不一样,update set from 一张表的时候 应该改为 UPDATE TABLE_AA INNER JOIN TABLE_BB ON TABLE_AA.ID ...

  7. net命令

    net命令可以完成非常多的任务.通过键入 net /? 可以查看net命令的详细列表. 在所有的Windows机器上,net命令使用统一的命令集合,这对于网络管理员来说是非常方便的. 使用net命令可 ...

  8. vs2010 创建预编译头 Debug 正常 Release Link Error问题解决

    问题:创建预编译头 Debug 正常 Release Link Error Main.obj : error LNK2005: ___@@_PchSym_@00@UmfilkilqUdrmzkkUki ...

  9. @MappedSuperclass注解的使用说明

    转载自:http://blog.sina.com.cn/s/blog_7085382f0100uk4p.html 基于代码复用和模型分离的思想,在项目开发中使用JPA的@MappedSuperclas ...

  10. SQL Server 索引(index) 和 视图(view) 的简单介绍和操作

    --索引(index)和视图(view)-- --索引(index)----概述: 数据库中的索引类似于书籍的目录,他以指针形式包含了表中一列或几列组合的新顺序,实现表中数据库的逻辑排序.索引创建在数 ...