Flutter如何实现微信支付验签

在Flutter中接入微信支付时,如何正确实现服务端返回的支付结果验签?我按照官方文档处理了sign字段,但总是验签失败。具体需要对比哪些参数?是否需要对参数进行URL编码或排序?有没有现成的Dart验签工具类可以参考?

2 回复

在Flutter中实现微信支付验签,需以下步骤:

  1. 获取支付结果,包含签名(sign字段)。
  2. 使用商户密钥(API密钥)按微信规则拼接参数。
  3. 对拼接字符串进行MD5加密生成签名。
  4. 比较生成的签名与返回的sign是否一致,一致则验签成功。

注意:确保参数按字典序排序且排除空值和sign字段。

更多关于Flutter如何实现微信支付验签的实战系列教程也可以访问 https://www.itying.com/category-92-b0.html


在Flutter中实现微信支付验签,主要涉及验证服务器返回的支付结果签名,确保数据未被篡改。以下是关键步骤和代码示例:

核心步骤

  1. 获取参数:从支付回调中获取所有参数(如 appid, mch_id, nonce_str, prepay_id, sign 等)。
  2. 排除签名字段:从参数中移除 sign 字段本身。
  3. 参数排序:按字典序对参数名进行升序排序。
  4. 拼接字符串:使用 key=value 格式拼接参数,用 & 连接。
  5. 生成签名:将拼接的字符串与商户密钥(API Key)连接,进行MD5加密(或HMAC-SHA256,根据配置)。
  6. 比对签名:将生成的签名与回调中的 sign 字段比对,一致则验签成功。

代码示例

import 'dart:convert';
import 'dart:io';
import 'package:crypto/crypto.dart';

bool verifyWeChatPaySignature(Map<String, dynamic> params, String apiKey) {
  // 1. 获取签名并移除sign字段
  String receivedSign = params['sign'] ?? '';
  params.remove('sign');

  // 2. 按字典序排序参数名
  List<String> keys = params.keys.toList()..sort();

  // 3. 拼接键值对
  StringBuffer sb = StringBuffer();
  for (String key in keys) {
    String value = params[key]?.toString() ?? '';
    if (value.isNotEmpty) {
      sb.write('$key=$value&');
    }
  }

  // 4. 添加商户密钥
  sb.write('key=$apiKey');

  // 5. 生成MD5签名(微信支付默认使用MD5)
  String generatedSign = md5.convert(utf8.encode(sb.toString())).toString().toUpperCase();

  // 6. 比对签名
  return generatedSign == receivedSign;
}

注意事项

  • 密钥管理:商户密钥(API Key)需安全存储,避免硬编码在客户端。
  • 签名类型:确认微信支付配置的签名类型(MD5或HMAC-SHA256),上述示例为MD5。
  • 服务端验证:建议在服务端进行验签,客户端仅作参考,避免密钥泄露风险。

通过以上步骤,即可在Flutter中完成微信支付结果的签名验证。

回到顶部