签名和加解密
本文档是对sdkVersion=47及以上的版本有效,服务端也同步做了低版本sdk兼容,设备端放心接入
EncryptionTests.java
EncryptionUtils.java
一 总体规则 (签名和加解密)
2.1、所有请求带在请求头带如下参数 (签名和加解密)
mac=A8:20:06:B7:C8:B9
cpu= 02c0008145f0462078a3840038350b53
api-version=47
host=api.yudao.iocoder.cn (设备端在请求时一般不用设置,web请求框架自动带入的)
2.2、加解密和验签整体情况说明 (签名和加解密)
对于设备端请求服务器的请求,除了心跳和获取时间戳的请求,其他请求都带签名,如果不带签名,服务端统一返回404错误码,包含http状态码也是404。
服务端返回时,如果返回头中的encryption=true表示返回体数据加密,设备端拿到密文之后,进行解密操作,记住只是data下的数据加密,msg和code正常。
二 盒子签名 (签名和加解密)
签名和验签,加密解密逻辑 1、设备发起业务请求前,先请求服务器拿到最新时钟。域名分 发为/app-api/hnc2fng/gnbht53hdv2/dhgb35dg,主UOTA为心跳接口。
2、备心跳请求时返回时间戳逻辑。 请求/app-api/hnc2fng/gnbht53hdv2/dhgb35dg,而时间戳永远放在data.time字段中,为13位时间戳。
3、主UOTA心跳请求时返回时间戳逻辑。 盒子端的UOTA程序内部不管是否已经激活,都要先请求心跳接口,而时间戳永远放在data.time字段中,为13位时间戳。
4、拿到时间戳之后,设备开始进行签名操作。签名工具类见【<一个文件链接>】,参数如下。
/**
*
* MD5签名
* @param domain 发起请求时使用的域名。从设备端的host请求头获取,设备端在请求时一般不用设置,web请求框架自动带入的。 请求头示例:host=api.yudao.iocoder.cn
* @param mac 设备mac。请求头示例: mac=A8:20:06:B7:C8:B9
* @param cpu 设备cpu。请求头示例:cpu= 02c0008145f0462078a3840038350b53
* @param time 13位时间戳。 服务器有个获取时间戳的接口,通过那个接口 获取后后续请求带上来。请求头示例:time=1750324247858
* @param salt 签名的盐值。建议每个uota版本都不一样,uota写入程序内部后进行混淆处理;服务端通过配置管理和版本对应关系。根据【sdkVersion】从服务端获配置获取
* @param sdkVersion sdk版本 ,机顶盒发起请求时手动设置,服务端从请求头获取。请求头示例: api-version=46
* @return 签名结果
*/
public static String sign(String domain,String mac,String cpu,Long time,String salt,int sdkVersion){
String sign = domain+salt+"8622Nbdf52"+mac+salt+"2d6fndw"+cpu+salt+"3hd73bx6g"+time+salt+"23jhY6DGVhbd";
return getMD5(sign);
}
5、签名结果放在请求头中。所以完整请求头示例如下:
mac=A8:20:06:B7:C8:B9
cpu= 02c0008145f0462078a3840038350b53
api-version=47
# 设备端在请求时一般不用设置,web请求框架自动带入的
host=api.yudao.iocoder.cn
time=1750324247858
# 签名结果
sign=bc7318a3dce54a3e3aa30785eae53abf
三 服务端验签 (签名和加解密)
在服务端进行验签操作。
/**
* 验证签名
* @param domain 发起请求时使用的域名。从设备端的host请求头获取,设备端在请求时一般不用设置,web请求框架自动带入的。 请求头示例:host=api.yudao.iocoder.cn
* @param mac 设备mac。请求头示例: mac=A8:20:06:B7:C8:B9
* @param cpu 设备cpu。请求头示例:cpu= 02c0008145f0462078a3840038350b53
* @param time 13位时间戳。 服务器有个获取时间戳的接口,通过那个接口获取后后续请求带上来。请求头示例:time=1750324247858
* @param salt 签名的盐值。建议每个uota版本都不一样,uota写入程序内部后进行混淆处理;服务端通过配置管理和版本对应关系。根据【sdkVersion】从服务端获配置获取
* @param sdkVersion sdk版本 ,从请求头获取。请求头示例: api-version=46
* @param receivedSign 和字段带上来的签名结果
* @return 验证结果(true=有效,false=无效)
*/
public static boolean verify(String domain, String mac, String cpu, Long time, String salt,int sdkVersion, String receivedSign)
四 数据加解密(当前仅用于域名分发) (签名和加解密)
1、 服务端返回给设备的数据都在body里面,且数据的data经过加密处理。
/**
* 加密方法
* @param plainText 明文
* @param secretKey 密钥。 建议每个uota版本都不一样,uota写入程序内部后进行混淆处理;服务端通过配置管理和版本对应关系。根据【sdkVersion】从服务端获配置获取
* @return 密文
* @throws Exception
*/
public static String encrypt(String plainText, String secretKey)
2、 设备端拿到密文之后,进行解密操作,记住只是data下的数据加密,msg和code正常。
/**
* 解密方法
* @param encryptedText 密文
* @param secretKey 密钥。建议每个uota版本都不一样,uota写入程序内部后进行混淆处理;服务端通过配置管理和版本对应关系。根据【sdkVersion】从服务端获配置获取
* @return 明文
* @throws Exception
*/
// 解密方法
public static String decrypt(String encryptedText, String secretKey)
五 测试环境秘钥信息 (签名和加解密)
--- ###################### 机顶盒请求时验签、加密相关 ######################
app:
api:
security:
# 不需要验签或者加密的的域名
no-need-domain:
# - 127.0.0.1
- localhost
- akrdinfo.cn
- 47.251.5.25
# 需要验证签名在处理的路径
sign-urls:
- /app-api/hnc2fng/ghbn1hebdsh/**
# 需要加密data后返回的路径
encryption-urls:
- /app-api/hnc2fng/ghbn1hebdsh/**
# sdk信息 version-版本号;singKey-sdk签名和验签密钥,其实就是md5盐值;encryptionKey-sdk用于数据加密解密;singTimeDiff-签名时间差,单位毫秒,当前时间和签名带上来的时间超过该值则直接验签失败
sdks:
- version: 47
singKey: jdh2dh7hdbhu3hbfcyHvdhf87NFH67b47
encryptionKey: 1234567887654347
singTimeDiff: 600000
- version: 48
singKey: jdh2dh7hdbhu3hbfcyHvdhf87NFH67b48
encryptionKey: 1234567887654348
singTimeDiff: 600000
六、apifox模拟请求 (签名和加解密)
6.1 获取当前时间 (签名和加解密)
调用【获取当前时间】接口拿到服务器时间,结果如下,记住这个时间,在【生成签名接口,生产环境需要屏蔽】和【获取域名和APK】中都要使用,crul如下
curl --location --request GET 'http://imptor.top:8742/app-api/hnc2fng/gnbht53hdv2/dhgb35dg' \
--header 'api-version: 47' \
--header 'User-Agent: Apifox/1.0.0 (https://apifox.com)' \
--header 'Accept: */*' \
--header 'Host: imptor.top:8742' \
--header 'Connection: keep-alive'
请求结果如下:
{
"code": 200,
"data": {
"time": 1753181666064
},
"msg": ""
}