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 throw new RuntimeException(e);
68 }
69 }
70
71 private void writeXmlReport(CPDReport cpd) throws IOException {
72 File targetFile = writeReport(cpd, new XMLRenderer(request.getOutputEncoding()), "xml");
73 if (request.isIncludeXmlInReports()) {
74 File outputDirectory = new File(request.getReportOutputDirectory());
75 if (!outputDirectory.exists() && !outputDirectory.mkdirs()) {
76 throw new IOException("Couldn't create report output directory: " + outputDirectory);
77 }
78 FileUtils.copyFile(targetFile, new File(outputDirectory, "cpd.xml"));
79 }
80 }
81
82 private void writeFormattedReport(CPDReport cpd) throws IOException, MavenReportException {
83 CPDReportRenderer renderer = CpdExecutor.createRenderer(request.getFormat(), request.getOutputEncoding());
84 writeReport(cpd, renderer, request.getFormat());
85 }
86
87 private File writeReport(CPDReport cpd, CPDReportRenderer renderer, String extension) throws IOException {
88 if (renderer == null) {
89 return null;
90 }
91
92 File targetDir = new File(request.getTargetDirectory());
93 if (!targetDir.exists() && !targetDir.mkdirs()) {
94 throw new IOException("Couldn't create report target directory: " + targetDir);
95 }
96
97 File targetFile = new File(targetDir, "cpd." + extension);
98 try (Writer writer =
99 Files.newBufferedWriter(targetFile.toPath(), Charset.forName(request.getOutputEncoding()))) {
100 renderer.render(cpd.filterMatches(filterMatches()), writer);
101 return targetFile;
102 } catch (UnsupportedCharsetException | IllegalCharsetNameException ex) {
103 throw new UnsupportedEncodingException(ex.getMessage());
104 }
105 }
106
107 private Predicate<Match> filterMatches() {
108 return (Match match) -> {
109 LOG.debug(
110 "Filtering duplications. Using {} configured exclusions.",
111 excludeDuplicationsFromFile.countExclusions());
112
113 if (excludeDuplicationsFromFile.isExcludedFromFailure(match)) {
114 LOG.debug("Excluded {} duplications.", match);
115 return false;
116 } else {
117 return true;
118 }
119 };
120 }
121 }