1、服务接口公共报文域-签名生成
<h1>1、上送报文的公共报文域</h1>
<p>定义说明:</p>
<table>
<thead>
<tr>
<th>报文域</th>
<th>格式</th>
<th>最大长度</th>
<th>必输</th>
<th>含义</th>
<th>备注</th>
</tr>
</thead>
<tbody>
<tr>
<td>merchant_id</td>
<td>String</td>
<td>50</td>
<td>Y</td>
<td>商户ID</td>
<td>由融赋通分配</td>
</tr>
<tr>
<td>partner_id</td>
<td>String</td>
<td>50</td>
<td>Y</td>
<td>代理渠道ID</td>
<td>由融赋通分配</td>
</tr>
<tr>
<td>timestamp</td>
<td>String</td>
<td>17</td>
<td>Y</td>
<td>当前时间戳,格式为yyyyMMddHHmmssSSS</td>
<td>由商户系统产生</td>
</tr>
<tr>
<td>sign_type</td>
<td>String</td>
<td>10</td>
<td>Y</td>
<td>签名类型SHA256</td>
<td>与商户服务平台中配置一致</td>
</tr>
<tr>
<td>sign</td>
<td>String</td>
<td>1024</td>
<td>Y</td>
<td>生成签名的base64编码</td>
<td>按约定生成</td>
</tr>
</tbody>
</table>
<h1>2、签名sign生成约定</h1>
<h2>1)、上送报文,加签前(举例)</h2>
<pre><code>{
&quot;merchant_id&quot;: &quot;testMerchant001&quot;,
&quot;partner_id&quot;: &quot;RFT&quot;,
&quot;timestamp&quot;: &quot;20180924235824387&quot;,
&quot;sign_type&quot;: &quot;SHA256&quot;
}</code></pre>
<h2>2)、把所有参数根据参数名k排序(升序)并拼接</h2>
<pre><code>merchant_id=testMerchant001&amp;partner_id=RFT&amp;sign_type=SHA256&amp;timestamp=20180924235824387</code></pre>
<h2>3)、追加签名密钥signGenerationKey(如:key=282b00eb561b455caac86925c6xxxxxx)</h2>
<p>merchant_id=testMerchant001&partner_id=RFT&sign_type=SHA256&timestamp=20180924235824387&key=282b00eb561b455caac86925c6xxxxxx</p>
<h2>4)、生成签名并base64</h2>
<pre><code>0g02YUW2fRRrAaMlYrwUmVAS1rb6loTJQ+4ffFNB7DM=</code></pre>
<h2>5)、最终上送报文</h2>
<pre><code>{
&quot;merchant_id&quot;: &quot;testMerchant001&quot;,
&quot;partner_id&quot;: &quot;RFT&quot;,
&quot;timestamp&quot;: &quot;20180924235824387&quot;,
&quot;sign_type&quot;: &quot;SHA256&quot;,
&quot;sign&quot;: &quot;0g02YUW2fRRrAaMlYrwUmVAS1rb6loTJQ+4ffFNB7DM=&quot;
}</code></pre>
<h1>3、生成签名核心代码参考</h1>
<pre><code>/**
* 参数排序
* @param values
* @return 排序后输出String
*/
private static String getSortKVStr(Map&lt;String, Object&gt; values) {
List&lt;String&gt; keys = new ArrayList&lt;&gt;(values.keySet());
Collections.sort(keys);
StringBuilder sb = new StringBuilder();
for (String key : keys) {
//附件不参与签名验签
if (&quot;file&quot;.equals(key)) {
continue;
}
Object value = values.get(key);
if (value == null) {
continue;
}
if (&quot;&quot;.equals(value))
continue;
if (sb.length() &gt; 0)
sb.append('&amp;');
sb.append(key).append(&quot;=&quot;).append(value);
}
String sortKVStr = sb.toString();
System.out.println(&quot;sort kv string for sign:&quot; + sortKVStr);
return sortKVStr;
}
public static void main(String[] args) {
try {
String signGenerationKey = &quot;282b00eb561b455caac86925c6xxxxxx&quot;;
// 举例输入参数
String param = &quot;{\n&quot; +
&quot;\t\&quot;merchant_id\&quot;: \&quot;testMerchant001\&quot;,\n&quot; +
&quot;\t\&quot;partner_id\&quot;: \&quot;RFT\&quot;,\n&quot; +
&quot;\t\&quot;timestamp\&quot;: \&quot;20180924235824387\&quot;,\n&quot; +
&quot;\t\&quot;sign_type\&quot;: \&quot;SHA256\&quot;\n&quot; +
&quot;}&quot;;
JSONObject jsonObject = JSON.parseObject(param);
// 参数排序
String paramSort = getSortKVStr(jsonObject);
System.out.println(paramSort);
// 追加签名密钥signGenerationKey
String paramSortAppendkey = paramSort + &quot;&amp;key=&quot; + signGenerationKey;
System.out.println(paramSortAppendkey);
MessageDigest digest = MessageDigest.getInstance(&quot;SHA-256&quot;);
// 执行加签转base64
byte[] paramHash = digest.digest(paramSortAppendkey.getBytes(StandardCharsets.UTF_8));
String base64Sign = Base64.getEncoder().encodeToString(paramHash);
System.out.println(&quot;Base64 encoded SHA256 hash: &quot; + base64Sign);
} catch (NoSuchAlgorithmException e) {
e.printStackTrace();
}
}</code></pre>