KickJava   Java API By Example, From Geeks To Geeks.

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


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.File JavaDoc;
23 import java.io.FileInputStream JavaDoc;
24 import java.io.FileWriter JavaDoc;
25 import java.io.IOException JavaDoc;
26 import java.io.InputStream JavaDoc;
27 import java.util.ArrayList JavaDoc;
28 import java.util.List JavaDoc;
29 import org.apache.tools.ant.BuildException;
30 import org.apache.tools.ant.FileScanner;
31 import org.apache.tools.ant.Project;
32 import org.apache.tools.ant.Task;
33 import org.apache.tools.ant.taskdefs.Ant;
34 import org.apache.tools.ant.types.FileSet;
35 import org.apache.tools.ant.util.FileUtils;
36
37 /** Assistent in changing of build scripts.
38  *
39  * @author Jaroslav Tulach
40  */

41 public class FixDependencies extends Task {
42     /** Replace*/
43     private List JavaDoc<Replace> replaces = new ArrayList JavaDoc<Replace>();
44     /** files to fix */
45     private FileSet set;
46     /** verify target */
47     private String JavaDoc target;
48     /** clean target */
49     private String JavaDoc clean;
50     /** relative path from module file to build script to use for verification */
51     private String JavaDoc ant;
52     /** trip only changed */
53     private boolean onlyChanged;
54     /** fail on error */
55     private boolean fail;
56     
57     
58     /** tasks to be executed */
59     
60     /** Initialize. */
61     public FixDependencies() {
62     }
63     
64     
65     public Replace createReplace () {
66         Replace r = new Replace ();
67         replaces.add (r);
68         return r;
69     }
70     
71     public FileSet createFileset() throws BuildException {
72         if (this.set != null) throw new BuildException ("Only one file set is allowed");
73         this.set = new FileSet();
74         return this.set;
75     }
76     
77     public void setBuildTarget (String JavaDoc s) {
78         target = s;
79     }
80     
81     public void setCleanTarget (String JavaDoc s) {
82         clean = s;
83     }
84     
85     public void setAntFile (String JavaDoc r) {
86         ant = r;
87     }
88     
89     public void setStripOnlyChanged (boolean b) {
90         onlyChanged = b;
91     }
92     
93     public void setFailOnError (boolean b) {
94         fail = b;
95     }
96
97     public void execute () throws org.apache.tools.ant.BuildException {
98         FileScanner scan = this.set.getDirectoryScanner(getProject());
99         File JavaDoc dir = scan.getBasedir();
100         for (String JavaDoc kid : scan.getIncludedFiles()) {
101             File JavaDoc xml = new File JavaDoc(dir, kid);
102             if (!xml.exists()) throw new BuildException("File does not exist: " + xml, getLocation());
103
104             log ("Fixing " + xml, Project.MSG_INFO);
105
106             File JavaDoc script = null;
107             Ant task = null;
108             Ant cleanTask = null;
109             if (ant != null && target != null) {
110                 task = (org.apache.tools.ant.taskdefs.Ant)getProject ().createTask ("ant");
111                 script = FileUtils.getFileUtils().resolveFile(xml, ant);
112                 if (!script.exists ()) {
113                     String JavaDoc msg = "Skipping. Cannot find file " + ant + " from + " + xml;
114                     if (fail) {
115                         throw new BuildException (msg);
116                     }
117                     log(msg, Project.MSG_ERR);
118                     continue;
119                 }
120                 task.setAntfile (script.getPath ());
121                 task.setDir (script.getParentFile ());
122                 task.setTarget (target);
123                 if (clean != null) {
124                     cleanTask = (Ant) getProject().createTask("ant");
125                     cleanTask.setAntfile (script.getPath ());
126                     cleanTask.setDir (script.getParentFile ());
127                     cleanTask.setTarget (clean);
128                 }
129
130                 try {
131                     // before we do anything else, let's verify that we build
132
if (cleanTask != null) {
133                         log ("Cleaning " + clean + " in " + script, org.apache.tools.ant.Project.MSG_INFO);
134                         cleanTask.execute ();
135                     }
136                     log ("Sanity check executes " + target + " in " + script, org.apache.tools.ant.Project.MSG_INFO);
137                     task.execute ();
138                 } catch (BuildException ex) {
139                     if (fail) {
140                         throw ex;
141                     }
142
143                     log("Skipping. Could not execute " + target + " in " + script, org.apache.tools.ant.Project.MSG_ERR);
144                     continue;
145                 }
146             }
147
148
149             
150             try {
151                 boolean change = fix (xml);
152                 if (onlyChanged && !change) {
153                     continue;
154                 }
155                 simplify (xml, script, task, cleanTask);
156             } catch (IOException JavaDoc ex) {
157                 throw new BuildException (ex, getLocation ());
158             }
159         }
160     }
161     
162     /** Modifies the xml file to replace dependencies wiht new ones.
163      * @return true if there was a change in the file
164      */

165     private boolean fix (File JavaDoc file) throws IOException JavaDoc, BuildException {
166         int s = (int)file.length ();
167         byte[] data = new byte[s];
168         InputStream JavaDoc is = new FileInputStream JavaDoc(file);
169         if (s != is.read (data)) {
170             is.close ();
171             throw new BuildException ("Cannot read " + file);
172         }
173         is.close ();
174         
175         String JavaDoc stream = new String JavaDoc (data);
176         String JavaDoc old = stream;
177         data = null;
178
179         for (Replace r : replaces) {
180             int idx = stream.indexOf ("<code-name-base>" + r.codeNameBase + "</code-name-base>");
181             if (idx == -1) continue;
182             
183             int from = stream.lastIndexOf ("<dependency>", idx);
184             if (from == -1) throw new BuildException ("No <dependency> tag before index " + idx);
185             int after = stream.indexOf ("</dependency>", idx);
186             if (after == -1) throw new BuildException ("No </dependency> tag after index " + idx);
187             after = findNonSpace (stream, after + "</dependency>".length ());
188             
189             String JavaDoc remove = stream.substring (from, after);
190             if (r.addCompileTime && remove.indexOf ("compile-dependency") == -1) {
191                 int fromAfter = "<dependency>".length();
192                 int nonSpace = findNonSpace (remove, fromAfter);
193                 String JavaDoc spaces = remove.substring (fromAfter, nonSpace);
194                 remove = remove.substring (0, fromAfter) + spaces + "<compile-dependency/>" + remove.substring (fromAfter);
195             }
196             
197             StringBuffer JavaDoc sb = new StringBuffer JavaDoc ();
198             sb.append (stream.substring (0, from));
199             
200             for (Module m : r.modules) {
201                 if (stream.indexOf ("<code-name-base>" + m.codeNameBase + "</code-name-base>") != -1) {
202                     continue;
203                 }
204
205                 int beg = remove.indexOf (r.codeNameBase);
206                 int aft = beg + r.codeNameBase.length ();
207                 sb.append (remove.substring (0, beg));
208                 sb.append (m.codeNameBase);
209                 String JavaDoc a = remove.substring (aft);
210                 if (m.specVersion != null) {
211                     a = a.replaceAll (
212                         "<specification-version>[0-9\\.]*</specification-version>",
213                         "<specification-version>" + m.specVersion + "</specification-version>"
214                     );
215                 }
216                 if (m.releaseVersion == null) {
217                     a = a.replaceAll (
218                         "<release-version>[0-9]*</release-version>[\n\r ]*",
219                         ""
220                     );
221                 }
222                 
223                 sb.append (a);
224             }
225             
226             sb.append (stream.substring (after));
227             
228             stream = sb.toString ();
229         }
230         
231         if (!old.equals (stream)) {
232             FileWriter JavaDoc fw = new FileWriter JavaDoc (file);
233             fw.write (stream);
234             fw.close ();
235             return true;
236         } else {
237             return false;
238         }
239     } // end of fix
240

241     private void simplify (
242         File JavaDoc file, File JavaDoc script, org.apache.tools.ant.taskdefs.Ant task, org.apache.tools.ant.taskdefs.Ant cleanTask
243     ) throws IOException JavaDoc, BuildException {
244         if (ant == null || target == null) {
245             return;
246         }
247         
248         int s = (int)file.length ();
249         byte[] data = new byte[s];
250         InputStream JavaDoc is = new FileInputStream JavaDoc(file);
251         if (s != is.read (data)) {
252             is.close ();
253             throw new BuildException ("Cannot read " + file);
254         }
255         is.close ();
256         
257         String JavaDoc stream = new String JavaDoc (data);
258         String JavaDoc old = stream;
259
260         int first = -1;
261         int last = -1;
262         int begin = -1;
263         StringBuffer JavaDoc success = new StringBuffer JavaDoc ();
264         StringBuffer JavaDoc sb = new StringBuffer JavaDoc ();
265         for (;;) {
266             if (cleanTask != null) {
267                 log ("Cleaning " + clean + " in " + script, Project.MSG_INFO);
268                 cleanTask.execute ();
269             }
270             
271             int from = stream.indexOf ("<dependency>", begin);
272             if (from == -1) {
273                 break;
274             }
275             
276             if (first == -1) {
277                 first = from;
278             }
279             
280             int after = stream.indexOf ("</dependency>", from);
281             if (after == -1) throw new BuildException ("No </dependency> tag after index " + from);
282             after = findNonSpace (stream, after + "</dependency>".length ());
283             
284             last = after;
285             begin = last;
286
287             // write the file without the
288
FileWriter JavaDoc fw = new FileWriter JavaDoc (file);
289             fw.write (stream.substring (0, from) + stream.substring (after));
290             fw.close ();
291             
292             String JavaDoc dep = stream.substring (from, after);
293             if (dep.indexOf ("compile-dependency") == -1) {
294                 // skip non-compile dependencies
295
sb.append (stream.substring (from, after));
296                 continue;
297             }
298             
299             
300             int cnbBeg = dep.indexOf ("<code-name-base>");
301             int cnbEnd = dep.indexOf ("</code-name-base>");
302             if (cnbBeg != -1 && cnbEnd != -1) {
303                 dep = dep.substring (cnbBeg + "<code-name-base>".length (), cnbEnd);
304             }
305             
306
307             String JavaDoc result;
308             try {
309                 log ("Executing target " + target + " in " + script, Project.MSG_INFO);
310                 task.execute ();
311                 result = "Ok";
312                 success.append (dep);
313                 success.append ("\n");
314             } catch (BuildException ex) {
315                 result = "Failure";
316                 // ok, this is needed dependency
317
sb.append (stream.substring (from, after));
318             }
319             log ("Removing dependency " + dep + ": " + result, Project.MSG_INFO);
320             
321         }
322
323         if (first != -1) {
324             // write the file without the
325
FileWriter JavaDoc fw = new FileWriter JavaDoc (file);
326             fw.write (stream.substring (0, first) + sb.toString () + stream.substring (last));
327             fw.close ();
328         }
329         
330         log ("Final verification runs " + target + " in " + script, Project.MSG_INFO);
331         // now verify, if there is a failure then something is wrong now
332
task.execute ();
333         
334         if (success.length () == 0) {
335             log ("No dependencies removed from " + script);
336         } else {
337             log ("Removed dependencies from " + script + ":\n" + success);
338         }
339     } // end of simplify
340

341     private static int findNonSpace (String JavaDoc where, int from) {
342         while (from < where.length () && Character.isWhitespace (where.charAt (from))) {
343             from++;
344         }
345         return from;
346     }
347
348     public static final class Replace extends Object JavaDoc {
349         String JavaDoc codeNameBase;
350         List JavaDoc<Module> modules = new ArrayList JavaDoc<Module>();
351         boolean addCompileTime;
352         
353         public void setCodeNameBase (String JavaDoc s) {
354             codeNameBase = s;
355         }
356         
357         public void setAddCompileTime (boolean b) {
358             addCompileTime = b;
359         }
360         
361         public Module createModule () {
362             Module m = new Module ();
363             modules.add (m);
364             return m;
365         }
366         
367     }
368     
369     public static final class Module extends Object JavaDoc {
370         String JavaDoc codeNameBase;
371         String JavaDoc specVersion;
372         String JavaDoc releaseVersion;
373         
374         public void setCodeNameBase (String JavaDoc s) {
375             codeNameBase = s;
376         }
377         
378         
379         public void setSpec (String JavaDoc s) {
380             specVersion = s;
381         }
382         
383         public void setRelease (String JavaDoc r) {
384             releaseVersion = r;
385         }
386     }
387 }
388
Popular Tags