1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19 package org.apache.maven.plugins.pmd.exec;
20
21 import java.io.File;
22 import java.io.IOException;
23 import java.io.UnsupportedEncodingException;
24 import java.io.Writer;
25 import java.nio.charset.Charset;
26 import java.nio.charset.IllegalCharsetNameException;
27 import java.nio.charset.UnsupportedCharsetException;
28 import java.nio.file.Files;
29 import java.util.function.Consumer;
30 import java.util.function.Predicate;
31
32 import net.sourceforge.pmd.cpd.CPDReport;
33 import net.sourceforge.pmd.cpd.CPDReportRenderer;
34 import net.sourceforge.pmd.cpd.Match;
35 import net.sourceforge.pmd.cpd.XMLRenderer;
36 import org.apache.maven.plugins.pmd.ExcludeDuplicationsFromFile;
37 import org.apache.maven.reporting.MavenReportException;
38 import org.codehaus.plexus.util.FileUtils;
39 import org.slf4j.Logger;
40 import org.slf4j.LoggerFactory;
41
42 class CpdReportConsumer implements Consumer<CPDReport> {
43 private static final Logger LOG = LoggerFactory.getLogger(CpdReportConsumer.class);
44
45 private final CpdRequest request;
46 private final ExcludeDuplicationsFromFile excludeDuplicationsFromFile;
47
48 CpdReportConsumer(CpdRequest request, ExcludeDuplicationsFromFile excludeDuplicationsFromFile) {
49 this.request = request;
50 this.excludeDuplicationsFromFile = excludeDuplicationsFromFile;
51 }
52
53 @Override
54 public void accept(CPDReport report) {
55 try {
56
57
58 writeXmlReport(report);
59
60
61
62 String format = request.getFormat();
63 if (!"html".equals(format) && !"xml".equals(format)) {
64 writeFormattedReport(report);
65 }
66 } catch (IOException | MavenReportException e) {
67
68
69
70 throw new RuntimeException(e);
71 }
72 }
73
74 private void writeXmlReport(CPDReport cpd) throws IOException {
75 File targetFile = writeReport(cpd, new XMLRenderer(request.getOutputEncoding()), "xml");
76 if (request.isIncludeXmlInReports()) {
77 File outputDirectory = new File(request.getReportOutputDirectory());
78 if (!outputDirectory.exists() && !outputDirectory.mkdirs()) {
79 throw new IOException("Couldn't create report output directory: " + outputDirectory);
80 }
81 FileUtils.copyFile(targetFile, new File(outputDirectory, "cpd.xml"));
82 }
83 }
84
85 private void writeFormattedReport(CPDReport cpd) throws IOException, MavenReportException {
86 CPDReportRenderer renderer = CpdExecutor.createRenderer(request.getFormat(), request.getOutputEncoding());
87 writeReport(cpd, renderer, request.getFormat());
88 }
89
90 private File writeReport(CPDReport cpd, CPDReportRenderer renderer, String extension) throws IOException {
91 if (renderer == null) {
92 return null;
93 }
94
95 File targetDir = new File(request.getTargetDirectory());
96 if (!targetDir.exists() && !targetDir.mkdirs()) {
97 throw new IOException("Couldn't create report target directory: " + targetDir);
98 }
99
100 File targetFile = new File(targetDir, "cpd." + extension);
101 try (Writer writer =
102 Files.newBufferedWriter(targetFile.toPath(), Charset.forName(request.getOutputEncoding()))) {
103 renderer.render(cpd.filterMatches(filterMatches()), writer);
104 return targetFile;
105 } catch (UnsupportedCharsetException | IllegalCharsetNameException ex) {
106 throw new UnsupportedEncodingException(ex.getMessage());
107 }
108 }
109
110 private Predicate<Match> filterMatches() {
111 return (Match match) -> {
112 LOG.debug(
113 "Filtering duplications. Using {} configured exclusions.",
114 excludeDuplicationsFromFile.countExclusions());
115
116 if (excludeDuplicationsFromFile.isExcludedFromFailure(match)) {
117 LOG.debug("Excluded {} duplications.", match);
118 return false;
119 } else {
120 return true;
121 }
122 };
123 }
124 }