KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > org > netbeans > nbbuild > Kvetcher


1 /*
2  * The contents of this file are subject to the terms of the Common Development
3  * and Distribution License (the License). You may not use this file except in
4  * compliance with the License.
5  *
6  * You can obtain a copy of the License at http://www.netbeans.org/cddl.html
7  * or http://www.netbeans.org/cddl.txt.
8  *
9  * When distributing Covered Code, include this CDDL Header Notice in each file
10  * and include the License file at http://www.netbeans.org/cddl.txt.
11  * If applicable, add the following below the CDDL Header, with the fields
12  * enclosed by brackets [] replaced by your own identifying information:
13  * "Portions Copyrighted [year] [name of copyright owner]"
14  *
15  * The Original Software is NetBeans. The Initial Developer of the Original
16  * Software is Sun Microsystems, Inc. Portions Copyright 1997-2006 Sun
17  * Microsystems, Inc. All Rights Reserved.
18  */

19
20 package org.netbeans.nbbuild;
21
22 import java.io.*;
23 import java.util.*;
24 import java.util.regex.*;
25
26 import org.apache.tools.ant.*;
27 import org.apache.tools.mail.MailMessage;
28
29 /** Task to complain (via email) to people when things fail in a build.
30  * XXX In Ant 1.4 this could be better written using TaskContainer, probably.
31  * XXX support fallback address for errors not otherwise handled
32  * XXX do not send the same error to more than one culprit
33  * XXX support ignore patterns for errors, to be useful with e.g. compile deprecations
34  * @author Jesse Glick
35  */

36 public class Kvetcher extends Task implements BuildListener {
37     
38     private Explanation explanation = null;
39     public final class Explanation {
40         StringBuffer JavaDoc text = new StringBuffer JavaDoc();
41         public void addText(String JavaDoc s) {
42             text.append(getProject().replaceProperties(s));
43         }
44     }
45     /** Provide some explanatory text for the message. */
46     public Explanation createExplanation() {
47         return explanation = new Explanation();
48     }
49     
50     private String JavaDoc target;
51     /** Set the target to run while listening. */
52     public void setTarget(String JavaDoc t) {
53         target = t;
54     }
55     
56     private String JavaDoc from = null;
57     /** Set the mail address to send from. */
58     public void setFrom(String JavaDoc f) {
59         from = f;
60     }
61     
62     private String JavaDoc subject="Errors in sources";
63     /** Set the mail subject. */
64     public void setSubject(String JavaDoc s) {
65         subject = s;
66     }
67     
68     private String JavaDoc mailhost = "localhost";
69     /** Set the SMTP mailhost to send from. */
70     public void setMailhost(String JavaDoc mh) {
71         mailhost = mh;
72     }
73     
74     private List<Culprit> culprits = new ArrayList<Culprit>(20);
75     public Culprit createCulprit() {
76         Culprit c = new Culprit();
77         culprits.add(c);
78         return c;
79     }
80     
81     public final class Culprit {
82         List<Address> to = new ArrayList<Address>(1);
83         List<Address> cc = new ArrayList<Address>(1);
84         List<Regexp> regexp = new ArrayList<Regexp>(5);
85         public Address createTo() {
86             Address a = new Address();
87             to.add(a);
88             return a;
89         }
90         public Address createCC() {
91             Address a = new Address();
92             cc.add(a);
93             return a;
94         }
95         public Regexp createRegexp() {
96             Regexp r = new Regexp();
97             regexp.add(r);
98             return r;
99         }
100         boolean isValid() {
101             if ((to.isEmpty() && cc.isEmpty()) || regexp.isEmpty()) return false;
102             Iterator it = to.iterator();
103             while (it.hasNext()) {
104                 if (! ((Address)it.next()).isValid()) return false;
105             }
106             it = cc.iterator();
107             while (it.hasNext()) {
108                 if (! ((Address)it.next()).isValid()) return false;
109             }
110             it = regexp.iterator();
111             while (it.hasNext()) {
112                 if (! ((Regexp)it.next()).isValid()) return false;
113             }
114             return true;
115         }
116     }
117     public final class Address {
118         String JavaDoc name;
119         public void setName(String JavaDoc n) {
120             name = n;
121         }
122         boolean isValid() {
123             return name != null;
124         }
125     }
126     public final class Regexp {
127         Pattern pattern;
128         int group = -1;
129         public void setPattern(String JavaDoc p) throws BuildException {
130             try {
131                 pattern = Pattern.compile(p);
132             } catch (PatternSyntaxException rese) {
133                 throw new BuildException(rese, getLocation());
134             }
135         }
136         /** Set which part of the message to actually send.
137          * By default, the entire message.
138          * But you may set this to 0 to mean the matched portion,
139          * or some number >0 to mean that parenthesized group.
140          */

141         public void setGroup(int g) {
142             group = g;
143         }
144         boolean isValid() {
145             return pattern != null;
146         }
147     }
148     
149     private List<String JavaDoc> messages = new ArrayList<String JavaDoc>(1000);
150     
151     public void execute() throws BuildException {
152         if (target == null) throw new BuildException("set the target");
153         if (culprits.isEmpty()) throw new BuildException("add some culprits");
154         Iterator it = culprits.iterator();
155         while (it.hasNext()) {
156             if (! ((Culprit)it.next()).isValid()) throw new BuildException("invalid <culprit>");
157         }
158         getProject().addBuildListener(this);
159         boolean success = false;
160         try {
161             getProject().executeTarget(target);
162             success = true;
163         } finally {
164             getProject().removeBuildListener(this);
165         }
166         if (success) sendMail();
167     }
168     
169     public void messageLogged(BuildEvent buildEvent) {
170         int pri = buildEvent.getPriority();
171         if (pri == Project.MSG_WARN || pri == Project.MSG_ERR) {
172             messages.add(buildEvent.getMessage());
173         }
174     }
175     
176     private void sendMail() throws BuildException {
177         for (Culprit c: culprits) {
178             try {
179                 MailMessage mail = null;
180                 //boolean send = false;
181
PrintStream ps = null;
182                 for (String JavaDoc msg: messages) {
183                     for (Regexp r: c.regexp) {
184                         Matcher m = r.pattern.matcher(msg);
185                         if (m.find()) {
186                             if (mail == null) {
187                                 // OK, time to start sending.
188
log("Sending mail to " + c.to.get(0).name);
189                                 mail = new MailMessage(mailhost);
190                                 if (from == null) from = "kvetcher@" + mailhost;
191                                 mail.from(from);
192                                 for (Address a: c.to) {
193                                     mail.to(a.name);
194                                 }
195                                 for (Address a: c.cc) {
196                                     mail.cc(a.name);
197                                 }
198                                 mail.setSubject(subject);
199                                 ps = mail.getPrintStream();
200                                 if (explanation != null) {
201                                     ps.println(explanation.text.toString());
202                                 }
203                                 ps.println();
204                             }
205                             ps.println(r.group == -1 ? msg : m.group(r.group));
206                             break; // this regexp matches, look for other messages
207
}
208                     }
209                 }
210                 if (mail != null) {
211                     mail.sendAndClose();
212                 }
213             } catch (IOException ioe) {
214                 throw new BuildException("While sending mail", ioe, getLocation());
215             }
216         }
217     }
218     
219     // Ignore these:
220
public void taskStarted(BuildEvent buildEvent) {
221     }
222     public void buildStarted(BuildEvent buildEvent) {
223     }
224     public void buildFinished(BuildEvent buildEvent) {
225     }
226     public void taskFinished(BuildEvent buildEvent) {
227     }
228     public void targetFinished(BuildEvent buildEvent) {
229     }
230     public void targetStarted(BuildEvent buildEvent) {
231     }
232     
233 }
234
Popular Tags