Java加密算法—消息摘要及文件消息摘要

导读:本篇文章讲解 Java加密算法—消息摘要及文件消息摘要,希望对大家有帮助,欢迎收藏,转发!站点地址:www.bmabk.com

1、概述

  • 消息摘要(Message Digest)又称为数字摘要(Digital Digest)。
  • 它是一个唯一对应一个消息或文本的固定长度的值,它由一个单向Hash加密函数对消息进行作用而产生。
  • 为了保证文件或者值的安全,使用数字摘要生成的值是不可以篡改的。

无论输入的消息有多长,计算出来的消息摘要的长度总是固定的。例如应用MD5算法摘要的消息有128个比特位,用SHA-1算法摘要的消息最终有160比特位的输出。

只要输入的消息不同,对其进行摘要以后产生的摘要消息也必不相同;但相同的输入必会产生相同的输出。

常见算法 :

  • MD5算法 : 摘要结果16个字节, 转16进制后32个字节
  • SHA1算法 : 摘要结果20个字节, 转16进制后40个字节
  • SHA256算法 : 摘要结果32个字节, 转16进制后64个字节
  • SHA512算法 : 摘要结果64个字节, 转16进制后128个字节

2、文本消息摘要

public class DigestUtil {
    /**
     * MD5 加密长度:32字节数量
     */
    private final static String MD5 = "MD5";
    /**
     * SHA1 加密长度:40字节数量
     */
    private final static String SHA1 = "SHA-1";
    /**
     * SHA256 加密长度:64字节数量
     */
    private final static String SHA256 = "SHA-256";
    /**
     * SHA512 加密长度:128字节数量
     */
    private final static String SHA512 = "SHA-512";


    public static void main(String[] args) {
        String input = "test";

        // 消息摘要算法
        System.out.println("MD5加密:" + encryptDigest(input, MD5));
        System.out.println("SHA1加密:" + encryptDigest(input, SHA1));
        System.out.println("SHA256加密:" + encryptDigest(input, SHA256));
        System.out.println("SHA512加密:" + encryptDigest(input, SHA512));
    }

    /***
     * 消息摘要算法,是单向、不可逆的
     *
     * @param input 消息类型
     * @param algorithm 算法类型:MD5、SHA-1、SHA-256、SHA-512
     * @return
     */
    public static String encryptDigest(String input, String algorithm) {
        try {
            MessageDigest messageDigest = MessageDigest.getInstance(algorithm);
            // 消息数字摘要
            byte[] digest = messageDigest.digest(input.getBytes());

            return toHex(digest);
        } catch (Exception e) {
            e.printStackTrace();
            throw new RuntimeException("加密失败!");
        }
    }

    private static String toHex(byte[] digest) {
        // 创建对象用来拼接
        StringBuilder sb = new StringBuilder();

        for (byte b : digest) {
            // 转成 16进制
            String s = Integer.toHexString(b & 0xff);
            if (s.length() == 1) {
                // 如果生成的字符只有一个,前面补0
                s = "0" + s;
            }
            sb.append(s);
        }
        return sb.toString();
    }
}

效果:
在这里插入图片描述

3、文件消息摘要

文件消息摘要的产生和文件名称没有关系,任意修改名称后摘要密文不会发生改变。

public class DigestUtil {
    /**
     * MD5 加密长度:32字节数量
     */
    private final static String MD5 = "MD5";
    /**
     * SHA1 加密长度:40字节数量
     */
    private final static String SHA1 = "SHA-1";
    /**
     * SHA256 加密长度:64字节数量
     */
    private final static String SHA256 = "SHA-256";
    /**
     * SHA512 加密长度:128字节数量
     */
    private final static String SHA512 = "SHA-512";


    public static void main(String[] args) {

        // 获取文件消息摘要
        String filePath = "C:\\Users\\Desktop\\test.txt";
        System.out.println("获取文件消息MD5摘要:" + getDigestFile(filePath, MD5));
        System.out.println("获取文件消息SHA1摘要:" + getDigestFile(filePath, SHA1));
        System.out.println("获取文件消息SHA256摘要:" + getDigestFile(filePath, SHA256));
        System.out.println("获取文件消息SHA512摘要:" + getDigestFile(filePath, SHA512));
    }

    /**
     * @param filePath
     * @param algorithm
     * @return
     * @throws Exception
     */
    private static String getDigestFile(String filePath, String algorithm) {
        try {
            FileInputStream fis = new FileInputStream(filePath);
            int len;
            byte[] buffer = new byte[1024];
            ByteArrayOutputStream baos = new ByteArrayOutputStream();
            while ((len = fis.read(buffer)) != -1) {
                baos.write(buffer, 0, len);
            }
            // 获取消息摘要对象
            MessageDigest messageDigest = MessageDigest.getInstance(algorithm);
            // 获取消息摘要
            byte[] digest = messageDigest.digest(baos.toByteArray());
            System.out.println("文件摘要-密文的字节长度:" + digest.length);
            return toHex(digest);
        } catch (Exception e) {
            e.printStackTrace();
            throw new RuntimeException("获取文件摘要失败!");
        }
    }


    private static String toHex(byte[] digest) {
        // 创建对象用来拼接
        StringBuilder sb = new StringBuilder();

        for (byte b : digest) {
            // 转成 16进制
            String s = Integer.toHexString(b & 0xff);
            if (s.length() == 1) {
                // 如果生成的字符只有一个,前面补0
                s = "0" + s;
            }
            sb.append(s);
        }
        return sb.toString();
    }
}

效果:
在这里插入图片描述

版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 举报,一经查实,本站将立刻删除。

文章由极客之家整理,本文链接:https://www.bmabk.com/index.php/post/18085.html

(0)
小半的头像小半

相关推荐

极客之家——专业性很强的中文编程技术网站,欢迎收藏到浏览器,订阅我们!