1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19 package org.apache.rat.mp;
20
21 import java.io.File;
22 import java.io.IOException;
23 import java.io.PrintWriter;
24 import java.net.URI;
25 import java.util.ArrayList;
26 import java.util.Arrays;
27 import java.util.Collection;
28 import java.util.List;
29 import java.util.Map;
30 import java.util.Objects;
31 import java.util.SortedSet;
32 import java.util.function.Consumer;
33 import java.util.stream.Collectors;
34 import java.util.stream.Stream;
35
36 import org.apache.commons.cli.Option;
37 import org.apache.commons.lang3.StringUtils;
38 import org.apache.maven.plugin.MojoExecutionException;
39 import org.apache.maven.plugins.annotations.Parameter;
40 import org.apache.maven.project.MavenProject;
41 import org.apache.rat.Defaults;
42 import org.apache.rat.OptionCollection;
43 import org.apache.rat.ReportConfiguration;
44 import org.apache.rat.analysis.license.DeprecatedConfig;
45 import org.apache.rat.commandline.Arg;
46 import org.apache.rat.config.exclusion.StandardCollection;
47 import org.apache.rat.configuration.Format;
48 import org.apache.rat.configuration.LicenseReader;
49 import org.apache.rat.configuration.MatcherReader;
50 import org.apache.rat.document.DocumentName;
51 import org.apache.rat.document.FileDocument;
52 import org.apache.rat.license.ILicense;
53 import org.apache.rat.license.ILicenseFamily;
54 import org.apache.rat.license.LicenseSetFactory.LicenseFilter;
55 import org.apache.rat.license.SimpleLicenseFamily;
56 import org.apache.rat.plugin.BaseRatMojo;
57 import org.apache.rat.utils.DefaultLog;
58 import org.apache.rat.utils.Log;
59 import org.apache.rat.walker.DirectoryWalker;
60
61 import static java.lang.String.format;
62
63
64
65
66 public abstract class AbstractRatMojo extends BaseRatMojo {
67
68 private ReportConfiguration reportConfiguration;
69
70
71
72 @Parameter(property = "rat.basedir", defaultValue = "${basedir}", required = true)
73 protected File basedir;
74
75
76
77
78
79 @Parameter(property = "rat.verbose", defaultValue = "false")
80 protected boolean verbose;
81
82
83
84
85
86
87
88
89 @Parameter
90 @Deprecated
91 private String[] defaultLicenseFiles;
92
93
94
95
96
97 @Parameter
98 @Deprecated
99 private String[] additionalLicenseFiles;
100
101
102
103
104
105 @Deprecated
106 @Parameter(property = "rat.addDefaultLicenses", name = "addDefaultLicenses")
107 public void setAddDefaultLicenses(final boolean addDefaultLicenses) {
108 setNoDefaultLicenses(!addDefaultLicenses);
109 }
110
111
112
113
114
115 @Deprecated
116 @Parameter(property = "rat.addDefaultLicenseMatchers")
117 private boolean addDefaultLicenseMatchers;
118
119
120
121
122 @Deprecated
123 @Parameter
124 private String[] approvedLicenses;
125
126
127
128
129 @Deprecated
130 @Parameter(property = "rat.approvedFile")
131 private String approvedLicenseFile;
132
133
134
135
136
137
138
139 @Deprecated
140 @Parameter
141 private SimpleLicenseFamily[] licenseFamilies;
142
143
144
145
146 @Deprecated
147 @Parameter
148 private Object[] licenses;
149
150
151
152
153 @Deprecated
154 @Parameter
155 private Family[] families;
156
157
158
159
160
161 @Parameter(property = "rat.includesFileCharset", defaultValue = "${project.build.sourceEncoding}")
162 private String includesFileCharset;
163
164
165
166
167
168 @Parameter(property = "rat.excludesFileCharset", defaultValue = "${project.build.sourceEncoding}")
169 private String excludesFileCharset;
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188 @Parameter(property = "rat.useDefaultExcludes", defaultValue = "true")
189 @Deprecated
190 private boolean useDefaultExcludes;
191
192
193
194
195
196
197
198
199
200 @Parameter(property = "rat.useMavenDefaultExcludes", defaultValue = "true")
201 @Deprecated
202 private boolean useMavenDefaultExcludes;
203
204
205
206
207
208
209
210
211
212
213 @Parameter(property = "rat.parseSCMIgnoresAsExcludes", defaultValue = "true")
214 @Deprecated
215 private boolean parseSCMIgnoresAsExcludes;
216
217
218
219
220
221
222
223
224
225 @Parameter(property = "rat.useEclipseDefaultExcludes", defaultValue = "true")
226 @Deprecated
227 private boolean useEclipseDefaultExcludes;
228
229
230
231
232
233
234
235
236
237 @Deprecated
238 @Parameter(property = "rat.useIdeaDefaultExcludes", defaultValue = "true")
239 private boolean useIdeaDefaultExcludes;
240
241
242
243
244
245 @Parameter(property = "rat.excludeSubprojects", defaultValue = "true")
246 private boolean excludeSubProjects;
247
248
249
250
251
252
253
254 @Parameter(property = "rat.skip", defaultValue = "false")
255 protected boolean skip;
256
257
258
259
260
261 @Parameter(defaultValue = "${project}", required = true, readonly = true)
262 protected MavenProject project;
263
264 protected AbstractRatMojo() {
265 DefaultLog.setInstance(makeLog());
266 }
267
268
269
270
271 protected MavenProject getProject() {
272 return project;
273 }
274
275 protected Defaults.Builder getDefaultsBuilder() {
276 Defaults.Builder result = Defaults.builder().noDefault();
277 if (defaultLicenseFiles != null) {
278 for (String defaultLicenseFile : defaultLicenseFiles) {
279 result.add(defaultLicenseFile);
280 }
281 }
282 return result;
283 }
284
285 @Deprecated
286 private Stream<License> getLicenses() {
287 if (licenses == null) {
288 return Stream.empty();
289 }
290 return Arrays.stream(licenses).filter(s -> s instanceof License).map(License.class::cast);
291 }
292
293 @Deprecated
294 private Stream<DeprecatedConfig> getDeprecatedConfigs() {
295 if (licenses == null) {
296 return Stream.empty();
297 }
298 return Arrays.stream(licenses).filter(s -> s instanceof DeprecatedConfig).map(DeprecatedConfig.class::cast);
299 }
300
301 @Deprecated
302 private void reportDeprecatedProcessing() {
303 if (getDeprecatedConfigs().findAny().isPresent()) {
304 DefaultLog.getInstance().warn("Configuration uses deprecated configuration. You need to upgrade to v0.17 configuration options.");
305 }
306 }
307
308 @Deprecated
309 private void processLicenseFamilies(final ReportConfiguration config) {
310 List<ILicenseFamily> families = getDeprecatedConfigs().map(DeprecatedConfig::getLicenseFamily).filter(Objects::nonNull).collect(Collectors.toList());
311 if (licenseFamilies != null) {
312 for (SimpleLicenseFamily slf : licenseFamilies) {
313 if (StringUtils.isBlank(slf.getFamilyCategory())) {
314 families.stream().filter(f -> f.getFamilyName().equalsIgnoreCase(slf.getFamilyName())).findFirst()
315 .ifPresent(config::addApprovedLicenseCategory);
316 } else {
317 config.addApprovedLicenseCategory(ILicenseFamily.builder().setLicenseFamilyCategory(slf.getFamilyCategory())
318 .setLicenseFamilyName(StringUtils.defaultIfBlank(slf.getFamilyName(), slf.getFamilyCategory()))
319 .build());
320 }
321 }
322 }
323 }
324
325
326
327
328
329
330
331 protected List<String> getValues(final Arg arg) {
332 List<String> result = new ArrayList<>();
333 for (Option option : arg.group().getOptions()) {
334 if (option.getLongOpt() != null) {
335 List<String> args = getArg(option.getLongOpt());
336 if (args != null) {
337 result.addAll(args);
338 }
339 }
340 }
341 return result;
342 }
343
344
345
346
347
348 protected void removeKey(final Arg arg) {
349 for (Option option : arg.group().getOptions()) {
350 if (option.getLongOpt() != null) {
351 removeArg(option.getLongOpt());
352 }
353 }
354 }
355
356 private org.apache.rat.utils.Log makeLog() {
357 return new org.apache.rat.utils.Log() {
358 @Override
359 public Level getLevel() {
360 final org.apache.maven.plugin.logging.Log log = getLog();
361 if (log.isDebugEnabled()) {
362 return Level.DEBUG;
363 }
364 if (log.isInfoEnabled()) {
365 return Level.INFO;
366 }
367 if (log.isWarnEnabled()) {
368 return Level.WARN;
369 }
370 if (log.isErrorEnabled()) {
371 return Level.ERROR;
372 }
373 return Level.OFF;
374 }
375
376 @Override
377 public void log(final Level level, final String message, final Throwable throwable) {
378 final org.apache.maven.plugin.logging.Log log = getLog();
379 switch (level) {
380 case DEBUG:
381 if (throwable != null) {
382 log.debug(message, throwable);
383 } else {
384 log.debug(message);
385 }
386 break;
387 case INFO:
388 if (throwable != null) {
389 log.info(message, throwable);
390 } else {
391 log.info(message);
392 }
393 break;
394 case WARN:
395 if (throwable != null) {
396 log.warn(message, throwable);
397 } else {
398 log.warn(message);
399 }
400 break;
401 case ERROR:
402 if (throwable != null) {
403 log.error(message, throwable);
404 } else {
405 log.error(message);
406 }
407 break;
408 case OFF:
409 break;
410 }
411 }
412
413 @Override
414 public void log(final Level level, final String msg) {
415 final org.apache.maven.plugin.logging.Log log = getLog();
416 switch (level) {
417 case DEBUG:
418 log.debug(msg);
419 break;
420 case INFO:
421 log.info(msg);
422 break;
423 case WARN:
424 log.warn(msg);
425 break;
426 case ERROR:
427 log.error(msg);
428 break;
429 case OFF:
430 break;
431 }
432 }
433 };
434 }
435
436 private void setIncludeExclude() {
437
438 if (excludeSubProjects && project != null && project.getModules() != null) {
439 List<String> subModules = new ArrayList<>();
440 project.getModules().forEach(s -> subModules.add(format("%s/**", s)));
441 setInputExcludes(subModules.toArray(new String[0]));
442 }
443
444 List<String> values = getValues(Arg.EXCLUDE);
445 if (values.isEmpty() && useDefaultExcludes) {
446 DefaultLog.getInstance().debug("Adding plexus default exclusions...");
447 setInputExcludes(StandardCollection.STANDARD_PATTERNS.patterns().toArray(new String[0]));
448
449 DefaultLog.getInstance().debug("Adding SCM default exclusions...");
450 setInputExcludes(StandardCollection.STANDARD_SCMS.patterns().toArray(new String[0]));
451 }
452
453 if (useMavenDefaultExcludes) {
454 setInputExcludeStd(StandardCollection.MAVEN.name());
455 }
456 if (useEclipseDefaultExcludes) {
457 setInputExcludeStd(StandardCollection.ECLIPSE.name());
458 }
459 if (useIdeaDefaultExcludes) {
460 setInputExcludeStd(StandardCollection.IDEA.name());
461 }
462
463 if (parseSCMIgnoresAsExcludes) {
464 setInputExcludeParsedScm(StandardCollection.STANDARD_SCMS.name());
465 }
466 }
467
468 protected ReportConfiguration getConfiguration() throws MojoExecutionException {
469 Log log = DefaultLog.getInstance();
470 if (reportConfiguration == null) {
471 try {
472 if (getLog().isDebugEnabled()) {
473 log.debug("Start BaseRatMojo Configuration options");
474 for (Map.Entry<String, List<String>> entry : args.entrySet()) {
475 log.debug(format(" * %s %s", entry.getKey(), String.join(", ", entry.getValue())));
476 }
477 log.debug("End BaseRatMojo Configuration options");
478 }
479
480 boolean helpLicenses = !getValues(Arg.HELP_LICENSES).isEmpty();
481 removeKey(Arg.HELP_LICENSES);
482 setIncludeExclude();
483
484 getLog().debug("Basedir is : " + basedir);
485 ReportConfiguration config = OptionCollection.parseCommands(basedir, args().toArray(new String[0]),
486 o -> getLog().warn("Help option not supported"),
487 true);
488 reportDeprecatedProcessing();
489
490 if (additionalLicenseFiles != null) {
491 for (String licenseFile : additionalLicenseFiles) {
492 URI uri = new File(licenseFile).toURI();
493 Format fmt = Format.from(licenseFile);
494 MatcherReader mReader = fmt.matcherReader();
495 if (mReader != null) {
496 mReader.addMatchers(uri);
497 }
498 LicenseReader lReader = fmt.licenseReader();
499 if (lReader != null) {
500 lReader.addLicenses(uri);
501 config.addLicenses(lReader.readLicenses());
502 config.addApprovedLicenseCategories(lReader.approvedLicenseId());
503 }
504 }
505 }
506 if (families != null || getDeprecatedConfigs().findAny().isPresent()) {
507 if (log.isEnabled(Log.Level.DEBUG) && families != null) {
508 log.debug(format("%s license families loaded from pom", families.length));
509 }
510 Consumer<ILicenseFamily> logger = super.getLog().isDebugEnabled() ? l -> log.debug(format("Family: %s", l))
511 : l -> {
512 };
513
514 Consumer<ILicenseFamily> process = logger.andThen(config::addFamily);
515 getDeprecatedConfigs().map(DeprecatedConfig::getLicenseFamily).filter(Objects::nonNull).forEach(process);
516 if (families != null) {
517 Arrays.stream(families).map(Family::build).forEach(process);
518 }
519 }
520
521 processLicenseFamilies(config);
522
523 if (approvedLicenses != null && approvedLicenses.length > 0) {
524 Arrays.stream(approvedLicenses).forEach(config::addApprovedLicenseCategory);
525 }
526
527 if (licenses != null) {
528 if (log.isEnabled(Log.Level.DEBUG)) {
529 log.debug(format("%s licenses loaded from pom", licenses.length));
530 }
531 Consumer<ILicense> logger = log.isEnabled(Log.Level.DEBUG) ? l -> log.debug(format("License: %s", l))
532 : l -> {
533 };
534 Consumer<ILicense> addApproved = (approvedLicenses == null || approvedLicenses.length == 0)
535 ? l -> config.addApprovedLicenseCategory(l.getLicenseFamily())
536 : l -> {
537 };
538
539 Consumer<ILicense> process = logger.andThen(config::addLicense).andThen(addApproved);
540 SortedSet<ILicenseFamily> families = config.getLicenseFamilies(LicenseFilter.ALL);
541 getDeprecatedConfigs().map(DeprecatedConfig::getLicense).filter(Objects::nonNull)
542 .map(x -> x.setLicenseFamilies(families).build()).forEach(process);
543 getLicenses().map(x -> x.build(families)).forEach(process);
544 }
545 DocumentName dirName = DocumentName.builder(basedir).build();
546 config.addSource(new DirectoryWalker(new FileDocument(dirName, basedir, config.getDocumentExcluder(dirName))));
547
548 if (helpLicenses) {
549 new org.apache.rat.help.Licenses(config, new PrintWriter(log.asWriter())).printHelp();
550 }
551 reportConfiguration = config;
552 } catch (IOException e) {
553 throw new MojoExecutionException(e);
554 }
555 }
556 return reportConfiguration;
557 }
558
559 protected void logLicenses(final Collection<ILicense> licenses) {
560 if (getLog().isDebugEnabled()) {
561 getLog().debug("The following " + licenses.size() + " licenses are activated:");
562 for (ILicense license : licenses) {
563 getLog().debug("* " + license.toString());
564 }
565 }
566 }
567 }