OSGi


  Óliver Centeno
Modularidad

   División lógica
   Partes independientes
   Oculta clases de implementación
Modularidad

   Visibilidad-Empaquetamiento
   Interfaces publicadas
   Dependencias externas entre módulos
Modularidad

   OOP
   Paquetes/Librerías
   Cohesion
   Acoplamiento
   División del trabajo
   Abstracción
   Reutilización
   Mantenimiento
Modularidad

   Ejemplo:
       Sistema de gestión de películas
Ficheros JAR

   ¿Son módulos?
   Classpath compartido
   No restringible
   No admite versiones
   No hay dependencias
   Condicionado por el orden
   Problemas de visibilidad
   …
Inversión del Control

   Contenedor
   Control de las dependencias
   Classpath específico de cada JAR
   Gestionar las Clases compartidas
Bundle

   Fichero JAR
   Código
   Recursos
   Metadata

   Módulo
   META-INF/MANIFEST.MF
Bundle

   Implica modularidad física de Clases
   Implica unidades de despliegue
   Permite restringir el acceso externo a Clases
¿Qué es OSGi?

   Open Service Gateway initiative
   Plataforma de Servicios
       OSGi Framework
       OSGi Standart Services


   OSGi Alliance (www.osgi.org)
   Versión 4
¿Qué es OSGi?

   OSGi Framework
       Entorno de ejecución Java
       Portable y seguro
       Gestor de servicios
       Sistema de módulos
       Escalable y ligero
       Dinámicamente instalables y actualizables
¿Qué es OSGi?
¿Qué es OSGi?

   Implementaciones

       Apache Felix (http://felix.apache.org)

       Eclipse Equinox (www.eclipse.org/equinox)

       Knopflerfish (www.knopflerfish.org)
¿Qué es OSGi?

   Eclipse Equinox (www.eclipse.org/equinox)
       Muy ligero
           java –jar org.eclipse.osgi_3.8.0.v20120529-1548.jar
                   –console
       Integrado en Eclipse
           Run Configurations > OSGi Framework
¿Qué es OSGi?

   Apache Felix (http://felix.apache.org)
       Ligero
       Intérprete de Comandos Gogo
       No integrado con Eclipse
       Configurable con Pax Runner
           http://www.ops4j.org/pax/eclipse/update/
           Entorno de ejecución embebido
           Run Configurations > OSGi Framework
           Entorno Felix v2.0.1
¿Qué es OSGi?

   Knopflerfish (www.knopflerfish.org)
       Robusto
       Interfaz gráfica
           java –jar framework.jar
       Plugin para Eclipse
       http://www.knopflerfish.org/eclipse-update/
¿Qué es OSGi?

   Conceptual Layers
       Module
       Lifecycle
       Service
Module Layer
   package curso.ejemplo;

   public class Saludo {
     static Saludo instance;
     final String nombre;

       public Saludo(String nombre) {
         this.nombre = nombre;
       }
       public static Saludo get() {
         return instance;
       }
       public void saludar() {
         System.out.println("Hola, " + nombre + "!");
       }
   }
Lifecycle Layer
   package curso.ejemplo;
   import org.osgi.framework.BundleActivator;
   import org.osgi.framework.BundleContext;

   public class Activator implements BundleActivator {

       public void start(BundleContext ctx) {
         Saludo.instance = new Saludo("lifecycle");
       }

       public void stop(BundleContext ctx) {
         Saludo.instance = null;
       }
   }
Service Layer
   package curso.ejemplo;

   import org.osgi.framework.BundleActivator;
   import org.osgi.framework.BundleContext;

   public class ServicioActivator
          implements BundleActivator {

       public void start(BundleContext ctx) {
         ctx.registerService(Saludo.class.getName(),
                  new Saludo("servicio"), null);
       }

       public void stop(BundleContext ctx) {}
   }
Cliente
   package curso.ejemplo;
   import org.osgi.framework.BundleActivator;
   import org.osgi.framework.BundleContext;
   import org.osgi.framework.ServiceReference;

   public class Cliente implements BundleActivator {

     public void start(BundleContext ctx) {
       ServiceReference ref = ctx.getServiceReference(
                                    Saludo.class.
   getName());
       ((Saludo) ctx.getService(ref)).saludar();
     }

       public void stop(BundleContext ctx) {}
   }
Tecnologías relacionadas

   RMI
       Proveedor
       Cliente
       Registro
       Multi-proceso
       No modular
Tecnologías relacionadas

   Spring
       Contenedor ligero
       Inyección de dependencias
       Sin módulos dinámicos
       Portando infraestructura a OSGi
Tecnologías relacionadas

   JSR
       JSR 277: Java Module System
           Propuesta de Sun alternativa a OSGi
       JSR 291: Dynamic Component Support for Java
           Mejora apoyada en OSGi
       JSR 294: Improved Modularity Support
           Intento de mejorar la visibilidad de módulos
Tecnologías relacionadas

   Service Component Architecture
       Modelo de componentes para SOA
       Integra BPEL, SOAP, JMS, JCA,..
       No define formato de módulos
¿Cómo funciona?

   MANIFEST.MF
       Formato “nombre: valor”
       Admite atributos y directivas
       Máximo 72 caracteres/línea

       Información legible
       Identificación del bundle
       Visibilidad externa del código (paquetes)
       Dependencias de paquetes
¿Cómo funciona?

   MANIFEST.MF
    Bundle-Name: Nombre descriptivo
    Bundle-SymbolicName: id.del.bundle
    Bundle-Version: 1.0.0.build-38
    Bundle-ManifestVersion: 2

    Export-Package: curso.ejemplo;version=1.0.0
    Import-Package: org.osgi.framework;version=[1.3,2.0)

    Bundle-ClassPath: .,imagenes/,embedded.jar
¿Cómo funciona?

   Ejemplo
¿Cómo funciona?

   Resolución de dependencias
¿Cómo funciona?

   Resolución de dependencias
       Transitiva
       Restringida en importación
           vendor
           version
           …
       Prioridad a la versión
       Prioridad a la instalación
       Prioridad a la resolución
¿Cómo funciona?

   Resolución de dependencias
       Directiva uses
           Restringe las importaciones de los clientes
            Export-Package: org.osgi.service.http;
             uses:="javax.servlet"
            Import-Package: javax.servlet; version=2.3.0
Ejercicio

   Desplegar un bundle
    public class Dao {
        public void sql(String message) {
           System.out.println(message + " v1");
        }
    }
   Un cliente del bundle y su activador
    public class Cliente {
        public void listar() {
           new Dao().sql("SELECT * FROM Tabla");
        }
    }
Ejercicio

   Crear una nueva versión del bundle
    public class Dao {
        public void sql(String message) {
           System.out.println(message + " v2");
        }
    }
   Desplegar y refrescar el bundle y su cliente
   Modificar la interfaz del bundle
   Restringir la versión máxima del cliente
Ejercicio

   Crear una nueva versión del cliente
   Ejecutarla con la 1.0 en ejecución
   Restringirla al bundle 1.1
   Ejecutar cliente y bundle 1.0
   Ejecutar cliente y bundle 1.1
   Refrescar cliente 1.0
Ciclo de Vida

   El Framework OSGi controla el ciclo de vida
    de los bundle
       install
       update
       start
       stop
       uninstall
Interacción con el Lifecycle

   Lifecycle Layer gestiona los bundles
   Resolviendo dependencias
   Permitiendo
       install
       update
       uninstall
       start
       stop
BundleActivator

   Interfaz de control del ciclo de vida
   Implementar y referenciar en el manifest.mf
   Métodos start y stop de retorno rápido
   Acceso al contexto del bundle
       BundleContext
       Instalar/desinstalar bundles
       Obtener todos o uno por id
       …
Eventos

   BundleListener
       Recibe eventos de los bundles
       bundleChanged()
       BundleEvent
             INSTALLED
             RESOLVED
             STARTED
             STOPED
             UPDATED
             UNINSTALLED
             UNRESOLVED
Eventos

   FrameworkListener
       Recibe eventos de OSGi
       FrameworkEvent
             STARTED
             INFO
             WARNING
             ERROR
             STARTLEVEL_CHANGED
             PACKAGES_REFRESHED
Eventos

   SynchronousBundleListener
       Recibe eventos antes que BundleListener
       bundleChanged()
       BundleEvent
             STARTING
             STOPING
Eventos

   Se registran contra el BundleContext
   Método addListener()
   Se eliminan mediante
       removeBundleListener()
       removeFrameworkListener()
Ejercicio

   Crear un observador de eventos
   Que muestre mensajes del bundle y el
    evento implicados
   Recargar los bundles
   Desinstalar 1.1
   Refrescar cliente 1.1
Servicios

   Interfaz
       java.lang.Class


   Implementación

   Service Properties
Servicios

   Service Registry
       Registrar
       Desregistrar
       Recuperar
       Librerar
Servicios

   Service Properties
       Predefinidas (Constants)
       Personalizadas
Filtros LDAP

   Formato ()
       & | ! Prefijos
       Ejemplos
           (name=John Smith)
           (age>=20)
           (name~=johnsmith)
           (&(name=John Smith)(occupation=doctor))
           (|(name~=John Smith)(name~=Smith John))
           (name=Jo*n*Smith*)
Ejercicio

   Convertir en Servicio
       Crear una interfaz Dao
       Crear una implementación en distinto paquete
       Se exportará el de la interfaz
       No se exportará el de la implementación
       Crear un Activador que registre la implementación
       Y desregistre en el stop
Ejercicio

   Crear un consumidor
       Crear un Thread implementando Runnable
       Que utilice la interfaz
    void start() {     public void run() {
      stop = false;      while (!stop) {
      new Thread(this)     printer.print("Hola...");
           .start();       try {
    }                         Thread.sleep(TWO_SECS);
                           } catch (InterruptedException e) {
    void stop(){              stop = true;
      stop = true;         }
    }                    }
                       }
Ejercicio

   Crear un activador del consumidor
       Que instancie el cliente
       Que busque el servicio
           getServiceReference()
           getService()
       Castear a la interfaz de servicio
       Arrancar el Consumidor
       Detenerlo en el stop
ServiceFactory

   Instanciación de servicios
   Registrarla en lugar del servicio
   Métodos getService() y ungetService()
   Permite implementar patrones creacionales
   Y modificar el ciclo de vida
ServiceListener

   Eventos de Servicio
       ServiceEvent
               REGISTERED
               UNREGISTERED
               MODIFIED
       context.addServiceListener()
           Filter="(objectClass=" + IDao.class.getName() + ")"
           Filtro formato LDAP
Consejos y trucos

   Mantener los paquetes privados
   Si SOLO se va a usar desde un bundle
       Incluir la librería en éste   META-INF/MANIFEST.MF
                                      lib/mylegacy.jar
       Bundle-Classpath              manning/osgi/MyClass.class
                                      Bundle-ClassPath: .,lib

   Si se va a usar desde más bundles
       Crear un bundle propio y referenciarlo
Consejos y trucos

   Evitar los bundles requeridos
       Ven todos los Exported-Packages del requerido
       Incluso de manera transitiva
        Bundle-SymbolicName: B1
        Require-Bundle: B2; visibility:=reexport


   Restringir las clases exportadas
       Directivas include y exclude de Export-Package
        Export-Package: manning.osgi.test;
         include:="Foo*, Bar"; exclude:=FooImpl
Consejos y trucos

   Desacoplar Bundles mediante servicios
       Importar únicamente interfaces
       Publicar Bundle-implementaciones
       Mediante su propio Activador
       Restringir la resolución del consumidor con
        propiedades
             md4Properties.put("PERFORMANCE", "FAST");
Consejos y trucos

    Desacoplar Bundles mediante servicios
        Usar filtros para restringir por propiedades
    String filter =
        "(&(objectClass=" + Servicio.class.getName() + ")" +
        "(PERFORMANCE=FAST))";

        Usar la Propiedad de ranking para priorizar
         md5Properties.put(Constants.SERVICE_RANKING, 10);

        Usar la Propiedad de PID para identificar
         servicios de manera unívoca
         properties.put(Constants.SERVICE_PID, "10.0.0.1");
Consejos y trucos

   Uso de fragmentos
       Bundles degenerados
       Se resuelven después del Bundle Host
       Pero deben instalarse antes que éste
       No pueden tener Activador
       Permiten aumentar el manifiesto
           Añadir un Import-Package propio

        Fragment-Host: symbolic-name-del-host-bundle
Consejos y trucos

   Carga dinámica de bundles
       Por ej.: Acceso a BBDD con reflexión
       DynamicImport-Package
           Último recurso de resolución que admite *
           Se carga en ejecución, no en resolución
            DynamicImport-Package: org.apache.derby.jdbc

       Paquetes opcionales
            Import-Package: x.y.z;resolution:=optional
Consejos y trucos

   Acceso a detalles del bundle
       OSGi 4.3 tiene un Wiring Framework
        BundleRevision revision =
            bundle.adapt(BundleRevision.class);

        List<BundleCapability> exportPackage =
            revision.getDeclaredCapabilities(
               BundleRevision.PACKAGE_NAMESPACE);

        List<BundleRequirement> importPackage =
            revision.getDeclaredRequirements(
               BundleRevision.PACKAGE_NAMESPACE);
Consejos y trucos

   Acceso a detalles del bundle
       OSGi 4.3 tiene un Wiring Framework
       Recorrer detalles de especificación
        for (BundleCapability capability : capabilities) {
            Map<String, Object> attributes =
               capability.getAttributes();
            System.out.println(
               attributes.get("osgi.wiring.package") +
               " version " + attributes.get("version")
            );
        }
Consejos y trucos

   Acceso a detalles del bundle
       OSGi 4.3 tiene un Wiring Framework
       Obtener enlaces/resoluciones en ejecución
        List<BundleWire> providedWires =
            revision.getWiring().getProvidedWires(
               BundleRevision.PACKAGE_NAMESPACE);

        for (BundleWire bundleWire : providedWires) {
             Bundle cliente =
                bundleWire.getRequirerWiring().getBundle();
             Bundle proveedor =
                bundleWire.getProviderWiring().getBundle();
         }
Servicios Remotos

   Configurar propiedades del servicio
   Exportar interfaces remotas
   Añadir Bundle de comunicación
        install http://repo1.maven.org/maven2/org/osgi/org.osgi.
         compendium/4.2.0/org.osgi.compendium-4.2.0.jar
        install http://www.apache.org/dist/cxf/dosgi/1.2/cxf-dosgi-
         ri-singlebundle-distribution-1.2.jar
Servicios Remotos

   Propiedades para acceso remoto
       service.exported.interfaces
       service.exported.configs
           org.apache.cxf.ws
           ws


       org.apache.cxf.ws.address
       SOAP.service.name
       …
Clientes Remotos

   Bundle de comunicación
   Clase ServiceTracker
       Equivalente al ServiceReference
       Método open() para iniciar el tracking
       Método addingService() al encontrar servicios
   Fichero XML de endpoints
       OSGI-INF/remote-services/remote-services.xml
Clientes Remotos

   Service Tracker
       Clase asociada al contexto y a la interfaz
       open() y close() registran Listeners internos
       Instanciarlo en un Activador
       Ejecutar el open() en start()
       Invocar a getService()
       Admite ServiceTrackerCustomizer
           Eventos del servicio
           addingService() y removedService()
Clientes Remotos

   Fichero de endpoints
<endpoint-descriptions xmlns="http://www.osgi.org/xmlns/rsa/v1.0.0">
 <endpoint-description>
  <property name="objectClass">
   <array>
    <value>servicio.wsdl.GreeterService</value>
   </array>
  </property>
  <property name="endpoint.id">http://localhost:9090/greeter</property>
  <property name="service.imported.configs">org.apache.cxf.ws</property>
 </endpoint-description>
</endpoint-descriptions>
Clientes Remotos

   Fichero de configuración
       OSGI-INF/cxf/intents/intent-map.xml
        <beans>
          <bean id="intentMap" class="org.apache.cxf.dosgi.dsw.qos.IntentMap">
            <property name="intents"><map>
              <entry key="reliability" value-ref="reliableMessaging"/>
              <entry key="decoupled" value-ref="decoupledAddressing"/>
            </map></property>
          </bean>

          <p:policies id="reliableMessaging">…</p:policies>
          <p:policies id="decoupledAddressing">…</p:policies>
          <wsp:Policy wsu:Id="ReliabilityPolicy">…</wsp:Policy>
          <wsp:Policy wsu:Id="DecoupledPolicy">…</wsp:Policy>
          <wsp:Policy wsu:Id="AddressingPolicy">…</wsp:Policy>
        </beans>
OSGi y J2EE

   2 opciones

       Embeber un servidor ligero en OSGi (Jetty)
           Práctico en fase de desarrollo


       Embeber OSGi en una aplicación Web
           Eficiente en fase de despliegue
OSGi y J2EE

   Crear un bundle con su activador
   Crear un Servlet
   Crear un directorio para las páginas Web
   Extender ServiceTracker
       Obtener el servicio HttpService de contexto
       Registrar recursos y servlets
       Liberarlos en removedService()
   Instanciarlo, abrirlo y cerrarlo en el activador
OSGi y J2EE

   Equinox tiene un bridge.war
       http://www.eclipse.
        org/equinox/server/http_in_container.php
       Plantilla de AppWeb con contexto /sp_test
       Con un OSGi embebido en la consola Tomcat
       BridgeServlet que hace de FrontController
   Desplegar los bundle web en
       WEB-INFEclipseplugins
   Y arrancarlos desde consola
Depuración

   Arrancar el framework en modo remoto
    java –Xdebug -Xrunjdwp:transport=
           dt_socket,address=8787,server=y,suspend=n
         -jar framework.jar

       Suspend indica que se pare en arranque
   Crear un Debug Configuration en Eclipse
       Remote Java Application
       Indicar el puerto
       Poner los puntos de ruptura y ejecutar OSGi
Eclipse Plugins

   Formato de bundle especial
   Con un activador estandart: AbstractUIPlugin
       Métodos getDefault() y getImageDescriptor()
   Configurado mediante plugin.xml
       Extensiones de la interfaz de Eclipse
       Views, ayuda contextual, menús,…
Eclipse Plugins

   Ejemplo
       Plugin con Custom Templates
       Seleccionar Popup Menu y View
       Asociar el Popup con org.eclipse.ui.IEditorInput
       Configurar la categoría de la vista
       Finish
       Añadir más opciones al menú
           Invocarán al método run() de la clase asociada

OSGi

  • 1.
    OSGi ÓliverCenteno
  • 2.
    Modularidad  División lógica  Partes independientes  Oculta clases de implementación
  • 3.
    Modularidad  Visibilidad-Empaquetamiento  Interfaces publicadas  Dependencias externas entre módulos
  • 4.
    Modularidad  OOP  Paquetes/Librerías  Cohesion  Acoplamiento  División del trabajo  Abstracción  Reutilización  Mantenimiento
  • 5.
    Modularidad  Ejemplo:  Sistema de gestión de películas
  • 6.
    Ficheros JAR  ¿Son módulos?  Classpath compartido  No restringible  No admite versiones  No hay dependencias  Condicionado por el orden  Problemas de visibilidad  …
  • 7.
    Inversión del Control  Contenedor  Control de las dependencias  Classpath específico de cada JAR  Gestionar las Clases compartidas
  • 8.
    Bundle  Fichero JAR  Código  Recursos  Metadata  Módulo  META-INF/MANIFEST.MF
  • 9.
    Bundle  Implica modularidad física de Clases  Implica unidades de despliegue  Permite restringir el acceso externo a Clases
  • 10.
    ¿Qué es OSGi?  Open Service Gateway initiative  Plataforma de Servicios  OSGi Framework  OSGi Standart Services  OSGi Alliance (www.osgi.org)  Versión 4
  • 11.
    ¿Qué es OSGi?  OSGi Framework  Entorno de ejecución Java  Portable y seguro  Gestor de servicios  Sistema de módulos  Escalable y ligero  Dinámicamente instalables y actualizables
  • 12.
  • 13.
    ¿Qué es OSGi?  Implementaciones  Apache Felix (http://felix.apache.org)  Eclipse Equinox (www.eclipse.org/equinox)  Knopflerfish (www.knopflerfish.org)
  • 14.
    ¿Qué es OSGi?  Eclipse Equinox (www.eclipse.org/equinox)  Muy ligero  java –jar org.eclipse.osgi_3.8.0.v20120529-1548.jar –console  Integrado en Eclipse  Run Configurations > OSGi Framework
  • 15.
    ¿Qué es OSGi?  Apache Felix (http://felix.apache.org)  Ligero  Intérprete de Comandos Gogo  No integrado con Eclipse  Configurable con Pax Runner  http://www.ops4j.org/pax/eclipse/update/  Entorno de ejecución embebido  Run Configurations > OSGi Framework  Entorno Felix v2.0.1
  • 16.
    ¿Qué es OSGi?  Knopflerfish (www.knopflerfish.org)  Robusto  Interfaz gráfica  java –jar framework.jar  Plugin para Eclipse  http://www.knopflerfish.org/eclipse-update/
  • 17.
    ¿Qué es OSGi?  Conceptual Layers  Module  Lifecycle  Service
  • 18.
    Module Layer package curso.ejemplo; public class Saludo { static Saludo instance; final String nombre; public Saludo(String nombre) { this.nombre = nombre; } public static Saludo get() { return instance; } public void saludar() { System.out.println("Hola, " + nombre + "!"); } }
  • 19.
    Lifecycle Layer package curso.ejemplo; import org.osgi.framework.BundleActivator; import org.osgi.framework.BundleContext; public class Activator implements BundleActivator { public void start(BundleContext ctx) { Saludo.instance = new Saludo("lifecycle"); } public void stop(BundleContext ctx) { Saludo.instance = null; } }
  • 20.
    Service Layer package curso.ejemplo; import org.osgi.framework.BundleActivator; import org.osgi.framework.BundleContext; public class ServicioActivator implements BundleActivator { public void start(BundleContext ctx) { ctx.registerService(Saludo.class.getName(), new Saludo("servicio"), null); } public void stop(BundleContext ctx) {} }
  • 21.
    Cliente package curso.ejemplo; import org.osgi.framework.BundleActivator; import org.osgi.framework.BundleContext; import org.osgi.framework.ServiceReference; public class Cliente implements BundleActivator { public void start(BundleContext ctx) { ServiceReference ref = ctx.getServiceReference( Saludo.class. getName()); ((Saludo) ctx.getService(ref)).saludar(); } public void stop(BundleContext ctx) {} }
  • 22.
    Tecnologías relacionadas  RMI  Proveedor  Cliente  Registro  Multi-proceso  No modular
  • 23.
    Tecnologías relacionadas  Spring  Contenedor ligero  Inyección de dependencias  Sin módulos dinámicos  Portando infraestructura a OSGi
  • 24.
    Tecnologías relacionadas  JSR  JSR 277: Java Module System  Propuesta de Sun alternativa a OSGi  JSR 291: Dynamic Component Support for Java  Mejora apoyada en OSGi  JSR 294: Improved Modularity Support  Intento de mejorar la visibilidad de módulos
  • 25.
    Tecnologías relacionadas  Service Component Architecture  Modelo de componentes para SOA  Integra BPEL, SOAP, JMS, JCA,..  No define formato de módulos
  • 26.
    ¿Cómo funciona?  MANIFEST.MF  Formato “nombre: valor”  Admite atributos y directivas  Máximo 72 caracteres/línea  Información legible  Identificación del bundle  Visibilidad externa del código (paquetes)  Dependencias de paquetes
  • 27.
    ¿Cómo funciona?  MANIFEST.MF Bundle-Name: Nombre descriptivo Bundle-SymbolicName: id.del.bundle Bundle-Version: 1.0.0.build-38 Bundle-ManifestVersion: 2 Export-Package: curso.ejemplo;version=1.0.0 Import-Package: org.osgi.framework;version=[1.3,2.0) Bundle-ClassPath: .,imagenes/,embedded.jar
  • 28.
  • 29.
    ¿Cómo funciona?  Resolución de dependencias
  • 30.
    ¿Cómo funciona?  Resolución de dependencias  Transitiva  Restringida en importación  vendor  version  …  Prioridad a la versión  Prioridad a la instalación  Prioridad a la resolución
  • 31.
    ¿Cómo funciona?  Resolución de dependencias  Directiva uses  Restringe las importaciones de los clientes Export-Package: org.osgi.service.http; uses:="javax.servlet" Import-Package: javax.servlet; version=2.3.0
  • 32.
    Ejercicio  Desplegar un bundle public class Dao { public void sql(String message) { System.out.println(message + " v1"); } }  Un cliente del bundle y su activador public class Cliente { public void listar() { new Dao().sql("SELECT * FROM Tabla"); } }
  • 33.
    Ejercicio  Crear una nueva versión del bundle public class Dao { public void sql(String message) { System.out.println(message + " v2"); } }  Desplegar y refrescar el bundle y su cliente  Modificar la interfaz del bundle  Restringir la versión máxima del cliente
  • 34.
    Ejercicio  Crear una nueva versión del cliente  Ejecutarla con la 1.0 en ejecución  Restringirla al bundle 1.1  Ejecutar cliente y bundle 1.0  Ejecutar cliente y bundle 1.1  Refrescar cliente 1.0
  • 35.
    Ciclo de Vida  El Framework OSGi controla el ciclo de vida de los bundle  install  update  start  stop  uninstall
  • 36.
    Interacción con elLifecycle  Lifecycle Layer gestiona los bundles  Resolviendo dependencias  Permitiendo  install  update  uninstall  start  stop
  • 37.
    BundleActivator  Interfaz de control del ciclo de vida  Implementar y referenciar en el manifest.mf  Métodos start y stop de retorno rápido  Acceso al contexto del bundle  BundleContext  Instalar/desinstalar bundles  Obtener todos o uno por id  …
  • 38.
    Eventos  BundleListener  Recibe eventos de los bundles  bundleChanged()  BundleEvent  INSTALLED  RESOLVED  STARTED  STOPED  UPDATED  UNINSTALLED  UNRESOLVED
  • 39.
    Eventos  FrameworkListener  Recibe eventos de OSGi  FrameworkEvent  STARTED  INFO  WARNING  ERROR  STARTLEVEL_CHANGED  PACKAGES_REFRESHED
  • 40.
    Eventos  SynchronousBundleListener  Recibe eventos antes que BundleListener  bundleChanged()  BundleEvent  STARTING  STOPING
  • 41.
    Eventos  Se registran contra el BundleContext  Método addListener()  Se eliminan mediante  removeBundleListener()  removeFrameworkListener()
  • 42.
    Ejercicio  Crear un observador de eventos  Que muestre mensajes del bundle y el evento implicados  Recargar los bundles  Desinstalar 1.1  Refrescar cliente 1.1
  • 43.
    Servicios  Interfaz  java.lang.Class  Implementación  Service Properties
  • 44.
    Servicios  Service Registry  Registrar  Desregistrar  Recuperar  Librerar
  • 45.
    Servicios  Service Properties  Predefinidas (Constants)  Personalizadas
  • 46.
    Filtros LDAP  Formato ()  & | ! Prefijos  Ejemplos  (name=John Smith)  (age>=20)  (name~=johnsmith)  (&(name=John Smith)(occupation=doctor))  (|(name~=John Smith)(name~=Smith John))  (name=Jo*n*Smith*)
  • 47.
    Ejercicio  Convertir en Servicio  Crear una interfaz Dao  Crear una implementación en distinto paquete  Se exportará el de la interfaz  No se exportará el de la implementación  Crear un Activador que registre la implementación  Y desregistre en el stop
  • 48.
    Ejercicio  Crear un consumidor  Crear un Thread implementando Runnable  Que utilice la interfaz void start() { public void run() { stop = false; while (!stop) { new Thread(this) printer.print("Hola..."); .start(); try { } Thread.sleep(TWO_SECS); } catch (InterruptedException e) { void stop(){ stop = true; stop = true; } } } }
  • 49.
    Ejercicio  Crear un activador del consumidor  Que instancie el cliente  Que busque el servicio  getServiceReference()  getService()  Castear a la interfaz de servicio  Arrancar el Consumidor  Detenerlo en el stop
  • 50.
    ServiceFactory  Instanciación de servicios  Registrarla en lugar del servicio  Métodos getService() y ungetService()  Permite implementar patrones creacionales  Y modificar el ciclo de vida
  • 51.
    ServiceListener  Eventos de Servicio  ServiceEvent  REGISTERED  UNREGISTERED  MODIFIED  context.addServiceListener()  Filter="(objectClass=" + IDao.class.getName() + ")"  Filtro formato LDAP
  • 52.
    Consejos y trucos  Mantener los paquetes privados  Si SOLO se va a usar desde un bundle  Incluir la librería en éste META-INF/MANIFEST.MF lib/mylegacy.jar  Bundle-Classpath manning/osgi/MyClass.class Bundle-ClassPath: .,lib  Si se va a usar desde más bundles  Crear un bundle propio y referenciarlo
  • 53.
    Consejos y trucos  Evitar los bundles requeridos  Ven todos los Exported-Packages del requerido  Incluso de manera transitiva Bundle-SymbolicName: B1 Require-Bundle: B2; visibility:=reexport  Restringir las clases exportadas  Directivas include y exclude de Export-Package Export-Package: manning.osgi.test; include:="Foo*, Bar"; exclude:=FooImpl
  • 54.
    Consejos y trucos  Desacoplar Bundles mediante servicios  Importar únicamente interfaces  Publicar Bundle-implementaciones  Mediante su propio Activador  Restringir la resolución del consumidor con propiedades md4Properties.put("PERFORMANCE", "FAST");
  • 55.
    Consejos y trucos  Desacoplar Bundles mediante servicios  Usar filtros para restringir por propiedades String filter = "(&(objectClass=" + Servicio.class.getName() + ")" + "(PERFORMANCE=FAST))";  Usar la Propiedad de ranking para priorizar md5Properties.put(Constants.SERVICE_RANKING, 10);  Usar la Propiedad de PID para identificar servicios de manera unívoca properties.put(Constants.SERVICE_PID, "10.0.0.1");
  • 56.
    Consejos y trucos  Uso de fragmentos  Bundles degenerados  Se resuelven después del Bundle Host  Pero deben instalarse antes que éste  No pueden tener Activador  Permiten aumentar el manifiesto  Añadir un Import-Package propio Fragment-Host: symbolic-name-del-host-bundle
  • 57.
    Consejos y trucos  Carga dinámica de bundles  Por ej.: Acceso a BBDD con reflexión  DynamicImport-Package  Último recurso de resolución que admite *  Se carga en ejecución, no en resolución DynamicImport-Package: org.apache.derby.jdbc  Paquetes opcionales Import-Package: x.y.z;resolution:=optional
  • 58.
    Consejos y trucos  Acceso a detalles del bundle  OSGi 4.3 tiene un Wiring Framework BundleRevision revision = bundle.adapt(BundleRevision.class); List<BundleCapability> exportPackage = revision.getDeclaredCapabilities( BundleRevision.PACKAGE_NAMESPACE); List<BundleRequirement> importPackage = revision.getDeclaredRequirements( BundleRevision.PACKAGE_NAMESPACE);
  • 59.
    Consejos y trucos  Acceso a detalles del bundle  OSGi 4.3 tiene un Wiring Framework  Recorrer detalles de especificación for (BundleCapability capability : capabilities) { Map<String, Object> attributes = capability.getAttributes(); System.out.println( attributes.get("osgi.wiring.package") + " version " + attributes.get("version") ); }
  • 60.
    Consejos y trucos  Acceso a detalles del bundle  OSGi 4.3 tiene un Wiring Framework  Obtener enlaces/resoluciones en ejecución List<BundleWire> providedWires = revision.getWiring().getProvidedWires( BundleRevision.PACKAGE_NAMESPACE); for (BundleWire bundleWire : providedWires) { Bundle cliente = bundleWire.getRequirerWiring().getBundle(); Bundle proveedor = bundleWire.getProviderWiring().getBundle(); }
  • 61.
    Servicios Remotos  Configurar propiedades del servicio  Exportar interfaces remotas  Añadir Bundle de comunicación  install http://repo1.maven.org/maven2/org/osgi/org.osgi. compendium/4.2.0/org.osgi.compendium-4.2.0.jar  install http://www.apache.org/dist/cxf/dosgi/1.2/cxf-dosgi- ri-singlebundle-distribution-1.2.jar
  • 62.
    Servicios Remotos  Propiedades para acceso remoto  service.exported.interfaces  service.exported.configs  org.apache.cxf.ws  ws  org.apache.cxf.ws.address  SOAP.service.name  …
  • 63.
    Clientes Remotos  Bundle de comunicación  Clase ServiceTracker  Equivalente al ServiceReference  Método open() para iniciar el tracking  Método addingService() al encontrar servicios  Fichero XML de endpoints  OSGI-INF/remote-services/remote-services.xml
  • 64.
    Clientes Remotos  Service Tracker  Clase asociada al contexto y a la interfaz  open() y close() registran Listeners internos  Instanciarlo en un Activador  Ejecutar el open() en start()  Invocar a getService()  Admite ServiceTrackerCustomizer  Eventos del servicio  addingService() y removedService()
  • 65.
    Clientes Remotos  Fichero de endpoints <endpoint-descriptions xmlns="http://www.osgi.org/xmlns/rsa/v1.0.0"> <endpoint-description> <property name="objectClass"> <array> <value>servicio.wsdl.GreeterService</value> </array> </property> <property name="endpoint.id">http://localhost:9090/greeter</property> <property name="service.imported.configs">org.apache.cxf.ws</property> </endpoint-description> </endpoint-descriptions>
  • 66.
    Clientes Remotos  Fichero de configuración  OSGI-INF/cxf/intents/intent-map.xml <beans> <bean id="intentMap" class="org.apache.cxf.dosgi.dsw.qos.IntentMap"> <property name="intents"><map> <entry key="reliability" value-ref="reliableMessaging"/> <entry key="decoupled" value-ref="decoupledAddressing"/> </map></property> </bean> <p:policies id="reliableMessaging">…</p:policies> <p:policies id="decoupledAddressing">…</p:policies> <wsp:Policy wsu:Id="ReliabilityPolicy">…</wsp:Policy> <wsp:Policy wsu:Id="DecoupledPolicy">…</wsp:Policy> <wsp:Policy wsu:Id="AddressingPolicy">…</wsp:Policy> </beans>
  • 67.
    OSGi y J2EE  2 opciones  Embeber un servidor ligero en OSGi (Jetty)  Práctico en fase de desarrollo  Embeber OSGi en una aplicación Web  Eficiente en fase de despliegue
  • 68.
    OSGi y J2EE  Crear un bundle con su activador  Crear un Servlet  Crear un directorio para las páginas Web  Extender ServiceTracker  Obtener el servicio HttpService de contexto  Registrar recursos y servlets  Liberarlos en removedService()  Instanciarlo, abrirlo y cerrarlo en el activador
  • 69.
    OSGi y J2EE  Equinox tiene un bridge.war  http://www.eclipse. org/equinox/server/http_in_container.php  Plantilla de AppWeb con contexto /sp_test  Con un OSGi embebido en la consola Tomcat  BridgeServlet que hace de FrontController  Desplegar los bundle web en  WEB-INFEclipseplugins  Y arrancarlos desde consola
  • 70.
    Depuración  Arrancar el framework en modo remoto java –Xdebug -Xrunjdwp:transport= dt_socket,address=8787,server=y,suspend=n -jar framework.jar  Suspend indica que se pare en arranque  Crear un Debug Configuration en Eclipse  Remote Java Application  Indicar el puerto  Poner los puntos de ruptura y ejecutar OSGi
  • 71.
    Eclipse Plugins  Formato de bundle especial  Con un activador estandart: AbstractUIPlugin  Métodos getDefault() y getImageDescriptor()  Configurado mediante plugin.xml  Extensiones de la interfaz de Eclipse  Views, ayuda contextual, menús,…
  • 72.
    Eclipse Plugins  Ejemplo  Plugin con Custom Templates  Seleccionar Popup Menu y View  Asociar el Popup con org.eclipse.ui.IEditorInput  Configurar la categoría de la vista  Finish  Añadir más opciones al menú  Invocarán al método run() de la clase asociada