2010-01-05 23 views
5

Tengo un problema al descubrir los servicios proporcionados por algunos paquetes OSGi que no se están activando. Permítaseme describir la situación:No se puede encontrar el servicio porque el paquete OSGi no está activado

  • Bundle A define la interfaz X
  • Lotes B, C y D proporcionan servicios que implementa la interfaz X
    • servicios de estos paquetes están registrados a través de la primavera DM, por lo que solo se crean cuando el paquete está activado y Spring DM inicializó el contexto de la aplicación definido en el paquete
  • El paquete A está activado y en algún momento le pide al servicio de registro de servicios para la interfaz X. Doe no encuentra ninguno, porque los paquetes B, C y D no se han movido al estado ACTIVO (solo se RESUELVEN).

Parece que no puedo obtener los paquetes B, C o D para comenzar y, por lo tanto, registrar sus servicios. Obligarlos a comenzar agregándolos al config.ini no es una opción, porque puede haber cualquier cantidad de paquetes que estén instalados en la aplicación (a través de un mecanismo de actualización tipo P2 de Eclipse) que implementen la interfaz X.

La aplicación es una aplicación RCP basada en Eclipse 3.5, que utiliza Spring 2.5.6 y Spring DM 1.2.1.

¿Cómo fuerzo estos paquetes a activarse?

+0

¿Podría proporcionarnos alguna información sobre los mensajes de error que recibe? Y: Bundle A exporta la interfaz X, y Bundle B, C, D lo importan, ¿verdad? – akr

+0

Sí, la interfaz X se exporta mediante el paquete A, y se importa mediante B, C y D. No hay ningún mensaje de error. La consulta de servicios que implementan X en el registro de servicio simplemente devuelve una lista vacía. –

+0

¿Cuál es la cardinalidad que está solicitando en 'A'? Si es '1..N' tienes una dependencia circular. –

Respuesta

6

Lo que realmente tiene es un problema de jerarquía de dependencias, su solución hacky propuesta es realmente solo una curita sobre el problema subyacente.

Lo que realmente debe considerar es la arquitectura de su sistema, ya que efectivamente lo que tiene es una dependencia circular (ref: discusión en los comentarios de su publicación original). Tiene (le guste o no) A requiere servicios de (y en cierto sentido depende de) B y C. Mientras tanto, B y C dependen directamente de A, y como tal, no puede comenzar hasta que A aparece.

En el mejor de los casos, puede escribir el código en B y C para escuchar la existencia de A, pero esto como mucho enmascara (como mencioné) el problema subyacente. Lo que realmente debería considerar es dividir A en dos paquetes, llamémoslos A1 y A2.

A1 debe proporcionar la interfaz que B y C requieren (depende de). A2 debe tener oyentes para los servicios de los que dependen B y C. Al inicio, si B y C son servicios requeridos, A1 debe ejecutarse, pero A2 puede comenzar en cualquier momento posterior, y todo debería funcionar.

+0

Voy a probar tu sugerencia y ver qué pasa. ¡Gracias! –

0

Creo que he encontrado la solución a este problema, aunque se siente un poco hackish.

Me encontré con this thread donde Adrian Colyer dio a entender que un "observador de paquetes" externo podría ser responsable de activar paquetes cuando están instalados en el marco.

lo tanto, mi solución fue:

  • Agregar un encabezado personalizado para agrupar B, C y respectivos manifiestos de D's, por ejemplo, "MiApl-AutoStart: false"
  • Crear un oyente paquete que responde cuando un paquete se mueve en el estado resuelto y busca la cabecera
  • Si el valor de la cabecera es "verdadero", el oyente llama paquete bundle.start()

Usando este método, el Bundl es Quiero comenzar se inician sin tener que recurrir al uso de config.ini, y pueden entrar y salir cuando lo deseen, pero sus servicios están disponibles cuando se solicitan.

0

También eche un vistazo a la instalación de archivos felix, que mira un directorio de paquetes y los instala e inicia automáticamente. Cuando se elimina un archivo, el paquete se detiene y se desinstala también.

Cuestiones relacionadas