CSDN博客安全认证机制揭秘:Java实现x-ca-nonce与x-ca-signature生成与验证
# 结论
**直接上结论,后面分析部分感兴趣的可以看一下,不感兴趣的忽略即可**
1. x-ca-key,x-ca-signature-headers:可以看做固定值
2. x-ca-nonce:随机串,只要格式和位数和csdn的一致即可,也可以用固定值
4. x-ca-signature:是对请求信息加密后的结果,用的是HmacSHA256加密算法,目前的加密appSecret = "9znpamsyl2c7cdrr9sas0le9vbc3r6ba",后续可能会变动
5. 需要加密的内容:请求方式,accept ,contentType ,date(默认空字符串),x-ca-key(固定值),x-ca-nonce(随机串),path(去掉域名部分),请求参数(只有get请求有,post请求,没有这部分)组成中间用\n分割,示例如下
```
"POST\n*/*\n\napplication/json\n\nx-ca-key:203803574\nx-ca-nonce:eff837eb-901e-403f-9ed3-d17d0227b16b\n/blog-console-api/v3/mdeditor/saveArticle"
```
7. post请求由于参数不参与加密,所以可以直接复用浏览器里面的x-ca-nonce和x-ca-signature
8. 怎么生成签名可以参考测试用例部分:将测试用例里面的请求方式信息和x-ca-nonce换成自己的即可,其中x-ca-nonce也可以不换,最好还是每次新生成一个
# Java代码实战
以下代码是基于springboot编写,基本框架已经搭建好,可以直接运行,获取签名的工具类已经准备到位,工具类的单元测试已经ok
## x-ca-nonce生成
直接调用就行,就是个随机串,格式一致就行,没啥特别好说的
```java
public class XCaNonceGenerator {
public static String generateXCaNonce() {
Random rand = new SecureRandom();
StringBuilder xCaNonce = new StringBuilder();
String charList = "abcdefghijklmnopqrstuvwxyz0123456789";
for (int i = 0; i < 36; i++) {
if (i == 8 || i == 13 || i == 18 || i == 23) {
xCaNonce.append("-");
} else if (i == 14) {
xCaNonce.append("4");
} else {
xCaNonce.append(charList.charAt(rand.nextInt(charList.length())));
}
}
return xCaNonce.toString();
}
public static void main(String[] args) {
System.out.println(generateXCaNonce());
}
}
```
## 自定义数据传输对象
只需要构建好此对象,直接传入HmacSHA256Util的getXCaSignature()方法即可获得x-ca-signature
```java
@Data
@Accessors(chain = true)
public class HmacSHA256Dto {
/**
* 请求方式(大写)
*/
public String method;
/**
* 请求头中的accept(直接从浏览器拷贝即可)
*/
public String accept;
/**
* 请求头中的content-type(直接从浏览器拷贝即可)
*/
public String contentType="";
/**
* 当前版本默认空字符串
*/
public String date = "";
/**
* 请求的url
*/
public String url;
/**
* 加密秘钥,暂时是这个固定值,后期可能会变,需要留意
*/
public String appSecret = "9znpamsyl2c7cdrr9sas0le9vbc3r6ba";
/**
* get请求的参数
*/
public Map<String,Object> params;
/**
* 当前默认值为203803574,后期可能会变
*/
public String xCaKey = "203803574";
/**
* 随机串
*/
public String xCaNonce;
}
```
## 获取签名的工具类
```java
public class HmacSHA256Util {
@SneakyThrows
private static String hmacSHA256(String secret, String message) {
Mac hmacSha256 = Mac.getInstance("HmacSHA256");
SecretKeySpec secret_key = new SecretKeySpec(secret.getBytes(), "HmacSHA256");
hmacSha256.init(secret_key);
byte[] bytes = hmacSha256.doFinal(message.getBytes());
return Base64.getEncoder().encodeToString(bytes);
}
/**
* 构建需要加密的字符串
*/
@SneakyThrows
private static String getMessage(HmacSHA256Dto hmacSHA256Dto) {
URL url = new URL(hmacSHA256Dto.url);
// 处理get请求的查询参数,例如 id=136507441&model_type=
String query = url.getQuery();
if (StringUtils.hasText(query)) {
// 例如 id=136507441
String[] split = query.split("&");
for (String s : split) {
String[] kv = s.split("=");
if (kv.length == 2) {
hmacSHA256Dto.getParams().put(kv[0], kv[1]);
} else {
hmacSHA256Dto.getParams().put(kv[0], "");
}
}
}
String path = url.getPath();
StringBuilder sb = new StringBuilder();
sb.append(hmacSHA256Dto.method).append("\n")
.append(hmacSHA256Dto.accept).append("\n\n")
.append(hmacSHA256Dto.contentType).append("\n")
.append(hmacSHA256Dto.date).append("\n")
.append("x-ca-key:").append(hmacSHA256Dto.xCaKey).append("\n")
.append("x-ca-nonce:").append(hmacSHA256Dto.xCaNonce).append("\n")
.append(path);
Map<String, Object> params = hmacSHA256Dto.params;
if (!CollectionUtils.isEmpty(params)) {
List<String> keys = new ArrayList<>(params.keySet());
Collections.sort(keys);
for (int i = 0; i < keys.size(); i++) {
String value = keys.get(i);
if (StringUtils.hasText(value)) {
if (i == 0) {
sb.append("?").append(value).append("=").append(params.get(value));
} else {
sb.append("&").append(value).append("=").append(params.get(value));
}
}
}
}
if (sb.lastIndexOf("=") == sb.length() - 1) {
sb.deleteCharAt(sb.lastIndexOf("="));
}
return sb.toString();
}
/**
* 获取签名
*/
public static String getXCaSignature(HmacSHA256Dto hmacSHA256Dto) {
String message = getMessage(hmacSHA256Dto);
return hmacSHA256(hmacSHA256Dto.getAppSecret(), message);
}
}
```
# 单元测试
单元测试所在包com.csdn.signature.utils.HmacSHA256UtilTest
## Post请求单元测试
```java
@Test
public void postTest() {
// 请求信息
// curl 'https://bizapi.csdn.net/blog-console-api/v3/mdeditor/saveArticle' \
// -H 'accept: */*' \
// -H 'accept-language: zh-CN,zh;q=0.9,en;q=0.8' \
// -H 'content-type: application/json' \
// -H 'cookie: ' \
// -H 'origin: https://editor.csdn.net' \
// -H 'referer: https://editor.csdn.net/' \
// -H 'sec-ch-ua: "Google Chrome";v="123", "Not:A-Brand";v="8", "Chromium";v="123"' \
// -H 'sec-ch-ua-mobile: ?0' \
// -H 'sec-ch-ua-platform: "Windows"' \
// -H 'sec-fetch-dest: empty' \
// -H 'sec-fetch-mode: cors' \
// -H 'sec-fetch-site: same-site' \
// -H 'user-agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/123.0.0.0 Safari/537.36' \
// -H 'x-ca-key: 203803574' \
// -H 'x-ca-nonce: 04db9c7c-b281-4117-944a-98c86d9f27a2' \
// -H 'x-ca-signature: qWbIIf/nSO/fNFuHO3cIl0kG+y2uZI2M+8xiLapq8B4=' \
// -H 'x-ca-signature-headers: x-ca-key,x-ca-nonce' \
HmacSHA256Dto hmacSHA256Dto = new HmacSHA256Dto();
hmacSHA256Dto.setMethod("POST").setAccept("*/*")
.setContentType("application/json")
.setXCaNonce("04db9c7c-b281-4117-944a-98c86d9f27a2")
.setUrl("https://bizapi.csdn.net/blog-console-api/v3/mdeditor/saveArticle");
String xCaSignature = HmacSHA256Util.getXCaSignature(hmacSHA256Dto);
System.out.println("x-ca-signature:" + xCaSignature);
}
```
运行结果
```java
x-ca-signature:qWbIIf/nSO/fNFuHO3cIl0kG+y2uZI2M+8xiLapq8B4=
```
可以看到只要随机串x-ca-nonce一样,我们生成的和页面的签名是一样的,此处也可以得出一个结论,相同请求(如果get请求参数也要相同),x-ca-nonce一样生成的x-ca-signature就是一样的,post请求的参数�
没有合适的资源?快使用搜索试试~ 我知道了~
CSDN博客安全认证机制揭秘:Java实现x-ca-nonce与x-ca-signature生成与验证.zip
共15个文件
class:5个
java:5个
properties:2个
1.该资源内容由用户上传,如若侵权请联系客服进行举报
2.虚拟产品一经售出概不退款(资源遇到问题,请及时私信上传者)
2.虚拟产品一经售出概不退款(资源遇到问题,请及时私信上传者)
版权申诉
0 下载量 200 浏览量
2024-04-29
13:21:45
上传
评论
收藏 55KB ZIP 举报
温馨提示
前端核心js分析,Java代码生成x-ca-nonce与x-ca-signature
资源推荐
资源详情
资源评论
收起资源包目录
CSDN博客安全认证机制揭秘:Java实现x-ca-nonce与x-ca-signature生成与验证.zip (15个子文件)
CSDN博客安全认证机制揭秘:Java实现x-ca-nonce与x-ca-signature生成与验证
csdn-signature
pom.xml 2KB
src
test
java
com
csdn
signature
ApplicationTests.java 226B
utils
HmacSHA256UtilTest.java 5KB
main
resources
application.properties 0B
java
com
csdn
signature
Application.java 324B
utils
HmacSHA256Util.java 3KB
dto
HmacSHA256Dto.java 1KB
target
classes
application.properties 0B
com
csdn
signature
Application.class 725B
utils
HmacSHA256Util.class 4KB
dto
HmacSHA256Dto.class 6KB
test-classes
com
csdn
signature
ApplicationTests.class 523B
utils
HmacSHA256UtilTest.class 3KB
generated-test-sources
test-annotations
generated-sources
annotations
.gitignore 428B
readme.md 14KB
共 15 条
- 1
资源评论
九转成圣
- 粉丝: 2159
- 资源: 354
上传资源 快速赚钱
- 我的内容管理 展开
- 我的资源 快来上传第一个资源
- 我的收益 登录查看自己的收益
- 我的积分 登录查看自己的积分
- 我的C币 登录后查看C币余额
- 我的收藏
- 我的下载
- 下载帮助
安全验证
文档复制为VIP权益,开通VIP直接复制
信息提交成功