- Revision
- 750
- Author
- rfscholte
- Date
- 2010-09-25 07:29:19 -0500 (Sat, 25 Sep 2010)
Log Message
Extracted BinaryClassPArser from JavaDocBuilder
Modified Paths
Added Paths
- trunk/qdox/src/java/com/thoughtworks/qdox/parser/impl/
- trunk/qdox/src/java/com/thoughtworks/qdox/parser/impl/BinaryClassParser.java
Diff
Modified: trunk/qdox/src/java/com/thoughtworks/qdox/JavaDocBuilder.java (749 => 750)
--- trunk/qdox/src/java/com/thoughtworks/qdox/JavaDocBuilder.java 2010-09-08 11:49:22 UTC (rev 749) +++ trunk/qdox/src/java/com/thoughtworks/qdox/JavaDocBuilder.java 2010-09-25 12:29:19 UTC (rev 750) @@ -1,26 +1,5 @@ package com.thoughtworks.qdox; -import com.thoughtworks.qdox.directorywalker.DirectoryScanner; -import com.thoughtworks.qdox.directorywalker.FileVisitor; -import com.thoughtworks.qdox.directorywalker.SuffixFilter; -import com.thoughtworks.qdox.model.ClassLibrary; -import com.thoughtworks.qdox.model.DefaultDocletTagFactory; -import com.thoughtworks.qdox.model.DocletTagFactory; -import com.thoughtworks.qdox.model.JavaClass; -import com.thoughtworks.qdox.model.JavaClassCache; -import com.thoughtworks.qdox.model.JavaSource; -import com.thoughtworks.qdox.model.ModelBuilder; -import com.thoughtworks.qdox.model.JavaPackage; -import com.thoughtworks.qdox.parser.Lexer; -import com.thoughtworks.qdox.parser.ParseException; -import com.thoughtworks.qdox.parser.impl.JFlexLexer; -import com.thoughtworks.qdox.parser.impl.Parser; -import com.thoughtworks.qdox.parser.structs.ClassDef; -import com.thoughtworks.qdox.parser.structs.FieldDef; -import com.thoughtworks.qdox.parser.structs.MethodDef; -import com.thoughtworks.qdox.parser.structs.PackageDef; -import com.thoughtworks.qdox.parser.structs.TypeDef; - import java.io.File; import java.io.FileInputStream; import java.io.FileNotFoundException; @@ -31,23 +10,31 @@ import java.io.ObjectOutputStream; import java.io.Reader; import java.io.Serializable; -import java.io.UnsupportedEncodingException; -import java.lang.reflect.Constructor; -import java.lang.reflect.Field; -import java.lang.reflect.Member; -import java.lang.reflect.Method; -import java.lang.reflect.Modifier; import java.net.URL; import java.util.ArrayList; -import java.util.HashMap; import java.util.HashSet; import java.util.Iterator; import java.util.LinkedList; import java.util.List; -import java.util.Map; import java.util.Set; -import java.util.StringTokenizer; +import com.thoughtworks.qdox.directorywalker.DirectoryScanner; +import com.thoughtworks.qdox.directorywalker.FileVisitor; +import com.thoughtworks.qdox.directorywalker.SuffixFilter; +import com.thoughtworks.qdox.model.ClassLibrary; +import com.thoughtworks.qdox.model.DefaultDocletTagFactory; +import com.thoughtworks.qdox.model.DocletTagFactory; +import com.thoughtworks.qdox.model.JavaClass; +import com.thoughtworks.qdox.model.JavaPackage; +import com.thoughtworks.qdox.model.JavaSource; +import com.thoughtworks.qdox.model.ModelBuilder; +import com.thoughtworks.qdox.parser.Lexer; +import com.thoughtworks.qdox.parser.ParseException; +import com.thoughtworks.qdox.parser.impl.BinaryClassParser; +import com.thoughtworks.qdox.parser.impl.JFlexLexer; +import com.thoughtworks.qdox.parser.impl.Parser; +import com.thoughtworks.qdox.parser.structs.ClassDef; + /** * Simple facade to QDox allowing a source tree to be parsed and the resulting object model navigated. * @@ -187,158 +174,21 @@ if (clazz == null) { return null; } else { - try { - // Create a new builder and mimic the behaviour of the parser. - // We're getting all the information we need via reflection instead. - ModelBuilder binaryBuilder = new ModelBuilder(context, docletTagFactory); - - // Set the package name and class name - String packageName = getPackageName(name); - binaryBuilder.addPackage(new PackageDef(packageName)); - - ClassDef classDef = new ClassDef(); - classDef.name = getClassName(name); - - // Set the extended class and interfaces. - Class[] interfaces = clazz.getInterfaces(); - if (clazz.isInterface()) { - // It's an interface - classDef.type = ClassDef.INTERFACE; - for (int i = 0; i < interfaces.length; i++) { - Class anInterface = interfaces[i]; - classDef.extendz.add(new TypeDef(anInterface.getName())); - } - } else { - // It's a class - for (int i = 0; i < interfaces.length; i++) { - Class anInterface = interfaces[i]; - classDef.implementz.add(new TypeDef(anInterface.getName())); - } - Class superclass = clazz.getSuperclass(); - if (superclass != null) { - classDef.extendz.add(new TypeDef(superclass.getName())); - } - } - - addModifiers(classDef.modifiers, clazz.getModifiers()); - - binaryBuilder.beginClass(classDef); - - // add the constructors - // - // This also adds the default constructor if any which is different - // to the source code as that does not create a default constructor - // if no constructor exists. - Constructor[] constructors = clazz.getDeclaredConstructors(); - for (int i = 0; i < constructors.length; i++) { - addMethodOrConstructor(constructors[i], binaryBuilder); - } - - // add the methods - Method[] methods = clazz.getDeclaredMethods(); - for (int i = 0; i < methods.length; i++) { - addMethodOrConstructor(methods[i], binaryBuilder); - } - - Field[] fields = clazz.getDeclaredFields(); - for (int i = 0; i < fields.length; i++) { - addField(fields[i], binaryBuilder); - } - - binaryBuilder.endClass(); - JavaSource binarySource = binaryBuilder.getSource(); - // There is always only one class in a "binary" source. - JavaClass result = binarySource.getClasses()[0]; - return result; - } catch (NoClassDefFoundError e) { - return null; - } + // Create a new builder and mimic the behaviour of the parser. + // We're getting all the information we need via reflection instead. + ModelBuilder binaryBuilder = new ModelBuilder(context, docletTagFactory); + BinaryClassParser parser = new BinaryClassParser( clazz, binaryBuilder ); + parser.parse(); + + JavaSource binarySource = binaryBuilder.getSource(); + // There is always only one class in a "binary" source. + JavaClass result = binarySource.getClasses()[0]; + return result; } } - private void addModifiers(Set set, int modifier) { - String modifierString = Modifier.toString(modifier); - for (StringTokenizer stringTokenizer = new StringTokenizer(modifierString); stringTokenizer.hasMoreTokens();) { - set.add(stringTokenizer.nextToken()); - } - } - - private void addField(Field field, ModelBuilder binaryBuilder) { - FieldDef fieldDef = new FieldDef(); - Class fieldType = field.getType(); - fieldDef.name = field.getName(); - fieldDef.type = getTypeDef(fieldType); - fieldDef.dimensions = getDimension(fieldType); - addModifiers( fieldDef.modifiers, field.getModifiers()); - binaryBuilder.addField(fieldDef); - } - - private void addMethodOrConstructor(Member member, ModelBuilder binaryBuilder) { - MethodDef methodDef = new MethodDef(); - // The name of constructors are qualified. Need to strip it. - // This will work for regular methods too, since -1 + 1 = 0 - int lastDot = member.getName().lastIndexOf('.'); - methodDef.name = member.getName().substring(lastDot + 1); - - addModifiers(methodDef.modifiers, member.getModifiers()); - Class[] exceptions; - Class[] parameterTypes; - if (member instanceof Method) { - methodDef.constructor = false; - - // For some stupid reason, these methods are not defined in Member, - // but in both Method and Construcotr. - exceptions = ((Method) member).getExceptionTypes(); - parameterTypes = ((Method) member).getParameterTypes(); - - Class returnType = ((Method) member).getReturnType(); - methodDef.returnType = getTypeDef(returnType); - methodDef.dimensions = getDimension(returnType); - - } else { - methodDef.constructor = true; - - exceptions = ((Constructor) member).getExceptionTypes(); - parameterTypes = ((Constructor) member).getParameterTypes(); - } - for (int j = 0; j < exceptions.length; j++) { - Class exception = exceptions[j]; - methodDef.exceptions.add(exception.getName()); - } - binaryBuilder.addMethod(methodDef); - for (int j = 0; j < parameterTypes.length; j++) { - FieldDef param = new FieldDef(); - Class parameterType = parameterTypes[j]; - param.name = "p" + j; - param.type = getTypeDef(parameterType); - param.dimensions = getDimension(parameterType); - binaryBuilder.addParameter( param ); - } - } - - private static final int getDimension(Class c) { - return c.getName().lastIndexOf('[') + 1; - } - - private static String getTypeName(Class c) { - return c.getComponentType() != null ? c.getComponentType().getName() : c.getName(); - } - private static TypeDef getTypeDef(Class c) { - return new TypeDef(getTypeName(c)); - } - - private String getPackageName(String fullClassName) { - int lastDot = fullClassName.lastIndexOf('.'); - return lastDot == -1 ? "" : fullClassName.substring(0, lastDot); - } - - private String getClassName(String fullClassName) { - int lastDot = fullClassName.lastIndexOf('.'); - return lastDot == -1 ? fullClassName : fullClassName.substring(lastDot + 1); - } - public JavaSource addSource(Reader reader) { return addSource(reader, "UNKNOWN SOURCE"); }
Added: trunk/qdox/src/java/com/thoughtworks/qdox/parser/impl/BinaryClassParser.java (0 => 750)
--- trunk/qdox/src/java/com/thoughtworks/qdox/parser/impl/BinaryClassParser.java (rev 0) +++ trunk/qdox/src/java/com/thoughtworks/qdox/parser/impl/BinaryClassParser.java 2010-09-25 12:29:19 UTC (rev 750) @@ -0,0 +1,176 @@ +package com.thoughtworks.qdox.parser.impl; + +import java.lang.reflect.Constructor; +import java.lang.reflect.Field; +import java.lang.reflect.Member; +import java.lang.reflect.Method; +import java.lang.reflect.Modifier; +import java.util.Set; +import java.util.StringTokenizer; + +import com.thoughtworks.qdox.model.ModelBuilder; +import com.thoughtworks.qdox.parser.structs.ClassDef; +import com.thoughtworks.qdox.parser.structs.FieldDef; +import com.thoughtworks.qdox.parser.structs.MethodDef; +import com.thoughtworks.qdox.parser.structs.PackageDef; +import com.thoughtworks.qdox.parser.structs.TypeDef; + +public class BinaryClassParser +{ + private Class clazz; + private ModelBuilder binaryBuilder; + + public BinaryClassParser(Class clazz, ModelBuilder modelBuilder) + { + this.clazz = clazz; + this.binaryBuilder = modelBuilder; + } + + public boolean parse() { + try { + String name = clazz.getName(); + + // Set the package name and class name + String packageName = getPackageName(name); + binaryBuilder.addPackage(new PackageDef(packageName)); + + ClassDef classDef = new ClassDef(); + classDef.name = getClassName(name); + + // Set the extended class and interfaces. + Class[] interfaces = clazz.getInterfaces(); + if (clazz.isInterface()) { + // It's an interface + classDef.type = ClassDef.INTERFACE; + for (int i = 0; i < interfaces.length; i++) { + Class anInterface = interfaces[i]; + classDef.extendz.add(new TypeDef(anInterface.getName())); + } + } else { + // It's a class + for (int i = 0; i < interfaces.length; i++) { + Class anInterface = interfaces[i]; + classDef.implementz.add(new TypeDef(anInterface.getName())); + } + Class superclass = clazz.getSuperclass(); + if (superclass != null) { + classDef.extendz.add(new TypeDef(superclass.getName())); + } + } + + addModifiers(classDef.modifiers, clazz.getModifiers()); + + binaryBuilder.beginClass(classDef); + + // add the constructors + // + // This also adds the default constructor if any which is different + // to the source code as that does not create a default constructor + // if no constructor exists. + Constructor[] constructors = clazz.getDeclaredConstructors(); + for (int i = 0; i < constructors.length; i++) { + addMethodOrConstructor(constructors[i], binaryBuilder); + } + + // add the methods + Method[] methods = clazz.getDeclaredMethods(); + for (int i = 0; i < methods.length; i++) { + addMethodOrConstructor(methods[i], binaryBuilder); + } + + Field[] fields = clazz.getDeclaredFields(); + for (int i = 0; i < fields.length; i++) { + addField(fields[i], binaryBuilder); + } + + binaryBuilder.endClass(); + + return true; + } catch (NoClassDefFoundError e) { + return false; + } + } + + private void addModifiers(Set set, int modifier) { + String modifierString = Modifier.toString(modifier); + for (StringTokenizer stringTokenizer = new StringTokenizer(modifierString); stringTokenizer.hasMoreTokens();) { + set.add(stringTokenizer.nextToken()); + } + } + + private void addField(Field field, ModelBuilder binaryBuilder) { + FieldDef fieldDef = new FieldDef(); + Class fieldType = field.getType(); + fieldDef.name = field.getName(); + fieldDef.type = getTypeDef(fieldType); + fieldDef.dimensions = getDimension(fieldType); + addModifiers( fieldDef.modifiers, field.getModifiers()); + binaryBuilder.addField(fieldDef); + } + + private void addMethodOrConstructor(Member member, ModelBuilder binaryBuilder) { + MethodDef methodDef = new MethodDef(); + // The name of constructors are qualified. Need to strip it. + // This will work for regular methods too, since -1 + 1 = 0 + int lastDot = member.getName().lastIndexOf('.'); + methodDef.name = member.getName().substring(lastDot + 1); + + addModifiers(methodDef.modifiers, member.getModifiers()); + Class[] exceptions; + Class[] parameterTypes; + if (member instanceof Method) { + methodDef.constructor = false; + + // For some stupid reason, these methods are not defined in Member, + // but in both Method and Construcotr. + exceptions = ((Method) member).getExceptionTypes(); + parameterTypes = ((Method) member).getParameterTypes(); + + Class returnType = ((Method) member).getReturnType(); + methodDef.returnType = getTypeDef(returnType); + methodDef.dimensions = getDimension(returnType); + + } else { + methodDef.constructor = true; + + exceptions = ((Constructor) member).getExceptionTypes(); + parameterTypes = ((Constructor) member).getParameterTypes(); + } + for (int j = 0; j < exceptions.length; j++) { + Class exception = exceptions[j]; + methodDef.exceptions.add(exception.getName()); + } + binaryBuilder.addMethod(methodDef); + for (int j = 0; j < parameterTypes.length; j++) { + FieldDef param = new FieldDef(); + Class parameterType = parameterTypes[j]; + param.name = "p" + j; + param.type = getTypeDef(parameterType); + param.dimensions = getDimension(parameterType); + binaryBuilder.addParameter( param ); + } + } + + private static final int getDimension(Class c) { + return c.getName().lastIndexOf('[') + 1; + } + + private static String getTypeName(Class c) { + return c.getComponentType() != null ? c.getComponentType().getName() : c.getName(); + } + + private static TypeDef getTypeDef(Class c) { + return new TypeDef(getTypeName(c)); + } + + + private String getPackageName(String fullClassName) { + int lastDot = fullClassName.lastIndexOf('.'); + return lastDot == -1 ? "" : fullClassName.substring(0, lastDot); + } + + private String getClassName(String fullClassName) { + int lastDot = fullClassName.lastIndexOf('.'); + return lastDot == -1 ? fullClassName : fullClassName.substring(lastDot + 1); + } +} Property changes on: trunk/qdox/src/java/com/thoughtworks/qdox/parser/impl/BinaryClassParser.java ___________________________________________________________________ Name: svn:keywords + Author Date Id Revision Name: svn:eol-style + native
To unsubscribe from this list please visit:
