KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > com > mchange > v2 > debug > DebugGen


1 /*
2  * Distributed as part of debuggen v.0.1.0
3  *
4  * Copyright (C) 2005 Machinery For Change, Inc.
5  *
6  * Author: Steve Waldman <swaldman@mchange.com>
7  *
8  * This library is free software; you can redistribute it and/or modify
9  * it under the terms of the GNU Lesser General Public License version 2.1, as
10  * published by the Free Software Foundation.
11  *
12  * This software is distributed in the hope that it will be useful,
13  * but WITHOUT ANY WARRANTY; without even the implied warranty of
14  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15  * GNU Lesser General Public License for more details.
16  *
17  * You should have received a copy of the GNU Lesser General Public License
18  * along with this software; see the file LICENSE. If not, write to the
19  * Free Software Foundation, Inc., 59 Temple Place, Suite 330,
20  * Boston, MA 02111-1307, USA.
21  */

22
23
24 package com.mchange.v2.debug;
25
26 import java.io.*;
27 import java.util.*;
28 import com.mchange.v2.cmdline.*;
29 import com.mchange.v2.io.FileIterator;
30 import com.mchange.v2.io.DirectoryDescentUtils;
31 import com.mchange.v1.io.WriterUtils;
32 import com.mchange.v1.lang.BooleanUtils;
33 import com.mchange.v1.util.SetUtils;
34 import com.mchange.v1.util.StringTokenizerUtils;
35
36 public final class DebugGen implements DebugConstants
37 {
38     final static String JavaDoc[] VALID = new String JavaDoc[]
39     {
40     "codebase",
41     "packages" ,
42     "trace",
43     "debug",
44     "recursive",
45     "javac",
46     "noclobber",
47     "classname",
48     "skipdirs",
49     "outputbase"
50     };
51
52     final static String JavaDoc[] REQUIRED = new String JavaDoc[]
53     { "codebase", "packages" , "trace", "debug" };
54
55     final static String JavaDoc[] ARGS = new String JavaDoc[]
56     { "codebase", "packages" , "trace", "debug", "classname", "outputbase" };
57
58     final static String JavaDoc EOL;
59
60     static
61     {
62     EOL = System.getProperty("line.separator");
63     }
64
65     static int trace_level;
66     static boolean debug;
67     static boolean recursive;
68     static String JavaDoc classname;
69     static boolean clobber;
70     static Set skipDirs;
71     
72     public synchronized static final void main(String JavaDoc[] argv)
73     {
74     String JavaDoc codebase;
75     String JavaDoc outputbase;
76     File[] srcPkgDirs;
77
78     try
79         {
80         ParsedCommandLine pcl = CommandLineUtils.parse( argv, "--", VALID, REQUIRED, ARGS);
81
82         //get and normalize the codebase
83
codebase = pcl.getSwitchArg("codebase");
84         codebase = platify( codebase );
85         if (! codebase.endsWith(File.separator))
86             codebase += File.separator;
87
88         //get and normalize the outputbase
89
outputbase = pcl.getSwitchArg("outputbase");
90         if ( outputbase != null )
91             {
92             outputbase = platify( outputbase );
93             if (! outputbase.endsWith(File.separator))
94                 outputbase += File.separator;
95             }
96         else
97             outputbase = codebase;
98
99         File outputBaseDir = new File( outputbase );
100         //System.err.println("outputBaseDir: " + outputBaseDir + "; exists? " + outputBaseDir.exists());
101
if (outputBaseDir.exists())
102             {
103             if (!outputBaseDir.isDirectory())
104                 {
105                 //System.err.println("Output Base '" + outputBaseDir.getPath() + "' is not a directory!");
106
System.exit(-1);
107                 }
108             else if (!outputBaseDir.canWrite())
109                 {
110                 System.err.println("Output Base '" + outputBaseDir.getPath() + "' is not writable!");
111                 System.exit(-1);
112                 }
113             }
114         else if (! outputBaseDir.mkdirs() )
115             {
116             System.err.println("Output Base directory '" + outputBaseDir.getPath() + "' does not exist, and could not be created!");
117             System.exit(-1);
118             }
119
120         //find existing package dirs
121
String JavaDoc[] packages = StringTokenizerUtils.tokenizeToArray(pcl.getSwitchArg("packages"),", \t");
122         srcPkgDirs = new File[ packages.length ];
123         for(int i = 0, len = packages.length; i < len; ++i)
124             srcPkgDirs[i] = new File(codebase + sepify(packages[i]));
125         
126         //find trace level
127
trace_level = Integer.parseInt( pcl.getSwitchArg("trace") );
128
129         //find debug
130
debug = BooleanUtils.parseBoolean( pcl.getSwitchArg("debug") );
131
132         //find classname, or use default
133
classname = pcl.getSwitchArg("classname");
134         if (classname == null)
135             classname = "Debug";
136
137         //find recursive
138
recursive = pcl.includesSwitch("recursive");
139
140         //find clobber
141
clobber = !pcl.includesSwitch("noclobber");
142
143         //find skipDirs
144
String JavaDoc skipdirStr = pcl.getSwitchArg("skipdirs");
145         if (skipdirStr != null)
146             {
147             String JavaDoc[] skipdirArray = StringTokenizerUtils.tokenizeToArray(skipdirStr, ", \t");
148             skipDirs = SetUtils.setFromArray( skipdirArray );
149             }
150         else
151             {
152             skipDirs = new HashSet();
153             skipDirs.add("CVS");
154             }
155
156         if ( pcl.includesSwitch("javac") )
157             System.err.println("autorecompilation of packages not yet implemented.");
158
159         for (int i = 0, len = srcPkgDirs.length; i < len; ++i)
160             {
161             if (recursive)
162                 {
163                 if (! recursivePrecheckPackages( codebase, srcPkgDirs[i], outputbase, outputBaseDir ))
164                     {
165                     System.err.println("One or more of the specifies packages" +
166                                " could not be processed. Aborting." +
167                                " No files have been modified.");
168                     System.exit(-1);
169                     }
170                 }
171             else
172                 {
173                 if (! precheckPackage( codebase, srcPkgDirs[i], outputbase, outputBaseDir ))
174                     {
175                     System.err.println("One or more of the specifies packages" +
176                                " could not be processed. Aborting." +
177                                " No files have been modified.");
178                     System.exit(-1);
179                     }
180                 }
181             }
182
183         for (int i = 0, len = srcPkgDirs.length; i < len; ++i)
184             {
185             if (recursive)
186                 recursiveWriteDebugFiles( codebase, srcPkgDirs[i], outputbase, outputBaseDir );
187             else
188                 writeDebugFile( outputbase, srcPkgDirs[i] );
189             }
190         }
191     catch (Exception JavaDoc e)
192         {
193         e.printStackTrace();
194         System.err.println();
195         usage();
196         }
197     }
198
199     private static void usage()
200     {
201     System.err.println("java " + DebugGen.class.getName() + " \\");
202     System.err.println("\t--codebase=<directory under which packages live> \\ (no default)");
203     System.err.println("\t--packages=<comma separated list of packages> \\ (no default)");
204     System.err.println("\t--debug=<true|false> \\ (no default)");
205     System.err.println("\t--trace=<an int between 0 and 10> \\ (no default)");
206     System.err.println("\t--outputdir=<directory under which to generate> \\ (defaults to same dir as codebase)");
207     System.err.println("\t--recursive \\ (no args)");
208     System.err.println("\t--noclobber \\ (no args)");
209     System.err.println("\t--classname=<class to generate> \\ (defaults to Debug)");
210     System.err.println("\t--skipdirs=<directories that should be skipped> \\ (defaults to CVS)");
211     }
212
213     private static String JavaDoc ify(String JavaDoc str, char fromChar, char toChar)
214     {
215     if ( fromChar == toChar ) return str;
216
217     StringBuffer JavaDoc sb = new StringBuffer JavaDoc(str);
218     for (int i = 0, len = sb.length(); i < len; ++i)
219         if (sb.charAt(i) == fromChar)
220         sb.setCharAt(i, toChar);
221     return sb.toString();
222     }
223
224     private static String JavaDoc platify( String JavaDoc str )
225     {
226     String JavaDoc out;
227     out = ify( str, '/', File.separatorChar );
228     out = ify( out, '\\', File.separatorChar );
229     out = ify( out, ':', File.separatorChar );
230     return out;
231     }
232
233     private static String JavaDoc dottify(String JavaDoc str)
234     { return ify(str, File.separatorChar, '.');}
235
236     private static String JavaDoc sepify(String JavaDoc str)
237     { return ify(str, '.', File.separatorChar);}
238
239     private static boolean recursivePrecheckPackages(String JavaDoc codebase, File srcPkgDir, String JavaDoc outputbase, File outputBaseDir) throws IOException
240     {
241     FileIterator fii = DirectoryDescentUtils.depthFirstEagerDescent( srcPkgDir );
242     while (fii.hasNext())
243         {
244         File pkgDir = fii.nextFile();
245         if (! pkgDir.isDirectory() || skipDirs.contains(pkgDir.getName()))
246             continue;
247
248         File outputDir = outputDir( codebase, pkgDir, outputbase, outputBaseDir );
249         if (! outputDir.exists() && !outputDir.mkdirs() )
250             {
251             System.err.println( "Required output dir: '" + outputDir +
252                         "' does not exist, and could not be created.");
253             return false;
254             }
255         if (!precheckOutputPackageDir( outputDir ))
256             return false;
257         }
258     return true;
259     }
260
261     private static File outputDir( String JavaDoc codebase, File srcPkgDir, String JavaDoc outputbase, File outputBaseDir )
262     {
263     //System.err.println("outputDir( " + codebase +", " + srcPkgDir + ", " + outputbase + ", " + outputBaseDir + " )");
264
if (codebase.equals(outputbase))
265         return srcPkgDir;
266
267     String JavaDoc srcPath = srcPkgDir.getPath();
268     if (! srcPath.startsWith( codebase ))
269         {
270         System.err.println(DebugGen.class.getName() + ": program bug. Source package path '" + srcPath +
271                    "' does not begin with codebase '" + codebase + "'.");
272         System.exit(-1);
273         }
274     return new File( outputBaseDir, srcPath.substring( codebase.length() ) );
275     }
276
277
278     private static boolean precheckPackage( String JavaDoc codebase, File srcPkgDir, String JavaDoc outputbase, File outputBaseDir ) throws IOException
279     { return precheckOutputPackageDir( outputDir(codebase, srcPkgDir, outputbase, outputBaseDir) ); }
280
281     private static boolean precheckOutputPackageDir(File dir) throws IOException
282     {
283     File outFile = new File( dir, classname + ".java" );
284     if (! dir.canWrite())
285         {
286         System.err.println("File '" + outFile.getPath() + "' is not writable.");
287         return false;
288         }
289     else if (!clobber && outFile.exists())
290         {
291         System.err.println("File '" + outFile.getPath() + "' exists, and we are in noclobber mode.");
292         return false;
293         }
294     else
295         return true;
296     }
297
298     private static void recursiveWriteDebugFiles( String JavaDoc codebase, File srcPkgDir, String JavaDoc outputbase, File outputBaseDir ) throws IOException
299     {
300     FileIterator fii = DirectoryDescentUtils.depthFirstEagerDescent( outputDir( codebase, srcPkgDir, outputbase, outputBaseDir ) );
301     while (fii.hasNext())
302         {
303         File pkgDir = fii.nextFile();
304         //System.err.println("pkgDir: " + pkgDir);
305
if (! pkgDir.isDirectory() || skipDirs.contains(pkgDir.getName()))
306             continue;
307         
308         writeDebugFile(outputbase, pkgDir);
309         }
310     }
311
312     private static void writeDebugFile(String JavaDoc outputbase, File pkgDir) throws IOException
313     {
314     //System.err.println("outputbase: " + outputbase + "; pkgDir: " + pkgDir);
315

316     File outFile = new File( pkgDir, classname + ".java" );
317     String JavaDoc pkg = dottify( pkgDir.getPath().substring( outputbase.length() ) );
318     System.err.println("Writing file: " + outFile.getPath());
319     Writer writer = null;
320     try
321         {
322         writer = new OutputStreamWriter(
323                new BufferedOutputStream(
324                              new FileOutputStream( outFile ) ), "UTF8" );
325         writer.write("/********************************************************************" + EOL);
326         writer.write(" * This class generated by " + DebugGen.class.getName() + EOL);
327         writer.write(" * and will probably be overwritten by the same! Edit at" + EOL);
328         writer.write(" * YOUR PERIL!!! Hahahahaha." + EOL);
329         writer.write(" ********************************************************************/" + EOL);
330         writer.write(EOL);
331         writer.write("package " + pkg + ';' + EOL);
332         writer.write(EOL);
333         writer.write("import com.mchange.v2.debug.DebugConstants;" + EOL);
334         writer.write(EOL);
335         writer.write("final class " + classname + " implements DebugConstants" + EOL);
336         writer.write("{" + EOL);
337         writer.write("\tfinal static boolean DEBUG = " + debug + ';' + EOL);
338         writer.write("\tfinal static int TRACE = " + traceStr( trace_level ) + ';' + EOL);
339         writer.write(EOL);
340         writer.write("\tprivate " + classname + "()" + EOL);
341         writer.write("\t{}" + EOL);
342         writer.write("}" + EOL);
343         writer.write(EOL);
344         writer.flush();
345         }
346     finally
347         { WriterUtils.attemptClose( writer ); }
348     }
349
350     private static String JavaDoc traceStr( int trace )
351     {
352     if (trace == TRACE_NONE)
353         return "TRACE_NONE";
354     else if (trace == TRACE_MED)
355         return "TRACE_MED";
356     else if (trace == TRACE_MAX)
357         return "TRACE_MAX";
358     else
359         return String.valueOf(trace);
360     }
361 }
362
363
364
365
366
367
368
369
370
371
372
Popular Tags