• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Licensed to the Apache Software Foundation (ASF) under one or more
3  * contributor license agreements.  See the NOTICE file distributed with
4  * this work for additional information regarding copyright ownership.
5  * The ASF licenses this file to You under the Apache License, Version 2.0
6  * (the "License"); you may not use this file except in compliance with
7  * the License.  You may obtain a copy of the License at
8  *
9  *      http://www.apache.org/licenses/LICENSE-2.0
10  *
11  * Unless required by applicable law or agreed to in writing, software
12  * distributed under the License is distributed on an "AS IS" BASIS,
13  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14  * See the License for the specific language governing permissions and
15  * limitations under the License.
16  */
17 package org.apache.commons.io.filefilter;
18 
19 import java.io.File;
20 import java.io.Serializable;
21 import java.nio.file.FileVisitResult;
22 import java.nio.file.Path;
23 import java.nio.file.attribute.BasicFileAttributes;
24 import java.time.Instant;
25 import java.util.Date;
26 
27 import org.apache.commons.io.FileUtils;
28 import org.apache.commons.io.file.PathUtils;
29 
30 /**
31  * Filters files based on a cutoff time, can filter either newer files or files equal to or older.
32  * <p>
33  * For example, to print all files and directories in the current directory older than one day:
34  * </p>
35  * <h2>Using Classic IO</h2>
36  * <pre>
37  * Path dir = PathUtils.current();
38  * // We are interested in files older than one day
39  * Instant cutoff = Instant.now().minus(Duration.ofDays(1));
40  * String[] files = dir.list(new AgeFileFilter(cutoff));
41  * for (String file : files) {
42  *     System.out.println(file);
43  * }
44  * </pre>
45  *
46  * <h2>Using NIO</h2>
47  * <pre>
48  * Path dir = PathUtils.current();
49  * // We are interested in files older than one day
50  * Instant cutoff = Instant.now().minus(Duration.ofDays(1));
51  * AccumulatorPathVisitor visitor = AccumulatorPathVisitor.withLongCounters(new AgeFileFilter(cutoff));
52  * //
53  * // Walk one dir
54  * Files.<b>walkFileTree</b>(dir, Collections.emptySet(), 1, visitor);
55  * System.out.println(visitor.getPathCounters());
56  * System.out.println(visitor.getFileList());
57  * //
58  * visitor.getPathCounters().reset();
59  * //
60  * // Walk dir tree
61  * Files.<b>walkFileTree</b>(dir, visitor);
62  * System.out.println(visitor.getPathCounters());
63  * System.out.println(visitor.getDirList());
64  * System.out.println(visitor.getFileList());
65  * </pre>
66  * <h2>Deprecating Serialization</h2>
67  * <p>
68  * <em>Serialization is deprecated and will be removed in 3.0.</em>
69  * </p>
70  *
71  * @see FileFilterUtils#ageFileFilter(Date)
72  * @see FileFilterUtils#ageFileFilter(File)
73  * @see FileFilterUtils#ageFileFilter(long)
74  * @see FileFilterUtils#ageFileFilter(Date, boolean)
75  * @see FileFilterUtils#ageFileFilter(File, boolean)
76  * @see FileFilterUtils#ageFileFilter(long, boolean)
77  * @since 1.2
78  */
79 public class AgeFileFilter extends AbstractFileFilter implements Serializable {
80 
81     private static final long serialVersionUID = -2132740084016138541L;
82 
83     /** Whether the files accepted will be older or newer. */
84     private final boolean acceptOlder;
85 
86     /** The cutoff time threshold measured in milliseconds since the epoch (00:00:00 GMT, January 1, 1970). */
87     private final Instant cutoffInstant;
88 
89     /**
90      * Constructs a new age file filter for files older than (at or before) a certain cutoff date.
91      *
92      * @param cutoffDate the threshold age of the files
93      */
AgeFileFilter(final Date cutoffDate)94     public AgeFileFilter(final Date cutoffDate) {
95         this(cutoffDate, true);
96     }
97 
98     /**
99      * Constructs a new age file filter for files on any one side of a certain cutoff date.
100      *
101      * @param cutoffDate the threshold age of the files
102      * @param acceptOlder if true, older files (at or before the cutoff) are accepted, else newer ones (after the
103      *        cutoff).
104      */
AgeFileFilter(final Date cutoffDate, final boolean acceptOlder)105     public AgeFileFilter(final Date cutoffDate, final boolean acceptOlder) {
106         this(cutoffDate.toInstant(), acceptOlder);
107     }
108 
109     /**
110      * Constructs a new age file filter for files older than (at or before) a certain File (whose last modification time
111      * will be used as reference).
112      *
113      * @param cutoffReference the file whose last modification time is used as the threshold age of the files
114      */
AgeFileFilter(final File cutoffReference)115     public AgeFileFilter(final File cutoffReference) {
116         this(cutoffReference, true);
117     }
118 
119     /**
120      * Constructs a new age file filter for files on any one side of a certain File (whose last modification time will
121      * be used as reference).
122      *
123      * @param cutoffReference the file whose last modification time is used as the threshold age of the files
124      * @param acceptOlder if true, older files (at or before the cutoff) are accepted, else newer ones (after the
125      *        cutoff).
126      */
AgeFileFilter(final File cutoffReference, final boolean acceptOlder)127     public AgeFileFilter(final File cutoffReference, final boolean acceptOlder) {
128         this(FileUtils.lastModifiedUnchecked(cutoffReference), acceptOlder);
129     }
130 
131     /**
132      * Constructs a new age file filter for files equal to or older than a certain cutoff.
133      *
134      * @param cutoffInstant The cutoff time threshold since the epoch (00:00:00 GMT, January 1, 1970).
135      * @since 2.12.0
136      */
AgeFileFilter(final Instant cutoffInstant)137     public AgeFileFilter(final Instant cutoffInstant) {
138         this(cutoffInstant, true);
139     }
140 
141     /**
142      * Constructs a new age file filter for files on any one side of a certain cutoff.
143      *
144      * @param cutoffInstant The cutoff time threshold since the epoch (00:00:00 GMT, January 1, 1970).
145      * @param acceptOlder if true, older files (at or before the cutoff) are accepted, else newer ones (after the cutoff).
146      * @since 2.12.0
147      */
AgeFileFilter(final Instant cutoffInstant, final boolean acceptOlder)148     public AgeFileFilter(final Instant cutoffInstant, final boolean acceptOlder) {
149         this.acceptOlder = acceptOlder;
150         this.cutoffInstant = cutoffInstant;
151     }
152 
153     /**
154      * Constructs a new age file filter for files equal to or older than a certain cutoff
155      *
156      * @param cutoffMillis The cutoff time threshold measured in milliseconds since the epoch (00:00:00 GMT, January 1,
157      *        1970).
158      */
AgeFileFilter(final long cutoffMillis)159     public AgeFileFilter(final long cutoffMillis) {
160         this(Instant.ofEpochMilli(cutoffMillis), true);
161     }
162 
163     /**
164      * Constructs a new age file filter for files on any one side of a certain cutoff.
165      *
166      * @param cutoffMillis The cutoff time threshold measured in milliseconds since the epoch (00:00:00 GMT, January 1,
167      *        1970).
168      * @param acceptOlder if true, older files (at or before the cutoff) are accepted, else newer ones (after the
169      *        cutoff).
170      */
AgeFileFilter(final long cutoffMillis, final boolean acceptOlder)171     public AgeFileFilter(final long cutoffMillis, final boolean acceptOlder) {
172         this(Instant.ofEpochMilli(cutoffMillis), acceptOlder);
173     }
174 
175     /**
176      * Checks to see if the last modification of the file matches cutoff favorably.
177      * <p>
178      * If last modification time equals cutoff and newer files are required, file <b>IS NOT</b> selected. If last
179      * modification time equals cutoff and older files are required, file <b>IS</b> selected.
180      * </p>
181      *
182      * @param file the File to check
183      * @return true if the file name matches
184      */
185     @Override
accept(final File file)186     public boolean accept(final File file) {
187         return acceptOlder != FileUtils.isFileNewer(file, cutoffInstant);
188     }
189 
190     /**
191      * Checks to see if the last modification of the file matches cutoff favorably.
192      * <p>
193      * If last modification time equals cutoff and newer files are required, file <b>IS NOT</b> selected. If last
194      * modification time equals cutoff and older files are required, file <b>IS</b> selected.
195      * </p>
196      * @param file the File to check
197      *
198      * @return true if the file name matches
199      * @since 2.9.0
200      */
201     @Override
accept(final Path file, final BasicFileAttributes attributes)202     public FileVisitResult accept(final Path file, final BasicFileAttributes attributes) {
203         return get(() -> toFileVisitResult(acceptOlder != PathUtils.isNewer(file, cutoffInstant)));
204     }
205 
206     /**
207      * Provide a String representation of this file filter.
208      *
209      * @return a String representation
210      */
211     @Override
toString()212     public String toString() {
213         final String condition = acceptOlder ? "<=" : ">";
214         return super.toString() + "(" + condition + cutoffInstant + ")";
215     }
216 }
217