1 16 package com.google.gwt.junit.rebind; 17 18 import com.google.gwt.core.ext.Generator; 19 import com.google.gwt.core.ext.GeneratorContext; 20 import com.google.gwt.core.ext.TreeLogger; 21 import com.google.gwt.core.ext.UnableToCompleteException; 22 import com.google.gwt.core.ext.typeinfo.JClassType; 23 import com.google.gwt.core.ext.typeinfo.JMethod; 24 import com.google.gwt.core.ext.typeinfo.NotFoundException; 25 import com.google.gwt.core.ext.typeinfo.TypeOracle; 26 import com.google.gwt.core.ext.typeinfo.JParameter; 27 import com.google.gwt.user.rebind.ClassSourceFileComposerFactory; 28 import com.google.gwt.user.rebind.SourceWriter; 29 30 import java.io.PrintWriter ; 31 import java.util.Map ; 32 import java.util.ArrayList ; 33 import java.util.List ; 34 import java.util.HashMap ; 35 36 42 public class JUnitTestCaseStubGenerator extends Generator { 43 44 interface MethodFilter { 45 public boolean accept( JMethod method ); 46 } 47 48 private static final String GWT_TESTCASE_CLASS_NAME = "com.google.gwt.junit.client.GWTTestCase"; 49 50 56 public static String [] getTestMethodNames(JClassType requestedClass) { 57 return (String []) getAllMethods( requestedClass, new MethodFilter() { 58 public boolean accept(JMethod method) { 59 return isJUnitTestMethod(method,false); 60 } 61 } ).keySet().toArray( new String [] {} ); 62 } 63 64 75 static Map getAllMethods( JClassType type, MethodFilter filter ) { 76 Map methods = new HashMap (); 77 JClassType cls = type; 78 79 while (cls != null) { 80 JMethod[] clsDeclMethods = cls.getMethods(); 81 82 for (int i = 0, n = clsDeclMethods.length; i < n; ++i) { 85 86 JMethod declMethod = clsDeclMethods[i]; 87 88 if ( ! filter.accept(declMethod) ) { 89 continue; 90 } 91 92 List list = (List )methods.get(declMethod.getName()); 93 94 if (list == null) { 95 list = new ArrayList (); 96 methods.put(declMethod.getName(),list); 97 list.add(declMethod); 98 continue; 99 } 100 101 JParameter[] declParams = declMethod.getParameters(); 102 103 for (int j = 0; j < list.size(); ++j) { 104 JMethod method = (JMethod)list.get(j); 105 JParameter[] parameters = method.getParameters(); 106 if ( ! equals( declParams, parameters )) { 107 list.add(declMethod ); 108 } 109 } 110 } 111 cls = cls.getSuperclass(); 112 } 113 114 return methods; 115 } 116 117 124 static boolean isJUnitTestMethod(JMethod method, boolean acceptArgs) { 125 if (!method.getName().startsWith("test")) { 126 return false; 127 } 128 129 if (!method.isPublic()) { 130 return false; 131 } 132 133 return acceptArgs || method.getParameters().length == 0 && ! acceptArgs; 134 } 135 136 142 private static boolean equals( JParameter[] params1, JParameter[] params2 ) { 143 if ( params1.length != params2.length ) { 144 return false; 145 } 146 for ( int i = 0; i < params1.length; ++i ) { 147 if ( params1[ i ].getType() != params2[ i ].getType() ) { 148 return false; 149 } 150 } 151 return true; 152 } 153 154 String qualifiedStubClassName; 155 String simpleStubClassName; 156 String typeName; 157 TreeLogger logger; 158 String packageName; 159 160 private JClassType requestedClass; 161 private SourceWriter sourceWriter; 162 private TypeOracle typeOracle; 163 164 167 public String generate(TreeLogger logger, GeneratorContext context, 168 String typeName) throws UnableToCompleteException { 169 170 if ( ! init( logger, context, typeName ) ) { 171 return qualifiedStubClassName; 172 } 173 174 writeSource(); 175 sourceWriter.commit( logger ); 176 177 return qualifiedStubClassName; 178 } 179 180 public JClassType getRequestedClass() { 181 return requestedClass; 182 } 183 184 public SourceWriter getSourceWriter() { 185 return sourceWriter; 186 } 187 188 public TypeOracle getTypeOracle() { 189 return typeOracle; 190 } 191 192 boolean init(TreeLogger logger, GeneratorContext context,String typeName) throws 193 UnableToCompleteException { 194 195 this.typeName = typeName; 196 this.logger = logger; 197 typeOracle = context.getTypeOracle(); 198 assert typeOracle != null; 199 200 try { 201 requestedClass = typeOracle.getType(typeName); 202 } catch (NotFoundException e) { 203 logger.log(TreeLogger.ERROR, "Could not find type '" + typeName 204 + "'; please see the log, as this usually indicates a previous error ", 205 e); 206 throw new UnableToCompleteException(); 207 } 208 209 simpleStubClassName = getSimpleStubClassName(requestedClass); 212 packageName = requestedClass.getPackage().getName(); 213 qualifiedStubClassName = packageName + "." + simpleStubClassName; 214 215 sourceWriter = getSourceWriter(logger, context, packageName, 216 simpleStubClassName, requestedClass.getQualifiedSourceName()); 217 218 return sourceWriter != null; 219 } 220 221 void writeSource() throws UnableToCompleteException { 222 String [] testMethods = getTestMethodNames(requestedClass); 223 writeGetNewTestCase(simpleStubClassName, sourceWriter); 224 writeDoRunTestMethod(testMethods, sourceWriter); 225 writeGetTestName(typeName, sourceWriter); 226 } 227 228 231 private String getSimpleStubClassName(JClassType baseClass) { 232 return "__" + baseClass.getSimpleSourceName() + "_unitTestImpl"; 233 } 234 235 private SourceWriter getSourceWriter(TreeLogger logger, GeneratorContext ctx, 236 String packageName, String className, String superclassName) { 237 238 PrintWriter printWriter = ctx.tryCreate(logger, packageName, className); 239 if (printWriter == null) { 240 return null; 241 } 242 243 ClassSourceFileComposerFactory composerFactory = new ClassSourceFileComposerFactory( 244 packageName, className); 245 246 composerFactory.setSuperclass(superclassName); 247 248 return composerFactory.createSourceWriter(ctx, printWriter); 249 } 250 251 private void writeDoRunTestMethod(String [] testMethodNames, SourceWriter sw) { 252 sw.println(); 253 sw.println("protected final void doRunTest(String name) throws Throwable {"); 254 sw.indent(); 255 for (int i = 0, n = testMethodNames.length; i < n; ++i) { 256 String methodName = testMethodNames[i]; 257 258 if (i > 0) { 259 sw.print("else "); 260 } 261 262 sw.println("if (name.equals(\"" + methodName + "\")) {"); 263 sw.indentln(methodName + "();"); 264 sw.println("}"); 265 } 266 sw.outdent(); 267 sw.println("}"); } 269 270 274 private void writeGetNewTestCase(String stubClassName, SourceWriter sw) { 275 sw.println(); 276 sw.println("public final " + GWT_TESTCASE_CLASS_NAME 277 + " getNewTestCase() {"); 278 sw.indent(); 279 sw.println("return new " + stubClassName + "();"); 280 sw.outdent(); 281 sw.println("}"); } 283 284 288 private void writeGetTestName(String testClassName, SourceWriter sw) { 289 sw.println(); 290 sw.println("public final String getTestName() {"); 291 sw.indent(); 292 sw.println("return \"" + testClassName + "\";"); 293 sw.outdent(); 294 sw.println("}"); } 296 } 297 | Popular Tags |