Project structure:
src | |--resource | |--PMD |-pmd-bin |-test.bat |-report |-report.xml | |--staticresource
Using maven-assembly
plugin, I am including the resources in the jar file.
As PMD folder will be used by the applcaition, I would like to create a copy of the PMD folder in the temp directory, so that I can start reading the bat files and other files from that temp directory.
ISSUE
When the jar loads, it fails to read the PMD folder inside resource.
Tried :
InputStream pmdFolder = classLoader.getResourceAsStream("PMD"); InputStreamReader isr = new InputStreamReader(pmdFolder, StandardCharsets.UTF_8); BufferedReader br = new BufferedReader(isr); List<URL> collect = br.lines().map(l -> "PMD" + "/" + l) .map(r -> classLoader.getResource(r)) .collect(toList()); Path tempPMDFolder = null; Path pmd = Files.createTempDirectory("PMD"); for (URL url : collect) { System.out.println(url.toString()); createSameTempStructure(url, pmd); } private static void createSameTempStructure(URL url, Path pmd) throws IOException { //tempPMDFolder.toFile().deleteOnExit(); try(final InputStream is = url.openStream()) { File file = FileUtils.toFile(url); System.out.println("file -> "+file.getName()); if(file.isDirectory()){ Path tempPMDFolder = createTempPMDFolder(pmd, file.getName()); System.out.println("tempPMDFolder -> "+tempPMDFolder.toString()); FileUtils.copyDirectory(file, tempPMDFolder.toFile()); } else { try (OutputStream outputStream = new FileOutputStream(file)) { IOUtils.copy(is, outputStream); } catch (IOException e) { System.out.println(e.getMessage()); } } } }
Here it just creates the PMD folder in temp directory and nothing, inner files and folders are not copied. Any way we can achieve this?
Advertisement
Answer
Here is what I came up with.
Converted the folder to zip
and put that zipped file in resources.
As inputstream can only read through a file.
InputStream pmdFolder = classLoader.getResourceAsStream("PMD.zip"); Path tempPMDDirectory = Files.createTempDirectory("PMD");
Then extracted the zip contents to the temp directory and then using that overall application.
if (pmdFolder != null) { try (ZipInputStream zipInputStream = new ZipInputStream(pmdFolder)) { // Extract the zip contents and keep in temp directory extract(zipInputStream, tempPMDDirectory.toFile()); } } public static void extract(ZipInputStream zip, File target) throws IOException { try { ZipEntry entry; while ((entry = zip.getNextEntry()) != null) { File file = new File(target, entry.getName()); if (!file.toPath().normalize().startsWith(target.toPath())) { throw new IOException("Bad zip entry"); } if (entry.isDirectory()) { file.mkdirs(); continue; } byte[] buffer = new byte[BUFFER_SIZE]; file.getParentFile().mkdirs(); BufferedOutputStream out = new BufferedOutputStream(new FileOutputStream(file)); int count; while ((count = zip.read(buffer)) != -1) { out.write(buffer, 0, count); } out.close(); } } finally { zip.close(); } }