java读取加密对象

标签 java encryption file-io

您好,我有以下问题:

我有一个可序列化的类/对象访问。

public class Access implements Serializable {

private static final long serialVersionUID = 1L;

private URL website;
private String username;
private String password;

// + some methods

}

现在,当将它们写入文件时,我使用密码对它们进行加密。看起来像这样:
写作:

ObservableList<Access> userData;
userData = FXCollections.observableArrayList();
...
Cipher cipher = Cipher.getInstance("AES");
cipher.init(Cipher.ENCRYPT_MODE, key128);
File file = new File("./resources/saves" + username);
file.createNewFile();
CipherOutputStream cipherOut = new CipherOutputStream(
        new BufferedOutputStream(new FileOutputStream(file, true)), cipher);
ObjectOutputStream out = new ObjectOutputStream(cipherOut);

userData.forEach((item) -> {
    try {
        out.writeObject(new SealedObject(item, cipher));
    } catch (IllegalBlockSizeException e) {
        e.printStackTrace();
    } catch (IOException e) {
        e.printStackTrace();
    }
});
out.flush();
out.close();

阅读:

ObservableList<Access> access = FXCollections.observableArrayList();

Cipher cipher = Cipher.getInstance("AES");
cipher.init(Cipher.DECRYPT_MODE, key128);

CipherInputStream cipherIn = new CipherInputStream(
        new BufferedInputStream(new FileInputStream("./resources/saves" + username)), cipher);
ObjectInputStream in = new ObjectInputStream(cipherIn);
SealedObject sealed;
while ((sealed = (SealedObject) in.readObject()) != null) {
    access.add((Access) sealed.getObject(cipher));
}

如果我现在加载文件,它似乎已损坏。我发现很难找到错误。我认为问题出在加载函数上。我在这里遗漏了一些明显的东西吗?

错误:

java.io.StreamCorruptedException: invalid stream header: 3D23898C

感谢您的时间和帮助! :*

最佳答案

好吧,问题是密码流和对象流之间的交互。

当您读取文件时,ObjectInputStream 会要求底层流(密码流)读取非常具体的 header 。但密码流对此的了解为零——根据他自己的协议(protocol),他读取了他应该读取的正常字节数,以便理解加密的数据。结果是 ObjectInputStream 获得截断/更改的 header ,并且无法正确处理流。

好消息是,您实际上并不需要它! SealedObject 将为您处理加密/解密。只需删除密码流就可以了。

ObjectOutputStream out = new ObjectOutputStream(new FileOutputStream(file, true));

并阅读:

    FileInputStream inputStream = new FileInputStream(fileName);
    ObjectInputStream ois = new ObjectInputStream(inputStream);

现在,如果您确实想要使用密码流(从而使用相同的 key 有效地加密/解密数据两次),您需要首先对文件进行“第一次传递”解密它,然后在新的解密文件上打开对象流。

关于java读取加密对象,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/42211257/

相关文章:

javascript - 字符串异或加密因某些 key 而失败

c++ - std::ofstream.write() 在写入字符数组时是否比单个字符更快?

带有 UTF 字符的 Java IO

java - 如何在等待长 POST 请求时显示进度/请等待类型组件

java - 在企业环境中分发 maven settings.xml 文件

java - 如何跨微服务拥有通用的 DTO 或实体

c - 打印整个指针

java - 使用 DES 的 URL 解密错误

c - 我如何获得此readdir代码示例以搜索其他目录

Java/JavaFX 类由另一个类的实例组成