View Javadoc
1   package org.codehaus.plexus.util.io;
2   
3   /*
4    * Copyright The Codehaus Foundation.
5    *
6    * Licensed under the Apache License, Version 2.0 (the "License");
7    * you may not use this file except in compliance with the License.
8    * You may obtain a copy of the License at
9    *
10   *     http://www.apache.org/licenses/LICENSE-2.0
11   *
12   * Unless required by applicable law or agreed to in writing, software
13   * distributed under the License is distributed on an "AS IS" BASIS,
14   * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15   * See the License for the specific language governing permissions and
16   * limitations under the License.
17   */
18  
19  import java.io.IOException;
20  import java.io.Writer;
21  import java.nio.charset.StandardCharsets;
22  import java.nio.file.Files;
23  import java.nio.file.Path;
24  import java.nio.file.Paths;
25  import java.nio.file.attribute.FileTime;
26  import java.util.Objects;
27  
28  import org.junit.jupiter.api.BeforeEach;
29  import org.junit.jupiter.api.Test;
30  
31  import static org.junit.jupiter.api.Assertions.assertEquals;
32  import static org.junit.jupiter.api.Assertions.assertFalse;
33  import static org.junit.jupiter.api.Assertions.assertNotEquals;
34  import static org.junit.jupiter.api.Assertions.assertTrue;
35  
36  public class CachingWriterTest {
37  
38      Path tempDir;
39      Path checkLastModified;
40  
41      @BeforeEach
42      public void setup() throws IOException {
43          Path dir = Paths.get("target/io");
44          Files.createDirectories(dir);
45          tempDir = Files.createTempDirectory(dir, "temp-");
46          checkLastModified = tempDir.resolve(".check");
47      }
48  
49      private void waitLastModified() throws IOException, InterruptedException {
50          Files.newOutputStream(checkLastModified).close();
51          FileTime lm = Files.getLastModifiedTime(checkLastModified);
52          while (true) {
53              Files.newOutputStream(checkLastModified).close();
54              FileTime nlm = Files.getLastModifiedTime(checkLastModified);
55              if (!Objects.equals(nlm, lm)) {
56                  break;
57              }
58              Thread.sleep(10);
59          }
60      }
61  
62      @Test
63      public void testNoOverwriteWithFlush() throws IOException, InterruptedException {
64          String data = "Hello world!";
65          Path path = tempDir.resolve("file-bigger.txt");
66          assertFalse(Files.exists(path));
67  
68          try (Writer w = Files.newBufferedWriter(path, StandardCharsets.UTF_8)) {
69              for (int i = 0; i < 10; i++) {
70                  w.write(data);
71              }
72          }
73          FileTime modified = Files.getLastModifiedTime(path);
74  
75          waitLastModified();
76  
77          try (Writer w = new CachingWriter(path, StandardCharsets.UTF_8)) {
78              for (int i = 0; i < 10; i++) {
79                  w.write(data);
80                  w.flush();
81              }
82          }
83          FileTime newModified = Files.getLastModifiedTime(path);
84          assertEquals(modified, newModified);
85      }
86  
87      @Test
88      public void testWriteNoExistingFile() throws IOException, InterruptedException {
89          String data = "Hello world!";
90          Path path = tempDir.resolve("file.txt");
91          assertFalse(Files.exists(path));
92  
93          try (CachingWriter cos = new CachingWriter(path, StandardCharsets.UTF_8, 4)) {
94              cos.write(data);
95          }
96          assertTrue(Files.exists(path));
97          String read = new String(Files.readAllBytes(path), StandardCharsets.UTF_8);
98          assertEquals(data, read);
99          FileTime modified = Files.getLastModifiedTime(path);
100 
101         waitLastModified();
102 
103         try (CachingWriter cos = new CachingWriter(path, StandardCharsets.UTF_8, 4)) {
104             cos.write(data);
105         }
106         assertTrue(Files.exists(path));
107         read = new String(Files.readAllBytes(path), StandardCharsets.UTF_8);
108         assertEquals(data, read);
109         FileTime newModified = Files.getLastModifiedTime(path);
110         assertEquals(modified, newModified);
111         modified = newModified;
112 
113         waitLastModified();
114 
115         // write longer data
116         data = "Good morning!";
117         try (CachingWriter cos = new CachingWriter(path, StandardCharsets.UTF_8, 4)) {
118             cos.write(data);
119         }
120         assertTrue(Files.exists(path));
121         read = new String(Files.readAllBytes(path), StandardCharsets.UTF_8);
122         assertEquals(data, read);
123         newModified = Files.getLastModifiedTime(path);
124         assertNotEquals(modified, newModified);
125         modified = newModified;
126 
127         waitLastModified();
128 
129         // different data same size
130         data = "Good mornong!";
131         try (CachingWriter cos = new CachingWriter(path, StandardCharsets.UTF_8, 4)) {
132             cos.write(data);
133         }
134         assertTrue(Files.exists(path));
135         read = new String(Files.readAllBytes(path), StandardCharsets.UTF_8);
136         assertEquals(data, read);
137         newModified = Files.getLastModifiedTime(path);
138         assertNotEquals(modified, newModified);
139         modified = newModified;
140 
141         waitLastModified();
142 
143         // same data but shorter
144         data = "Good mornon";
145         try (CachingWriter cos = new CachingWriter(path, StandardCharsets.UTF_8, 4)) {
146             cos.write(data);
147         }
148         assertTrue(Files.exists(path));
149         read = new String(Files.readAllBytes(path), StandardCharsets.UTF_8);
150         assertEquals(data, read);
151         newModified = Files.getLastModifiedTime(path);
152         assertNotEquals(modified, newModified);
153         modified = newModified;
154     }
155 }