From eb163a8e90ce3247322d63e151c9324d90796dab Mon Sep 17 00:00:00 2001
From: Christopher Frost
Date: Mon, 14 Nov 2011 13:00:40 +0200
Subject: Add support for introspection of a single service to
ServiceStateMBean. Fix for bug 363458.
---
.gitignore | 3 +-
gemini.mgmt.releng/pom.xml | 14 +-
org.eclipse.gemini.mgmt/META-INF/MANIFEST.MF | 2 -
.../src/org/eclipse/gemini/mgmt/Monitor.java | 11 -
.../gemini/mgmt/framework/ServiceState.java | 224 +++++++++++++++------
.../gemini/mgmt/framework/codec/OSGiService.java | 31 ++-
6 files changed, 186 insertions(+), 99 deletions(-)
diff --git a/.gitignore b/.gitignore
index da92513..66772f8 100644
--- a/.gitignore
+++ b/.gitignore
@@ -1 +1,2 @@
-*/target
\ No newline at end of file
+*/target
+*/bin
diff --git a/gemini.mgmt.releng/pom.xml b/gemini.mgmt.releng/pom.xml
index fbdf7a5..34e85f7 100644
--- a/gemini.mgmt.releng/pom.xml
+++ b/gemini.mgmt.releng/pom.xml
@@ -38,13 +38,13 @@
p2
-
- org.eclipse.gemini.mgmt
- target-platform
- 1.0.0-SNAPSHOT
- gemini-management
-
-
+
+ org.eclipse.gemini.mgmt
+ target-platform
+ 1.0.0-SNAPSHOT
+ gemini-management
+
+
diff --git a/org.eclipse.gemini.mgmt/META-INF/MANIFEST.MF b/org.eclipse.gemini.mgmt/META-INF/MANIFEST.MF
index acc55d6..74af427 100644
--- a/org.eclipse.gemini.mgmt/META-INF/MANIFEST.MF
+++ b/org.eclipse.gemini.mgmt/META-INF/MANIFEST.MF
@@ -3,7 +3,6 @@ Bundle-ManifestVersion: 2
Bundle-Name: Gemini Management
Bundle-SymbolicName: org.eclipse.gemini.mgmt
Bundle-Version: 1.0.0.qualifier
-Bundle-Vendor: Oracle
Bundle-RequiredExecutionEnvironment: JavaSE-1.6
Import-Package: org.osgi.framework;version="1.3.0",
org.osgi.jmx,
@@ -22,4 +21,3 @@ Import-Package: org.osgi.framework;version="1.3.0",
javax.management,
javax.management.openmbean
Bundle-Activator: org.eclipse.gemini.mgmt.Activator
-Bundle-ActivationPolicy: lazy
diff --git a/org.eclipse.gemini.mgmt/src/org/eclipse/gemini/mgmt/Monitor.java b/org.eclipse.gemini.mgmt/src/org/eclipse/gemini/mgmt/Monitor.java
index 01bbfaf..8da3874 100644
--- a/org.eclipse.gemini.mgmt/src/org/eclipse/gemini/mgmt/Monitor.java
+++ b/org.eclipse.gemini.mgmt/src/org/eclipse/gemini/mgmt/Monitor.java
@@ -23,27 +23,16 @@ import javax.management.ObjectName;
/**
*
*/
-
abstract public class Monitor extends NotificationBroadcasterSupport implements
MBeanRegistration {
public void postDeregister() {
}
- /*
- * (non-Javadoc)
- *
- * @see javax.management.MBeanRegistration#postRegister(java.lang.Boolean)
- */
public void postRegister(Boolean registrationDone) {
addListener();
}
- /*
- * (non-Javadoc)
- *
- * @see javax.management.MBeanRegistration#preDeregister()
- */
public void preDeregister() throws Exception {
removeListener();
}
diff --git a/org.eclipse.gemini.mgmt/src/org/eclipse/gemini/mgmt/framework/ServiceState.java b/org.eclipse.gemini.mgmt/src/org/eclipse/gemini/mgmt/framework/ServiceState.java
index e40e727..cf2c569 100644
--- a/org.eclipse.gemini.mgmt/src/org/eclipse/gemini/mgmt/framework/ServiceState.java
+++ b/org.eclipse.gemini.mgmt/src/org/eclipse/gemini/mgmt/framework/ServiceState.java
@@ -11,18 +11,28 @@
*
* Contributors:
* Hal Hildebrand - Initial JMX support
+ * Christopher Frost - Updates for RFC 169
******************************************************************************/
package org.eclipse.gemini.mgmt.framework;
import static org.osgi.framework.Constants.OBJECTCLASS;
+import static org.osgi.framework.Constants.SERVICE_ID;
import java.io.IOException;
import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.List;
import javax.management.Notification;
+import javax.management.openmbean.CompositeData;
import javax.management.openmbean.TabularData;
+import org.eclipse.gemini.mgmt.Monitor;
+import org.eclipse.gemini.mgmt.codec.OSGiProperties;
+import org.eclipse.gemini.mgmt.codec.Util;
+import org.eclipse.gemini.mgmt.framework.codec.OSGiService;
+import org.eclipse.gemini.mgmt.framework.codec.OSGiServiceEvent;
import org.osgi.framework.AllServiceListener;
import org.osgi.framework.Bundle;
import org.osgi.framework.BundleContext;
@@ -32,53 +42,57 @@ import org.osgi.framework.InvalidSyntaxException;
import org.osgi.framework.ServiceEvent;
import org.osgi.framework.ServiceListener;
import org.osgi.framework.ServiceReference;
-
import org.osgi.jmx.framework.ServiceStateMBean;
import org.osgi.util.tracker.ServiceTracker;
-import org.eclipse.gemini.mgmt.Monitor;
-import org.eclipse.gemini.mgmt.codec.OSGiProperties;
-import org.eclipse.gemini.mgmt.framework.codec.OSGiService;
-import org.eclipse.gemini.mgmt.framework.codec.OSGiServiceEvent;
-
/**
*
*/
public class ServiceState extends Monitor implements ServiceStateMBean {
+
+ protected ServiceListener serviceListener;
+
+ protected BundleContext bundleContext;
+
+ /**
+ * Constructor
+ *
+ * @param bundleContext
+ */
public ServiceState(BundleContext bc) {
- this.bc = bc;
+ this.bundleContext = bc;
}
+ /**
+ * {@inheritDoc}
+ */
public long getBundleIdentifier(long serviceId) throws IOException {
return ref(serviceId).getBundle().getBundleId();
}
+ /**
+ * {@inheritDoc}
+ */
public TabularData getProperties(long serviceId) throws IOException {
return OSGiProperties.tableFrom(ref(serviceId));
}
- /*
- * (non-Javadoc)
- *
- * @see org.osgi.jmx.core.ServiceStateMBean#getBundle(long)
+ /**
+ * {@inheritDoc}
*/
-
public String[] getObjectClass(long serviceId) throws IOException {
return (String[]) ref(serviceId).getProperty(OBJECTCLASS);
}
- /*
- * (non-Javadoc)
- *
- * @see org.osgi.jmx.core.ServiceStateMBean#listServices()
+ /**
+ * {@inheritDoc}
*/
-
public TabularData listServices() {
ArrayList services = new ArrayList();
- for (Bundle bundle : bc.getBundles()) {
- ServiceReference[] refs = bundle.getRegisteredServices();
+ for (Bundle bundle : bundleContext.getBundles()) {
+ ServiceReference>[] refs = bundle.getRegisteredServices();
if (refs != null) {
- for (ServiceReference ref : refs) {
+ for (ServiceReference> ref : refs) {
services.add(new OSGiService(ref));
}
}
@@ -86,12 +100,9 @@ public class ServiceState extends Monitor implements ServiceStateMBean {
return OSGiService.tableFrom(services);
}
- /*
- * (non-Javadoc)
- *
- * @see org.osgi.jmx.core.ServiceStateMBean#getServiceInterfaces(long)
+ /**
+ * {@inheritDoc}
*/
-
public long[] getUsingBundles(long serviceId) throws IOException {
Bundle[] bundles = ref(serviceId).getUsingBundles();
long[] ids = new long[bundles.length];
@@ -101,28 +112,137 @@ public class ServiceState extends Monitor implements ServiceStateMBean {
return ids;
}
- /*
- * (non-Javadoc)
- *
- * @see org.osgi.jmx.core.ServiceStateMBean#getServices()
+ /**
+ * {@inheritDoc}
*/
+ public CompositeData getService(long serviceId) throws IOException {
+ for (Bundle bundle : bundleContext.getBundles()) {
+ ServiceReference>[] refs = bundle.getRegisteredServices();
+ if (refs != null) {
+ for (ServiceReference> ref : refs) {
+ if(serviceId == (Long) ref.getProperty(Constants.SERVICE_ID)){
+ return new OSGiService(ref).asCompositeData();
+ }
+ }
+ }
+ }
+ return null;
+ }
- /*
- * (non-Javadoc)
- *
- * @see org.osgi.jmx.Monitor#addListener()
+ /**
+ * {@inheritDoc}
+ * @param
+ */
+ public CompositeData getProperty(long serviceId, String key) throws IOException {
+ for (Bundle bundle : bundleContext.getBundles()) {
+ ServiceReference>[] refs = bundle.getRegisteredServices();
+ if (refs != null) {
+ for (ServiceReference> ref : refs) {
+ if(serviceId == (Long) ref.getProperty(Constants.SERVICE_ID)){
+ return OSGiProperties.encode(key, ref.getProperty(key));
+ }
+ }
+ }
+ }
+ return null;
+ }
+
+ /**
+ * {@inheritDoc}
+ */
+ public TabularData listServices(String clazz, String filter) throws IOException {
+ ArrayList services = new ArrayList();
+ try {
+ ServiceReference>[] allServiceReferences = bundleContext.getAllServiceReferences(clazz, filter);
+ for (ServiceReference> ref : allServiceReferences) {
+ services.add(new OSGiService(ref));
+ }
+ return OSGiService.tableFrom(services);
+ } catch (InvalidSyntaxException e) {
+ throw new IOException(e);
+ }
+ }
+
+ /**
+ * {@inheritDoc}
+ */
+ public TabularData listServices(String clazz, String filter, String... serviceTypeItems) throws IOException {
+ ArrayList services = new ArrayList();
+ List serviceTypeNames = Arrays.asList(serviceTypeItems);
+ try {
+ ServiceReference>[] allServiceReferences = bundleContext.getAllServiceReferences(clazz, filter);
+ for (ServiceReference> reference : allServiceReferences) {
+ Long identifier;
+ if(serviceTypeNames.contains(ServiceStateMBean.IDENTIFIER)){
+ identifier = (Long) reference.getProperty(SERVICE_ID);
+ } else {
+ identifier = null;
+ }
+ String[] interfaces;
+ if(serviceTypeNames.contains(ServiceStateMBean.OBJECT_CLASS)){
+ interfaces = (String[]) reference.getProperty(OBJECTCLASS);
+ } else {
+ interfaces = null;
+ }
+ Long bundle;
+ if(serviceTypeNames.contains(ServiceStateMBean.BUNDLE_IDENTIFIER)){
+ bundle = reference.getBundle().getBundleId();
+ } else {
+ bundle = null;
+ }
+ long[] usingBundles;
+ if(serviceTypeNames.contains(ServiceStateMBean.USING_BUNDLES)){
+ usingBundles = Util.bundleIds(reference.getUsingBundles());
+ } else {
+ usingBundles = null;
+ }
+ services.add(new OSGiService(identifier, interfaces, bundle, usingBundles));
+ }
+ return OSGiService.tableFrom(services);
+ } catch (InvalidSyntaxException e) {
+ throw new IOException(e);
+ }
+ }
+
+ /**
+ * {@inheritDoc}
+ */
+ public long[] getServiceIds() throws IOException {
+ ServiceReference>[] allServiceReferences;
+ try {
+ allServiceReferences = bundleContext.getAllServiceReferences(null, null);
+ long[] serviceIds = new long[allServiceReferences.length];
+ for (int i = 0; i < allServiceReferences.length; i++) {
+ serviceIds[i] = (Long) allServiceReferences[i].getProperty(Constants.SERVICE_ID);
+ }
+ return serviceIds;
+ } catch (InvalidSyntaxException e) {
+ //passing in null so should never happen
+ throw new IOException(e);
+ }
+ }
+
+ //End methods for the MBean
+
+
+ /**
+ * {@inheritDoc}
*/
@Override
protected void addListener() {
- serviceListener = getServiceListener();
- bc.addServiceListener(serviceListener);
+ serviceListener = this.getServiceListener();
+ bundleContext.addServiceListener(serviceListener);
}
- /*
- * (non-Javadoc)
- *
- * @see org.osgi.jmx.core.ServiceStateMBean#getUsingBundles(long)
+ /**
+ * {@inheritDoc}
*/
+ @Override
+ protected void removeListener() {
+ if (serviceListener != null) {
+ bundleContext.removeServiceListener(serviceListener);
+ }
+ }
protected ServiceListener getServiceListener() {
return new AllServiceListener() {
@@ -135,30 +255,17 @@ public class ServiceState extends Monitor implements ServiceStateMBean {
}
};
}
-
- /*
- * (non-Javadoc)
- *
- * @see org.osgi.jmx.Monitor#removeListener()
- */
- @Override
- protected void removeListener() {
- if (serviceListener != null) {
- bc.removeServiceListener(serviceListener);
- }
- }
-
- protected ServiceReference ref(long serviceId) throws IOException {
+
+ protected ServiceReference> ref(long serviceId) throws IOException {
Filter filter;
try {
- filter = bc.createFilter("(" + Constants.SERVICE_ID + "="
- + serviceId + ")");
+ filter = bundleContext.createFilter("(" + Constants.SERVICE_ID + "=" + serviceId + ")");
} catch (InvalidSyntaxException e) {
throw new IOException("Invalid filter syntax: " + e);
}
- ServiceTracker tracker = new ServiceTracker(bc, filter, null);
+ ServiceTracker, ?> tracker = new ServiceTracker