历史版本20 :数字签名认证 返回文档
编辑时间: 内容长度:图片数:目录数: 修改原因:

目录:

1. 描述编辑

数字签名是以电子的形式存在于数据信息中,或者是作为附件,或者是逻辑上与之有联系的数据,可用于辨别使用人的身份,保证数据的安全性。
目前的数字签名是建立在公共密钥体制基础上,它是公用密钥加密技术的另一类应用。它的主要方式是:报文的发送方从报文文本中生成一个128位的散列值(或报文摘要)。
发送方用自己的私人密钥对这个散列值进行加密来形成发送方的数字签名。这个数字签名将作为报文的附件和报文一起发送给报文的接收方。
报文的接收方首先从接收到的原始报文中计算出128位的散列值(或报文摘要),再用发送方的公用密钥来对报文附加的数字签名进行解密。
如果两个散列值相同、那么接收方就能确认该数字签名是发送方的。通过数字签名能够实现对原始报文的鉴别。
222

2. 思路编辑

9.0采用的方案是RSA的公私钥方案,该方案在跨平台支持不够好,所以10.0引入JWT方案,由于JWT是一个通用的规范,有很多语言版本能支持,并且校验起来更为简单,有使用方便、环境搭建更为容易的优点。

3. 实现方法编辑

3.1 生成密钥
目前只支持HS256(HmacSHA256)的签名算法,所以需要提供一个HmacSHA256的秘钥,以下是JAVA生成的源码,可参考:
import sun.misc.BASE64Encoder; import javax.crypto.Mac; import javax.crypto.spec.SecretKeySpec; private String createSecret() { try { //secret可以自定义的 String secret = "123456"; String message = ""; Mac sha256Hmac = Mac.getInstance("HmacSHA256");//指定算法 SecretKeySpec secret_key = new SecretKeySpec(secret.getBytes(), "HmacSHA256"); sha256Hmac.init(secret_key); BASE64Encoder encoder = new BASE64Encoder();//使用base64对生成的二进制byte流编码 String hash = encoder.encode(sha256Hmac.doFinal(message.getBytes())); return hash;//最终结果 } catch (Exception e) { System.out.println(e.getMessage()); } return ""; }
3.2 获取密钥和fine_digital_signature值
修改上述中的代码,用来获取密钥fine_digital_signature值,这里以GettingStarted.cpt模板为例:
import com.fr.cert.token.JwtBuilder; import com.fr.cert.token.Jwts; import com.fr.cert.token.SignatureAlgorithm; import sun.misc.BASE64Encoder; import javax.crypto.Mac; import javax.crypto.spec.SecretKeySpec; import java.util.Date; public class Test2 { public static void main(String[] args) { //数字签名有效时长 long validTime = 30 * 60 * 1000; //数字签名内容,以访问资源的相对路径作为内容 String path = "GettingStarted.cpt"; //数字签名用的HS256的密钥 String key = createSecret(); //生成fine_digital_signature String fine_digital_signature = createJwt("", "", path, validTime, key); //输出密钥 System.out.println(key); //输出fine_digital_signature System.out.println(fine_digital_signature); } private static String createJwt(String issuer, String id, String subject, long validTime, String key) { SignatureAlgorithm signatureAlgorithm = SignatureAlgorithm.HS256; Date currentTime = new Date(); Date expirationTime = new Date(currentTime.getTime() + validTime); JwtBuilder builder = Jwts.builder() .setIssuer(issuer) .setSubject(subject) .setIssuedAt(currentTime) .setExpiration(expirationTime) .setId(id) .signWith(signatureAlgorithm, key); return builder.compact(); } private static String createSecret() { try { //secret可以自定义的 String secret = "2222222"; String message = ""; Mac sha256Hmac = Mac.getInstance("HmacSHA256"); SecretKeySpec secret_key = new SecretKeySpec(secret.getBytes(), "HmacSHA256"); sha256Hmac.init(secret_key); BASE64Encoder encoder = new BASE64Encoder(); String hash = encoder.encode(sha256Hmac.doFinal(message.getBytes())); return hash; } catch (Exception e) { System.out.println(e.getMessage()); } return ""; } }
编译运行,得到密钥fine_digital_signature的值,如下图:
222
4.2 平台设置

打开决策平台,将【密钥】值拷贝到管理系统>模板认证>数字签名密钥地址中,如下所示:

222

4.3 效果预览

重启服务器,访问模板/view/report?viewlet=***.cpt的时候,需要在访问的url的QueryString或者是请求头中,携带有认证服务器认证通过的签名,参数名为fine_digital_signature,url格式为:/view/report?viewlet=GettingStarted.cpt&fine_digital_signature=值

平台会根据签名来进行数字签名认证的判断,通过认证,显示模板,通不过认证,显示无权限。

效果如下:

222