Rumah  >  Artikel  >  Java  >  Bagaimana untuk membaca fail sumber dalam pakej JAR di Java?

Bagaimana untuk membaca fail sumber dalam pakej JAR di Java?

WBOY
WBOYke hadapan
2023-05-08 18:49:098146semak imbas

1. Keperluan

Dalam projek Java, anda perlu membaca fail dalam direktori sumber, melintasi semua fail dalam direktori sumber yang ditentukan dan mengekalkan laluan relatif fail semasa membaca fail.

2. Masalah

Apabila berjalan dalam IDEA, anda boleh mendapatkan dan melintasi sumber yang ditentukan, tetapi selepas menjalankan projek Java ke dalam pakej balang, anda tidak boleh mendapatkan fail dalam direktori sumber.

3. IDEA membaca sumber sumber

Selepas penyusunan, fail sumber diletakkan dalam direktori sasaran, dan setiap fail sumber sebenarnya wujud pada cakera.

3.1. Kaedah 1.

Baca terus melalui laluan mutlak Jika fail ialah direktori, anda juga boleh melintasi fail dalam direktori melalui listFiles:

String absolutePath = "资源文件绝对路径";
File file = new File(absolutePath);
if (file.isDirectory()) {
    File[] children = file.listFiles();
}

3.2. Kaedah 2. 🎜>

Baca melalui laluan relatif:

String path = "template";    //相对resource路径
File file = ResourceUtils.getFile(ResourceUtils.CLASSPATH_URL_PREFIX + path);
if (file.isDirectory()) {
    File[] children = file.listFiles();
}

4. Baca sumber sumber selepas menjadikannya dalam pakej balang fail dalam pakej balang.

Selepas disusun ke dalam pakej jar, pakej jar adalah fail yang berasingan dan bukannya folder, jadi fail sumber tidak boleh ditemui melalui laluan fail. Pada masa ini, fail sumber dalam pakej balang boleh dibaca melalui pemuat kelas.

4.1. Baca fail sumber dalam pakej balang

Kaedah ini hanya boleh membaca satu fail dalam pakej balang, kerana apa yang dibaca ialah aliran InputStream, dan fail itu tidak boleh. disimpan relatif kepada laluan sumber, jadi sumber dalam pakej balang tidak boleh dilalui.

String path = "/resource相对路径";
InputStream is = this.class.getResourceAsStream(path);
byte[] buff = new byte[1024];
String filePath = "保存文件路径";
String fileName = "保存文件名";
File file = new File(filePath + fileName);
FileUtils.copyInputStreamToFile(is, file);

4.2. Lintas direktori sumber pakej jar

Mengambil penyalinan direktori sumber sumber sebagai contoh, salin sumber dalam pakej tempatan dan jar masing-masing.

Seperti yang ditunjukkan di bawah:

Saya mahu menyalin semua kandungan dalam folder templat di bawah direktori sumber sumber

Kemudian simpan ke C:/Users/ASUS/; Folder Desktop/ savePath.

4.2.1. Pertimbangan alam sekitar

public static void main(String[] args) throws URISyntaxException {
    // Test为当前类名
    URI uri = Test.class.getProtectionDomain().getCodeSource().getLocation().toURI();
    // tempPath: 文件保存路径
    String tempPath = "C:/Users/ASUS/Desktop/savePath";
    String sourceDir = "template";  //资源文件夹
    if (uri.toString().startsWith("file")) {
        // IDEA运行时,进行资源复制
        copyLocalResourcesFileToTemp(sourceDir + "/", "*", tempPath + "/" + sourceDir);
    } else {
        // 获取jar包所在路径
        String jarPath = uri.toString();
        uri = URI.create(jarPath.substring(jarPath.indexOf("file:"),jarPath.indexOf(".jar") + 4));
        // 打成jar包后,进行资源复制
        Test.copyJarResourcesFileToTemp(uri, tempPath, "BOOT-INF/classes/" + sourceDir);
    }
}
4.2.2. Salin fail sumber projek tempatan

rreee. 4.2.3 Salin fail sumber dalam pakej balang

/**
     * 复制本地资源文件到指定目录
     * @param fileRoot      需要复制的资源目录文件夹
     * @param regExpStr     资源文件匹配正则,*表示匹配所有
     * @param tempParent    保存地址
     */
    public static void copyLocalResourcesFileToTemp(String fileRoot, String regExpStr, String tempParent) {
        try {
            ResourcePatternResolver resolver = new PathMatchingResourcePatternResolver();
            Resource[] resources = resolver.getResources(fileRoot + regExpStr);
            for (Resource resource : resources) {
                File newFile = new File(tempParent, resource.getFilename());
                if (newFile.exists()) {
                    newFile.delete();
                }
                InputStream stream = null;
                try {
                    stream = resource.getInputStream();
                } catch (Exception e) {
                    // 如果resource为文件夹时,会报异常,这里直接忽略这个异常
                }
                if (stream == null) {
                    newFile.mkdirs();
                    copyLocalResourcesFileToTemp(fileRoot + resource.getFilename()  + "/", regExpStr, tempParent + "/" + resource.getFilename());
                } else {
                    if (!newFile.getParentFile().exists()) {
                        newFile.getParentFile().mkdirs();
                    }
                    org.apache.commons.io.FileUtils.copyInputStreamToFile(stream, newFile);
                }
            }
        } catch (Exception e) {
            log.error("failed to copy local source template", e);
        }
    }
/**
     * 复制jar包中的资源文件到指定目录
     * @param path          jar包所在路径
     * @param tempPath      保存目录
     * @param filePrefix    需要进行复制的资源文件目录:以BOOT-INF/classes/开头
     */
    public static void copyJarResourcesFileToTemp(URI path, String tempPath, String filePrefix) {
        try {
            List<Map.Entry<ZipEntry, InputStream>> collect =
                    readJarFile(new JarFile(path.getPath()), filePrefix).collect(Collectors.toList());
            for (Map.Entry<ZipEntry, InputStream> entry : collect) {
                // 文件相对路径
                String key = entry.getKey().getName();
                // 文件流
                InputStream stream = entry.getValue();
                File newFile = new File(tempPath + key.replaceAll("BOOT-INF/classes", ""));
                if (!newFile.getParentFile().exists()) {
                    newFile.getParentFile().mkdirs();
                }
                org.apache.commons.io.FileUtils.copyInputStreamToFile(stream, newFile);
            }
        } catch (IOException e) {
            log.error("failed to copy jar source template", e);
        }
    }

Atas ialah kandungan terperinci Bagaimana untuk membaca fail sumber dalam pakej JAR di Java?. Untuk maklumat lanjut, sila ikut artikel berkaitan lain di laman web China PHP!

Kenyataan:
Artikel ini dikembalikan pada:yisu.com. Jika ada pelanggaran, sila hubungi admin@php.cn Padam