KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > org > netbeans > modules > java > freeform > JavaProjectGenerator


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.modules.java.freeform;
21
22 import java.io.File JavaDoc;
23 import java.util.ArrayList JavaDoc;
24 import java.util.HashSet JavaDoc;
25 import java.util.Iterator JavaDoc;
26 import java.util.List JavaDoc;
27 import java.util.Set JavaDoc;
28 import org.netbeans.api.java.project.JavaProjectConstants;
29 import org.netbeans.api.project.ant.AntArtifact;
30 import org.netbeans.api.project.ant.AntArtifactQuery;
31 import org.netbeans.modules.ant.freeform.spi.support.Util;
32 import org.netbeans.spi.project.AuxiliaryConfiguration;
33 import org.netbeans.spi.project.support.ant.AntProjectHelper;
34 import org.netbeans.spi.project.support.ant.EditableProperties;
35 import org.netbeans.spi.project.support.ant.PropertyEvaluator;
36 import org.netbeans.spi.project.support.ant.PropertyUtils;
37 import org.openide.filesystems.FileUtil;
38 import org.w3c.dom.Document JavaDoc;
39 import org.w3c.dom.Element JavaDoc;
40
41 /**
42  * Reads/writes project.xml.
43  * Handling of /1 vs. /2 namespace: either namespace can be read;
44  * when writing, attempts to keep existing namespace when possible, but
45  * will always write a /2 namespace when it is necessary (for isTests or javadoc).
46  * @author Jesse Glick, David Konecny, Pavel Buzek
47  */

48 public class JavaProjectGenerator {
49
50     /** Keep root elements in the order specified by project's XML schema. */
51     private static final String JavaDoc[] rootElementsOrder = new String JavaDoc[]{"name", "properties", "folders", "ide-actions", "export", "view", "subprojects"}; // NOI18N
52
private static final String JavaDoc[] viewElementsOrder = new String JavaDoc[]{"items", "context-menu"}; // NOI18N
53

54     // this order is not required by schema, but follow it to minimize randomness a bit
55
private static final String JavaDoc[] folderElementsOrder = new String JavaDoc[]{"source-folder", "build-folder"}; // NOI18N
56
private static final String JavaDoc[] viewItemElementsOrder = new String JavaDoc[]{"source-folder", "source-file"}; // NOI18N
57

58     /**
59      * Structure describing source folder.
60      * Data in the struct are in the same format as they are stored in XML.
61      * Beware that when used in <folders> you must specify label, location, and optional type;
62      * in <view><items>, you must specify label, location, and style. So if you are switching
63      * from the latter to the former you must add style; if vice-versa, you may need to add type.
64      */

65     public static final class SourceFolder {
66         public SourceFolder() {}
67         public String JavaDoc label;
68         public String JavaDoc type;
69         public String JavaDoc location;
70         public String JavaDoc style;
71         public String JavaDoc includes;
72         public String JavaDoc excludes;
73         public String JavaDoc toString() {
74             return "FPG.SF[label=" + label + ",type=" + type + ",location=" + location + ",style=" + style + ",includes=" + includes + ",excludes=" + excludes + "]"; // NOI18N
75
}
76     }
77
78     /**
79      * Read source folders from the project.
80      * @param helper AntProjectHelper instance
81      * @param type type of source folders to be read. Can be null in which case
82      * all types will be read. Useful for reading one type of source folders.
83      * Source folders without type are read only when type == null.
84      * @return list of SourceFolder instances; style value will be always null
85      */

86     public static List JavaDoc<SourceFolder> getSourceFolders(AntProjectHelper helper, String JavaDoc type) {
87         //assert ProjectManager.mutex().isReadAccess() || ProjectManager.mutex().isWriteAccess();
88
List JavaDoc<SourceFolder> list = new ArrayList JavaDoc<SourceFolder>();
89         Element JavaDoc data = Util.getPrimaryConfigurationData(helper);
90         Element JavaDoc foldersEl = Util.findElement(data, "folders", Util.NAMESPACE); // NOI18N
91
if (foldersEl == null) {
92             return list;
93         }
94         for (Element JavaDoc sourceFolderEl : Util.findSubElements(foldersEl)) {
95             if (!sourceFolderEl.getLocalName().equals("source-folder")) { // NOI18N
96
continue;
97             }
98             SourceFolder sf = new SourceFolder();
99             Element JavaDoc el = Util.findElement(sourceFolderEl, "label", Util.NAMESPACE); // NOI18N
100
if (el != null) {
101                 sf.label = Util.findText(el);
102             }
103             el = Util.findElement(sourceFolderEl, "type", Util.NAMESPACE); // NOI18N
104
if (el != null) {
105                 sf.type = Util.findText(el);
106             }
107             el = Util.findElement(sourceFolderEl, "location", Util.NAMESPACE); // NOI18N
108
if (el != null) {
109                 sf.location = Util.findText(el);
110             }
111             el = Util.findElement(sourceFolderEl, "includes", Util.NAMESPACE); // NOI18N
112
if (el != null) {
113                 sf.includes = Util.findText(el);
114             }
115             el = Util.findElement(sourceFolderEl, "excludes", Util.NAMESPACE); // NOI18N
116
if (el != null) {
117                 sf.excludes = Util.findText(el);
118             }
119             if (type == null || type.equals(sf.type)) {
120                 if (sf.label == null || sf.label.length() == 0) {
121                     throw new IllegalArgumentException JavaDoc("label element is empty or not specified. "+helper.getProjectDirectory()); // NOI18N
122
}
123                 if (sf.location == null || sf.location.length() == 0) {
124                     throw new IllegalArgumentException JavaDoc("location element is empty or not specified. "+helper.getProjectDirectory()); // NOI18N
125
}
126                 list.add(sf);
127             }
128         }
129         return list;
130     }
131
132     /**
133      * Update source folders of the project. Project is left modified and you
134      * must save it explicitely.
135      * @param helper AntProjectHelper instance
136      * @param sources list of SourceFolder instances
137      * @param type type of source folders to update.
138      * Can be null in which case all types will be overriden.
139      * Useful for overriding just one type of source folders. Source folders
140      * without type are overriden only when type == null.
141      */

142     public static void putSourceFolders(AntProjectHelper helper, List JavaDoc<SourceFolder> sources, String JavaDoc type) {
143         //assert ProjectManager.mutex().isWriteAccess();
144
Element JavaDoc data = Util.getPrimaryConfigurationData(helper);
145         Document JavaDoc doc = data.getOwnerDocument();
146         Element JavaDoc foldersEl = Util.findElement(data, "folders", Util.NAMESPACE); // NOI18N
147
if (foldersEl == null) {
148             foldersEl = doc.createElementNS(Util.NAMESPACE, "folders"); // NOI18N
149
Util.appendChildElement(data, foldersEl, rootElementsOrder);
150         } else {
151             for (Element JavaDoc sourceFolderEl : Util.findSubElements(foldersEl)) {
152                 if (!sourceFolderEl.getLocalName().equals("source-folder")) { // NOI18N
153
continue;
154                 }
155                 if (type == null) {
156                     foldersEl.removeChild(sourceFolderEl);
157                 } else {
158                     Element JavaDoc typeEl = Util.findElement(sourceFolderEl, "type", Util.NAMESPACE); // NOI18N
159
if (typeEl != null) {
160                         String JavaDoc typeElValue = Util.findText(typeEl);
161                         if (type.equals(typeElValue)) {
162                             foldersEl.removeChild(sourceFolderEl);
163                         }
164                     }
165                 }
166             }
167         }
168         for (SourceFolder sf : sources) {
169             Element JavaDoc sourceFolderEl = doc.createElementNS(Util.NAMESPACE, "source-folder"); // NOI18N
170
Element JavaDoc el;
171             if (sf.label != null && sf.label.length() > 0) {
172                 el = doc.createElementNS(Util.NAMESPACE, "label"); // NOI18N
173
el.appendChild(doc.createTextNode(sf.label)); // NOI18N
174
sourceFolderEl.appendChild(el);
175             } else {
176                 throw new IllegalArgumentException JavaDoc("label cannot be empty. "+helper.getProjectDirectory()); // NOI18N
177
}
178             if (sf.type != null) {
179                 el = doc.createElementNS(Util.NAMESPACE, "type"); // NOI18N
180
el.appendChild(doc.createTextNode(sf.type)); // NOI18N
181
sourceFolderEl.appendChild(el);
182             }
183             if (sf.location != null && sf.location.length() > 0) {
184                 el = doc.createElementNS(Util.NAMESPACE, "location"); // NOI18N
185
el.appendChild(doc.createTextNode(sf.location)); // NOI18N
186
sourceFolderEl.appendChild(el);
187             } else {
188                 throw new IllegalArgumentException JavaDoc("location cannot be empty. "+helper.getProjectDirectory()); // NOI18N
189
}
190             if (sf.includes != null) {
191                 el = doc.createElementNS(Util.NAMESPACE, "includes"); // NOI18N
192
el.appendChild(doc.createTextNode(sf.includes)); // NOI18N
193
sourceFolderEl.appendChild(el);
194             }
195             if (sf.excludes != null) {
196                 el = doc.createElementNS(Util.NAMESPACE, "excludes"); // NOI18N
197
el.appendChild(doc.createTextNode(sf.excludes)); // NOI18N
198
sourceFolderEl.appendChild(el);
199             }
200             Util.appendChildElement(foldersEl, sourceFolderEl, folderElementsOrder);
201         }
202         Util.putPrimaryConfigurationData(helper, data);
203     }
204     
205     /**
206      * Read source views from the project. At the moment only source-folder
207      * elements are read and source-file ones are ignored.
208      * @param helper AntProjectHelper instance
209      * @param style style of source folders to be read. Can be null in which case
210      * all styles will be read. Useful for reading one style of source folders.
211      * @return list of SourceFolder instances; type value will be always null
212      */

213     public static List JavaDoc getSourceViews(AntProjectHelper helper, String JavaDoc style) {
214         //assert ProjectManager.mutex().isReadAccess() || ProjectManager.mutex().isWriteAccess();
215
List JavaDoc<SourceFolder> list = new ArrayList JavaDoc<SourceFolder>();
216         Element JavaDoc data = Util.getPrimaryConfigurationData(helper);
217         Element JavaDoc viewEl = Util.findElement(data, "view", Util.NAMESPACE); // NOI18N
218
if (viewEl == null) {
219             return list;
220         }
221         Element JavaDoc itemsEl = Util.findElement(viewEl, "items", Util.NAMESPACE); // NOI18N
222
if (itemsEl == null) {
223             return list;
224         }
225         for (Element JavaDoc sourceFolderEl : Util.findSubElements(itemsEl)) {
226             if (!sourceFolderEl.getLocalName().equals("source-folder")) { // NOI18N
227
continue;
228             }
229             SourceFolder sf = new SourceFolder();
230             sf.style = sourceFolderEl.getAttribute("style"); // NOI18N
231
assert sf.style != null && sf.style.length() > 0 : "Bad style attr on <source-folder> in " + helper; // NOI18N
232
Element JavaDoc el = Util.findElement(sourceFolderEl, "label", Util.NAMESPACE); // NOI18N
233
if (el != null) {
234                 sf.label = Util.findText(el);
235             }
236             el = Util.findElement(sourceFolderEl, "location", Util.NAMESPACE); // NOI18N
237
if (el != null) {
238                 sf.location = Util.findText(el);
239             }
240             el = Util.findElement(sourceFolderEl, "includes", Util.NAMESPACE); // NOI18N
241
if (el != null) {
242                 sf.includes = Util.findText(el);
243             }
244             el = Util.findElement(sourceFolderEl, "excludes", Util.NAMESPACE); // NOI18N
245
if (el != null) {
246                 sf.excludes = Util.findText(el);
247             }
248             if (style == null || style.equals(sf.style)) {
249                 list.add(sf);
250             }
251         }
252         return list;
253     }
254     
255     /**
256      * Update source views of the project.
257      * This method should be called always after the putSourceFolders method
258      * to keep views and folders in sync.
259      * Project is left modified and you must save it explicitely.
260      * @param helper AntProjectHelper instance
261      * @param sources list of SourceFolder instances
262      * @param style style of source views to update.
263      * Can be null in which case all styles will be overriden.
264      * Useful for overriding just one style of source view.
265      */

266     public static void putSourceViews(AntProjectHelper helper, List JavaDoc<SourceFolder> sources, String JavaDoc style) {
267         //assert ProjectManager.mutex().isWriteAccess();
268
ArrayList JavaDoc list = new ArrayList JavaDoc();
269         Element JavaDoc data = Util.getPrimaryConfigurationData(helper);
270         Document JavaDoc doc = data.getOwnerDocument();
271         Element JavaDoc viewEl = Util.findElement(data, "view", Util.NAMESPACE); // NOI18N
272
if (viewEl == null) {
273             viewEl = doc.createElementNS(Util.NAMESPACE, "view"); // NOI18N
274
Util.appendChildElement(data, viewEl, rootElementsOrder);
275         }
276         Element JavaDoc itemsEl = Util.findElement(viewEl, "items", Util.NAMESPACE); // NOI18N
277
if (itemsEl == null) {
278             itemsEl = doc.createElementNS(Util.NAMESPACE, "items"); // NOI18N
279
Util.appendChildElement(viewEl, itemsEl, viewElementsOrder);
280         }
281         List JavaDoc<Element JavaDoc> sourceViews = Util.findSubElements(itemsEl);
282         Iterator JavaDoc it = sourceViews.iterator();
283         while (it.hasNext()) {
284             Element JavaDoc sourceViewEl = (Element JavaDoc)it.next();
285             if (!sourceViewEl.getLocalName().equals("source-folder")) { // NOI18N
286
continue;
287             }
288             String JavaDoc sourceStyle = sourceViewEl.getAttribute("style"); // NOI18N
289
if (style == null || style.equals(sourceStyle)) {
290                 itemsEl.removeChild(sourceViewEl);
291             }
292         }
293         Iterator JavaDoc it2 = sources.iterator();
294         while (it2.hasNext()) {
295             SourceFolder sf = (SourceFolder)it2.next();
296             if (sf.style == null || sf.style.length() == 0) {
297                 // perhaps this is principal source folder?
298
continue;
299             }
300             Element JavaDoc sourceFolderEl = doc.createElementNS(Util.NAMESPACE, "source-folder"); // NOI18N
301
sourceFolderEl.setAttribute("style", sf.style); // NOI18N
302
Element JavaDoc el;
303             if (sf.label != null) {
304                 el = doc.createElementNS(Util.NAMESPACE, "label"); // NOI18N
305
el.appendChild(doc.createTextNode(sf.label)); // NOI18N
306
sourceFolderEl.appendChild(el);
307             }
308             if (sf.location != null) {
309                 el = doc.createElementNS(Util.NAMESPACE, "location"); // NOI18N
310
el.appendChild(doc.createTextNode(sf.location)); // NOI18N
311
sourceFolderEl.appendChild(el);
312             }
313             if (sf.includes != null) {
314                 el = doc.createElementNS(Util.NAMESPACE, "includes"); // NOI18N
315
el.appendChild(doc.createTextNode(sf.includes)); // NOI18N
316
sourceFolderEl.appendChild(el);
317             }
318             if (sf.excludes != null) {
319                 el = doc.createElementNS(Util.NAMESPACE, "excludes"); // NOI18N
320
el.appendChild(doc.createTextNode(sf.excludes)); // NOI18N
321
sourceFolderEl.appendChild(el);
322             }
323             Util.appendChildElement(itemsEl, sourceFolderEl, viewItemElementsOrder);
324         }
325         Util.putPrimaryConfigurationData(helper, data);
326     }
327     
328     
329     /**
330      * Read Java compilation units from the project.
331      * @param helper AntProjectHelper instance
332      * @param aux AuxiliaryConfiguration instance
333      * @return list of JavaCompilationUnit instances; never null;
334      */

335     public static List JavaDoc<JavaCompilationUnit> getJavaCompilationUnits(
336             AntProjectHelper helper, AuxiliaryConfiguration aux) {
337         //assert ProjectManager.mutex().isReadAccess() || ProjectManager.mutex().isWriteAccess();
338
List JavaDoc<JavaCompilationUnit> list = new ArrayList JavaDoc<JavaCompilationUnit>();
339         Element JavaDoc data = aux.getConfigurationFragment(JavaProjectNature.EL_JAVA, JavaProjectNature.NS_JAVA_2, true);
340         if (data == null) {
341             data = aux.getConfigurationFragment(JavaProjectNature.EL_JAVA, JavaProjectNature.NS_JAVA_1, true);
342         }
343         if (data == null) {
344             return list;
345         }
346         for (Element JavaDoc cuEl : Util.findSubElements(data)) {
347             JavaCompilationUnit cu = new JavaCompilationUnit();
348             List JavaDoc<String JavaDoc> outputs = new ArrayList JavaDoc<String JavaDoc>();
349             List JavaDoc<String JavaDoc> javadoc = new ArrayList JavaDoc<String JavaDoc>();
350             List JavaDoc<JavaCompilationUnit.CP> cps = new ArrayList JavaDoc<JavaCompilationUnit.CP>();
351             List JavaDoc<String JavaDoc> packageRoots = new ArrayList JavaDoc<String JavaDoc>();
352             for (Element JavaDoc el : Util.findSubElements(cuEl)) {
353                 if (el.getLocalName().equals("package-root")) { // NOI18N
354
packageRoots.add(Util.findText(el));
355                     continue;
356                 }
357                 if (el.getLocalName().equals("classpath")) { // NOI18N
358
JavaCompilationUnit.CP cp = new JavaCompilationUnit.CP();
359                     cp.classpath = Util.findText(el);
360                     cp.mode = el.getAttribute("mode"); // NOI18N
361
if (cp.mode != null && cp.classpath != null) {
362                         cps.add(cp);
363                     }
364                     continue;
365                 }
366                 if (el.getLocalName().equals("built-to")) { // NOI18N
367
outputs.add(Util.findText(el));
368                     continue;
369                 }
370                 if (el.getLocalName().equals("javadoc-built-to")) { // NOI18N
371
javadoc.add(Util.findText(el));
372                     continue;
373                 }
374                 if (el.getLocalName().equals("source-level")) { // NOI18N
375
cu.sourceLevel = Util.findText(el);
376                 }
377                 if (el.getLocalName().equals("unit-tests")) { // NOI18N
378
cu.isTests = true;
379                 }
380             }
381             cu.output = outputs.size() > 0 ? outputs : null;
382             cu.javadoc = javadoc.size() > 0 ? javadoc : null;
383             cu.classpath = cps.size() > 0 ? cps: null;
384             cu.packageRoots = packageRoots.size() > 0 ? packageRoots: null;
385             list.add(cu);
386         }
387         return list;
388     }
389
390     /**
391      * Update Java compilation units of the project. Project is left modified
392      * and you must save it explicitely.
393      * @param helper AntProjectHelper instance
394      * @param aux AuxiliaryConfiguration instance
395      * @param compUnits list of JavaCompilationUnit instances
396      */

397     public static void putJavaCompilationUnits(AntProjectHelper helper,
398             AuxiliaryConfiguration aux, List JavaDoc<JavaCompilationUnit> compUnits) {
399         //assert ProjectManager.mutex().isWriteAccess();
400
// First check whether we need /2 data.
401
boolean need2 = false;
402         for (JavaCompilationUnit unit : compUnits) {
403             if (unit.isTests || (unit.javadoc != null && !unit.javadoc.isEmpty())) {
404                 need2 = true;
405                 break;
406             }
407         }
408         String JavaDoc namespace;
409         // Look for existing /2 data.
410
Element JavaDoc data = aux.getConfigurationFragment(JavaProjectNature.EL_JAVA, JavaProjectNature.NS_JAVA_2, true);
411         if (data != null) {
412             // Fine, use it as is.
413
namespace = JavaProjectNature.NS_JAVA_2;
414         } else {
415             // Or, for existing /1 data.
416
namespace = need2 ? JavaProjectNature.NS_JAVA_2 : JavaProjectNature.NS_JAVA_1;
417             data = aux.getConfigurationFragment(JavaProjectNature.EL_JAVA, JavaProjectNature.NS_JAVA_1, true);
418             if (data != null) {
419                 if (need2) {
420                     // Have to upgrade.
421
aux.removeConfigurationFragment(JavaProjectNature.EL_JAVA, JavaProjectNature.NS_JAVA_1, true);
422                     data = Util.getPrimaryConfigurationData(helper).getOwnerDocument().
423                         createElementNS(JavaProjectNature.NS_JAVA_2, JavaProjectNature.EL_JAVA);
424                 } // else can use it as is
425
} else {
426                 // Create /1 or /2 data acc. to need.
427
data = Util.getPrimaryConfigurationData(helper).getOwnerDocument().
428                     createElementNS(namespace, JavaProjectNature.EL_JAVA);
429             }
430         }
431         Document JavaDoc doc = data.getOwnerDocument();
432         for (Element JavaDoc cuEl : Util.findSubElements(data)) {
433             data.removeChild(cuEl);
434         }
435         for (JavaCompilationUnit cu : compUnits) {
436             Element JavaDoc cuEl = doc.createElementNS(namespace, "compilation-unit"); // NOI18N
437
data.appendChild(cuEl);
438             Element JavaDoc el;
439             if (cu.packageRoots != null) {
440                 for (String JavaDoc packageRoot : cu.packageRoots) {
441                     el = doc.createElementNS(namespace, "package-root"); // NOI18N
442
el.appendChild(doc.createTextNode(packageRoot));
443                     cuEl.appendChild(el);
444                 }
445             }
446             if (cu.isTests) {
447                 assert namespace.equals(JavaProjectNature.NS_JAVA_2);
448                 cuEl.appendChild(doc.createElementNS(namespace, "unit-tests")); // NOI18N
449
}
450             if (cu.classpath != null) {
451                 for (JavaCompilationUnit.CP cp : cu.classpath) {
452                     el = doc.createElementNS(namespace, "classpath"); // NOI18N
453
el.appendChild(doc.createTextNode(cp.classpath));
454                     el.setAttribute("mode", cp.mode); // NOI18N
455
cuEl.appendChild(el);
456                 }
457             }
458             if (cu.output != null) {
459                 Iterator JavaDoc it3 = cu.output.iterator();
460                 while (it3.hasNext()) {
461                     String JavaDoc output = (String JavaDoc)it3.next();
462                     el = doc.createElementNS(namespace, "built-to"); // NOI18N
463
el.appendChild(doc.createTextNode(output));
464                     cuEl.appendChild(el);
465                 }
466             }
467             if (cu.javadoc != null) {
468                 Iterator JavaDoc it3 = cu.javadoc.iterator();
469                 while (it3.hasNext()) {
470                     String JavaDoc javadoc = (String JavaDoc) it3.next();
471                     assert namespace.equals(JavaProjectNature.NS_JAVA_2);
472                     el = doc.createElementNS(namespace, "javadoc-built-to"); // NOI18N
473
el.appendChild(doc.createTextNode(javadoc));
474                     cuEl.appendChild(el);
475                 }
476             }
477             if (cu.sourceLevel != null) {
478                 el = doc.createElementNS(namespace, "source-level"); // NOI18N
479
el.appendChild(doc.createTextNode(cu.sourceLevel));
480                 cuEl.appendChild(el);
481             }
482         }
483         aux.putConfigurationFragment(data, true);
484     }
485
486     
487     /**
488      * Structure describing compilation unit.
489      * Data in the struct are in the same format as they are stored in XML.
490      */

491     public static final class JavaCompilationUnit {
492         public List JavaDoc<String JavaDoc> packageRoots;
493         public List JavaDoc<CP> classpath;
494         public List JavaDoc<String JavaDoc> output;
495         public List JavaDoc<String JavaDoc> javadoc;
496         public String JavaDoc sourceLevel;
497         public boolean isTests;
498         
499         public String JavaDoc toString() {
500             return "FPG.JCU[packageRoots=" + packageRoots + ", classpath=" + classpath + ", output=" + output + ", javadoc=" + javadoc + ", sourceLevel=" + sourceLevel + ",isTests=" + isTests + "]"; // NOI18N
501
}
502         
503         public static final class CP {
504             public String JavaDoc classpath;
505             public String JavaDoc mode;
506             
507             public String JavaDoc toString() {
508                 return "FPG.JCU.CP:[classpath="+classpath+", mode="+mode+", this="+super.toString()+"]"; // NOI18N
509
}
510             
511         }
512         
513     }
514     
515     /**
516      * Structure describing one export record.
517      * Data in the struct are in the same format as they are stored in XML.
518      */

519     public static final class Export {
520         public String JavaDoc type;
521         public String JavaDoc location;
522         public String JavaDoc script; // optional
523
public String JavaDoc buildTarget;
524         public String JavaDoc cleanTarget; // optional
525
}
526
527     /**
528      * Try to guess project's exports. See issue #49221 for more details.
529      */

530     public static List JavaDoc<Export> guessExports(PropertyEvaluator evaluator, File JavaDoc baseFolder,
531             List JavaDoc<TargetMapping> targetMappings, List JavaDoc<JavaCompilationUnit> javaCompilationUnits) {
532         //assert ProjectManager.mutex().isReadAccess() || ProjectManager.mutex().isWriteAccess();
533
List JavaDoc<Export> exports = new ArrayList JavaDoc<Export>();
534         String JavaDoc targetName = null;
535         String JavaDoc scriptName = null;
536         for (TargetMapping tm : targetMappings) {
537             if (tm.name.equals("build")) { // NOI18N
538
if (tm.targets.size() == 1) {
539                     targetName = tm.targets.get(0);
540                     scriptName = tm.script;
541                 } else {
542                     return new ArrayList JavaDoc<Export>();
543                 }
544             }
545         }
546         if (targetName == null) {
547             return new ArrayList JavaDoc<Export>();
548         }
549         for (JavaCompilationUnit cu : javaCompilationUnits) {
550             if (cu.output != null) {
551                 for (String JavaDoc output : cu.output) {
552                     String JavaDoc output2 = evaluator.evaluate(output);
553                     if (output2.endsWith(".jar")) { // NOI18N
554
Export e = new Export();
555                         e.type = JavaProjectConstants.ARTIFACT_TYPE_JAR;
556                         e.location = output;
557                         e.script = scriptName;
558                         e.buildTarget = targetName;
559                         exports.add(e);
560                     }
561                     else if (isFolder(evaluator, baseFolder, output2)) {
562                         Export e = new Export();
563                         e.type = JavaProjectConstants.ARTIFACT_TYPE_FOLDER;
564                         e.location = output;
565                         e.script = scriptName;
566                         e.buildTarget = targetName;
567                         exports.add(e);
568                     }
569                 }
570             }
571         }
572         return exports;
573     }
574     
575     /**
576      * Update exports of the project.
577      * Project is left modified and you must save it explicitely.
578      * @param helper AntProjectHelper instance
579      * @param exports list of Export instances
580      */

581     public static void putExports(AntProjectHelper helper, List JavaDoc<Export> exports) {
582         //assert ProjectManager.mutex().isWriteAccess();
583
ArrayList JavaDoc list = new ArrayList JavaDoc();
584         Element JavaDoc data = Util.getPrimaryConfigurationData(helper);
585         Document JavaDoc doc = data.getOwnerDocument();
586         Iterator JavaDoc it = Util.findSubElements(data).iterator();
587         while (it.hasNext()) {
588             Element JavaDoc exportEl = (Element JavaDoc)it.next();
589             if (!exportEl.getLocalName().equals("export")) { // NOI18N
590
continue;
591             }
592             data.removeChild(exportEl);
593         }
594         Iterator JavaDoc it2 = exports.iterator();
595         while (it2.hasNext()) {
596             Export export = (Export)it2.next();
597             Element JavaDoc exportEl = doc.createElementNS(Util.NAMESPACE, "export"); // NOI18N
598
Element JavaDoc el;
599             el = doc.createElementNS(Util.NAMESPACE, "type"); // NOI18N
600
el.appendChild(doc.createTextNode(export.type)); // NOI18N
601
exportEl.appendChild(el);
602             el = doc.createElementNS(Util.NAMESPACE, "location"); // NOI18N
603
el.appendChild(doc.createTextNode(export.location)); // NOI18N
604
exportEl.appendChild(el);
605             if (export.script != null) {
606                 el = doc.createElementNS(Util.NAMESPACE, "script"); // NOI18N
607
el.appendChild(doc.createTextNode(export.script)); // NOI18N
608
exportEl.appendChild(el);
609             }
610             el = doc.createElementNS(Util.NAMESPACE, "build-target"); // NOI18N
611
el.appendChild(doc.createTextNode(export.buildTarget)); // NOI18N
612
exportEl.appendChild(el);
613             if (export.cleanTarget != null) {
614                 el = doc.createElementNS(Util.NAMESPACE, "clean-target"); // NOI18N
615
el.appendChild(doc.createTextNode(export.cleanTarget)); // NOI18N
616
exportEl.appendChild(el);
617             }
618             Util.appendChildElement(data, exportEl, rootElementsOrder);
619         }
620         Util.putPrimaryConfigurationData(helper, data);
621     }
622     
623     /**
624      * Try to guess project's subprojects. See issue #49640 for more details.
625      */

626     public static List JavaDoc<String JavaDoc> guessSubprojects(PropertyEvaluator evaluator,
627             List JavaDoc<JavaCompilationUnit> javaCompilationUnits, File JavaDoc projectBase, File JavaDoc freeformBase) {
628         //assert ProjectManager.mutex().isReadAccess() || ProjectManager.mutex().isWriteAccess();
629
Set JavaDoc<String JavaDoc> subprojs = new HashSet JavaDoc<String JavaDoc>();
630         for (JavaCompilationUnit cu : javaCompilationUnits) {
631             if (cu.classpath != null) {
632                 for (JavaCompilationUnit.CP cp : cu.classpath) {
633                     if (!"compile".equals(cp.mode)) { // NOI18N
634
continue;
635                     }
636                     String JavaDoc classpath = evaluator.evaluate(cp.classpath);
637                     if (classpath == null) {
638                         continue;
639                     }
640                     for (String JavaDoc s : PropertyUtils.tokenizePath(classpath)) {
641                         File JavaDoc file = FileUtil.normalizeFile(new File JavaDoc(s));
642                         AntArtifact aa = AntArtifactQuery.findArtifactFromFile(file);
643                         if (aa != null) {
644                             File JavaDoc proj = FileUtil.toFile(aa.getProject().getProjectDirectory());
645                             String JavaDoc p = Util.relativizeLocation(projectBase, freeformBase, proj);
646                             subprojs.add(p);
647                         }
648                     }
649                 }
650             }
651         }
652         return new ArrayList JavaDoc<String JavaDoc>(subprojs);
653     }
654     
655     /**
656      * Update subprojects of the project.
657      * Project is left modified and you must save it explicitely.
658      * @param helper AntProjectHelper instance
659      * @param subprojects list of paths to subprojects
660      */

661     public static void putSubprojects(AntProjectHelper helper, List JavaDoc<String JavaDoc> subprojects) {
662         //assert ProjectManager.mutex().isWriteAccess();
663
ArrayList JavaDoc list = new ArrayList JavaDoc();
664         Element JavaDoc data = Util.getPrimaryConfigurationData(helper);
665         Document JavaDoc doc = data.getOwnerDocument();
666         Element JavaDoc subproject = Util.findElement(data, "subprojects", Util.NAMESPACE); // NOI18N
667
if (subproject != null) {
668             data.removeChild(subproject);
669         }
670         subproject = doc.createElementNS(Util.NAMESPACE, "subprojects"); // NOI18N
671
Util.appendChildElement(data, subproject, rootElementsOrder);
672         
673         Iterator JavaDoc it = subprojects.iterator();
674         while (it.hasNext()) {
675             String JavaDoc proj = (String JavaDoc)it.next();
676             Element JavaDoc projEl = doc.createElementNS(Util.NAMESPACE, "project"); // NOI18N
677
projEl.appendChild(doc.createTextNode(proj));
678             subproject.appendChild(projEl);
679         }
680         Util.putPrimaryConfigurationData(helper, data);
681     }
682     
683     /**
684      * Try to guess project's build folders. See issue #50934 for more details.
685      */

686     public static List JavaDoc<String JavaDoc> guessBuildFolders(PropertyEvaluator evaluator,
687             List JavaDoc<JavaCompilationUnit> javaCompilationUnits, File JavaDoc projectBase, File JavaDoc freeformBase) {
688         //assert ProjectManager.mutex().isReadAccess() || ProjectManager.mutex().isWriteAccess();
689
List JavaDoc<String JavaDoc> buildFolders = new ArrayList JavaDoc<String JavaDoc>();
690         for (JavaCompilationUnit cu : javaCompilationUnits) {
691             if (cu.output != null) {
692                 for (String JavaDoc output : cu.output) {
693                     File JavaDoc f = Util.resolveFile(evaluator, freeformBase, output);
694                     if (f.exists()) {
695                         if (f.isFile()) {
696                             f = f.getParentFile();
697                         }
698                     } else {
699                         // guess: if name contains dot then it is probably file
700
if (f.getName().indexOf('.') != -1) {
701                             f = f.getParentFile();
702                         }
703                     }
704                     output = f.getAbsolutePath();
705                     if (!output.endsWith(File.separator)) {
706                         output += File.separatorChar;
707                     }
708
709                     if (output.startsWith(projectBase.getAbsolutePath()+File.separatorChar) ||
710                         output.startsWith(freeformBase.getAbsolutePath()+File.separatorChar)) {
711                         // ignore output which lies below project base or freeform base
712
continue;
713                     }
714                     boolean add = true;
715                     Iterator JavaDoc<String JavaDoc> it = buildFolders.iterator();
716                     while (it.hasNext()) {
717                         String JavaDoc path = it.next();
718                         if (!path.endsWith(File.separator)) {
719                             path += File.separatorChar;
720                         }
721                         if (path.equals(output)) {
722                             // such a path is already there
723
add = false;
724                             break;
725                         } else if (output.startsWith(path)) {
726                             // such a patch is already there
727
add = false;
728                             break;
729                         } else if (path.startsWith(output)) {
730                             it.remove();
731                         }
732                     }
733                     if (add) {
734                         buildFolders.add(f.getAbsolutePath());
735                     }
736                 }
737             }
738         }
739         return buildFolders;
740     }
741     
742     /**
743      * Update build folders of the project.
744      * Project is left modified and you must save it explicitely.
745      * @param helper AntProjectHelper instance
746      * @param buildFolders list of build folder locations
747      */

748     public static void putBuildFolders(AntProjectHelper helper, List JavaDoc<String JavaDoc> buildFolders) {
749         //assert ProjectManager.mutex().isWriteAccess();
750
ArrayList JavaDoc list = new ArrayList JavaDoc();
751         Element JavaDoc data = Util.getPrimaryConfigurationData(helper);
752         Document JavaDoc doc = data.getOwnerDocument();
753         Element JavaDoc foldersEl = Util.findElement(data, "folders", Util.NAMESPACE); // NOI18N
754
if (foldersEl == null) {
755             foldersEl = doc.createElementNS(Util.NAMESPACE, "folders"); // NOI18N
756
Util.appendChildElement(data, foldersEl, rootElementsOrder);
757         } else {
758             List JavaDoc<Element JavaDoc> folders = Util.findSubElements(foldersEl);
759             Iterator JavaDoc it = folders.iterator();
760             while (it.hasNext()) {
761                 Element JavaDoc buildFolderEl = (Element JavaDoc)it.next();
762                 if (!buildFolderEl.getLocalName().equals("build-folder")) { // NOI18N
763
continue;
764                 }
765                 foldersEl.removeChild(buildFolderEl);
766             }
767         }
768         Iterator JavaDoc it = buildFolders.iterator();
769         while (it.hasNext()) {
770             String JavaDoc location = (String JavaDoc)it.next();
771             Element JavaDoc buildFolderEl = doc.createElementNS(Util.NAMESPACE, "build-folder"); // NOI18N
772
Element JavaDoc locationEl = doc.createElementNS(Util.NAMESPACE, "location"); // NOI18N
773
locationEl.appendChild(doc.createTextNode(location));
774             buildFolderEl.appendChild(locationEl);
775             Util.appendChildElement(foldersEl, buildFolderEl, folderElementsOrder);
776         }
777         Util.putPrimaryConfigurationData(helper, data);
778     }
779
780     // XXX: copy&pasted from FreeformProjectGenerator
781
/**
782      * Read target mappings from project.
783      * @param helper AntProjectHelper instance
784      * @return list of TargetMapping instances
785      */

786     public static List JavaDoc<TargetMapping> getTargetMappings(AntProjectHelper helper) {
787         //assert ProjectManager.mutex().isReadAccess() || ProjectManager.mutex().isWriteAccess();
788
List JavaDoc<TargetMapping> list = new ArrayList JavaDoc<TargetMapping>();
789         Element JavaDoc genldata = Util.getPrimaryConfigurationData(helper);
790         Element JavaDoc actionsEl = Util.findElement(genldata, "ide-actions", Util.NAMESPACE); // NOI18N
791
if (actionsEl == null) {
792             return list;
793         }
794         for (Element JavaDoc actionEl : Util.findSubElements(actionsEl)) {
795             TargetMapping tm = new TargetMapping();
796             tm.name = actionEl.getAttribute("name"); // NOI18N
797
List JavaDoc<String JavaDoc> targetNames = new ArrayList JavaDoc<String JavaDoc>();
798             EditableProperties props = new EditableProperties(false);
799             for (Element JavaDoc subEl : Util.findSubElements(actionEl)) {
800                 if (subEl.getLocalName().equals("target")) { // NOI18N
801
targetNames.add(Util.findText(subEl));
802                     continue;
803                 }
804                 if (subEl.getLocalName().equals("script")) { // NOI18N
805
tm.script = Util.findText(subEl);
806                     continue;
807                 }
808                 if (subEl.getLocalName().equals("context")) { // NOI18N
809
TargetMapping.Context ctx = new TargetMapping.Context();
810                     for (Element JavaDoc contextSubEl : Util.findSubElements(subEl)) {
811                         if (contextSubEl.getLocalName().equals("property")) { // NOI18N
812
ctx.property = Util.findText(contextSubEl);
813                             continue;
814                         }
815                         if (contextSubEl.getLocalName().equals("format")) { // NOI18N
816
ctx.format = Util.findText(contextSubEl);
817                             continue;
818                         }
819                         if (contextSubEl.getLocalName().equals("folder")) { // NOI18N
820
ctx.folder = Util.findText(contextSubEl);
821                             continue;
822                         }
823                         if (contextSubEl.getLocalName().equals("pattern")) { // NOI18N
824
ctx.pattern = Util.findText(contextSubEl);
825                             continue;
826                         }
827                         if (contextSubEl.getLocalName().equals("arity")) { // NOI18N
828
Element JavaDoc sepFilesEl = Util.findElement(contextSubEl, "separated-files", Util.NAMESPACE); // NOI18N
829
if (sepFilesEl != null) {
830                                 ctx.separator = Util.findText(sepFilesEl);
831                             }
832                             continue;
833                         }
834                     }
835                     tm.context = ctx;
836                 }
837                 if (subEl.getLocalName().equals("property")) { // NOI18N
838
readProperty(subEl, props);
839                     continue;
840                 }
841             }
842             tm.targets = targetNames;
843             if (props.keySet().size() > 0) {
844                 tm.properties = props;
845             }
846             list.add(tm);
847         }
848         return list;
849     }
850     
851     
852     /*package private*/ static boolean isFolder (PropertyEvaluator eval, File JavaDoc baseFolder, String JavaDoc folder) {
853         File JavaDoc f = Util.resolveFile(eval, baseFolder, folder);
854         if (f != null && f.isDirectory()) {
855             return true;
856         }
857         int dotIndex = folder.lastIndexOf('.'); //NOI18N
858
int slashIndex = folder.lastIndexOf('/'); //NOI18N
859
return dotIndex == -1 || (dotIndex < slashIndex) ;
860     }
861     
862     /**
863      * Structure describing target mapping.
864      * Data in the struct are in the same format as they are stored in XML.
865      */

866     public static final class TargetMapping {
867         public String JavaDoc script;
868         public List JavaDoc<String JavaDoc> targets;
869         public String JavaDoc name;
870         public EditableProperties properties;
871         public Context context; // may be null
872

873         public static final class Context {
874             public String JavaDoc property;
875             public String JavaDoc format;
876             public String JavaDoc folder;
877             public String JavaDoc pattern; // may be null
878
public String JavaDoc separator; // may be null
879
}
880     }
881     
882     private static void readProperty(Element JavaDoc propertyElement, EditableProperties props) {
883         String JavaDoc key = propertyElement.getAttribute("name"); // NOI18N
884
String JavaDoc value = Util.findText(propertyElement);
885         props.setProperty(key, value);
886     }
887
888 }
889
Popular Tags