0

我有一个存储密码的类(我将添加更多的东西,而不仅仅是密码),名为 Data:

import java.io.Serializable;

public class Data implements Serializable{

    public String password = "";    

}

作为测试,我运行了这两个:

private static File datafile = new File("data.src");

public static void checkDatafile() {
        try {
            Data data = new Data();
            data.password = "Newwww";
            if (!datafile.exists()) {
                datafile.createNewFile();
                ObjectOutputStream oos = new ObjectOutputStream(
                        new FileOutputStream(datafile));
                oos.writeObject(data);
                oos.flush();
                oos.close();
            }

        } catch (IOException e) {
            e.printStackTrace();
        }
    }

public static Data loadData(Data data) {
    try {
    ObjectInputStream ois = new ObjectInputStream(new FileInputStream(datafile));
    data = (Data) ois.readObject();
    ois.close();
    } catch (IOException | ClassNotFoundException e) {
        e.printStackTrace();
    }
    return data;
}

它可以完美地写入和读取,但是当我在记事本中打开 data.src 时,人类有点可读并且密码不安全,这是 data.src 的输出:

ャ・ sr data.Data克ラ淕6J・ L passwordt Ljava/lang/String;xpt Newwww

密码很容易看到并且不安全,有没有办法在写入文件时加密/编码对象以使其不被人类读取?

此外,我宁愿坚持使用标准 Java 库,然后下载和使用其他库。

4

4 回答 4

2

这取决于您所说的“不可读”是什么意思。如果您的目标是防止恶意人员提取密码,即使他们拥有运行您的程序所需的权限,您也很难这样做。毕竟,如果一个程序可以解密密码,具有相同权限的人也可以。即使没有适当的权限,恶意用户也可能会检查内存中的原始字节并在他们有权访问机器时提取密码。

另一方面,如果您可以合理地信任用户,但只是想避免让他们意外看到明文密码,那么任何数量的简单方案都可以使用;即使只是将字符串序列化为其十六进制代码点就足够了。

如果您必须自己存储密码,即您正在访问需要密码的第三方服务,您基本上必须锁定机器并限制您绝对信任的人访问。没有办法解决这个问题。有许多资源描述了加密密码,但它们都依赖于您能够将用户锁定在系统的某些部分,通常是加密密钥或密文。

但是,您可能根本不需要也不应该实际存储密码。验证用户的标准方法是从不存储他们的密码,而是存储密码的单向哈希。这(理论上)不可能破译成原始密码,但是通过对用户登录时输入的密码进行哈希处理并将其与您存档的哈希值进行比较,您可以验证他们的身份,而无需知道他们的密码是什么。

编辑:关于需要存储实际密码的系统的另一件事。除了锁定机器之外,您还需要创建一个强大的审计跟踪来记录所有访问密码的尝试。应该记录和跟踪与该机器及其数据的每次交互,以便在出现问题时,您可以检查您的审计历史并了解问题的范围。如果您没有审计跟踪,您将不得不假设您的系统已完全受到损害,因为您将没有相反的证据。

于 2015-04-06T22:53:03.260 回答
1

不是通过ObjectOutputStream. 您必须使用加密库并加密整个文件或密码。

于 2015-04-06T22:40:02.377 回答
0

您可以尝试编码/解码您的内容。您可以使用 MD5 哈希函数。有预先编写的功能,它的使用非常简单。

以下链接可以帮助您了解如何在代码中使用它。 http://www.asjava.com/core-java/java-md5-example/

于 2015-04-06T23:37:04.537 回答
0

您可以让 Data 类实现 writeObject/readObject 方法,以便在您读取和写入对象时加密/解密密码。

private void writeObject(ObjectOutputStream os) throws IOException{
     password = encrypt(password);
     os.defaultWriteObject();
}

private void readObject(ObjectOutputStream os) throws IOException{
     os.defaultReadObject();
     password = decrypt(password);
}

其中 encrypt/decrypt 定义您希望使用的加密/解密算法。话虽如此,正如 Gregor Raýman 在评论中所指出的那样,您可能会考虑只对密码进行散列而不是存储它们。

于 2015-04-06T22:47:48.270 回答