1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19 package org.apache.maven.buildcache.checksum.exclude;
20
21 import java.nio.file.FileSystems;
22 import java.nio.file.Path;
23 import java.nio.file.PathMatcher;
24 import java.nio.file.Paths;
25
26 import org.apache.commons.io.FilenameUtils;
27 import org.apache.commons.lang3.StringUtils;
28 import org.apache.maven.buildcache.xml.config.Exclude;
29
30 public class Exclusion {
31
32
33
34
35 private static final String GLOB_PX = "glob:";
36
37 private static final String GLOB_ALL_PATHS = "**";
38 private static final String GLOB_ALL_NAMES = "*";
39
40
41
42
43 private static final String DEFAULT_GLOB = GLOB_ALL_PATHS;
44
45 private final Path absolutePath;
46 private final PathMatcher matcher;
47
48 private final MatcherType matcherType;
49
50 private final EntryType entryType;
51
52
53
54
55 private boolean matchesAllNames;
56
57
58
59
60 private boolean matchesAllPaths;
61
62
63
64
65 private final boolean configuredAsAbsolute;
66
67 public Exclusion(Path basedir, Exclude exclude) {
68
69 if (StringUtils.isNotBlank(exclude.getValue())) {
70 Path candidate = Paths.get(FilenameUtils.separatorsToSystem(exclude.getValue()));
71 configuredAsAbsolute = candidate.isAbsolute();
72 Path resolvedPath = configuredAsAbsolute ? candidate : basedir.resolve(candidate);
73 this.absolutePath = resolvedPath.toAbsolutePath().normalize();
74 } else {
75 configuredAsAbsolute = false;
76 this.absolutePath = basedir;
77 }
78
79 String unixStyleGlob = convertGlobToUnixStyle(exclude.getGlob());
80 this.matcher = FileSystems.getDefault().getPathMatcher(GLOB_PX + unixStyleGlob);
81 this.matcherType = MatcherType.valueOf(exclude.getMatcherType().toUpperCase());
82 this.entryType = EntryType.valueOf(exclude.getEntryType().toUpperCase());
83 computeMatcherDenormalization(unixStyleGlob);
84 }
85
86 public Exclusion(Path absolutePath, MatcherType resolutionType, EntryType entryType) {
87 this.configuredAsAbsolute = false;
88 this.absolutePath = absolutePath;
89 this.matcher = absolutePath.getFileSystem().getPathMatcher(GLOB_PX + DEFAULT_GLOB);
90 this.matcherType = resolutionType;
91 this.entryType = entryType;
92 computeMatcherDenormalization(DEFAULT_GLOB);
93 }
94
95 private String convertGlobToUnixStyle(String glob) {
96 return glob.replace("\\\\", "/");
97 }
98
99 private void computeMatcherDenormalization(String glob) {
100 if (GLOB_ALL_PATHS.equals(glob)) {
101 matchesAllPaths = true;
102 } else if (GLOB_ALL_NAMES.equals(glob)) {
103 matchesAllNames = true;
104 }
105 }
106
107 public Path getAbsolutePath() {
108 return absolutePath;
109 }
110
111 public EntryType getEntryType() {
112 return entryType;
113 }
114
115
116
117
118
119
120 private boolean applies(Path path) {
121 return path.startsWith(this.absolutePath);
122 }
123
124 public boolean excludesPath(Path parentPath, Path path) {
125 if (applies(path)) {
126 switch (matcherType) {
127 case FILENAME:
128 if (matchesAllPaths || matchesAllNames || matcher.matches(path.getFileName())) {
129 return true;
130 }
131 break;
132 case PATH:
133
134
135
136 if (matchesAllPaths || matcher.matches(configuredAsAbsolute ? path : parentPath.relativize(path))) {
137 return true;
138 }
139 break;
140 default:
141 throw new RuntimeException("Exclusion resolution type not handled.");
142 }
143 }
144 return false;
145 }
146
147 public enum MatcherType {
148 FILENAME,
149 PATH;
150 }
151
152 public enum EntryType {
153 FILE,
154 DIRECTORY,
155 ALL;
156 }
157 }