java SHA加密/解密(附带源码)

06-01 252阅读

目录

  1. 项目背景与动机

  2. 哈希算法概述

    1. 哈希函数基本特性

    2. SHA 系列演进

  3. SHA 算法数学原理

    1. 压缩函数与分组迭代

    2. 初始向量与常量表

    3. 消息填充与附加长度

  4. Java 环境与依赖

    1. JDK 版本与安全策略

    2. Maven/Gradle 配置

  5. 项目结构与模块设计

    1. 包结构

    2. 模块职责

  6. 核心代码实现(SHA-1/SHA-256/SHA-512)

    java SHA加密/解密(附带源码)
    (图片来源网络,侵删)
    1. 通用哈希工具类

    2. 各种 SHA 算法实现方法

      java SHA加密/解密(附带源码)
      (图片来源网络,侵删)
    3. 带盐哈希与多次迭代

    4. HMAC-SHA 实现

      java SHA加密/解密(附带源码)
      (图片来源网络,侵删)
  7. 代码整合示例(详注版)

  8. 方法解读

    1. hash(byte[])

    2. hashHex(String)

    3. hashWithSalt(String, byte[])

    4. verify(String, String)

  9. 进阶话题

    1. 摘要长度与安全性

    2. 碰撞攻击与防范

    3. 密钥派生函数(PBKDF2)

    4. 高性能实现与并行化

  10. 性能优化与安全实践

    1. 缓存与复用 MessageDigest 实例

    2. 防止时序攻击

    3. 安全随机数源

    4. 密码存储最佳实践

  11. 项目实战:Web 登录系统中的 SHA 应用

    1. Spring Boot 集成

    2. 前端密码散列示例

  12. CI/CD 与自动化测试

    1. 单元测试覆盖

    2. 集成测试

    3. 安全扫描

  13. 项目总结与展望

  14. 参考资料与延伸阅读


1. 项目背景与动机

在信息安全领域,数据完整性和身份验证是核心需求之一。与非对称加密不同,哈希算法是一种单向函数,无法从输出反推输入,广泛用于密码存储、消息摘要、数字签名前置处理、数据完整性校验等场景。本项目旨在使用 Java 原生 API(JCA/JCE)及少量手写逻辑,全方位实现 SHA 系列哈希(SHA-1、SHA-256、SHA-512)以及基于 HMAC 的消息认证,提供高可用、易扩展、可测试的工具类,帮助读者:

  • 深入理解 SHA 家族算法原理及实现细节

  • 掌握 Java 中 MessageDigest 的使用与优化

  • 学会带盐(Salted)哈希、多次迭代和 HMAC 的正确姿势

  • 在 Web 系统中安全地存储与校验密码

  • 了解密码学攻击手段及防范最佳实践


    2. 哈希算法概述

    2.1 哈希函数基本特性

    1. 单向性:给定消息 M,易于计算 H(M);但仅凭 H(M),无法高效恢复 M。

    2. 抗碰撞:难以找到 M1≠M2 且 H(M1)=H(M2)。

    3. 抗篡改:对消息进行微小修改,哈希值发生巨大变化(雪崩效应)。

    4. 效率:对任意长度输入都能快速计算。

    2.2 SHA 系列演进

    • SHA-0:1978 年发布,存在安全缺陷,迅速废弃。

    • SHA-1:1995 年发布,输出 160 位摘要;2005 年起被认为不安全,陆续弃用。

    • SHA-2 家族(2001 年):包括 SHA-224、SHA-256、SHA-384、SHA-512;目前主流。

    • SHA-3(Keccak,2015 年):NIST 全面标准,抗碰撞更强。

      本项目聚焦 SHA-1、SHA-256、SHA-512,并扩展 HMAC-SHA256 用于消息认证。


      3. SHA 算法数学原理

      3.1 压缩函数与分组迭代

      SHA 基于 Merkle–Damgård 结构,将任意长度消息分为固定大小的分组(512 位或 1024 位),通过压缩函数迭代处理,并将上一分组的输出作为下一分组的输入状态(中间哈希值)。

      3.2 初始向量与常量表

      • 每种 SHA 算法有一组固定的初始哈希值(IV),如 SHA-256 的 8 个 32 位常量。

      • 压缩函数中使用一系列常量 K,用于每轮迭代的消息扩展与混合。

        3.3 消息填充与附加长度

        • 首先在消息后附加一位“1”位,再用“0”填充,直到消息长度 ≡ (block_size − 64) mod block_size。

        • 最后附加一个 64 位(或 128 位)的大端整数,表示原消息长度(位为单位)。

          整个填充保证消息长度可被分组大小整除。


          4. Java 环境与依赖

          4.1 JDK 版本与安全策略

          • 建议:JDK 11 及以上,内置最新 JCA/JCE,性能更好。

          • 对超长摘要(如 SHA-512)无需额外策略包支持。

            4.2 Maven/Gradle 配置

              
              
                org.slf4j
                slf4j-api
                1.7.36
              
              
                ch.qos.logback
                logback-classic
                1.2.11
              
              
              
                org.junit.jupiter
                junit-jupiter
                5.9.0
                test
              
            
            
            dependencies {
                implementation 'org.slf4j:slf4j-api:1.7.36'
                implementation 'ch.qos.logback:logback-classic:1.2.11'
                testImplementation 'org.junit.jupiter:junit-jupiter:5.9.0'
            }
            

            5. 项目结构与模块设计

            src/main/java
             └─ com.example.sha
                 ├─ util
                 │    └─ SHAUtil.java        # 核心哈希工具类
                 ├─ demo
                 │    └─ App.java            # 演示入口
                 └─ security
                      └─ HMACUtil.java       # HMAC 实现工具
            src/test/java
             └─ com.example.sha
                 ├─ SHAUtilTest.java        # 单元测试
                 └─ HMACUtilTest.java       # HMAC 测试
            
            • SHAUtil:封装 SHA-1、SHA-256、SHA-512、带盐、多次迭代等方法。

            • HMACUtil:基于 Mac 类实现 HMAC-SHA256。

            • App:演示从命令行读取输入,输出哈希结果。

            • 测试类:覆盖各种输入、盐、迭代次数及异常场景。


              6. 核心代码实现(SHA-1/256/512)

              package com.example.sha.util;
              import javax.xml.bind.DatatypeConverter;
              import java.nio.charset.StandardCharsets;
              import java.security.MessageDigest;
              import java.security.NoSuchAlgorithmException;
              import java.security.SecureRandom;
              /**
               * SHAUtil:提供 SHA-1、SHA-256、SHA-512 哈希计算,
               * 支持带盐和多次迭代,以及十六进制输出。
               */
              public class SHAUtil {
                  // 默认迭代次数
                  private static final int DEFAULT_ITERATIONS = 1;
                  /**
                   * 计算纯 SHA-256 哈希,返回十六进制字符串
                   */
                  public static String sha256Hex(String input) {
                      return hashHex(input.getBytes(StandardCharsets.UTF_8), "SHA-256", null, 1);
                  }
                  /**
                   * 计算带 salt 的 SHA-256 哈希,返回十六进制字符串
                   */
                  public static String sha256Hex(String input, byte[] salt, int iterations) {
                      return hashHex(input.getBytes(StandardCharsets.UTF_8), "SHA-256", salt, iterations);
                  }
                  /**
                   * 通用哈希方法
                   *
                   * @param data       要哈希的字节数组
                   * @param algorithm  算法名称,如 SHA-1、SHA-256、SHA-512
                   * @param salt       可选 salt,null 则无盐
                   * @param iterations 迭代次数,至少 1
                   * @return 哈希后十六进制字符串
                   */
                  public static String hashHex(byte[] data, String algorithm, byte[] salt, int iterations) {
                      try {
                          MessageDigest md = MessageDigest.getInstance(algorithm);
                          if (salt != null) {
                              md.update(salt);
                          }
                          byte[] result = md.digest(data);
                          for (int i = 1; i  
              

              7. 代码整合示例

              package com.example.sha.demo;
              import com.example.sha.util.SHAUtil;
              import java.util.Scanner;
              /**
               * App:命令行演示 SHA 哈希功能
               */
              public class App {
                  public static void main(String[] args) {
                      Scanner scanner = new Scanner(System.in, "UTF-8");
                      System.out.println("请输入要计算哈希的字符串:");
                      String input = scanner.nextLine();
                      // 纯 SHA-256
                      String sha256 = SHAUtil.sha256Hex(input);
                      System.out.println("SHA-256: " + sha256);
                      // 带盐 SHA-256,迭代 2 次
                      byte[] salt = SHAUtil.generateSalt(16);
                      String salted = SHAUtil.sha256Hex(input, salt, 2);
                      System.out.println("带盐+迭代 SHA-256: " + salted);
                      System.out.println("Salt (Hex): " + bytesToHex(salt));
                      scanner.close();
                  }
                  private static String bytesToHex(byte[] bytes) {
                      StringBuilder sb = new StringBuilder(bytes.length * 2);
                      for (byte b : bytes) {
                          sb.append(String.format("%02x", b));
                      }
                      return sb.toString();
                  }
              }
              

              注释解读

              • 使用 Scanner 读取用户输入,支持 UTF-8。

              • 调用 SHAUtil 提供的纯哈希和带盐多次迭代哈希两种方式。

              • bytesToHex 辅助方法将 salt 转为可阅读的十六进制字符串。


                8. 方法解读

                8.1 hashHex(byte[] data, String algorithm, byte[] salt, int iterations)

                • 通过 MessageDigest.getInstance(algorithm) 获取实例

                • 如有 salt,先 update(salt),再对数据 digest(data)

                • 迭代多次:对上次输出再次 digest

                • 最终使用 DatatypeConverter.printHexBinary 转为十六进制

                  8.2 sha256Hex(String)

                  • 直接调用通用方法,算法固定为 "SHA-256",无盐,1 次迭代

                    8.3 sha256Hex(String, byte[] salt, int iterations)

                    • 支持自定义 salt 和迭代次数,可用于密码存储强化

                      8.4 generateSalt(int length)

                      • 使用 SecureRandom 生成高质量随机数,保证 salt 不能预测


                        9. 进阶话题

                        9.1 摘要长度与安全性

                        • SHA-1(160 位)已被碰撞攻击击破

                        • SHA-256(256 位)目前认为安全

                        • SHA-512(512 位)更强但性能稍低

                          9.2 碰撞攻击与防范

                          • 预映像攻击:给定 H,难以找到 M 使 H(M)=H

                          • 碰撞攻击:找任意 M1,M2 使 H(M1)=H(M2)

                          • 防范:选用 SHA-2 或 SHA-3 家族,不使用已弃用 SHA-1

                            9.3 密钥派生函数(PBKDF2)

                            • 基于 HMAC-SHA256 的迭代派生,可用 SecretKeyFactory 实现

                            • 用于密码存储,比简单迭代更安全

                              9.4 高性能实现与并行化

                              • 对大数据可分块并行调用 MessageDigest 多实例

                              • 使用 Java 9+ 的 MessageDigest.digest(ByteBuffer) 零拷贝


                                10. 性能优化与安全实践

                                10.1 缓存与复用 MessageDigest 实例

                                • MessageDigest 线程不安全,建议使用 ThreadLocal 缓存

                                  10.2 防止时序攻击

                                  • 对比哈希结果时使用常量时间比对,避免泄露长度或内容差异

                                  • 示例:

                                    public static boolean constantTimeEquals(byte[] a, byte[] b) {
                                        if (a.length != b.length) return false;
                                        int result = 0;
                                        for (int i = 0; i  
                                    

                                    10.3 安全随机数源

                                    • 强制使用 SecureRandom.getInstanceStrong(),在高安全需求下确保熵的质量

                                      10.4 密码存储最佳实践

                                      • 使用带盐、多次迭代或 PBKDF2/HMAC/KDF 存储密码

                                      • 永不保存明文密码


                                        11. 项目实战:Web 登录系统中的 SHA 应用

                                        11.1 Spring Boot 集成

                                        1. 配置:在 application.properties 中存储盐长度和迭代次数

                                        2. 服务层:注册用户时生成 salt 并存储 hash(salt+password);登录时取出 salt 重新哈希比对

                                        3. Controller:接收 JSON,调用服务层完成注册/登录

                                        示例注册流程片段:

                                        byte[] salt = SHAUtil.generateSalt(16);
                                        String passwordHash = SHAUtil.sha256Hex(rawPassword, salt, 10000);
                                        user.setSalt(bytesToHex(salt));
                                        user.setPasswordHash(passwordHash);
                                        userRepository.save(user);
                                        

                                        11.2 前端密码散列示例

                                        • 可在前端使用 Web Crypto API 进行 SHA-256 初步哈希,减轻服务器压力

                                        • 仍需后端带盐迭代以确保安全


                                          12. CI/CD 与自动化测试

                                          12.1 单元测试覆盖

                                          • 测试空字符串、普通字符串、带 Unicode 字符串哈希结果

                                          • 测试带盐、不带盐、不同迭代次数的输出长度与稳定性

                                            12.2 集成测试

                                            • Spring Boot @WebMvcTest 模拟注册登录接口,确保哈希、存储、比对流程正确

                                              12.3 安全扫描

                                              • 使用 OWASP Dependency-Check 插件扫描依赖

                                              • 定期使用 Snyk 运行安全审计


                                                13. 项目总结与展望

                                                本文从理论到实践,完整讲解了 Java 版 SHA 哈希(含带盐、多次迭代、HMAC)项目的设计与实现。通过本项目,你将能够:

                                                • 深刻理解 SHA 系列算法原理

                                                • 熟练使用 Java MessageDigest、Mac 等 API

                                                • 掌握密码存储与验证的安全最佳实践

                                                • 在 Web 应用中安全集成哈希流程

                                                  未来可继续拓展:

                                                  • 引入 PBKDF2、bcrypt、scrypt 等专业 KDF 算法

                                                  • 对接硬件安全模块(HSM)增强安全

                                                  • 实现 SHA-3 与其它哈希函数对比研究


                                                    14. 参考资料与延伸阅读

                                                    • Java 官方文档:Java Cryptography Architecture (JCA)

                                                    • NIST FIPS PUB 180-4: Secure Hash Standard

                                                    • OWASP 密码存储指南

                                                    • 《Applied Cryptography》 by Bruce Schneier

免责声明:我们致力于保护作者版权,注重分享,被刊用文章因无法核实真实出处,未能及时与作者取得联系,或有版权异议的,请联系管理员,我们会立即处理! 部分文章是来自自研大数据AI进行生成,内容摘自(百度百科,百度知道,头条百科,中国民法典,刑法,牛津词典,新华词典,汉语词典,国家院校,科普平台)等数据,内容仅供学习参考,不准确地方联系删除处理! 图片声明:本站部分配图来自人工智能系统AI生成,觅知网授权图片,PxHere摄影无版权图库和百度,360,搜狗等多加搜索引擎自动关键词搜索配图,如有侵权的图片,请第一时间联系我们。

相关阅读

目录[+]

取消
微信二维码
微信二维码
支付宝二维码