加密功能实现

1. 前言

本文 主要实现 对密码进行加密 ,因为 使用 md5 容易被穷举 (彩虹表) 而破解 ,使用 spring security 框架又太大了 (杀鸡用牛刀) 。

所以本文 就自己实现一个密码加密 .

2. 密码加密

这里我们通过 加盐是方式 来 对密码进行加密 .

加盐 通常分为两部分 :

  1. 盐值 : 通常使用随机数
  2. 加密数据


将盐值与加密数据合在一起 就是 加盐数据了 , 加盐数据通常来说是安全的


这里我们 盐值 是 随机的 每次加盐的数字都是不同的,这里通过穷举 来 破解我们的数据 假设破解 一条数据 花费的时间 1 天 , 我们 有 1 千w 个数据, 一个数据

是一天 , 那么 1 千 w 个数 , 全部破解 时间是非常多的 .


这里成本大于利益 , 那么谁去破解呢 , 所以这样做 我们的密码 就是安全的 .


知道加盐 , 下面就来自己实现一个加盐的方法

  1. 加密 : 随机盐 + $ + 最终加密密码
  2. 解密 : 先通过 $ 进行分割 , 得到随机盐 + 最终密码 ,然后通过 md5 对 新输入的密码 与 得到的随机盐 进行加密 , 将得到的 新的加密密码 和 之前分割得到的 最终密码 进行对比 如果 相等 那么 就是相同的密码 返回 true,如果不相等 就是不同的密码 返回 false


代码实现 :

这里我采用 的 是 使用 hutool 中的 MD5 进行 加密 的 所以需要引入 依赖

  <!--        添加 hutool -->
        <dependency>
            <groupId>cn.hutool</groupId>
            <artifactId>hutool-all</artifactId>
            <version>5.8.12</version>
        </dependency>


创建一个 PasswordUtil , 在这个类里面完成我们的加密和 解密 .

package com.example.usermanager.tools;

import cn.hutool.core.util.IdUtil;
import cn.hutool.crypto.SecureUtil;
import org.springframework.util.StringUtils;

import java.util.UUID;

/**
 * 密码工具类
 * 1. 加密 (加盐)
 * 2. 解密
 */

public class PasswordUtil {

    /**
     * 加密 (加盐)
     *
     * @param password
     * @return
     */

//         生成的 UUID 带有 - : UUID.randomUUID();
    
    public static String encrypt(String password) {
        // 生成 uuid 不加 - 的 .
        // 随机盐值
        String salt = IdUtil.simpleUUID();

        // 密码 (随机盐值 + 密码)

        String finalPassword = SecureUtil.md5(salt + password);


        return salt + "$" + finalPassword;

    }

    /**
     * 解密
     *
     * @param password 要验证的密码 (未加密)
     * @return 数据库中的加了盐值的密码
     */

    public static boolean decrypt(String password, String securePassword) {
        boolean result = false;

        if (StringUtils.hasLength(password) && StringUtils.hasLength(securePassword)) {

            if (securePassword.length() == 65 && securePassword.contains("$")) {
                // 注意 : $ 是特殊字符 使用 split 需要转义
                String[] securePasswordArr = securePassword.split("\\$");

                // 盐值
                String salt = securePasswordArr[0];

                // 根据盐值加密的密码
                String finalPassword = securePasswordArr[1];

                // 使用同样的加密算法 和 随机盐值生成最终的加密的密码
                password = SecureUtil.md5(salt + password);

                // 进行对比
                if (finalPassword.equals(password)) {
                    result = true;
                }
            }
        }
        return result;
    }

    public static void main(String[] args) {
        String password = "123456";
        String dbPassword = PasswordUtil.encrypt(password);

        System.out.println("加密密码 " + dbPassword);

        boolean result = PasswordUtil.decrypt("123456",dbPassword);

        String password2 = "123456789";

        boolean result2 = PasswordUtil.decrypt(password2,dbPassword);

        System.out.println(result);

        System.out.println(result2);
    }
}


效果 :

在这里插入图片描述

扩展 : 这里我们可以 对 加密密码 进行一个对称加密 ,对称加密后得到一个 32 位 数据 , 我们的程序可以通过 公钥 对 32 数据 还原 ,然后再通过我们写的 decrypt 进行 解密 .


这里主要是一个小功能, 可以将这个加密 放在我们的项目中 .

评论 8
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值