使用Java FileSystem打捞临时zip文件

时间:2018-09-27 13:43:54

标签: java file zip

在使用Java的FileSystem API创建zip文件时遇到了意外情况,在创建文件的过程中磁盘空间用光了。

由于编码错误,即使未创建zip文件,也删除了源文件。我已经从服务器中挽救了一个tmp文件,并且想知道是否可以使用FileSystem API通过加载临时文件并完成写入来挽救数据。

用于编写zip文件的代码如下:

    final Map<String, String> env = new HashMap<>();
    env.put("create", "true");
    final String zipArchiveFilename = System.currentTimeMillis() + ".zip";
    final URI uri = URI.create("jar:file:" + zipDir.getAbsolutePath() + "/" + zipArchiveFilename);
    final List<Path> files = ...;

    try (FileSystem zipfs = FileSystems.newFileSystem(uri, env)) {
        for (Path file : files) {
            Files.copy(file, zipfs.getPath(file.toFile().getAbsolutePath().replace(dir.getAbsolutePath(), "")), StandardCopyOption.REPLACE_EXISTING);
        }
    } catch (IOException e) {
        Logger.error("Failed to create zip file:", e);
    }

1 个答案:

答案 0 :(得分:0)

可以尝试如下操作:

    Path path = Paths.get("C:\\Users\\... .zip");
    final URI uri = URI.create("jar:" + path.toUri().toString());

    Map<String, Object> env = new HashMap<>();
    try (FileSystem zipfs = FileSystems.newFileSystem(uri, env)) {
        Path root = zipfs.getPath("/");
        final Path targetDir = Paths.get("C:/Users/Joop/limbo");
        Files.createDirectories(targetDir);
        final AtomicInteger fno = new AtomicInteger();
        Files.walkFileTree(root, new SimpleFileVisitor<Path>() {
            @Override
            public FileVisitResult visitFileFailed(Path file, IOException exc) throws IOException {
                System.out.println("Failed: " + file);
                return FileVisitResult.CONTINUE;
            }

            @Override
            public FileVisitResult visitFile(Path file, BasicFileAttributes attrs) throws IOException {
                String name = fno.incrementAndGet() + "-"
                        + file.getFileName().toString().replaceAll("[^-.\\w]+", "");
                Path targetFile = targetDir.resolve(name);
                System.out.println("+ " + file + " - " + targetFile);
                Files.copy(file, targetFile, StandardCopyOption.REPLACE_EXISTING);
                return FileVisitResult.CONTINUE;
            }

        });
    }

我不是从File中获取的URI,而是从File.toURI中获取的,以摆脱Windows上的反斜杠。

文件名可能已损坏或编码错误,因此转换了文件名。

我不确定zip文件系统是否可以使用。