📄 configurationadminfactory.java
字号:
/* * Copyright (c) 2003-2004, KNOPFLERFISH project * All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following * conditions are met: * * - Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * - Redistributions in binary form must reproduce the above * copyright notice, this list of conditions and the following * disclaimer in the documentation and/or other materials * provided with the distribution. * * - Neither the name of the KNOPFLERFISH project nor the names of its * contributors may be used to endorse or promote products derived * from this software without specific prior written permission. * * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED * OF THE POSSIBILITY OF SUCH DAMAGE. */package org.knopflerfish.bundle.cm;import java.io.File;import java.io.IOException;import java.security.AccessController;import java.security.PrivilegedActionException;import java.security.PrivilegedExceptionAction;import java.util.Dictionary;import java.util.Enumeration;import java.util.Hashtable;import java.util.Vector;import org.osgi.framework.AdminPermission;import org.osgi.framework.Bundle;import org.osgi.framework.BundleEvent;import org.osgi.framework.BundleListener;import org.osgi.framework.Constants;import org.osgi.framework.Filter;import org.osgi.framework.InvalidSyntaxException;import org.osgi.framework.ServiceEvent;import org.osgi.framework.ServiceFactory;import org.osgi.framework.ServiceListener;import org.osgi.framework.ServiceReference;import org.osgi.framework.ServiceRegistration;import org.osgi.service.cm.Configuration;import org.osgi.service.cm.ConfigurationAdmin;import org.osgi.service.cm.ConfigurationPlugin;import org.osgi.service.cm.ManagedService;import org.osgi.service.cm.ManagedServiceFactory;/** * ConfigurationAdmin implementation * * @author Per Gustafson * @version $Revision: 1.2 $ */class ConfigurationAdminFactory implements ServiceFactory, ServiceListener, BundleListener { private Hashtable locationToPids = new Hashtable(); private Hashtable existingBundleLocations = new Hashtable(); ConfigurationStore store; private PluginManager pluginManager; private ConfigurationDispatcher configurationDispatcher; // Constants static AdminPermission ADMIN_PERMISSION = new AdminPermission(); static String SERVICE_PID = Constants.SERVICE_PID; static String FACTORY_PID = "service.factoryPid"; static String BUNDLE_LOCATION = "service.bundleLocation"; static String DYNAMIC_BUNDLE_LOCATION = "dynamic.service.bundleLocation"; static String DUMMY_PROPERTY = "org.knopflerfish.dummy.property"; static String CM_RANKING = "service.cmRanking"; static String ANY_LOCATION = "*"; public ConfigurationAdminFactory(File storeDir) { storeDir.mkdirs(); try { this.store = new ConfigurationStore(storeDir); } catch (Exception e) { Activator.log.error( "Error while initializing configurations store", e); } pluginManager = new PluginManager(); configurationDispatcher = new ConfigurationDispatcher(pluginManager); lookForExisitingBundleLocations(); String filter = "(|(objectClass=" + ManagedServiceFactory.class.getName() + ")" + "(objectClass=" + ManagedService.class.getName() + ")" + "(objectClass=" + ConfigurationPlugin.class.getName() + "))"; try { Activator.bc.addServiceListener(this, filter); Activator.bc.addBundleListener(this); } catch (InvalidSyntaxException ignored) { } lookForAlreadyRegisteredServices(); } private void lookForAlreadyRegisteredServices() { lookForAlreadyRegisteredServices(ConfigurationPlugin.class); lookForAlreadyRegisteredServices(ManagedServiceFactory.class); lookForAlreadyRegisteredServices(ManagedService.class); } private void lookForAlreadyRegisteredServices(Class c) { ServiceReference[] srs = null; try { srs = Activator.bc.getServiceReferences(c.getName(), null); } catch (InvalidSyntaxException ignored) { } if (srs == null) { return; } for (int i = 0; i < srs.length; ++i) { serviceChanged(srs[i], ServiceEvent.REGISTERED, c.getName()); } } private void lookForExisitingBundleLocations() { Bundle[] bs = Activator.bc.getBundles(); for (int i = 0; bs != null && i < bs.length; ++i) { existingBundleLocations.put(bs[i].getLocation(), bs[i] .getLocation()); } } private boolean isNonExistingBundleLocation(String bundleLocation) { return bundleLocation != null && existingBundleLocations.get(bundleLocation) == null; } private ConfigurationDictionary bindLocationIfNeccesary( ServiceReference[] srs, ConfigurationDictionary d) throws IOException { if (d == null) { return null; } if (srs == null || srs.length == 0) { return d; } String configLocation = (String) d.get(BUNDLE_LOCATION); if (isNonExistingBundleLocation(configLocation)) { Boolean dynamicLocation = (Boolean) d.get(DYNAMIC_BUNDLE_LOCATION); if (dynamicLocation != null && dynamicLocation.booleanValue()) { configLocation = null; } } if (configLocation == null) { String fpid = (String) d.get(FACTORY_PID); String pid = (String) d.get(SERVICE_PID); String serviceLocation = srs[0].getBundle().getLocation(); ConfigurationDictionary copy = d.createCopy(); copy.put(BUNDLE_LOCATION, serviceLocation); copy.put(DYNAMIC_BUNDLE_LOCATION, Boolean.TRUE); store.store(pid, fpid, copy); return copy; } return d; } private void findAndUnbindConfigurationsDynamicallyBoundTo( String bundleLocation) { String filter = "(&(" + BUNDLE_LOCATION + "=" + bundleLocation + ")" + "(" + DYNAMIC_BUNDLE_LOCATION + "=" + Boolean.TRUE + "))"; try { Configuration[] configurations = listConfigurations(filter); for (int i = 0; configurations != null && i < configurations.length; ++i) { configurations[i].setBundleLocation(null); } } catch (Exception e) { Activator.log.error( "[CM] Error while unbinding configurations bound to " + bundleLocation, e); } } private ServiceReference[] filterOnMatchingLocations( ServiceReference[] srs, String configLocation) { if (srs.length == 1) { String serviceLocation = srs[0].getBundle().getLocation(); if (locationsMatch(serviceLocation, configLocation)) { return srs; } Activator.log .error("[CM] The bundle " + serviceLocation + " has registered a ManagedService(Factory) for a pid bound to " + configLocation); return new ServiceReference[0]; } Vector v = new Vector(); for (int i = 0; i < srs.length; ++i) { String serviceLocation = srs[i].getBundle().getLocation(); if (locationsMatch(serviceLocation, configLocation)) { v.addElement(srs[i]); } else { Activator.log .error("[CM] The bundle " + serviceLocation + " has registered a ManagedService(Factory) for a pid bound to " + configLocation); } } ServiceReference[] matching = new ServiceReference[v.size()]; v.copyInto(matching); return matching; } private boolean locationsMatch(String serviceLocation, String configLocation) { if (configLocation == null) { return false; } else if (configLocation.equals(ANY_LOCATION)) { return true; } else if (configLocation.equals(serviceLocation)) { return true; } else { return false; } } private void addToLocationToPidsAndCheck(ServiceReference sr) { if (sr == null) { return; } String bundleLocation = sr.getBundle().getLocation(); String pid = (String) sr.getProperty(SERVICE_PID); if (pid == null) { return; } Hashtable pidsForLocation = (Hashtable) locationToPids .get(bundleLocation); if (pidsForLocation == null) { pidsForLocation = new Hashtable(); locationToPids.put(bundleLocation, pidsForLocation); } if (pidsForLocation.contains(pid)) { Activator.log .error("[CM] Multiple ManagedServices registered from bundle " + bundleLocation + " for " + pid); } pidsForLocation.put(sr, pid); } private void removeFromLocationToPids(ServiceReference sr) { if (sr == null) { return; } String bundleLocation = sr.getBundle().getLocation(); Hashtable pidsForLocation = (Hashtable) locationToPids .get(bundleLocation); if (pidsForLocation == null) {
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -