1 package net.sourceforge.pmd.cpd;
2
3 import org.apache.tools.ant.BuildException;
4 import org.apache.tools.ant.DirectoryScanner;
5 import org.apache.tools.ant.Project;
6 import org.apache.tools.ant.Task;
7 import org.apache.tools.ant.types.EnumeratedAttribute;
8 import org.apache.tools.ant.types.FileSet;
9
10 import java.io.File;
11 import java.io.IOException;
12 import java.util.ArrayList;
13 import java.util.Iterator;
14 import java.util.List;
15
16 /***
17 * CPDTask
18 *
19 * Runs the CPD utility via ant. The ant task looks like this:
20 *
21 * <project name="CPDProj" default="main" basedir=".">
22 * <taskdef name="cpd" classname="net.sourceforge.pmd.cpd.CPDTask" />
23 * <target name="main">
24 * <cpd minimumTokenCount="100" outputFile="c:\cpdrun.txt" verbose=true>
25 * <fileset dir="/path/to/my/src">
26 * <include name="*.java"/>
27 * </fileset>
28 * </cpd>
29 * </target>
30 *</project>
31 *
32 * Required: minimumTokenCount, outputFile, and at least one file
33 * Optional: verbose
34 */
35 public class CPDTask extends Task {
36
37 private static final String TEXT_FORMAT = "text";
38 private static final String XML_FORMAT = "xml";
39
40 private String format = TEXT_FORMAT;
41 private int minimumTokenCount;
42 private File outputFile;
43 private List filesets = new ArrayList();
44
45 public void execute() throws BuildException {
46 try {
47 validateFields();
48
49 log("Tokenizing files", Project.MSG_INFO);
50 CPD cpd = new CPD(minimumTokenCount, new JavaLanguage());
51 tokenizeFiles(cpd);
52
53 log("Starting to analyze code", Project.MSG_INFO);
54 long timeTaken = analyzeCode(cpd);
55 log("Done analyzing code; that took " + timeTaken + " milliseconds");
56
57 log("Generating report", Project.MSG_INFO);
58 report(cpd);
59 } catch (IOException ioe) {
60 log(ioe.toString(), Project.MSG_ERR);
61 throw new BuildException("IOException during task execution", ioe);
62 } catch (ReportException re) {
63 log(re.toString(), Project.MSG_ERR);
64 throw new BuildException("ReportException during task execution", re);
65 }
66 }
67
68 private void report(CPD cpd) throws ReportException {
69 if (!cpd.getMatches().hasNext()) {
70 log("No duplicates over " + minimumTokenCount + " tokens found", Project.MSG_INFO);
71 }
72 Renderer renderer = createRenderer();
73 if (outputFile.isAbsolute()) {
74 new FileReporter(outputFile).report(renderer.render(cpd.getMatches()));
75 } else {
76 new FileReporter(new File(project.getBaseDir(), outputFile.toString()));
77 }
78 }
79
80
81 private void tokenizeFiles(CPD cpd) throws IOException {
82 for (Iterator iterator = filesets.iterator(); iterator.hasNext();) {
83 FileSet fileSet = (FileSet) iterator.next();
84 DirectoryScanner directoryScanner = fileSet.getDirectoryScanner(project);
85 String[] includedFiles = directoryScanner.getIncludedFiles();
86 for (int i = 0; i < includedFiles.length; i++) {
87 File file = new File(directoryScanner.getBasedir() + System.getProperty("file.separator") + includedFiles[i]);
88 log("Tokenizing " + file.getAbsolutePath(), Project.MSG_VERBOSE);
89 cpd.add(file);
90 }
91 }
92 }
93
94 private long analyzeCode(CPD cpd) {
95 long start = System.currentTimeMillis();
96 cpd.go();
97 long stop = System.currentTimeMillis();
98 return stop - start;
99 }
100
101 private Renderer createRenderer() {
102 if (format.equals(TEXT_FORMAT)) {
103 return new SimpleRenderer();
104 } else
105 return new XMLRenderer();
106 }
107
108 private void validateFields() throws BuildException{
109 if(minimumTokenCount == 0){
110 throw new BuildException("minimumTokenCount is required and must be greater than zero");
111 } else if(outputFile == null) {
112 throw new BuildException("outputFile is a required attribute");
113 } else if (filesets.isEmpty()) {
114 throw new BuildException("Must include at least one FileSet");
115 }
116
117 }
118
119 public void addFileset(FileSet set) {
120 filesets.add(set);
121 }
122
123 public void setMinimumTokenCount(int minimumTokenCount) {
124 this.minimumTokenCount = minimumTokenCount;
125 }
126
127 public void setOutputFile(File outputFile) {
128 this.outputFile = outputFile;
129 }
130
131 public void setFormat(FormatAttribute formatAttribute) {
132 format = formatAttribute.getValue();
133 }
134
135 public static class FormatAttribute extends EnumeratedAttribute {
136 private String[] formats = new String[] {XML_FORMAT, TEXT_FORMAT};
137
138 public String[] getValues() {
139 return formats;
140 }
141 }
142 }
This page was automatically generated by Maven