### [MD5] 签名规则
#### 所有接口都需签名验证 方式统一 回调同理
空值不参与签名,url参数如果携带了url字符串则需要urlencode
**sign_type 不参与签名**
* * *
假如签名数据为 A
1 . 将A按照 字段名的ASCII码从小到大排序 (A-Z)
2 . 除Sign 与 空值参数外 所有参数进行Url字符串形式的拼接 例:appid=12345678&out\_trade\_no=xxx.... 且假设拼接好的Url字符串为B
3 . 将B与Key进行拼接 b+key**注意 + 为各语言的分隔符 并不是字符**
最后MD5一下即为Sign签名(小写)
* * *
### PHP:
~~~
function getSign($param, $key)
{
$signPars = "";
ksort($param);
foreach ($param as $k => $v) {
if ("sign" != $k && "" != $v) {
$signPars .= $k . "=" . $v . "&";
}
}
$signPars = rtrim($signPars, '&');
$signPars .= $key;
$sign = md5($signPars);
return $sign;
}
~~~
* * *
### JAVA:
~~~
/**
* 签名生成算法
* @param HashMap params 请求参数集,所有参数必须已转换为字符串类型
* @param String secret 签名密钥
* @return 签名
* @throws IOException
*/
public static String getSignature(HashMap params, String secret) throws IOException
{
// 先将参数以其参数名的字典序升序进行排序
Map sortedParams = new TreeMap(params);
Set> entrys = sortedParams.entrySet();
// 遍历排序后的字典,将所有参数按"key=value"格式拼接在一起
StringBuilder basestring = new StringBuilder();
for (Entry param : entrys) {
basestring.append(param.getKey()).append("=").append(param.getValue());
}
basestring.append(secret);
// 使用MD5对待签名串求签
byte[] bytes = null;
try {
MessageDigest md5 = MessageDigest.getInstance("MD5");
bytes = md5.digest(basestring.toString().getBytes("UTF-8"));
} catch (GeneralSecurityException ex) {
throw new IOException(ex);
}
// 将MD5输出的二进制结果转换为小写的十六进制
StringBuilder sign = new StringBuilder();
for (int i = 0; i < bytes.length; i++) {
String hex = Integer.toHexString(bytes[i] & 0xFF);
if (hex.length() == 1) {
sign.append("0");
}
sign.append(hex);
}
return sign.toString();
}
~~~
* * *
### 易语言:
~~~
.子程序 sign计算, 文本型, 公开
.参数 param, 文本型
.参数 key, 文本型
.局部变量 signpars, 文本型
.局部变量 分割, 文本型, , "0"
.局部变量 x, 整数型
.局部变量 k, 文本型
.局部变量 v, 文本型
.局部变量 sign, 文本型
分割 = 分割文本 (param, “&”, )
数组_排序 (分割, 0, )
.计次循环首 (取数组成员数 (分割), x)
k = 文本_取左边 (分割 [x], “=”, , )
v = 文本_取右边 (分割 [x], “=”, , )
.如果真 (k ≠ “sign” 且 v ≠ “”)
.如果 (x = 取数组成员数 (分割))
signpars = signpars + k + “=” + v
.否则
signpars = signpars + k + “=” + v + “&”
.如果结束
.如果真结束
.计次循环尾 ()
signpars = signpars + key
sign = 取数据摘要 (到字节集 (signpars))
返回 (sign)
~~~
* * *
### C#:
~~~
///
/// 计算参数签名
///
/// 请求参数集,所有参数必须已转换为字符串类型
/// 签名密钥
/// 签名
public static string getSignature(IDictionary parameters, string secret)
{
// 先将参数以其参数名的字典序升序进行排序
IDictionary sortedParams = new SortedDictionary(parameters);
IEnumerator> iterator= sortedParams.GetEnumerator();
// 遍历排序后的字典,将所有参数按"key=value"格式拼接在一起
StringBuilder basestring= new StringBuilder();
while (iterator.MoveNext()) {
string key = iterator.Current.Key;
string value = iterator.Current.Value;
if (!string.IsNullOrEmpty(key) && !string.IsNullOrEmpty(value)){
basestring.Append(key).Append("=").Append(value);
}
}
basestring.Append(secret);
// 使用MD5对待签名串求签
MD5 md5 = MD5.Create();
byte[] bytes = md5.ComputeHash(Encoding.UTF8.GetBytes(basestring.ToString()));
// 将MD5输出的二进制结果转换为小写的十六进制
StringBuilder result = new StringBuilder();
for (int i = 0; i < bytes.Length; i++) {
string hex = bytes[i].ToString("x");
if (hex.Length == 1) {
result.Append("0");
}
result.Append(hex);
}
return result.ToString();
~~~