1 23 package com.sun.enterprise.deployment.annotation.impl; 24 25 import java.util.EmptyStackException ; 26 import java.util.Map ; 27 import java.util.HashMap ; 28 import java.util.List ; 29 import java.util.ArrayList ; 30 import java.util.Set ; 31 import java.util.HashSet ; 32 import java.util.Stack ; 33 import java.lang.annotation.Annotation ; 34 import java.lang.annotation.ElementType ; 35 import java.lang.reflect.AnnotatedElement ; 36 import java.lang.reflect.Field ; 37 import java.lang.reflect.Method ; 38 import java.lang.reflect.Constructor ; 39 import java.util.logging.Logger ; 40 41 import com.sun.enterprise.deployment.annotation.ProcessingContext; 42 import com.sun.enterprise.deployment.annotation.AnnotationProcessor; 43 import com.sun.enterprise.deployment.annotation.AnnotationInfo; 44 import com.sun.enterprise.deployment.annotation.AnnotationProcessorException; 45 import com.sun.enterprise.deployment.annotation.AnnotationHandler; 46 import com.sun.enterprise.deployment.annotation.AnnotatedElementHandler; 47 import com.sun.enterprise.deployment.annotation.ComponentInfo; 48 import com.sun.enterprise.deployment.annotation.ResultType; 49 import com.sun.enterprise.deployment.annotation.HandlerProcessingResult; 50 import com.sun.enterprise.deployment.annotation.ProcessingResult; 51 import com.sun.enterprise.deployment.annotation.Scanner; 52 import java.util.logging.Level ; 53 54 55 59 public class AnnotationProcessorImpl implements AnnotationProcessor { 60 61 AnnotationProcessorImpl delegate; 62 Map <Class <? extends Annotation >, List <AnnotationHandler>> handlers = 63 new HashMap <Class <? extends Annotation >, List <AnnotationHandler>>(); 64 65 int errorCount; 66 Logger logger; 67 Stack <StackElement> annotatedElements = new Stack <StackElement>(); 68 Set <Package > visitedPackages = new HashSet <Package >(); 69 70 71 public AnnotationProcessorImpl() { 72 logger = AnnotationUtils.getLogger(); 73 } 74 75 public void setDelegate(AnnotationProcessorImpl delegate) { 76 this.delegate = delegate; 77 } 78 public ProcessingContext createContext() { 79 ProcessingContext ctx = new ProcessingContextImpl(this); 80 ctx.setErrorHandler(new DefaultErrorHandler()); 81 return ctx; 82 } 83 84 87 public void log(Level level, AnnotationInfo locator, String localizedMessage){ 88 if (logger!=null && logger.isLoggable(level)){ 89 if (locator!=null){ 90 logger.log(level, AnnotationUtils.getLocalString( 91 "enterprise.deployment.annotation.error", 92 "{2}\n symbol: {0}\n location: {1}", 93 new Object [] { locator.getAnnotation().annotationType().getName(), locator.getAnnotatedElement(), localizedMessage})); 94 } else{ 95 logger.log(level, localizedMessage); 96 } 97 } 98 } 99 100 106 public ProcessingResult process(ProcessingContext ctx) 107 throws AnnotationProcessorException 108 { 109 110 Scanner scanner = ctx.getProcessingInput(); 111 ProcessingResultImpl result = new ProcessingResultImpl(); 112 errorCount=0; 113 114 for (Class c : scanner.getElements()) { 115 116 result.add(process(ctx, c)); 117 } 118 return result; 119 } 120 121 133 public ProcessingResult process(ProcessingContext ctx, Class [] classes) 134 throws AnnotationProcessorException { 135 136 ProcessingResultImpl result = new ProcessingResultImpl(); 137 for (Class c : classes) { 138 result.add(process(ctx, c)); 139 } 140 return result; 141 } 142 143 private ProcessingResult process(ProcessingContext ctx, Class c) 144 throws AnnotationProcessorException { 145 146 Scanner scanner = ctx.getProcessingInput(); 147 ProcessingResultImpl result = new ProcessingResultImpl(); 148 149 Package classPackage = c.getPackage(); 151 if (classPackage != null && visitedPackages.add(classPackage)) { 152 result.add(classPackage, 154 processAnnotations(ctx, ElementType.PACKAGE, classPackage)); 155 } 156 157 ComponentInfo info = null; 158 try { 159 info = scanner.getComponentInfo(c); 160 } catch (NoClassDefFoundError err) { 161 AnnotationProcessorException ape = 163 new AnnotationProcessorException( 164 AnnotationUtils.getLocalString( 165 "enterprise.deployment.annotation.classnotfounderror", 166 "Class [ {0} ] not found. Error while loading [ {1} ]", 167 new Object []{err.getMessage(), c})); 168 ctx.getErrorHandler().error(ape); 169 throw err; 170 } 171 172 AnnotatedElementHandler handler= ctx.getHandler(); 174 logStart(handler, ElementType.TYPE,c); 175 result.add(c, processAnnotations(ctx, c)); 176 177 for (Field field : info.getFields()) { 179 result.add(field,processAnnotations(ctx, ElementType.FIELD, field)); 180 } 181 182 for (Constructor constructor : info.getConstructors()) { 184 logStart(ctx.getHandler(), ElementType.CONSTRUCTOR, constructor); 185 result.add(constructor, processAnnotations(ctx, constructor)); 186 187 processParameters(ctx, constructor.getParameterAnnotations()); 189 190 logEnd(ctx.getHandler(), ElementType.CONSTRUCTOR, constructor); 191 192 } 193 194 for (Method method : info.getMethods()) { 196 logStart(ctx.getHandler(), ElementType.METHOD, method); 197 result.add(method, processAnnotations(ctx, method)); 198 199 processParameters(ctx, method.getParameterAnnotations()); 201 202 logEnd(ctx.getHandler(), ElementType.METHOD, method); 203 } 204 205 Class currentClass = c.getSuperclass(); 210 while (currentClass!=null && !currentClass.equals(Object .class)) { 211 result.add(c, processAnnotations(ctx, currentClass)); 214 currentClass = currentClass.getSuperclass(); 215 } 216 217 logEnd(ctx.getHandler(), ElementType.TYPE, c); 220 221 return result; 222 } 223 224 private HandlerProcessingResult processParameters(ProcessingContext ctx, Annotation [][] parametersAnnotations) 225 throws AnnotationProcessorException 226 { 227 228 HandlerProcessingResultImpl result = new HandlerProcessingResultImpl(); 229 230 for (Annotation [] parameterAnnotations : parametersAnnotations) { 232 logStart(ctx.getHandler(), ElementType.PARAMETER, null); 233 if (parameterAnnotations!=null) { 234 for (Annotation annotation : parameterAnnotations) { 235 AnnotationInfo info = new AnnotationInfo(ctx, null, annotation, ElementType.PARAMETER); 236 process(ctx, info, result); 237 dumpProcessingResult(result); 238 } 239 } 240 logEnd(ctx.getHandler(), ElementType.PARAMETER, null); 241 } 242 return result; 243 } 244 245 private HandlerProcessingResult processAnnotations(ProcessingContext ctx, ElementType type, AnnotatedElement element) 246 throws AnnotationProcessorException 247 { 248 249 AnnotatedElementHandler handler = ctx.getHandler(); 250 logStart(handler, type, element); 251 HandlerProcessingResult result = processAnnotations(ctx, element); 252 logEnd(handler, type, element); 253 254 dumpProcessingResult(result); 255 256 return result; 257 } 258 259 private HandlerProcessingResult processAnnotations(ProcessingContext ctx, AnnotatedElement element) 260 throws AnnotationProcessorException 261 { 262 263 HandlerProcessingResultImpl result= new HandlerProcessingResultImpl(); 264 265 for (Annotation annotation : element.getAnnotations()) { 266 AnnotationInfo subElement = new AnnotationInfo(ctx, element, annotation, getTopElementType()); 268 if (!result.processedAnnotations().containsKey(annotation.annotationType())) { 269 process(ctx, subElement, result); 270 } else { 271 if (AnnotationUtils.shouldLog("annotation")) { 272 logger.finer("Annotation " + annotation.annotationType() + " already processed"); 273 } 274 } 275 } 276 return result; 277 } 278 279 private void process(ProcessingContext ctx, AnnotationInfo element, HandlerProcessingResultImpl result) 280 throws AnnotationProcessorException 281 { 282 283 284 Annotation annotation = element.getAnnotation(); 285 if (AnnotationUtils.shouldLog("annotation")) { 286 logger.finer("Annotation : " + annotation.annotationType().getName() + " delegate = " + delegate); 287 } 288 result.addResult(annotation.annotationType(), ResultType.UNPROCESSED); 289 290 Package annPackage = annotation.annotationType().getPackage(); 292 if (annPackage != null && annPackage.getName().startsWith("java.lang")) 293 return; 294 295 List <AnnotationHandler> annotationHandlers = handlers.get(annotation.annotationType()); 296 if (annotationHandlers!=null) { 297 for (AnnotationHandler handler : annotationHandlers) { 298 299 Class <? extends Annotation >[] dependencies = handler.getTypeDependencies(); 305 if (dependencies!=null) { 306 AnnotatedElement ae = element.getAnnotatedElement(); 307 for (Class <? extends Annotation > annotationType : dependencies) { 308 Annotation depAnnotation = ae.getAnnotation(annotationType); 309 if (depAnnotation!=null) { 310 ResultType resultType = result.processedAnnotations().get(annotationType); 311 if (resultType==null || resultType==ResultType.UNPROCESSED){ 312 AnnotationInfo info = new AnnotationInfo(ctx, ae, depAnnotation, getTopElementType()); 314 process(ctx, info, result); 315 } 316 } 317 } 318 } 319 320 HandlerProcessingResult processingResult = null; 323 try { 324 processingResult = handler.processAnnotation(element); 325 } catch(AnnotationProcessorException ape) { 326 log(Level.SEVERE, ape.getLocator(), ape.getMessage()); 328 329 if (ape.isFatal()) { 333 throw ape; 334 } 335 336 if (++errorCount>100){ 337 throw new AnnotationProcessorException( 338 AnnotationUtils.getLocalString( 339 "enterprise.deployment.annotation.toomanyerror", 340 "Too many errors, annotation processing abandoned.")); 341 } 342 343 processingResult = 344 HandlerProcessingResultImpl.getDefaultResult( 345 annotation.annotationType(), ResultType.FAILED); 346 } catch(Throwable e){ 347 AnnotationProcessorException ape = new AnnotationProcessorException(e.getMessage(), element); 348 ape.initCause(e); 349 throw ape; 350 } 351 result.addAll(processingResult); 352 } 353 } else { 354 if (delegate!=null) { 355 delegate.process(ctx, element, result); 356 } else { 357 ctx.getErrorHandler().fine( 358 new AnnotationProcessorException("No handler defined for " 359 + annotation.annotationType())); 360 } 361 } 362 } 363 364 private void dumpProcessingResult(HandlerProcessingResult result) { 365 366 if (result==null || !AnnotationUtils.shouldLog("annotation")) { 367 return; 368 } 369 370 Map <Class <? extends Annotation >, ResultType> annotationResults = 371 result.processedAnnotations(); 372 for (Class annotationType : annotationResults.keySet()) { 373 logger.finer("Annotation " + annotationType + " : " + 374 annotationResults.get(annotationType)); 375 } 376 } 377 public void pushAnnotationHandler(AnnotationHandler handler) { 378 379 Class <? extends Annotation > type = handler.getAnnotationType(); 380 List <AnnotationHandler> currentHandlers = handlers.get(type); 381 if (currentHandlers==null) { 382 currentHandlers = new ArrayList <AnnotationHandler>(); 383 handlers.put(type, currentHandlers); 384 } 385 currentHandlers.add(handler); 386 } 387 388 public void popAnnotationHandler(Class <? extends Annotation > type) { 389 List <AnnotationHandler> currentHandlers = handlers.get(type); 390 if (currentHandlers!=null) { 391 currentHandlers.remove(currentHandlers.size()); 392 } 393 } 394 395 public AnnotationHandler getAnnotationHandler(Class <? extends Annotation > type) { 396 List <AnnotationHandler> currentHandlers = handlers.get(type); 397 if (currentHandlers!=null && currentHandlers.size()>0) { 398 return currentHandlers.get(0); 399 } 400 return null; 401 } 402 403 407 public AnnotatedElement getLastAnnotatedElement(ElementType type) { 408 for (int i=annotatedElements.size();i!=0;i--) { 409 StackElement e = annotatedElements.get(i - 1); 410 if (e.getElementType().equals(type)) 411 return e.getAnnotatedElement(); 412 } 413 return null; 414 } 415 416 public Stack <StackElement> getStack() { 417 return annotatedElements; 418 } 419 420 private void logStart(AnnotatedElementHandler handler, ElementType type, AnnotatedElement c) throws AnnotationProcessorException { 421 422 if (AnnotationUtils.shouldLog("types")) { 423 AnnotationUtils.getLogger().finer(type + " START : " + c); 424 } 425 426 annotatedElements.push(new StackElement(type, c)); 428 if(delegate!=null) { 429 delegate.getStack().push(new StackElement(type, c)); 430 } 431 432 if (handler!=null) { 433 handler.startElement(type, c); 434 } 435 } 436 437 private void logEnd(AnnotatedElementHandler handler, ElementType type, AnnotatedElement c) throws AnnotationProcessorException { 438 439 if (AnnotationUtils.shouldLog("types")) { 440 AnnotationUtils.getLogger().finer(type + " END : " + c); 441 } 442 443 annotatedElements.pop(); 445 if(delegate!=null) { 446 delegate.getStack().pop(); 447 } 448 449 if (handler!=null) { 450 handler.endElement(type, c); 451 } 452 } 453 454 457 private ElementType getTopElementType() { 458 try { 459 StackElement top = annotatedElements.peek(); 460 return top.getElementType(); 461 } catch(EmptyStackException ex) { 462 return null; 463 } 464 } 465 } 466 | Popular Tags |