[jboss-cvs] JBossAS SVN: r62035 - in projects/microcontainer/trunk: osgi-int/src/main/org/jboss/osgi/plugins/facade and 1 other directory.

jboss-cvs-commits at lists.jboss.org jboss-cvs-commits at lists.jboss.org
Tue Apr 3 10:39:48 EDT 2007


Author: alesj
Date: 2007-04-03 10:39:48 -0400 (Tue, 03 Apr 2007)
New Revision: 62035

Added:
   projects/microcontainer/trunk/osgi-int/src/main/org/jboss/osgi/plugins/facade/ServiceFactoryProxy.java
Removed:
   projects/microcontainer/trunk/osgi-int/src/main/org/jboss/osgi/plugins/facade/ServiceFactoryImpl.java
Modified:
   projects/microcontainer/trunk/kernel/src/main/org/jboss/kernel/spi/registry/KernelRegistry.java
   projects/microcontainer/trunk/osgi-int/src/main/org/jboss/osgi/plugins/facade/AbstractServiceEvent.java
   projects/microcontainer/trunk/osgi-int/src/main/org/jboss/osgi/plugins/facade/BundleContextImpl.java
   projects/microcontainer/trunk/osgi-int/src/main/org/jboss/osgi/plugins/facade/OSGiUtils.java
   projects/microcontainer/trunk/osgi-int/src/main/org/jboss/osgi/plugins/facade/ServiceRegistrationImpl.java
Log:
ServiceRegistration implementation work.

Modified: projects/microcontainer/trunk/kernel/src/main/org/jboss/kernel/spi/registry/KernelRegistry.java
===================================================================
--- projects/microcontainer/trunk/kernel/src/main/org/jboss/kernel/spi/registry/KernelRegistry.java	2007-04-03 14:37:56 UTC (rev 62034)
+++ projects/microcontainer/trunk/kernel/src/main/org/jboss/kernel/spi/registry/KernelRegistry.java	2007-04-03 14:39:48 UTC (rev 62035)
@@ -38,6 +38,9 @@
    /** Event type for registered event */
    public static final String KERNEL_REGISTRY_REGISTERED = "KERNEL_REGISTRY_REGISTERED";
 
+   /** Event type for modified event */
+   public static final String KERNEL_REGISTRY_MODIFIED = "KERNEL_REGISTRY_MODIFIED";
+
    /** Event type for unregistered event */
    public static final String KERNEL_REGISTRY_UNREGISTERED = "KERNEL_REGISTRY_UNREGISTERED";
    

Modified: projects/microcontainer/trunk/osgi-int/src/main/org/jboss/osgi/plugins/facade/AbstractServiceEvent.java
===================================================================
--- projects/microcontainer/trunk/osgi-int/src/main/org/jboss/osgi/plugins/facade/AbstractServiceEvent.java	2007-04-03 14:37:56 UTC (rev 62034)
+++ projects/microcontainer/trunk/osgi-int/src/main/org/jboss/osgi/plugins/facade/AbstractServiceEvent.java	2007-04-03 14:39:48 UTC (rev 62035)
@@ -32,7 +32,7 @@
  */
 public class AbstractServiceEvent extends AbstractEvent implements ServiceEventAdapter
 {
-   // todo - service modified type, ServiceReference
+   // todo - ServiceReference
    public AbstractServiceEvent(Object source, String type, long sequence, long timestamp, Object context)
    {
       super(source, type, sequence, timestamp, context);
@@ -45,6 +45,10 @@
       {
          serviceType = ServiceEvent.REGISTERED;
       }
+      else if (KernelRegistry.KERNEL_REGISTRY_MODIFIED.equals(type))
+      {
+         serviceType = ServiceEvent.MODIFIED;
+      }
       else if (KernelRegistry.KERNEL_REGISTRY_UNREGISTERED.equals(type))
       {
          serviceType = ServiceEvent.UNREGISTERING;

Modified: projects/microcontainer/trunk/osgi-int/src/main/org/jboss/osgi/plugins/facade/BundleContextImpl.java
===================================================================
--- projects/microcontainer/trunk/osgi-int/src/main/org/jboss/osgi/plugins/facade/BundleContextImpl.java	2007-04-03 14:37:56 UTC (rev 62034)
+++ projects/microcontainer/trunk/osgi-int/src/main/org/jboss/osgi/plugins/facade/BundleContextImpl.java	2007-04-03 14:39:48 UTC (rev 62035)
@@ -29,18 +29,22 @@
 import java.util.Dictionary;
 import java.util.EventListener;
 import java.util.HashMap;
-import java.util.Hashtable;
 import java.util.List;
 import java.util.Map;
 
+import org.jboss.beans.metadata.spi.BeanMetaData;
+import org.jboss.beans.metadata.spi.builder.BeanMetaDataBuilder;
 import org.jboss.deployers.spi.structure.DeploymentContext;
 import org.jboss.kernel.spi.config.KernelConfigurator;
+import org.jboss.kernel.spi.dependency.KernelController;
+import org.jboss.kernel.spi.dependency.KernelControllerContext;
 import org.jboss.kernel.spi.event.KernelEvent;
 import org.jboss.kernel.spi.event.KernelEventEmitter;
 import org.jboss.kernel.spi.event.KernelEventFilter;
-import org.jboss.kernel.spi.registry.KernelRegistry;
+import org.jboss.kernel.spi.event.KernelEventListener;
 import org.jboss.logging.Logger;
 import org.jboss.reflect.spi.ClassInfo;
+import org.jboss.util.id.GUID;
 import org.osgi.framework.Bundle;
 import org.osgi.framework.BundleContext;
 import org.osgi.framework.BundleException;
@@ -60,7 +64,7 @@
  *
  * @author <a href="mailto:ales.justin at jboss.com">Ales Justin</a>
  */
-public class BundleContextImpl implements BundleContext
+public class BundleContextImpl implements BundleContext, KernelEventEmitter
 {
    /** The log */
    private static final Logger log = Logger.getLogger(BundleContextImpl.class);
@@ -69,8 +73,9 @@
 
    protected DeploymentContext context;
    protected Bundle bundle;
-   protected KernelEventEmitter eventEmitter; // todo - get it
-   protected KernelConfigurator kernelConfigurator; // todo - get it
+   protected KernelController controller; // todo - get it
+   protected KernelEventEmitter emitterDelegate; // todo - get it
+   protected KernelConfigurator configurator; // todo - get it
 
    protected Map<EventListener, AbstractDelegateListener> listeners = Collections.synchronizedMap(new HashMap<EventListener, AbstractDelegateListener>());
    protected Map<ServiceListener, KernelEventFilter> filters = Collections.synchronizedMap(new HashMap<ServiceListener, KernelEventFilter>());
@@ -96,6 +101,21 @@
       return null;
    }
 
+   public void registerListener(KernelEventListener listener, KernelEventFilter filter, Object handback) throws Throwable
+   {
+      emitterDelegate.registerListener(listener, filter, handback);
+   }
+
+   public void unregisterListener(KernelEventListener listener, KernelEventFilter filter, Object handback) throws Throwable
+   {
+      emitterDelegate.unregisterListener(listener, filter, handback);
+   }
+
+   public void fireKernelEvent(KernelEvent event)
+   {
+      emitterDelegate.fireKernelEvent(event);
+   }
+
    // --------------- OSGi framework -----------------------
 
    public String getProperty(String string)
@@ -152,7 +172,7 @@
       }
       try
       {
-         eventEmitter.registerListener(listener, eventFilter, this);
+         registerListener(listener, eventFilter, this);
          listeners.put(serviceListener, listener);
       }
       catch (Throwable throwable)
@@ -184,7 +204,7 @@
          KernelEventFilter filter = filters.get(serviceListener);
          try
          {
-            eventEmitter.unregisterListener(listener, filter, this);
+            unregisterListener(listener, filter, this);
          }
          catch (Throwable t)
          {
@@ -210,7 +230,7 @@
          listener.addValidate();
          try
          {
-            eventEmitter.registerListener(listener, null, this);
+            registerListener(listener, null, this);
             listeners.put(bundleListener, listener);
          }
          catch (Throwable t)
@@ -229,7 +249,7 @@
          listener.removeValidate();
          try
          {
-            eventEmitter.unregisterListener(listener, null, this);
+            unregisterListener(listener, null, this);
          }
          catch (Throwable t)
          {
@@ -251,7 +271,7 @@
          listener.addValidate();
          try
          {
-            eventEmitter.registerListener(listener, null, this);
+            registerListener(listener, null, this);
             listeners.put(frameworkListener, listener);
          }
          catch (Throwable t)
@@ -270,7 +290,7 @@
          listener.removeValidate();
          try
          {
-            eventEmitter.unregisterListener(listener, null, this);
+            unregisterListener(listener, null, this);
          }
          catch (Throwable t)
          {
@@ -294,12 +314,14 @@
 
       ClassInfo serviceInfo;
       ClassInfo[] infos = new ClassInfo[clazzes.length];
+      Class[] interfaces = new Class[clazzes.length];
       try
       {
-         serviceInfo = kernelConfigurator.getClassInfo(service.getClass());
+         serviceInfo = configurator.getClassInfo(service.getClass());
          for(int i=0; i < clazzes.length; i++)
          {
-            infos[i] = kernelConfigurator.getClassInfo(clazzes[i], getClassLoader());
+            infos[i] = configurator.getClassInfo(clazzes[i], getClassLoader());
+            interfaces[i] = infos[i].getType();
          }
       }
       catch (Throwable t)
@@ -317,18 +339,27 @@
          }
       }
       // handle properties
-      if (properties == null)
+      Map<String, Object> serviceMap = OSGiUtils.toMap(properties);
+      Long serviceId = NumberUtil.nextLong();
+      serviceMap.put(Constants.SERVICE_ID, serviceId);
+      serviceMap.put(Constants.OBJECTCLASS, clazzes);
+      if (isServiceFactory)
       {
-         properties = new Hashtable();
+         service = ServiceFactoryProxy.createProxy(service, interfaces);
       }
-      Long serviceId = NumberUtil.nextLong();
-      properties.put(Constants.SERVICE_ID, serviceId);
-      properties.put(Constants.OBJECTCLASS, clazzes);
-      // todo - add to framework --> controller + handle factory bean!
+      BeanMetaDataBuilder builder = new BeanMetaDataBuilder(GUID.asString(), serviceInfo.getName());
+      BeanMetaData metaData = builder.getBeanMetaData();
+      KernelControllerContext context;
+      try
+      {
+         context = controller.install(metaData, service);
+      }
+      catch (Throwable t)
+      {
+         throw new InternalOSGiFacadeException(t);
+      }
       // todo - get underlying bundle --> ServiceReference
-      KernelEvent event = new AbstractServiceEvent(this, KernelRegistry.KERNEL_REGISTRY_REGISTERED, serviceId, System.currentTimeMillis(), service);
-      eventEmitter.fireKernelEvent(event);
-      return new ServiceRegistrationImpl();
+      return new ServiceRegistrationImpl(this, context, serviceId, serviceMap);
    }
 
    public ServiceRegistration registerService(String clazz, Object service, Dictionary properties)
@@ -390,15 +421,17 @@
 
    public Object getService(ServiceReference reference)
    {
-      return null;  //To change body of implemented methods use File | Settings | File Templates.
+      validateBundle();
+      return null;
    }
 
    public boolean ungetService(ServiceReference reference)
    {
+      validateBundle();
       return false;  //To change body of implemented methods use File | Settings | File Templates.
    }
 
-   public File getDataFile(String string)
+   public File getDataFile(String filename)
    {
       return null;  //To change body of implemented methods use File | Settings | File Templates.
    }

Modified: projects/microcontainer/trunk/osgi-int/src/main/org/jboss/osgi/plugins/facade/OSGiUtils.java
===================================================================
--- projects/microcontainer/trunk/osgi-int/src/main/org/jboss/osgi/plugins/facade/OSGiUtils.java	2007-04-03 14:37:56 UTC (rev 62034)
+++ projects/microcontainer/trunk/osgi-int/src/main/org/jboss/osgi/plugins/facade/OSGiUtils.java	2007-04-03 14:39:48 UTC (rev 62035)
@@ -21,6 +21,11 @@
 */
 package org.jboss.osgi.plugins.facade;
 
+import java.util.Dictionary;
+import java.util.Enumeration;
+import java.util.HashMap;
+import java.util.Map;
+
 import org.osgi.framework.Constants;
 import org.osgi.framework.ServiceReference;
 
@@ -32,6 +37,28 @@
 public abstract class OSGiUtils
 {
    /**
+    * Transform from Dictionary to Map
+    *
+    * @param dictionary dictionary to transform
+    * @return Map<String, Object>
+    */
+   public static Map<String, Object> toMap(Dictionary dictionary)
+   {
+      Map<String, Object> map = new HashMap<String, Object>();
+      if (dictionary != null && dictionary.size() > 0)
+      {
+         Enumeration keys = dictionary.keys();
+         while(keys.hasMoreElements())
+         {
+            String key = keys.nextElement().toString();
+            Object value = dictionary.get(key);
+            map.put(key, value);
+         }
+      }
+      return map;
+   }
+
+   /**
     * Get ServiceReference id.
     *
     * @param reference service reference to look for id

Deleted: projects/microcontainer/trunk/osgi-int/src/main/org/jboss/osgi/plugins/facade/ServiceFactoryImpl.java
===================================================================
--- projects/microcontainer/trunk/osgi-int/src/main/org/jboss/osgi/plugins/facade/ServiceFactoryImpl.java	2007-04-03 14:37:56 UTC (rev 62034)
+++ projects/microcontainer/trunk/osgi-int/src/main/org/jboss/osgi/plugins/facade/ServiceFactoryImpl.java	2007-04-03 14:39:48 UTC (rev 62035)
@@ -1,44 +0,0 @@
-/*
-* JBoss, Home of Professional Open Source
-* Copyright 2006, JBoss Inc., and individual contributors as indicated
-* by the @authors tag. See the copyright.txt in the distribution for a
-* full listing of individual contributors.
-*
-* This is free software; you can redistribute it and/or modify it
-* under the terms of the GNU Lesser General Public License as
-* published by the Free Software Foundation; either version 2.1 of
-* the License, or (at your option) any later version.
-*
-* This software is distributed in the hope that it will be useful,
-* but WITHOUT ANY WARRANTY; without even the implied warranty of
-* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
-* Lesser General Public License for more details.
-*
-* You should have received a copy of the GNU Lesser General Public
-* License along with this software; if not, write to the Free
-* Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
-* 02110-1301 USA, or see the FSF site: http://www.fsf.org.
-*/
-package org.jboss.osgi.plugins.facade;
-
-import org.osgi.framework.Bundle;
-import org.osgi.framework.ServiceFactory;
-import org.osgi.framework.ServiceRegistration;
-
-/**
- * Servicefactory implementation on top of Controller
- *
- * @author <a href="mailto:ales.justin at jboss.com">Ales Justin</a>
- */
-public class ServiceFactoryImpl implements ServiceFactory
-{
-   public Object getService(Bundle bundle, ServiceRegistration serviceRegistration)
-   {
-      return null;  //To change body of implemented methods use File | Settings | File Templates.
-   }
-
-   public void ungetService(Bundle bundle, ServiceRegistration serviceRegistration, Object object)
-   {
-      //To change body of implemented methods use File | Settings | File Templates.
-   }
-}

Added: projects/microcontainer/trunk/osgi-int/src/main/org/jboss/osgi/plugins/facade/ServiceFactoryProxy.java
===================================================================
--- projects/microcontainer/trunk/osgi-int/src/main/org/jboss/osgi/plugins/facade/ServiceFactoryProxy.java	                        (rev 0)
+++ projects/microcontainer/trunk/osgi-int/src/main/org/jboss/osgi/plugins/facade/ServiceFactoryProxy.java	2007-04-03 14:39:48 UTC (rev 62035)
@@ -0,0 +1,124 @@
+/*
+* JBoss, Home of Professional Open Source
+* Copyright 2006, JBoss Inc., and individual contributors as indicated
+* by the @authors tag. See the copyright.txt in the distribution for a
+* full listing of individual contributors.
+*
+* This is free software; you can redistribute it and/or modify it
+* under the terms of the GNU Lesser General Public License as
+* published by the Free Software Foundation; either version 2.1 of
+* the License, or (at your option) any later version.
+*
+* This software is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+* Lesser General Public License for more details.
+*
+* You should have received a copy of the GNU Lesser General Public
+* License along with this software; if not, write to the Free
+* Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
+* 02110-1301 USA, or see the FSF site: http://www.fsf.org.
+*/
+package org.jboss.osgi.plugins.facade;
+
+import java.lang.reflect.InvocationHandler;
+import java.lang.reflect.Method;
+import java.lang.reflect.Proxy;
+import java.util.Arrays;
+
+import org.osgi.framework.ServiceFactory;
+
+/**
+ * An implementation of InvocationHandler used to proxy of the ServiceFactory
+ * interface for OSGi services.
+ *
+ * @author <a href="mailto:ales.justin at jboss.com">Ales Justin</a>
+ */
+public class ServiceFactoryProxy implements InvocationHandler
+{
+   public static final String GET_SERVICE = "getService";
+   public static final String UNGET_SERVICE = "ungetService";
+
+/*
+   private static final Logger log = Logger.getLogger(ServiceFactoryProxy.class);
+
+   public static Method GET_SERVICE_METHOD;
+   static
+   {
+      try
+      {
+         GET_SERVICE_METHOD = ServiceFactory.class.getMethod(GET_SERVICE, Bundle.class, ServiceRegistration.class);
+      }
+      catch (NoSuchMethodException e)
+      {
+         log.error("Unable to prepare getService method.", e);        
+      }
+   }
+*/
+   protected Object serviceFactory;
+   protected Class[] interfaces;
+   protected Object service;
+   protected Boolean checked;
+
+   private ServiceFactoryProxy(Object serviceFactory, Class[] interfaces)
+   {
+      this.serviceFactory = serviceFactory;
+      this.interfaces = interfaces;
+   }
+
+   public static Object createProxy(Object serviceFactory, Class[] interfaces)
+   {
+      int lenght = interfaces.length;
+      Class[] allIntefaces = new Class[lenght + 1];
+      System.arraycopy(interfaces, 0, allIntefaces, 0, lenght);
+      allIntefaces[lenght] = ServiceFactory.class;
+      InvocationHandler handler = new ServiceFactoryProxy(serviceFactory, interfaces);
+      return Proxy.newProxyInstance(ServiceFactory.class.getClassLoader(), allIntefaces, handler);
+   }
+
+   protected boolean checkInterfaces()
+   {
+      // already checked
+      if (checked != null)
+         return checked;
+      // can be null
+      if (service == null)
+         return true;
+
+      Class serviceInterface = service.getClass();
+      for(Class exposedInterface : interfaces)
+      {
+         if (exposedInterface.isAssignableFrom(serviceInterface) == false)
+         {
+            return (checked = false);
+         }
+      }
+      return (checked = true);
+   }
+
+   public Object invoke(Object proxy, Method method, Object[] args) throws Throwable
+   {
+      String methodName = method.getName();
+      if (GET_SERVICE.equals(methodName))
+      {
+         service = method.invoke(serviceFactory, args);
+         if (checkInterfaces() == false)
+            return null;
+         return service;
+      }
+      else if (UNGET_SERVICE.equals(methodName))
+      {
+         service = null;
+         checked = null;
+         return method.invoke(serviceFactory, args);
+      }
+      else
+      {
+         if (service == null)
+            throw new IllegalStateException("Service not yet created from ServiceFactory!"); // todo - or create it now?
+         if (checkInterfaces() == false)
+            throw new IllegalArgumentException("Illegal exposed interfaces: " + service + "; " + Arrays.asList(interfaces));
+         return method.invoke(service, args);
+      }
+   }
+}

Modified: projects/microcontainer/trunk/osgi-int/src/main/org/jboss/osgi/plugins/facade/ServiceRegistrationImpl.java
===================================================================
--- projects/microcontainer/trunk/osgi-int/src/main/org/jboss/osgi/plugins/facade/ServiceRegistrationImpl.java	2007-04-03 14:37:56 UTC (rev 62034)
+++ projects/microcontainer/trunk/osgi-int/src/main/org/jboss/osgi/plugins/facade/ServiceRegistrationImpl.java	2007-04-03 14:39:48 UTC (rev 62035)
@@ -22,9 +22,16 @@
 package org.jboss.osgi.plugins.facade;
 
 import java.util.Dictionary;
+import java.util.Enumeration;
 import java.util.Map;
+import java.util.Set;
+import java.util.TreeSet;
 
-import org.jboss.reflect.spi.ClassInfo;
+import org.jboss.kernel.spi.dependency.KernelControllerContext;
+import org.jboss.kernel.spi.event.KernelEvent;
+import org.jboss.kernel.spi.event.KernelEventEmitter;
+import org.jboss.kernel.spi.registry.KernelRegistry;
+import org.osgi.framework.Constants;
 import org.osgi.framework.ServiceReference;
 import org.osgi.framework.ServiceRegistration;
 
@@ -35,22 +42,70 @@
  */
 public class ServiceRegistrationImpl implements ServiceRegistration
 {
-   private ClassInfo serviceInfo;
-   private ClassInfo[] interfaces;
-   private Map properties;
+   protected KernelEventEmitter emitter;
+   protected KernelControllerContext context;
+   protected Long serviceId;
+   protected Map<String, Object> properties;
 
+   protected boolean isRegistered;
+
+   public ServiceRegistrationImpl(KernelEventEmitter emitter, KernelControllerContext context, Long serviceId, Map<String, Object> properties)
+   {
+      this.emitter = emitter;
+      this.context = context;
+      this.serviceId = serviceId;
+      this.properties = properties;
+      init();
+   }
+   protected void init()
+   {
+      KernelEvent event = new AbstractServiceEvent(this, KernelRegistry.KERNEL_REGISTRY_REGISTERED, serviceId, System.currentTimeMillis(), emitter);
+      emitter.fireKernelEvent(event);
+   }
+
+   protected void validateServiceRegistration()
+   {
+      if (isServiceRegistered() == false)
+         throw new IllegalStateException("ServiceRegistration object has already been unregistered.");
+   }
+
+   protected boolean isServiceRegistered()
+   {
+      return isRegistered;
+   }
+
    public ServiceReference getReference()
    {
       return null;  //To change body of implemented methods use File | Settings | File Templates.
    }
 
-   public void setProperties(Dictionary dictionary)
+   public void setProperties(Dictionary properties)
    {
-      //To change body of implemented methods use File | Settings | File Templates.
+      validateServiceRegistration();
+      if (properties != null && properties.size() > 0)
+      {
+         Set<String> names = new TreeSet<String>(String.CASE_INSENSITIVE_ORDER);
+         Enumeration keys = properties.keys();
+         for(String key = (String)keys.nextElement(); keys.hasMoreElements();)
+         {
+            if (names.add(key) == false)
+               throw new IllegalArgumentException("properties contains case variants of the same key name.");
+
+            if (Constants.OBJECTCLASS.equals(key) == false && Constants.SERVICE_ID.equals(key) == false)
+            {
+               this.properties.put(key, properties.get(key));
+            }
+         }
+         KernelEvent event = new AbstractServiceEvent(this, KernelRegistry.KERNEL_REGISTRY_MODIFIED, serviceId, System.currentTimeMillis(), emitter);
+         emitter.fireKernelEvent(event);
+      }
    }
 
    public void unregister()
    {
-      //To change body of implemented methods use File | Settings | File Templates.
+      validateServiceRegistration();
+      isRegistered = false;
+      KernelEvent event = new AbstractServiceEvent(this, KernelRegistry.KERNEL_REGISTRY_UNREGISTERED, serviceId, System.currentTimeMillis(), emitter);
+      emitter.fireKernelEvent(event);
    }
 }




More information about the jboss-cvs-commits mailing list