欢迎访问宙启技术站
智能推送

Java函数如何实现加密解密字符串

发布时间:2023-06-07 07:03:36

Java函数可以用很多方法来加密解密字符串,其中最常用的是使用加解密算法库(例如java.security.*,javax.crypto.*等),也可以手动实现基于算法的加解密函数。下面我们讨论一下使用加解密算法库的方法。

加密解密的核心逻辑:

加密:

1.获取加密算法实例 Cipher

2.根据加密算法初始化 Cipher,指定加密模式、密钥、填充方式等(根据用途不同)

3.执行加密过程

4.将加密结果转为 Base64 编码字符串输出

解密:

1.获取解密算法实例 Cipher

2.根据解密算法初始化 Cipher,指定解密模式、密钥、填充方式等(需与加密时一致)

3.将 Base64 编码字符串转为二进制数组

4.执行解密过程

5.输出解密结果

实现代码如下(以AES算法为例,一般用于对称加密):

import javax.crypto.Cipher;
import javax.crypto.spec.IvParameterSpec;
import javax.crypto.spec.SecretKeySpec;
import java.nio.charset.StandardCharsets;
import java.util.Base64;

public class EncryptUtil {

    // 加密方法
    public static String encrypt(String data, String key, String iv) throws Exception {
        try {
            Cipher cipher = Cipher.getInstance("AES/CBC/NoPadding");

            int blockSize = cipher.getBlockSize();

            byte[] dataBytes = data.getBytes(StandardCharsets.UTF_8);
            int plaintextLength = dataBytes.length;

            if (plaintextLength % blockSize != 0) {
                plaintextLength += blockSize - (plaintextLength % blockSize);
            }

            byte[] plaintext = new byte[plaintextLength];
            System.arraycopy(dataBytes, 0, plaintext, 0, dataBytes.length);

            SecretKeySpec keyspec = new SecretKeySpec(key.getBytes(StandardCharsets.UTF_8), "AES");
            IvParameterSpec ivspec = new IvParameterSpec(iv.getBytes(StandardCharsets.UTF_8));

            cipher.init(Cipher.ENCRYPT_MODE, keyspec, ivspec);
            byte[] encrypted = cipher.doFinal(plaintext);

            return Base64.getEncoder().encodeToString(encrypted);

        } catch (Exception e) {
            e.printStackTrace();
        }
        return null;
    }

    // 解密方法
    public static String decrypt(String encryptedData, String key, String iv) throws Exception {
        try {
            byte[] encryptedBytes = Base64.getDecoder().decode(encryptedData);

            Cipher cipher = Cipher.getInstance("AES/CBC/NoPadding");
            SecretKeySpec keyspec = new SecretKeySpec(key.getBytes(StandardCharsets.UTF_8), "AES");
            IvParameterSpec ivspec = new IvParameterSpec(iv.getBytes(StandardCharsets.UTF_8));

            cipher.init(Cipher.DECRYPT_MODE, keyspec, ivspec);

            byte[] decrypted = cipher.doFinal(encryptedBytes);

            return new String(decrypted, StandardCharsets.UTF_8).trim();
        } catch (Exception e) {
            e.printStackTrace();
        }
        return null;
    }

}

这里采用AES算法,使用CBC模式,NoPadding填充方式,加解密使用同一密钥和向量。其中加密时将数据长度调整为16的倍数,解密后处理末尾多余填充的空格。使用Base64对结果进行编码和解码。

示例:

public static void main(String[] args) throws Exception {

    String key = "1234567812345678";
    String iv = "1234567812345678";

    String data = "hello world";

    String encryptedData = EncryptUtil.encrypt(data, key, iv);
    String decryptedData = EncryptUtil.decrypt(encryptedData, key, iv);

    System.out.println("encryptedData: " + encryptedData);
    System.out.println("decryptedData: " + decryptedData);

}

输出:

encryptedData: lZxyNsRZG/mIncAdt2YwMg==
decryptedData: hello world

加密后得到的Base64编码字符串可以用于数据传输或存储,解密后仍然是原字符串。