View Javadoc
1   /*
2    * Licensed to the Apache Software Foundation (ASF) under one
3    * or more contributor license agreements.  See the NOTICE file
4    * distributed with this work for additional information
5    * regarding copyright ownership.  The ASF licenses this file
6    * to you under the Apache License, Version 2.0 (the
7    * "License"); you may not use this file except in compliance
8    * with the License.  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,
13   * software distributed under the License is distributed on an
14   * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
15   * KIND, either express or implied.  See the License for the
16   * specific language governing permissions and limitations
17   * under the License.
18   */
19  package org.apache.maven.shared.model.fileset.util;
20  
21  import java.io.File;
22  import java.io.IOException;
23  import java.net.URL;
24  import java.net.URLDecoder;
25  import java.nio.file.Files;
26  
27  import org.apache.commons.io.FileUtils;
28  import org.apache.maven.shared.model.fileset.FileSet;
29  import org.junit.jupiter.api.Test;
30  import org.junit.jupiter.api.io.TempDir;
31  
32  import static org.junit.jupiter.api.Assertions.assertEquals;
33  import static org.junit.jupiter.api.Assertions.assertFalse;
34  import static org.junit.jupiter.api.Assertions.assertTrue;
35  import static org.junit.jupiter.api.Assertions.fail;
36  import static org.junit.jupiter.api.Assumptions.assumeTrue;
37  
38  /**
39   * Test the FileSet
40   */
41  public class FileSetUtilsTest {
42      @TempDir
43      File testDirectory;
44  
45      /**
46       * @throws IOException if any
47       */
48      @Test
49      void testGetIncludedFiles() throws IOException {
50          File directory = setupTestDirectory("testGetIncludedFiles");
51  
52          FileSet set = new FileSet();
53          set.setDirectory(directory.getPath());
54          set.addInclude("**/included.txt");
55  
56          FileSetManager fileSetManager = new FileSetManager();
57  
58          String[] included = fileSetManager.getIncludedFiles(set);
59  
60          assertEquals(1, included.length);
61      }
62  
63      @Test
64      void testIncludesDontFollowSymlinks() throws IOException {
65          File directory = setupTestDirectory("testIncludesDontFollowSymlinks");
66          File subdir = new File(directory, directory.getName());
67  
68          createSymlink(directory, subdir);
69  
70          FileSet set = new FileSet();
71          set.setDirectory(directory.getPath());
72          set.addInclude("**/included.txt");
73          set.setFollowSymlinks(false);
74  
75          FileSetManager fileSetManager = new FileSetManager();
76  
77          String[] included = fileSetManager.getIncludedFiles(set);
78  
79          assertEquals(1, included.length);
80      }
81  
82      @Test
83      void testDeleteDontFollowSymlinks() throws IOException {
84          File directory = setupTestDirectory("testDeleteDontFollowSymlinks");
85          File subdir = new File(directory, directory.getName());
86  
87          createSymlink(directory, subdir);
88  
89          FileSet set = new FileSet();
90          set.setDirectory(directory.getPath());
91          set.addInclude("**/included.txt");
92          set.addInclude("**/" + subdir.getName());
93          set.setFollowSymlinks(false);
94  
95          FileSetManager fileSetManager = new FileSetManager();
96  
97          fileSetManager.delete(set);
98  
99          assertFalse(subdir.exists());
100     }
101 
102     /**
103      * @throws IOException if any
104      */
105     @Test
106     void testDelete() throws IOException {
107         File directory = setupTestDirectory("testDelete");
108         File subdirFile = new File(directory, "subdir/excluded.txt");
109 
110         FileSet set = new FileSet();
111         set.setDirectory(directory.getPath());
112         set.addInclude("**/included.txt");
113         set.addInclude("**/subdir");
114 
115         FileSetManager fileSetManager = new FileSetManager();
116 
117         fileSetManager.delete(set);
118 
119         assertFalse(subdirFile.exists(), "file in marked subdirectory still exists.");
120     }
121 
122     /**
123      * @throws Exception if any
124      */
125     @Test
126     void testDeleteDanglingSymlink() throws Exception {
127         File directory = setupTestDirectory("testDeleteDanglingSymlink");
128         File targetFile = new File(directory, "test.txt");
129         File linkFile = new File(directory, "symlink");
130 
131         createSymlink(targetFile, linkFile);
132 
133         targetFile.delete();
134 
135         FileSet set = new FileSet();
136         set.setDirectory(directory.getPath());
137         set.addInclude("**");
138 
139         FileSetManager fileSetManager = new FileSetManager();
140 
141         fileSetManager.delete(set);
142 
143         assertFalse(directory.exists(), "directory still exists");
144     }
145 
146     /**
147      * @throws Exception if any
148      */
149     @Test
150     void testDeleteExcludeParentOfExcludedFile() throws Exception {
151         File directory = setupTestDirectory("testDeleteExcludeParentOfExcludedFile");
152 
153         FileSet set = new FileSet();
154         set.setDirectory(directory.getPath());
155         set.addExclude("*excluded*");
156         set.setFollowSymlinks(true);
157 
158         FileSetManager fileSetManager = new FileSetManager();
159 
160         fileSetManager.delete(set);
161 
162         assertTrue(new File(directory, "excluded.txt").exists(), "excluded file has been deleted");
163     }
164 
165     /**
166      * @throws Exception if any
167      */
168     @Test
169     void testDeleteExcludeParentOfExcludedDir() throws Exception {
170         File directory = setupTestDirectory("testDeleteExcludeParentOfExcludedDir");
171 
172         FileSet set = new FileSet();
173         set.setDirectory(directory.getPath());
174         set.addExclude("*excluded*");
175         set.setFollowSymlinks(true);
176 
177         FileSetManager fileSetManager = new FileSetManager();
178 
179         fileSetManager.delete(set);
180 
181         assertTrue(new File(directory, "excluded").exists(), "excluded directory has been deleted");
182     }
183 
184     /**
185      * @throws Exception if any
186      */
187     @Test
188     void testDeleteExcludeFollowSymlinks() throws Exception {
189         File directory = setupTestDirectory("testDeleteExcludeFollowSymlinks");
190 
191         FileSet set = new FileSet();
192         set.setDirectory(directory.getPath());
193         set.addExclude("*excluded*");
194         set.setFollowSymlinks(true);
195 
196         FileSetManager fileSetManager = new FileSetManager();
197 
198         fileSetManager.delete(set);
199 
200         assertTrue(new File(directory, "excluded.txt").exists(), "excluded file has been deleted");
201         assertTrue(new File(directory, "excluded").exists(), "excluded directory has been deleted");
202         assertFalse(new File(directory, "included.txt").exists(), "included file has not been deleted");
203     }
204 
205     /**
206      * @throws Exception if any
207      */
208     @Test
209     void testDeleteExcludeDontFollowSymlinks() throws Exception {
210         File directory = setupTestDirectory("testDeleteExcludeDontFollowSymlinks");
211 
212         FileSet set = new FileSet();
213         set.setDirectory(directory.getPath());
214         set.addExclude("*excluded*");
215         set.setFollowSymlinks(false);
216 
217         FileSetManager fileSetManager = new FileSetManager();
218 
219         fileSetManager.delete(set);
220 
221         assertTrue(new File(directory, "excluded.txt").exists(), "excluded file has been deleted");
222         assertTrue(new File(directory, "excluded").exists(), "excluded directory has been deleted");
223         assertFalse(new File(directory, "included.txt").exists(), "included file has not been deleted");
224     }
225 
226     @Test
227     void testDeleteDontFollowSymlinksButDeleteThem() throws Exception {
228         File directory = setupTestDirectory("testDeleteDontFollowSymlinksButDeleteThem");
229 
230         createSymlink(new File(directory, "excluded"), new File(directory, "dirlink"));
231         createSymlink(new File(directory, "excluded.txt"), new File(directory, "filelink"));
232         createSymlink(new File(directory, "excluded"), new File(directory, "dir0/dirlink"));
233         createSymlink(new File(directory, "excluded.txt"), new File(directory, "dir1/filelink"));
234 
235         FileSet set = new FileSet();
236         set.setDirectory(directory.getPath());
237         set.addExclude("*excluded*");
238         set.setFollowSymlinks(false);
239 
240         FileSetManager fileSetManager = new FileSetManager();
241 
242         fileSetManager.delete(set);
243 
244         assertTrue(new File(directory, "excluded.txt").exists(), "excluded file has been deleted");
245         assertTrue(new File(directory, "excluded").exists(), "excluded directory has been deleted");
246         assertFalse(new File(directory, "dirlink").exists(), "included dirlink has not been deleted");
247         assertFalse(new File(directory, "filelink").exists(), "included filelink has not been deleted");
248         assertFalse(new File(directory, "dir0").exists(), "included directory has not been deleted");
249         assertFalse(new File(directory, "dir1").exists(), "included directory has not been deleted");
250     }
251 
252     private void createSymlink(File target, File link) {
253         if (link.exists()) {
254             link.delete();
255         }
256 
257         try {
258             Files.createSymbolicLink(link.toPath(), target.toPath());
259         } catch (IOException | SecurityException | UnsupportedOperationException ex) {
260             // assume failure to create a symlink is because the system does not support
261             // them and not because the symlink creation failed.
262             assumeTrue(false);
263         }
264     }
265 
266     private File setupTestDirectory(String directoryName) throws IOException {
267         URL sourceResource = getClass().getClassLoader().getResource(directoryName);
268 
269         if (sourceResource == null) {
270             fail("Source directory for test: " + directoryName + " cannot be found.");
271         }
272 
273         File sourceDir = new File(URLDecoder.decode(sourceResource.getPath(), "UTF-8"));
274 
275         String testBase = System.getProperty("testBase", "target/test-directories");
276 
277         File testDir = new File(testDirectory, testBase + "/" + directoryName);
278         if (testDir.mkdirs()) {
279             FileUtils.copyDirectory(sourceDir, testDir);
280             return testDir;
281         } else {
282             throw new IOException("Could not create test directory " + testDir);
283         }
284     }
285 }