2010-02-23 12 views
5

parece ser imposible utilizar javax.tools.ToolProvider de un cargador de clase personalizada como lo requiere la hormiga o Webstart: http://bugs.sun.com/view_bug.do?bug_id=6548428¿Cómo usar javax.tools.ToolProvider desde un cargador de clases personalizado?

javax.tools.ToolProvider.getSystemJavaCompiler() cargas javax.tools.JavaCompiler en un URLClassLoader cuyo padre es el cargador de clases del sistema. La API no parece permitir a los usuarios especificar un cargador de clases principal.

¿Cómo se puede usar javax.tools.JavaCompiler desde un cargador de clases personalizado?

Por ejemplo:

  • cargas Ant MyParserTask
  • MyParserTask analiza Java código fuente
  • MyParserTask es cargado por AntClassLoader que los delegados a la classloader sistema
  • javax.tools.JavaCompiler es cargado por URLClassLoader thast delegados al sistema classloader

En un momento posterior, MyParserTask invoca:

javax.tools.CompilationTask task = compiler.getTask(...); 
com.sun.source.util.JavacTask javacTask = (com.sun.source.util.JavacTask) task; 
javacTask.parse().next().accept(visitor, unused); // parsing happens here 
  • ver cómo las dos clases residen en cargadores de clases separadas, no parece ser un camino para MyParserTask para interactuar con JavacTask sin conseguir ClassCastException errores.

¿Alguna idea?

Respuesta

0

Este problema ocurre con frecuencia con OSGi. Algunas personas han creado "cargadores de clase puente", ver por ejemplo this article (que probablemente solo conecta interfaces, no subclases, así que tal vez no puedas usarlo directamente).

Si hay sólo unos pocos métodos que desea invocar en el objeto "extraño", también se puede conseguir lejos con la reflexión:

javax.tools.CompilationTask task; 
task.getClass().getMethod("someMethodInTheSubclassThatICannotSee").invoke("a"); 

Partiendo de la idea de la reflexión, tal vez un lenguaje de script es útil, también (Groovy, Beanshell, JavaScript).

0

La respuesta simple es que la misma clase cargada por dos cargadores de clases diferentes es un tipo diferente y nunca los dos serán asignables cruzadamente. Eso es. Debes tener ambas clases para usar el mismo cargador de clases para obtener la clase compartida.

Esto normalmente sería el resultado de la violación del aplazamiento preventivo de la carga de clase a un elemento primario de ClassLoader. En pocas palabras, cualquier cargador de clase debe primero solicite a su padre cargar una clase antes de intentar cargarla. Hacer lo contrario da lugar a todo tipo de problemas "interesantes". En su ejemplo específico, ya que A invocó a B, era el cargador de clases de B que no pudo delegar en su padre, ya que si A puede ver la clase objetivo, el cargador de clases de B no necesitó cargarlo. B y, por lo tanto, el cargador de clases de A o B. cargado.

+0

Reescribí la pregunta para centrarme en CompilationTask. Por favor echa un vistazo. – Gili

2

Tuve exactamente el mismo problema.Estoy usando una tarea ant personalizada para escanear el AST para ciertos tipos de invocaciones de métodos. Mi solución, que puede no ser adecuada para usted, fue crear una instancia del compilador en lugar de utilizar el ToolProvider.

que sustituyen

JavaCompiler compiler = ToolProvider.getSystemJavaCompiler();

con

JavaCompiler compiler = (JavaCompiler)Class.forName("com.sun.tools.javac.api.JavacTool").newInstance();

Esto ciertamente no es a prueba del futuro o segura en todos los ambientes, pero es una opción en función de sus necesidades. Si alguien más tiene una mejor forma de utilizar el ToolProvider en las tareas Ant personalizadas, comparta.

0

Estaba teniendo problemas similares tuve que cargar las herramientas.jar Cuando descubrí que una subclase no se estaba cargando. detalles en este enlace https://stackoverflow.com/questions/14619179/webappclassloader-loadclass-cannot-find-class-at-runtime Como menciono esto puede no ser una buena solución ya que estamos tratando de jugar con la carga de clases a través de un programa. encontrado algunas notas útiles aquí también http://easternlights-wisdomtree.blogspot.in/2013/02/classloading-blues-part1.html

Cuestiones relacionadas