KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > spoon > AbstractLauncher


1 package spoon;
2
3 import java.io.File JavaDoc;
4 import java.io.FileNotFoundException JavaDoc;
5 import java.io.IOException JavaDoc;
6 import java.lang.reflect.InvocationTargetException JavaDoc;
7 import java.lang.reflect.Method JavaDoc;
8 import java.util.ArrayList JavaDoc;
9 import java.util.List JavaDoc;
10
11 import org.xml.sax.InputSource JavaDoc;
12 import org.xml.sax.SAXException JavaDoc;
13 import org.xml.sax.XMLReader JavaDoc;
14 import org.xml.sax.helpers.XMLReaderFactory JavaDoc;
15
16 import spoon.processing.Builder;
17 import spoon.processing.BuildingException;
18 import spoon.processing.ProcessingManager;
19 import spoon.processing.Severity;
20 import spoon.reflect.Factory;
21 import spoon.support.DefaultCoreFactory;
22 import spoon.support.JavaOutputProcessor;
23 import spoon.support.QueueProcessingManager;
24 import spoon.support.StandardEnvironment;
25 import spoon.support.builder.CtFile;
26 import spoon.support.builder.CtFolder;
27 import spoon.support.builder.CtResource;
28 import spoon.support.builder.FileFactory;
29 import spoon.support.builder.SpoonBuildingManager;
30 import spoon.support.builder.support.CtFolderZip;
31 import spoon.support.processing.SpoonletXmlHandler;
32
33 import com.martiansoftware.jsap.FlaggedOption;
34 import com.martiansoftware.jsap.JSAP;
35 import com.martiansoftware.jsap.JSAPException;
36 import com.martiansoftware.jsap.JSAPResult;
37 import com.martiansoftware.jsap.Switch;
38 import com.martiansoftware.jsap.UnflaggedOption;
39 import com.martiansoftware.jsap.stringparsers.FileStringParser;
40
41 /**
42  * This abstract class defines the common tasks and options for launching a
43  * program processing. To be subclassed for concrete launchers.
44  */

45 public abstract class AbstractLauncher implements Runnable JavaDoc {
46
47     private String JavaDoc[] args = new String JavaDoc[0];
48
49     private JSAPResult arguments;
50
51     private Factory JavaDoc factory;
52
53     private List JavaDoc<CtResource> inputResources = new ArrayList JavaDoc<CtResource>();
54
55     /**
56      * Contains the arguments accepted by this launcher (available after
57      * construction and accessible by sub-classes).
58      */

59     protected JSAP jsapArgs;
60
61     private List JavaDoc<String JavaDoc> processors = new ArrayList JavaDoc<String JavaDoc>();
62
63     private List JavaDoc<CtResource> templateResources = new ArrayList JavaDoc<CtResource>();
64
65     /**
66      * Constructor with no arguments.
67      */

68     protected AbstractLauncher() throws JSAPException {
69         jsapArgs = defineArgs();
70     }
71
72     /**
73      * Default constructor takes the command-line arguments.
74      */

75     protected AbstractLauncher(String JavaDoc[] args) throws JSAPException {
76         this();
77         this.args = args;
78     }
79
80     /**
81      * Adds an input resource to be processed by Spoon.
82      */

83     public void addInputResource(CtResource resource) {
84         inputResources.add(resource);
85     }
86
87     /**
88      * Adds a processor.
89      */

90     public void addProcessor(String JavaDoc name) {
91         processors.add(name);
92     }
93
94     /**
95      * Adds a resource that contains a template (usually a source File).
96      */

97     public void addTemplateResource(CtResource resource) {
98         templateResources.add(resource);
99     }
100
101     /**
102      * Do the model building.
103      */

104     protected void build() {
105         getFactory().getEnvironment().debugMessage("Building model");
106
107         // building
108
Builder builder = new SpoonBuildingManager();
109
110         try {
111             for (CtResource f : getInputSources()) {
112                 builder.addInputSource(f);
113             }
114             for (CtResource f : getTemplateSources()) {
115                 builder.addTemplateSource(f);
116             }
117         } catch (IOException JavaDoc e) {
118             getFactory().getEnvironment().report(null, Severity.ERROR,
119                     "Error while loading resource : " + e.getMessage());
120             if (getFactory().getEnvironment().isDebug())
121                 e.printStackTrace();
122         }
123         try {
124             builder.build(getFactory());
125         } catch (BuildingException e) {
126             getFactory().getEnvironment().report(null, Severity.ERROR,
127                     "Error while loading resource : " + e.getMessage());
128             if (getFactory().getEnvironment().isDebug())
129                 e.printStackTrace();
130         }
131     }
132
133     /**
134      * Creates the factory and associated environment for constructing the
135      * model, initialized with the launcher's arguments.
136      */

137     protected Factory JavaDoc createFactory() {
138         // Create programm spoon Model
139
StandardEnvironment env = new StandardEnvironment();
140         env.setComplianceLevel(getArguments().getInt("compliance"));
141         env.setVerbose(true);
142         env.setXmlRootFolder(getArguments().getFile("properties"));
143
144         // environment initialization
145
JavaOutputProcessor printer = new JavaOutputProcessor(getArguments()
146                 .getFile("output"));
147         env.setDefaultFileGenerator(printer);
148
149         env.setVerbose(getArguments().getBoolean("verbose")
150                 || getArguments().getBoolean("debug"));
151         env.setDebug(getArguments().getBoolean("debug"));
152
153         Factory JavaDoc factory = new Factory JavaDoc(new DefaultCoreFactory(), env);
154
155         return factory;
156     }
157
158     /**
159      * Defines the common arguments for sub-launchers.
160      *
161      * @return the JSAP arguments
162      * @throws JSAPException
163      * when the creation fails
164      */

165     protected JSAP defineArgs() throws JSAPException {
166         // Verbose output
167
JSAP jsap = new JSAP();
168
169         // help
170
Switch sw1 = new Switch("help");
171         sw1.setShortFlag('h');
172         sw1.setLongFlag("help");
173         sw1.setDefault("false");
174         jsap.registerParameter(sw1);
175
176         // Verbose
177
sw1 = new Switch("verbose");
178         sw1.setShortFlag('v');
179         sw1.setLongFlag("verbose");
180         sw1.setDefault("false");
181         sw1.setHelp("Output messages about what the compiler is doing");
182         jsap.registerParameter(sw1);
183
184         // Super Verbose
185
sw1 = new Switch("debug");
186         sw1.setLongFlag("vvv");
187         sw1.setDefault("false");
188         sw1.setHelp("Generate all debugging info");
189         jsap.registerParameter(sw1);
190
191         // java compliance
192
FlaggedOption opt2 = new FlaggedOption("compliance");
193         opt2.setLongFlag("compliance");
194         opt2.setHelp("set java compliance level (1,2,3,4,5 or 6)");
195         opt2.setStringParser(JSAP.INTEGER_PARSER);
196         opt2.setDefault("5");
197         jsap.registerParameter(opt2);
198
199         // setting Input files & Directory
200
opt2 = new FlaggedOption("spoonlet");
201         opt2.setShortFlag('s');
202         opt2.setLongFlag("spoonlet");
203         opt2.setStringParser(JSAP.STRING_PARSER);
204         opt2.setRequired(false);
205         opt2.setHelp("List of spoonlet files to load");
206         jsap.registerParameter(opt2);
207
208         // setting Input files & Directory
209
opt2 = new FlaggedOption("input");
210         opt2.setShortFlag('i');
211         opt2.setLongFlag("input");
212         opt2.setStringParser(JSAP.STRING_PARSER);
213         opt2.setRequired(false);
214         opt2.setHelp("List of path to sources files");
215         jsap.registerParameter(opt2);
216
217         // Processor qualified name
218
opt2 = new FlaggedOption("processors");
219         opt2.setShortFlag('p');
220         opt2.setLongFlag("processors");
221         opt2.setHelp("List of processor's qualified name to be used");
222         opt2.setStringParser(JSAP.STRING_PARSER);
223         opt2.setRequired(false);
224         jsap.registerParameter(opt2);
225
226         // setting input template
227
opt2 = new FlaggedOption("template");
228         opt2.setShortFlag('t');
229         opt2.setLongFlag("template");
230         opt2.setHelp("list of source templates");
231         opt2.setStringParser(JSAP.STRING_PARSER);
232         opt2.setRequired(false);
233         opt2.setHelp("list of path to templates java files");
234         jsap.registerParameter(opt2);
235
236         // Spooned output directory
237
opt2 = new FlaggedOption("output");
238         opt2.setShortFlag('o');
239         opt2.setLongFlag("output");
240         opt2.setDefault("spooned");
241         opt2.setHelp("specify where to place generated java files");
242         opt2.setStringParser(FileStringParser.getParser());
243         opt2.setRequired(false);
244         jsap.registerParameter(opt2);
245
246         // Location of properties files
247
opt2 = new FlaggedOption("properties");
248         opt2.setLongFlag("properties");
249         opt2.setStringParser(FileStringParser.getParser());
250         opt2.setRequired(false);
251         opt2.setHelp("Directory to search for spoon properties files");
252         jsap.registerParameter(opt2);
253
254         // class to be run
255
UnflaggedOption opt3 = new UnflaggedOption("class");
256         opt3.setStringParser(JSAP.STRING_PARSER);
257         opt3.setRequired(false);
258         opt3.setHelp("class to launch within the Spoon context (Main class)");
259         jsap.registerParameter(opt3);
260
261         opt3 = new UnflaggedOption("arguments");
262         opt3.setStringParser(JSAP.STRING_PARSER);
263         opt3.setRequired(false);
264         opt3.setGreedy(true);
265         opt3.setHelp("parameters to be passed to the main method");
266         jsap.registerParameter(opt3);
267
268         return jsap;
269     }
270
271     /**
272      * Returns the command-line given launching arguments in JSAP format.
273      */

274     protected final JSAPResult getArguments() {
275         if (arguments == null) {
276             try {
277                 arguments = parseArgs(args);
278             } catch (JSAPException e) {
279                 throw new RuntimeException JavaDoc(e);
280             }
281         }
282         return arguments;
283     }
284
285     /**
286      * Gets the factory which contains the built model.
287      */

288     public final Factory JavaDoc getFactory() {
289         if (factory == null) {
290             factory = createFactory();
291         }
292         return factory;
293     }
294
295     /**
296      * Processes the arguments.
297      */

298     protected void processArguments() {
299
300         if (getArguments().getString("input") != null) {
301             for (String JavaDoc s : getArguments().getString("input").split(
302                     "[" + File.pathSeparatorChar + "]")) {
303                 try {
304                     inputResources.add(FileFactory.createResource(new File JavaDoc(s)));
305                 } catch (FileNotFoundException JavaDoc e) {
306                     getFactory().getEnvironment().report(null, Severity.ERROR,
307                             "Unable to add source file : " + e.getMessage());
308                     if (getFactory().getEnvironment().isDebug())
309                         e.printStackTrace();
310                 }
311             }
312         }
313
314         if (getArguments().getString("spoonlet") != null) {
315             for (String JavaDoc s : getArguments().getString("spoonlet").split(
316                     "[" + File.pathSeparatorChar + "]")) {
317                 loadSpoonlet(new File JavaDoc(s));
318             }
319         }
320
321         // Adding template from command-line
322
if (getArguments().getString("template") != null) {
323             for (String JavaDoc s : getArguments().getString("template").split(
324                     "[" + File.pathSeparatorChar + "]")) {
325                 try {
326                     addTemplateResource(FileFactory.createResource(new File JavaDoc(s)));
327                 } catch (FileNotFoundException JavaDoc e) {
328                     getFactory().getEnvironment().report(null, Severity.ERROR,
329                             "Unable to add template file : " + e.getMessage());
330                     if (getFactory().getEnvironment().isDebug())
331                         e.printStackTrace();
332                 }
333             }
334         }
335
336         if (getArguments().getString("processors") != null) {
337             for (String JavaDoc processorName : getArguments().getString("processors")
338                     .split(File.pathSeparator)) {
339                 addProcessor(processorName);
340             }
341         }
342     }
343
344     /**
345      * Gets the list of input sources as files. This method can be overloaded to
346      * customize this list.
347      */

348     protected java.util.List JavaDoc<CtResource> getInputSources() {
349         return inputResources;
350     }
351
352     /**
353      * Gets the list of processor types to be initially applied during the
354      * processing (-p option).
355      */

356     protected java.util.List JavaDoc<String JavaDoc> getProcessorTypes() {
357         return processors;
358     }
359
360     /**
361      * Gets the list of template sources as files.
362      */

363     protected List JavaDoc<CtResource> getTemplateSources() {
364         return templateResources;
365     }
366
367     /**
368      * Load content of spoonlet file (template and processor list).
369      */

370     protected void loadSpoonlet(File JavaDoc spoonletFile) {
371         CtFolder folder;
372         try {
373             folder = new CtFolderZip(spoonletFile);
374         } catch (IOException JavaDoc e) {
375             getFactory().getEnvironment().report(null, Severity.ERROR,
376                     "Unable to load spoonlet : " + e.getMessage());
377             if (getFactory().getEnvironment().isDebug())
378                 e.printStackTrace();
379             return;
380         }
381         List JavaDoc<CtResource> spoonletIndex = new ArrayList JavaDoc<CtResource>();
382         CtFile configFile = null;
383         for (CtFile file : folder.getAllFile()) {
384             if (file.isJava())
385                 spoonletIndex.add(file);
386             else if (file.getName().endsWith("spoon.xml")) {
387                 // Loading spoonlet properties
388
configFile = file;
389             }
390         }
391
392         if (configFile == null) {
393             getFactory().getEnvironment().report(
394                     null,
395                     Severity.ERROR,
396                     "No configuration file in spoonlet "
397                             + spoonletFile.getName());
398         } else {
399             try {
400                 XMLReader JavaDoc xr = XMLReaderFactory.createXMLReader();
401                 SpoonletXmlHandler loader = new SpoonletXmlHandler(this,
402                         spoonletIndex);
403                 xr.setContentHandler(loader);
404                 xr.parse(new InputSource JavaDoc(configFile.getContent()));
405             } catch (SAXException JavaDoc e) {
406                 e.printStackTrace();
407             } catch (IOException JavaDoc e) {
408                 e.printStackTrace();
409             }
410         }
411
412     }
413
414     /**
415      * Parses the arguments given by the command line.
416      *
417      * @param args
418      * the command-line arguments as a string array
419      * @return the JSAP-presented arguments
420      * @throws JSAPException
421      * when an error occurs in the argument parsing
422      */

423     protected JSAPResult parseArgs(String JavaDoc[] args) throws JSAPException {
424         JSAPResult arguments = jsapArgs.parse(args);
425         if (!arguments.success()) {
426             // print out specific error messages describing the problems
427
for (java.util.Iterator JavaDoc errs = arguments.getErrorMessageIterator(); errs
428                     .hasNext();) {
429                 System.err.println("Error: " + errs.next());
430             }
431         }
432         if (!arguments.success() || arguments.getBoolean("help")) {
433             System.err.println();
434             System.err.println("Usage: java <launcher name> [option(s)]");
435             System.err.println();
436             System.err.println("Options : ");
437             System.err.println();
438             System.err.println(jsapArgs.getHelp());
439             System.exit(-1);
440         }
441
442         return arguments;
443     }
444
445     /**
446      * Prints out the built model into files.
447      */

448     protected void print() {
449         if (getFactory().getEnvironment().getDefaultFileGenerator() != null) {
450             getFactory().getEnvironment().debugMessage("Start printing");
451             ProcessingManager processing = new QueueProcessingManager(
452                     getFactory());
453             processing.addProcessor(getFactory().getEnvironment()
454                     .getDefaultFileGenerator());
455             processing.process();
456         }
457     }
458
459     /**
460      * Processes the built model with the processors.
461      */

462     protected void process() {
463         getFactory().getEnvironment().debugMessage("process model");
464         // processing (consume all the processors)
465
ProcessingManager processing = new QueueProcessingManager(getFactory());
466         for (String JavaDoc processorName : getProcessorTypes()) {
467             getFactory().getEnvironment().debugMessage(
468                     "loading processor " + processorName);
469             processing.addProcessor(processorName);
470         }
471
472         processing.process();
473     }
474
475     /**
476      * Starts the Spoon processing.
477      */

478     public void run() {
479
480         getFactory().getEnvironment().debugMessage(
481                 "loading command-line arguments");
482         processArguments();
483
484         getFactory().getEnvironment().debugMessage("Start Processing");
485
486         build();
487         process();
488         print();
489
490         getFactory().getEnvironment().debugMessage("Processing Done");
491         getFactory().getEnvironment().reportEnd();
492
493         // Gets main class
494
String JavaDoc progClass = getArguments().getString("class");
495         String JavaDoc progArgs[] = getArguments().getStringArray("arguments");
496
497         if (progClass != null) {
498             try {
499                 // Launch main class using reflection
500
getFactory().getEnvironment().debugMessage(
501                         "Running class : " + progClass);
502                 Class JavaDoc clas = getClass().getClassLoader().loadClass(progClass);
503                 Class JavaDoc mainArgType[] = { (new String JavaDoc[0]).getClass() };
504                 Method JavaDoc main = clas.getMethod("main", mainArgType);
505                 Object JavaDoc argsArray[] = { progArgs };
506                 main.invoke(null, argsArray);
507
508             } catch (ClassNotFoundException JavaDoc e) {
509                 getFactory().getEnvironment().report(null, Severity.ERROR,
510                         "Class not found : " + e.getMessage());
511                 if (getFactory().getEnvironment().isDebug())
512                     e.printStackTrace();
513             } catch (NoSuchMethodException JavaDoc e) {
514                 getFactory().getEnvironment().report(null, Severity.ERROR,
515                         "No such method : " + e.getMessage());
516                 if (getFactory().getEnvironment().isDebug())
517                     e.printStackTrace();
518             } catch (SecurityException JavaDoc e) {
519                 e.printStackTrace();
520             } catch (IllegalArgumentException JavaDoc e) {
521                 e.printStackTrace();
522             } catch (IllegalAccessException JavaDoc e) {
523                 e.printStackTrace();
524             } catch (InvocationTargetException JavaDoc e) {
525                 e.printStackTrace();
526             }
527
528         }
529
530     }
531 }
532
Popular Tags