kg5425
kg5425

Reputation: 469

Java inputstream/outputstream write to file with same name

I have some code that goes through a file tree and adds roots to xml files that don't have them. My problem is when I try to write from the inputstream to an output stream. I'd like to REPLACE the current xml file with the updated version (the one with the root added). I think there's a problem occurring if I make the outputstream the same file as the inputstream. Intuitively it seems to make sense that that'd be a problem. If not, let me know.

How can I remedy this? How can I essentially "update" the xml file, in effect overwriting the other one? I've looked at other answers on here but haven't gotten far.

private static void addRootHelper(File root){
    FileInputStream fis;
    List<InputStream> streams;
    InputStream is;
    OutputStream os;

    File[] directoryListing = root.listFiles();
    if (directoryListing != null) {
        for (File child : directoryListing) {
            addRootHelper(child);
        }
    }
    else {
        try{
            // Add root to input stream and create output stream
            fis = new FileInputStream(root);
            streams = Arrays.asList(new ByteArrayInputStream("<root>".getBytes()),fis, new ByteArrayInputStream("</root>".getBytes()));
            is = new SequenceInputStream(Collections.enumeration(streams));
            os = new FileOutputStream(root.getAbsolutePath());

            // Write from is -> os
            byte[] buffer = new byte[1024];
            int bytesRead;

            // Read from is to buffer
            while((bytesRead = is.read(buffer)) !=-1){
                os.write(buffer, 0, bytesRead);
            }
            is.close();
            os.flush();
            os.close();
            System.out.println("Added root to " + root.getName());

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

Upvotes: 0

Views: 1157

Answers (1)

Leo Aso
Leo Aso

Reputation: 12513

If you'd prefer not to use the popular temporary-file approach, then you can always just read in the whole file, then write back to it afterwards.

Here's a straight-forward implementation.

public static void addRootTag(File xml) throws IOException {
    final List<String> lines = new ArrayList<>();;
    try (Scanner in = new Scanner(xml)) {
        while (in.hasNextLine())
            lines.add(in.nextLine());
    }

    try (PrintStream out = new PrintStream(xml)) {
        out.println("<root>");
        for (String line : lines) {
            // indentation, if you want
            out.print("    ");
            out.println(line);
        }
        out.println("</root>");
    }
}

Upvotes: 1

Related Questions