生成秘钥

可以去支付宝开放平台-开发文档下载秘钥生成器
运行可以直接生成长度为2048标准为PKCS1的公钥和私钥。

设置应用公钥

我们生成密钥之后,需要到支付宝后台设置应用公钥,就是我们生成的公钥。

设置之后,支付宝会给我们一个支付宝公钥,保存这个支付宝公钥

这个支付宝公钥和我们自己生成的公钥是不一样的,我们在配置SDK时用的公钥就是支付宝公钥

配置SDK

新建一个Config类,在里面存储我们的配置。
其他信息不变只需要配置

  • 应用ID
  • 商户私钥
  • 支付宝公钥
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
/// <summary>
/// SDK配置
/// </summary>
public class ZFBPayconfig
{
// 应用ID,您的APPID
public static string app_id = "";

// 支付宝网关
public static string gatewayUrl = "https://openapi.alipay.com/gateway.do";

// 商户私钥,您的原始格式RSA私钥
public static string private_key = "";

// 支付宝公钥,查看地址:https://openhome.alipay.com/platform/keyManage.htm 对应APPID下的支付宝公钥。
public static string alipay_public_key = "";

// 签名方式
public static string sign_type = "RSA2";

// 编码格式
public static string charset = "UTF-8";
}

下载官网demo 并将SDK引入到自己的项目中
支付宝当面付demo

直接将demo中的dll复制到项目中直接引用就行

支付

成功之后会返回一个form表单会直接提交
打开一个新页面将要支付的金额传过去

1
window.open("/Fly_Fp/Fly_Fp_Rechargelog/Recharge?money=" 1000;
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
/// <summary>
/// 支付宝充值
/// </summary>
/// <returns></returns>
public string Recharge(string money)
{
try
{
DefaultAopClient client = new DefaultAopClient(ZFBPayconfig.gatewayUrl, ZFBPayconfig.app_id, ZFBPayconfig.private_key, "json", "1.0", ZFBPayconfig.sign_type, ZFBPayconfig.alipay_public_key, ZFBPayconfig.charset, false);

// 外部订单号,商户网站订单系统中唯一的订单号
string out_trade_no = DateTime.Now.ToString("yyyyMMddHHmmss");

// 订单名称
string subject = "发票抬头查询";

// 付款金额
string total_amout = money;

// 商品描述
string body = "";

// 组装业务参数model
AlipayTradePagePayModel model = new AlipayTradePagePayModel();
model.Body = body;
model.Subject = subject;
model.TotalAmount = total_amout;
model.OutTradeNo = out_trade_no;
model.ProductCode = "FAST_INSTANT_TRADE_PAY";

AlipayTradePagePayRequest request = new AlipayTradePagePayRequest();
// 设置同步回调地址
request.SetReturnUrl("http://hc.feiliankeji.cn/Fly_Fp_Rechargelog/Return_url");
// 设置异步通知接收地址
request.SetNotifyUrl("http://hc.feiliankeji.cn/Utility/Notify_url");
// 将业务model载入到request
request.SetBizModel(model);

AlipayTradePagePayResponse response = null;
response = client.pageExecute(request, null, "post");
return response.Body;
}
catch (Exception ex)
{
if (ex is ExceptionEx)
{
throw;
}
else
{
throw ExceptionEx.ThrowServiceException(ex);
}
}
}

运行

异步回调

支付宝同步回调通知(支付成功后跳转到商户网站),是不可靠的,所以这里必须使用异步通知来获取支付结果,异步通知即支付宝主动请求我们提供的地址,我们根据请求数据来校验,获取支付结果。

切记:异步回调请求的方法一定要可以外网访问的不能有过滤器 切记切记

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
/// <summary>
/// 设置异步通知接收地址
/// <summary>
/// <returns></returns>
public ActionResult Notify_url()
{
var res = "";
/* 实际验证过程建议商户添加以下校验。
1、商户需要验证该通知数据中的out_trade_no是否为商户系统中创建的订单号,
2、判断total_amount是否确实为该订单的实际金额(即商户订单创建时的金额),
3、校验通知中的seller_id(或者seller_email) 是否为out_trade_no这笔单据的对应的操作方(有的时候,一个商户可能有多个seller_id/seller_email)
4、验证app_id是否为该商户本身。
*/
Dictionary<string, string> sArray = GetRequestPost();
if (sArray.Count != 0)
{
bool flag = AlipaySignature.RSACheckV1(sArray, ZFBPayconfig.alipay_public_key, ZFBPayconfig.charset, ZFBPayconfig.sign_type, false);
if (flag)
{
//交易状态
//判断该笔订单是否在商户网站中已经做过处理
//如果没有做过处理,根据订单号(out_trade_no)在商户网站的订单系统中查到该笔订单的详细,并执行商户的业务程序
//请务必判断请求时的total_amount与通知时获取的total_fee为一致的
//如果有做过处理,不执行商户的业务程序

//注意:
//退款日期超过可退款期限后(如三个月可退款),支付宝系统发送该交易状态通知
string trade_status = Request.Form["trade_status"];

res = "success";
}
else
{
res = "fail";
}
}
return Content(res);
}
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
/// <summary>
/// 设置异步通知接收地址
/// </summary>
/// <returns></returns>
public Dictionary<string, string> GetRequestPost()
{
int i = 0;
Dictionary<string, string> sArray = new Dictionary<string, string>();
NameValueCollection coll;
//coll = Request.Form;
coll = Request.Form;
String[] requestItem = coll.AllKeys;
for (i = 0; i < requestItem.Length; i++)
{
sArray.Add(requestItem[i], Request.Form[requestItem[i]]);
}
return sArray;

}

同步回调

同步回调即支付成功跳转回商户网站

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
  /// <summary>
/// 设置同步回调地址
/// <summary>
/// <returns></returns>
public ActionResult Return_url()
{
var res = "";
/* 实际验证过程建议商户添加以下校验。
1、商户需要验证该通知数据中的out_trade_no是否为商户系统中创建的订单号,
2、判断total_amount是否确实为该订单的实际金额(即商户订单创建时的金额),
3、校验通知中的seller_id(或者seller_email) 是否为out_trade_no这笔单据的对应的操作方(有的时候,一个商户可能有多个seller_id/seller_email)
4、验证app_id是否为该商户本身。
*/
Dictionary<string, string> sArray = GetRequestGet();
if (sArray.Count != 0)
{
bool flag = AlipaySignature.RSACheckV1(sArray, ZFBPayconfig.alipay_public_key, ZFBPayconfig.charset, ZFBPayconfig.sign_type, false);
if (flag)
{
res = "同步验证通过";
}
else
{
res = "同步验证失败";
}
}
return Content(res);
}
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
/// <summary>
/// 设置同步回调地址
/// </summary>
/// <returns></returns>
public Dictionary<string, string> GetRequestGet()
{
int i = 0;
Dictionary<string, string> sArray = new Dictionary<string, string>();
NameValueCollection coll;
//coll = Request.Form;
coll = Request.QueryString;
String[] requestItem = coll.AllKeys;
for (i = 0; i < requestItem.Length; i++)
{
sArray.Add(requestItem[i], Request.QueryString[requestItem[i]]);
}
return sArray;

}