2012-03-18 11 views
6

Estoy trabajando en un proyecto de código abierto. A partir de ahora no tengo ninguna personalización en ninguna clase. Entonces, usando todos los archivos jar provistos por el proyecto opensource. Mi pregunta es si modifico un archivo java, lo compilo y lo empaqueté con la misma estructura de carpetas, ¿habrá algún problema al inicio del servidor o en el tiempo de ejecución? Si no, ¿qué archivo de clase se llamará (archivo predeterminado o mi archivo de clase Java personalizada)?¿Qué archivo de clase java se llamará si la misma clase está empaquetada en dos archivos jar?

+0

Creo que la JVM usará la clase del primer archivo jar que pueda encontrar en el classpath. Y una pregunta similar ha sido respondida hoy mismo "Cómo funciona JVM cuando se incluyen dos jar iguales en classpath" – sachinrahulsourav

+0

posible duplicado de [Cómo funciona JVM cuando dos mismos jar se incluyen en classpath] (http://stackoverflow.com/ preguntas/9757279/how-jvm-works-when-two-same-jar-be-included-in-classpath) –

Respuesta

10

De hecho, depende de muchos factores:

  • Si los dos archivos jar están en el mismo cargador de clases, por ejemplo, la ruta de clases de Java (-cp opción), normalmente debería ser el primer archivo encontrado en el frasco orden de la lista.

  • Si se implementa en un contenedor JavaEE, como en un archivo EAR o en WEB-INF/lib o un archivo WAR, no hay garantía de que el contenedor cargue la misma clase entre dos startups. En ese contexto, lo único seguro es que WEB-INF/classes se busca antes de WEB-INF/lib

  • en una jerarquía ClassLoader compleja, el comportamiento por defecto es la búsqueda de padres y primera pero las implementaciones JavaEE han introducido mecanismos como la política de padres y última (WebSphere) o filtrado gracias a los descriptores de despliegue (WebLogic)

Una opción puede ser la de declarar jar file dependencies en META-INF/MANIFEST.MF de archivos gracias al atributo Class-Path. Debe hacer cumplir una orden de carga en el nivel de ClassLoader, particularmente cuando se inicia con java -jar myapp.jar pero puede depender de implementaciones en un contexto de JavaEE.

Observación: Al utilizar un proyecto de OpenSource, puede ser justo enviar una solicitud de cambio y publicar los cambios o mejoras para que la comunidad se beneficie de ella. Entonces su proyecto puede actualizarse a la transmisión principal sin tanta dificultad de parches en su ClassPath.

+0

Como dijo Si ambos archivos jar están en el mismo ClassLoader, por ejemplo, el classpath de Java (opción -cp), normalmente debería ser el primer archivo encontrado en el orden de la lista jar. Pero nuevamente en el segundo punto, usted dijo que si es el caso con el archivo war desplegado en un contenedor web como tomcat, no se garantiza qué archivo de clase se llamará. ¿Es eso correcto? –

+0

Un punto más. Dijiste Una opción puede ser declarar dependencias de archivos jar en el archivo META-INF/MANIFEST.MF gracias al atributo Class-Path. Debe hacer cumplir una orden de carga en el nivel de ClassLoader pero puede depender de implementaciones en un contexto de JavaEE. Solo para confirmar que entiendo si la clase A está empaquetada en dos archivos jar J1 y J2. La clase A se llama desde la clase B (empaquetada en J3). Ahora, si queremos que se llame a la clase A del jar J2, entonces debemos mencionar esto en el archivo de jar J3. ¿Correcto? –

+0

Sí correcto. El manifiesto J3 debe contener la ruta de clase: j2.jar y el manifiesto J2 debe contener la ruta de clase: j1.jar. Por lo tanto, impone orden de carga primero: j3, luego j2, luego j1. Particularmente útil cuando está empaquetado con el atributo de clase principal. –

1

El cargador de clases está buscando el primer lugar donde se encuentra el recurso necesario. Significa que si la clase con el mismo nombre y paquete aparece en 2 jarras, se usará la primera encontrada. ¿Cuál es el primero? De acuerdo con la ruta de clases: si por ejemplo la clase A aparece en frascos one.jar y two.jar y la línea de comandos es:

java -cp one.jar;two.jar MyMain`

se utilizará la versión de one.jar. Pero si la línea de comandos es

java -cp two.jar;one.jar MyMain`

se creará una instancia de la clase two.jar.

+4

¿Tiene alguna referencia que indique que se trata de un comportamiento * especificado/documentado *? Estoy [no viendo uno] (http://stackoverflow.com/questions/9757279/how-jvm-works-when-swo-same-jar-be-included-in-classpath/9757720#9757720). –

+0

¿Qué sucede cuando es 'java -cp/src/lib/* MyMain' y el directorio lib contiene one.jar y two.jar? – enator

Cuestiones relacionadas