以下是将加密用户字符串的代码:
import java.io.UnsupportedEncodingException;
import java.security.MessageDigest;
import java.security.NoSuchAlgorithmException;
import sun.misc.BASE64Encoder;
import java.io.*;
class Encrypter {
public synchronized String encrypt(String plainText) throws Exception {
MessageDigest md = null;
try {
md = MessageDigest.getInstance("SHA");
}catch(Exception exc) {
throw new Exception(exc.getMessage());
}
try {
md.update(plainText.getBytes("UTF-8"));
}catch(Exception exc) {
throw new Exception(exc.getMessage());
}
byte raw[] = md.digest();
String hash = (new BASE64Encoder()).encode(raw);
return hash;
}
public static void main(String args[]) {
try {
Encrypter encrypter = new Encrypter();
BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
String userInput = br.readLine();
String encryptedPassword = encrypter.encrypt(userInput);
System.out.println(encryptedPassword);
} catch(Exception exc) {
System.out.println(exc);
}
}
}
当我编译代码时,我得到了这些警告:
Encrypter.java:4: warning: BASE64Encoder is internal proprietary API and may be removed in a future release
import sun.misc.BASE64Encoder;
^
Encrypter.java:23: warning: BASE64Encoder is internal proprietary API and may be removed in a future release
String hash = (new BASE64Encoder()).encode(raw);
^
2 warnings
是否还有其他方法可以加密java中的字符串?
类update
的方法MessageDigest
有什么作用?那句话md.update(plainText.getBytes("UTF-8"));
做了什么?
什么是BASE64Encoder
课程?我找不到它的DOC
答案 0 :(得分:12)
首先,您没有执行任何加密。您正在计算输入的单向散列或摘要。此哈希稍后可用于验证消息的完整性。请参阅Hashing,SHA1和MessageDigest。
Base64 encoding是一种用ASCII表示二进制数据的方法。这通常是可取的,因为并非所有数据存储和传输机制都支持原始二进制。例如,如果要通过http查询字符串参数传输计算摘要,则需要将其编码为Base64。另外,将原始二进制文件保存或打印到控制台会产生一系列时髦字符,这些字符可能超出可打印范围,并且还可能会从PC扬声器发出蜂鸣声!
您使用的Base64Encoder
来自sun.misc
包,不应使用。这是内部Sun JVM代码,将来可能会或可能不会提供。这也解释了为什么你无法找到任何javadoc。
幸运的是,存在一些免费且开放的Base64编码器和解码器。 Apache Commons Codec是一个广泛使用且稳定的库,其中包含多个包含Base64的编解码器。
md.update(plainText.getBytes("UTF-8"))
更新摘要的输入。调用digest
执行最终更新并计算输入的摘要。请参阅md.digest
和md.update
答案 1 :(得分:2)
查看Apache Commons Codec: https://commons.apache.org/codec/
例如为: https://commons.apache.org/codec/api-release/org/apache/commons/codec/digest/DigestUtils.html
答案 2 :(得分:2)
虽然这里的旧帖子是更新的答案。 Java 8的Base64。
答案 3 :(得分:1)
对于Base64加密和解密,这个警告清楚地表明它不鼓励使用Sun实现的Base64Encoder并发出警告,可能会在将来的版本中删除实现,我们可以做的是切换到Base64的其他实现编码器。我们可以将Commons Codec library用于Base64编码器。以下是一个例子:
1. Add Commons Codec library in classpath of your project
2. Add import statement for Base64 Class.
import org.apache.commons.codec.binary.Base64;
3. Encrypt your data
String testString = "Hello World";
byte[] encodedBytes = Base64.encodeBase64(testString.getBytes());
// Get encoded string
String encodedString = new String(encodedBytes);
// Get decoded string back
String decodedString = new String(Base64.decodeBase64(encodedBytes));
使用Commons编解码器库后,您不应再次看到上述警告。
答案 4 :(得分:0)
要以bullet 5 from Sahil Muthoo's excellent answer为基础,下面是对源代码的更深入研究。
默认情况下,update
方法只是将输入字节数组附加到tempArray
抽象类的当前MessageDigestSpi
。
MessageDigest
类扩展了MessageDigestSpi
类。然后,MessageDigest.update
被称为方法MessageDigestSpi.engineUpdate
,这可以通过研究源代码来找到:
MessageDigest.java(source code)
196: /**
197: * Updates the digest with the byte.
...
200: */
201: public void update(byte input)
202: {
203: engineUpdate(input);
204: }
205:
206: /**
207: * Updates the digest with the bytes from the array starting from the
208: * specified offset and using the specified length of bytes.
209: *
210: * @param input
211: * bytes to update the digest with.
212: * @param offset
213: * the offset to start at.
214: * @param len
215: * length of the data to update with.
216: */
217: public void update(byte[] input, int offset, int len)
218: {
219: engineUpdate(input, offset, len);
220: }
...
227: public void update(byte[] input)
228: {
229: engineUpdate(input, 0, input.length);
230: }
...
238: public void update (ByteBuffer input)
239: {
240: engineUpdate (input);
241: }
MessageDigestSpi.engineUpdate
是一种抽象方法,必须通过扩展类来实现,如下所示:
MessageDigestSpi.java(source code)
42: /**
43: * Updates this {@code MessageDigestSpi} using the given {@code byte}.
44: *
45: * @param input
46: * the {@code byte} to update this {@code MessageDigestSpi} with.
47: * @see #engineReset()
48: */
49: protected abstract void engineUpdate(byte input);
50: /**
51: * Updates this {@code MessageDigestSpi} using the given {@code byte[]}.
52: *
53: * @param input
54: * the {@code byte} array.
55: * @param offset
56: * the index of the first byte in {@code input} to update from.
57: * @param len
58: * the number of bytes in {@code input} to update from.
59: * @throws IllegalArgumentException
60: * if {@code offset} or {@code len} are not valid in respect to
61: * {@code input}.
62: */
63: protected abstract void engineUpdate(byte[] input, int offset, int len);
64: /**
65: * Updates this {@code MessageDigestSpi} using the given {@code input}.
66: *
67: * @param input
68: * the {@code ByteBuffer}.
69: */
70: protected void engineUpdate(ByteBuffer input) {
71: if (!input.hasRemaining()) {
72: return;
73: }
74: byte[] tmp;
75: if (input.hasArray()) {
76: tmp = input.array();
77: int offset = input.arrayOffset();
78: int position = input.position();
79: int limit = input.limit();
80: engineUpdate(tmp, offset+position, limit - position);
81: input.position(limit);
82: } else {
83: tmp = new byte[input.limit() - input.position()];
84: input.get(tmp);
85: engineUpdate(tmp, 0, tmp.length);
86: }
87: }