/plugin-module-codegen-engine/src/main/java/com/atlassian/plugins/codegen/annotations/asm/ModuleCreatorAnnotationParser.java

https://bitbucket.org/mmeinhold/amps · Java · 185 lines · 149 code · 31 blank · 5 comment · 8 complexity · 309cd813d6e1ce0e7383eee9b8a8f02c MD5 · raw file

  1. package com.atlassian.plugins.codegen.annotations.asm;
  2. import java.io.InputStream;
  3. import java.util.HashMap;
  4. import java.util.Map;
  5. import com.atlassian.plugins.codegen.annotations.*;
  6. import com.atlassian.plugins.codegen.modules.PluginModuleCreator;
  7. import com.atlassian.plugins.codegen.modules.PluginModuleCreatorRegistry;
  8. import org.apache.commons.io.IOUtils;
  9. import org.apache.commons.lang.ArrayUtils;
  10. import org.apache.commons.lang.StringUtils;
  11. import org.objectweb.asm.AnnotationVisitor;
  12. import org.objectweb.asm.ClassReader;
  13. import org.objectweb.asm.FieldVisitor;
  14. import org.objectweb.asm.MethodVisitor;
  15. import org.objectweb.asm.commons.EmptyVisitor;
  16. /**
  17. * @since 3.6
  18. */
  19. public class ModuleCreatorAnnotationParser extends AbstractAnnotationParser
  20. {
  21. public static final String MODULE_PACKAGE = "com.atlassian.plugins.codegen.modules";
  22. protected static final Map<String, String> annotationProductMap = new HashMap<String, String>();
  23. static
  24. {
  25. annotationProductMap.put(JiraPluginModuleCreator.class.getName(), PluginModuleCreatorRegistry.JIRA);
  26. annotationProductMap.put(ConfluencePluginModuleCreator.class.getName(), PluginModuleCreatorRegistry.CONFLUENCE);
  27. annotationProductMap.put(BambooPluginModuleCreator.class.getName(), PluginModuleCreatorRegistry.BAMBOO);
  28. annotationProductMap.put(CrowdPluginModuleCreator.class.getName(), PluginModuleCreatorRegistry.CROWD);
  29. annotationProductMap.put(FeCruPluginModuleCreator.class.getName(), PluginModuleCreatorRegistry.FECRU);
  30. annotationProductMap.put(StashPluginModuleCreator.class.getName(), PluginModuleCreatorRegistry.STASH);
  31. annotationProductMap.put(RefAppPluginModuleCreator.class.getName(), PluginModuleCreatorRegistry.REFAPP);
  32. }
  33. private final PluginModuleCreatorRegistry pluginModuleCreatorRegistry;
  34. public ModuleCreatorAnnotationParser(PluginModuleCreatorRegistry pluginModuleCreatorRegistry)
  35. {
  36. super();
  37. this.pluginModuleCreatorRegistry = pluginModuleCreatorRegistry;
  38. }
  39. public void parse() throws Exception
  40. {
  41. ClassLoader oldLoader = Thread.currentThread()
  42. .getContextClassLoader();
  43. Thread.currentThread()
  44. .setContextClassLoader(getClass().getClassLoader());
  45. parse(MODULE_PACKAGE, new ModuleClassVisitor());
  46. Thread.currentThread()
  47. .setContextClassLoader(oldLoader);
  48. }
  49. public void parse(String basePackage) throws Exception
  50. {
  51. ClassLoader oldLoader = Thread.currentThread()
  52. .getContextClassLoader();
  53. Thread.currentThread()
  54. .setContextClassLoader(getClass().getClassLoader());
  55. parse(basePackage, new ModuleClassVisitor());
  56. Thread.currentThread()
  57. .setContextClassLoader(oldLoader);
  58. }
  59. public class ModuleClassVisitor extends EmptyVisitor
  60. {
  61. private String visitedClassname;
  62. private boolean isModuleCreator;
  63. @Override
  64. public void visit(final int version, final int access, final String name, final String signature, final String superName, final String[] interfaces)
  65. {
  66. this.visitedClassname = normalize(name);
  67. String iface = PluginModuleCreator.class.getName()
  68. .replace('.', '/');
  69. this.isModuleCreator = ArrayUtils.contains(interfaces, iface);
  70. if (!isModuleCreator)
  71. {
  72. this.isModuleCreator = superHasInterface(superName, iface);
  73. }
  74. }
  75. private boolean superHasInterface(String superName, String interfaceName)
  76. {
  77. boolean hasInterface = false;
  78. if (normalize(superName).equals("java.lang.Object"))
  79. {
  80. return hasInterface;
  81. }
  82. ClassLoader classLoader = Thread.currentThread().getContextClassLoader();
  83. String path = superName.replace('.', '/');
  84. InputStream is = null;
  85. try
  86. {
  87. is = classLoader.getResourceAsStream(path + ".class");
  88. if (null != is)
  89. {
  90. ClassReader classReader = new ClassReader(is);
  91. hasInterface = ArrayUtils.contains(classReader.getInterfaces(), interfaceName);
  92. if (!hasInterface)
  93. {
  94. hasInterface = superHasInterface(classReader.getSuperName(), interfaceName);
  95. }
  96. }
  97. } catch (Exception e)
  98. {
  99. //don't care
  100. } finally
  101. {
  102. IOUtils.closeQuietly(is);
  103. }
  104. return hasInterface;
  105. }
  106. @Override
  107. public AnnotationVisitor visitAnnotation(String annotationName, boolean isVisible)
  108. {
  109. String normalizedName = normalize(annotationName);
  110. if (isModuleCreator && annotationProductMap.containsKey(normalizedName))
  111. {
  112. return new ProductCreatorAnnotationVisitor(normalizedName);
  113. }
  114. return null;
  115. }
  116. @Override
  117. public MethodVisitor visitMethod(int i, String s, String s1, String s2, String[] strings)
  118. {
  119. return null;
  120. }
  121. @Override
  122. public FieldVisitor visitField(int i, String s, String s1, String s2, Object o)
  123. {
  124. return null;
  125. }
  126. private class ProductCreatorAnnotationVisitor extends EmptyVisitor
  127. {
  128. private String annotationName;
  129. private ProductCreatorAnnotationVisitor(String annotationName)
  130. {
  131. this.annotationName = annotationName;
  132. }
  133. @Override
  134. public void visitEnd()
  135. {
  136. super.visitEnd();
  137. String productId = annotationProductMap.get(annotationName);
  138. if (StringUtils.isNotBlank(productId))
  139. {
  140. try
  141. {
  142. PluginModuleCreator creator = (PluginModuleCreator) Class.forName(visitedClassname)
  143. .newInstance();
  144. pluginModuleCreatorRegistry.registerModuleCreator(productId, creator);
  145. } catch (Exception e)
  146. {
  147. e.printStackTrace();
  148. //just don't register
  149. }
  150. }
  151. }
  152. }
  153. }
  154. }