001/* 002 * Copyright (c) 2006-2011 Nuxeo SA (http://nuxeo.com/) and others. 003 * 004 * All rights reserved. This program and the accompanying materials 005 * are made available under the terms of the Eclipse Public License v1.0 006 * which accompanies this distribution, and is available at 007 * http://www.eclipse.org/legal/epl-v10.html 008 * 009 * Contributors: 010 * Nuxeo - initial API and implementation 011 * 012 * $Id$ 013 */ 014 015package org.nuxeo.runtime.osgi; 016 017import java.net.URL; 018 019import org.apache.commons.logging.Log; 020import org.apache.commons.logging.LogFactory; 021import org.nuxeo.common.Environment; 022import org.nuxeo.runtime.api.Framework; 023import org.osgi.framework.Bundle; 024import org.osgi.framework.BundleActivator; 025import org.osgi.framework.BundleContext; 026import org.osgi.framework.ServiceReference; 027import org.osgi.service.packageadmin.PackageAdmin; 028 029/** 030 * The default BundleActivator for NXRuntime over an OSGi comp. platform. 031 * 032 * @author <a href="mailto:bs@nuxeo.com">Bogdan Stefanescu</a> 033 */ 034public class OSGiRuntimeActivator implements BundleActivator { 035 036 private static final Log log = LogFactory.getLog(OSGiRuntimeActivator.class); 037 038 private static OSGiRuntimeActivator instance; 039 040 protected OSGiRuntimeService runtime; 041 042 protected OSGiComponentLoader componentLoader; 043 044 protected ServiceReference pkgAdmin; 045 046 protected BundleContext context; 047 048 public static OSGiRuntimeActivator getInstance() { 049 return instance; 050 } 051 052 @Override 053 public void start(BundleContext context) { 054 log.info("Starting Runtime Activator"); 055 instance = this; 056 this.context = context; 057 058 pkgAdmin = context.getServiceReference(PackageAdmin.class.getName()); 059 060 // assert the environment is setup 061 if (Environment.getDefault() == null) { 062 throw new IllegalStateException("Environment is not setup"); 063 } 064 065 // create the runtime 066 runtime = new OSGiRuntimeService(context); 067 068 // load main config file if any 069 URL config = context.getBundle().getResource("/OSGI-INF/nuxeo.properties"); 070 if (config != null) { 071 System.setProperty(OSGiRuntimeService.PROP_CONFIG_DIR, config.toExternalForm()); 072 } 073 074 initialize(runtime); 075 // start it 076 Framework.initialize(runtime); 077 // register bundle component loader 078 componentLoader = new OSGiComponentLoader(runtime); 079 // TODO register osgi services 080 } 081 082 @Override 083 public void stop(BundleContext context) { 084 log.info("Stopping Runtime Activator"); 085 instance = null; 086 pkgAdmin = null; 087 // remove component loader 088 componentLoader.uninstall(); 089 componentLoader = null; 090 // unregister 091 Framework.shutdown(); 092 uninitialize(runtime); 093 runtime = null; 094 context = null; 095 } 096 097 public Bundle getBundle(String name) { 098 if (pkgAdmin == null) { 099 return null; 100 } 101 PackageAdmin pa = (PackageAdmin) context.getService(pkgAdmin); 102 Bundle[] bundles = pa.getBundles(name, null); 103 context.ungetService(pkgAdmin); 104 return bundles == null ? null : bundles[0]; 105 } 106 107 /** 108 * Load a class from another bundle given its reference as <code>bundleSymbolicName:className</code> If no 109 * <code>bundleSymbolicName:</code> prefix is given then a classForName will be done 110 * 111 * @param ref 112 * @return 113 */ 114 public Class<?> loadClass(String ref) throws ReflectiveOperationException { 115 int i = ref.indexOf(':'); 116 if (i == -1) { 117 return Class.forName(ref); 118 } 119 return loadClass(ref.substring(0, i), ref.substring(i + 1)); 120 } 121 122 public Class<?> loadClass(String bundleName, String className) throws ReflectiveOperationException { 123 Bundle bundle = getBundle(bundleName); 124 if (bundle == null) { 125 throw new ClassNotFoundException("No bundle found with name: " + bundleName + ". Unable to load class " 126 + className); 127 } 128 return bundle.loadClass(className); 129 } 130 131 public Object newInstance(String ref) throws ReflectiveOperationException { 132 return loadClass(ref).newInstance(); 133 } 134 135 public Object newInstance(String bundleName, String className) throws ReflectiveOperationException { 136 return loadClass(bundleName, className).newInstance(); 137 } 138 139 /** 140 * Gives a chance to derived classes to initialize them before the runtime is started. 141 * 142 * @param runtime the current runtime 143 */ 144 protected void initialize(OSGiRuntimeService runtime) { 145 // do nothing 146 } 147 148 /** 149 * Gives a chance to derived classes to uninitialize them after the runtime is stopped. 150 * 151 * @param runtime the current runtime 152 */ 153 protected void uninitialize(OSGiRuntimeService runtime) { 154 // do nothing 155 } 156 157}