Foros del Web » Programación para mayores de 30 ;) » Java »

Problema introspeccion java

Estas en el tema de Problema introspeccion java en el foro de Java en Foros del Web. Muy buenas, recientemente he descubierto la posibilidad de utilizar introspeccion(api de reflection) en java. Pero me encuentro un error que no se como solucionar... Por ...
  #1 (permalink)  
Antiguo 23/05/2010, 08:22
 
Fecha de Ingreso: mayo-2010
Mensajes: 6
Antigüedad: 13 años, 11 meses
Puntos: 0
Problema introspeccion java

Muy buenas, recientemente he descubierto la posibilidad de utilizar introspeccion(api de reflection) en java. Pero me encuentro un error que no se como solucionar...


Por introspeccion recupero una clase:

Class clazz = Class.forName(nombreDeLaClase);

// obtengo la instancia a traves del ctor nulo
Object obj = clazz.newInstance();

// defino el Class[] con el que voy a indicar que el metodo que espero
// obtener recibe dos parametros de tipo int
Class cArgs1[] = { Integer.TYPE,Integer.TYPE };

// defino un array de argumentos. Al metodo le voy a pasar
// los argumentos: 300,300
Object oParams1[] = { new Integer(300), new Integer(300) };

// obtengo el metodo identificado por su nombre y un Class[]
Method mtd1 = clazz.getMethod(nombreMetodo,cArgs1);

// lo invoco sobre el objeto obj
mtd1.invoke(obj,oParams1);

Cuando ejecuto un ejemplo como el de arriba todo funciona correcto,
pero si los parametros del metodo que busco en lugar de ser integer o string o tipos primitivos es una clase que me he definido yo siempre obtengo el error:
NoSuchMethodException, y el metodo lo tengo bien definido.
Es mas he probado a sobrecargar ese mismo metodo y pasarle como parametro un String en lugar del objeto de una clase definida por mi y todo funciona correcto.

Por tanto mi problema es recuperar un metodo por introspección que tenga como argumento alguna instancia de alguna clase definida por mi.¿No se puede hacer esto en introspeccion?¿Algo que este haciendo mal?
Me estoy volviendo loco.....
  #2 (permalink)  
Antiguo 23/05/2010, 09:22
 
Fecha de Ingreso: octubre-2003
Mensajes: 3.578
Antigüedad: 20 años, 6 meses
Puntos: 51
Respuesta: Problema introspeccion java

Se puede recuperar cualquier método con cualquier argumento, así que algo debes estar haciendo mal.

S!
__________________
Para obtener respuestas, pregunta de forma inteligente o si no, pregunta lo que quieras que yo contestaré lo que me dé la gana.
  #3 (permalink)  
Antiguo 24/05/2010, 00:32
 
Fecha de Ingreso: mayo-2010
Mensajes: 6
Antigüedad: 13 años, 11 meses
Puntos: 0
De acuerdo Respuesta: Problema introspeccion java

Si tengo claro que algo estoy haciendo mal seguro. Os pongo el codigo que utilizo a ver si alguien me puede echar una mano:

Por un lado tengo la clase Mms:

package org.mms.implementacion;

public class Mms implements Imms {

public void sendMessage(Photo photo) {
// TODO Auto-generated method stub

System.out.println("sendMessage invoked");

}
}

que como veis tiene un metodo que se llama sendMessage que recibe como argumento un objeto de tipo Photo.

Por otro lado esta la clase Photo

package org.mms.implementacion;
public class Photo {

public Photo(){

}
}

que esta vacia y con un constructor por defecto nada mas.
Y este es el codigo donde intento invocar a sendMessage:


System.out.println("inicio de la prueba");
// cargaClaseClassPath me carga la clase que le indico en el claspath

Class claseCargada= lector.cargaClaseClassPath("org.mms.implementacion .Mms");
Class clasePhoto=lector.cargaClaseClassPath("org.mms.imp lementacion.Photo");
Object objetoPhoto=clasePhoto.newInstance();
Class cArgsSendMessage[]=new Class[]{clasePhoto};


Object objPhotoArray[]=new Object[]{objetoPhoto};

Method mtd1 = claseCargada.getMethod("sendMessage",cArgsSendMess age);

Y esto me da una NoSuchMethodException porque me dice que los parametros que yo le paso no coinciden con los parametros del metodo.
En cambio si sendMessage usara un String como parametro en lugar de un objeto Photo le pasaria como tipo de parametros esto cArgsSendMessage[]=new Class[]{String.class} y con esto me devolveria el metodo perfectamente.

¿Que es lo que puedo estar haciendo mal?
  #4 (permalink)  
Antiguo 24/05/2010, 00:55
 
Fecha de Ingreso: octubre-2003
Mensajes: 3.578
Antigüedad: 20 años, 6 meses
Puntos: 51
Respuesta: Problema introspeccion java

A mi me funciona, con el unico cambio de que en vez de cargaClaseClassPath uso Class.forName ya que la clase Lector no la tengo.
Cita:
Class claseCargada = Class.forName("test.Mms");
Class clasePhoto = Class.forName("test.Photo");
Object objetoCls = claseCargada.newInstance();
Object objetoPhoto = clasePhoto.newInstance();
Class cArgsSendMessage[] = new Class[]{clasePhoto};
Object objPhotoArray[] = new Object[]{objetoPhoto};
Method mtd1 = claseCargada.getMethod("sendMessage", cArgsSendMessage);
System.err.println("mtd1: " + mtd1.getName());
mtd1.invoke(objetoCls, objPhotoArray);
Me devuelve:
Cita:
mtd1: sendMessage
sendMessage invoked
__________________
Para obtener respuestas, pregunta de forma inteligente o si no, pregunta lo que quieras que yo contestaré lo que me dé la gana.
  #5 (permalink)  
Antiguo 24/05/2010, 01:37
 
Fecha de Ingreso: mayo-2010
Mensajes: 6
Antigüedad: 13 años, 11 meses
Puntos: 0
Respuesta: Problema introspeccion java

Hola , gracias por probarlo.
Te cuento....

Si yo hiciera directamente Class.forName("test.Mms") me daria un ClassNotFoundException porque al no tener la clase cargada en el classpath no sabria donde buscar. Por eso en la llamada cargaClaseClassPath la cargo en el classpath y de ahi ya la cojo directamente.

Si dices que a ti eso te funciona bien, quizas si hago:

las cargo primero en el classpath

lector.cargaClaseClassPath("org.mms.implementacion .Mms");
lector.cargaClaseClassPath("org.mms.imp lementacion.Photo");

y luego las defino como tu

Class claseCargada = Class.forName("test.Mms");
Class clasePhoto = Class.forName("test.Photo");

Voy a ver si lo pruebo y te cuento
  #6 (permalink)  
Antiguo 24/05/2010, 01:38
 
Fecha de Ingreso: mayo-2010
Mensajes: 6
Antigüedad: 13 años, 11 meses
Puntos: 0
Respuesta: Problema introspeccion java

Por que tu como solucionas el tema de cargar las clases dinamicamente en el casspath en funcion de la que necesites??

Un saludo
  #7 (permalink)  
Antiguo 24/05/2010, 03:52
 
Fecha de Ingreso: octubre-2003
Mensajes: 3.578
Antigüedad: 20 años, 6 meses
Puntos: 51
Respuesta: Problema introspeccion java

El tema de cargar clases dinámicamente en el classpath es algo que evito al máximo por que jugar con classloaders es mucho jugar y mientras pueda prefiero evitarlo . Ahora mismo no tengo ningún caso en que eso me haga falta ya que normalmente tengo todas en el classpath y e instancio la que hace falta, pero ya están todas.
Otros casos donde necesito definir clases dinámicamente lo soluciono con lenguajes de Scripting, como Groovy, y por último, en caso de tener que ponerme a cargar clases dinámicamente, supongo que tiraría por un modelo "sencillo" haciendo un URLClassLoader propio etc. o un modelo complejo usando OSGI.
El problema de los classloaders es que si intentas usar una clase desde un classloader diferente del que se cargo, y sin relacion padre-hijo entre ellos, puede que te la cargue otra vez (si está en el classpath) y te diga que las clases no son iguales. O que te diga ClassNotFound si no está en el classpath.
Además si no liberas bien las referencias es un caso habitual de Memory Leaks etc.

Por eso lo evito .

Creo que el problema debe estar en la forma en que se cargan las clases y como reflection intenta saber que clases se usan, ya que debe cargarlas por otro lado y por eso te dice que no coinciden.

S!
__________________
Para obtener respuestas, pregunta de forma inteligente o si no, pregunta lo que quieras que yo contestaré lo que me dé la gana.
  #8 (permalink)  
Antiguo 24/05/2010, 04:06
 
Fecha de Ingreso: mayo-2010
Mensajes: 6
Antigüedad: 13 años, 11 meses
Puntos: 0
Respuesta: Problema introspeccion java

Pues seguramente el problema este en el classLoader, ahora no tengo a mano el metodo que me carga las clases en classLoader poruqe no tengo a mano la maquina donde lo hago. A ver si luego te lo pongo y me dices que te parece, es que el tema de cargar clases dinamicamente al classpath lo voy a tener que utilizar si o si, porque en tiempo de compilacion no se porque clases me van a preguntar y entonces en tiempo de ejecucion las tengo que ir cargando al vuelo para evitar los classNotFoundException.
  #9 (permalink)  
Antiguo 24/05/2010, 06:38
 
Fecha de Ingreso: octubre-2003
Mensajes: 3.578
Antigüedad: 20 años, 6 meses
Puntos: 51
Respuesta: Problema introspeccion java

Si luego las vas a tener en el classpath, aunque en tiempo de compilación no sepas cuales son no importa. Lo que importa es si vas a tener que poder añadir clases nuevas en tiempo de ejecución sin reiniciar la JVM. Ese caso es el más complejo, para el resto no hace falta meterse en complicaciones de ClassLoaders.

S!
__________________
Para obtener respuestas, pregunta de forma inteligente o si no, pregunta lo que quieras que yo contestaré lo que me dé la gana.
  #10 (permalink)  
Antiguo 24/05/2010, 06:41
 
Fecha de Ingreso: mayo-2010
Mensajes: 6
Antigüedad: 13 años, 11 meses
Puntos: 0
Respuesta: Problema introspeccion java

Este el metodo que utilizo para cargar clases dinamicamente:


public Class cargaClaseClassPath(String clase){

try{
System.out.println("clase classpath"+clase);
String repositorio="E:\\alberto\\PFC\\bundlesEquinox\\plu gins\\";
String terminacion="_1.0.0.jar";
String[] campos=clase.split("\\.");
String ruta=repositorio+campos[1]+terminacion;
File miClass = new File(ruta);
URL[] urls = new URL [] {miClass.toURL() };

ClassLoader loader = this.getClass().getClassLoader();
URLClassLoader nuevoLoader = new URLClassLoader (urls,loader);
Class claseResultado = nuevoLoader .loadClass(clase);


return claseResultado;
}catch(Exception e){
System.err.println(e);
return null;
}

}

que por que me comentas el problema va a estar aqui seguro.
Se te ocurre alguna buena manera de cargar clases de manera dinamica con el classLoader que pueda estar mas correcto que mi metodo "chapucilla"?¿?¿
  #11 (permalink)  
Antiguo 25/05/2010, 00:37
 
Fecha de Ingreso: octubre-2003
Mensajes: 3.578
Antigüedad: 20 años, 6 meses
Puntos: 51
Respuesta: Problema introspeccion java

Ya te he dicho que no he jugueteado mucho con los classloaders y por eso no tengo información concreta sobre este tipo de problemas.

Una opción para no tener que usar reflection es usar una interfaz que deben implementar tus clases, y ejecutar los metodos a través de dicha interfaz.

PD: Equinox.... ¿OSGi? ¿Por que no usar OSGi directamente?
__________________
Para obtener respuestas, pregunta de forma inteligente o si no, pregunta lo que quieras que yo contestaré lo que me dé la gana.

Etiquetas: Ninguno
Atención: Estás leyendo un tema que no tiene actividad desde hace más de 6 MESES, te recomendamos abrir un Nuevo tema en lugar de responder al actual.
Respuesta




La zona horaria es GMT -6. Ahora son las 21:57.