/******************************************************************************* * Copyright 2012 Geoscience Australia * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. ******************************************************************************/ package au.gov.ga.earthsci.injectable; import java.util.Comparator; import java.util.List; import org.eclipse.core.runtime.IConfigurationElement; import org.eclipse.core.runtime.RegistryFactory; import org.eclipse.e4.core.contexts.ContextInjectionFactory; import org.eclipse.e4.core.contexts.IEclipseContext; import org.eclipse.e4.core.di.InjectorFactory; import org.slf4j.Logger; import org.slf4j.LoggerFactory; import au.gov.ga.earthsci.common.collection.ArrayListTreeMap; import au.gov.ga.earthsci.common.collection.ListSortedMap; import au.gov.ga.earthsci.common.util.ExtensionPointHelper; /** * Helper class for reading extensions that extend the injectable extension * point, and injects them into a provided {@link IEclipseContext}. * * @author Michael de Hoog (michael.dehoog@ga.gov.au) */ public final class Injector { private static final String INJECTOR_ID = "au.gov.ga.earthsci.injectables"; //$NON-NLS-1$ private static final Logger logger = LoggerFactory.getLogger(Injector.class); private Injector() { } public static void injectIntoContext(IEclipseContext context) { //first sort the configuration elements by priority, descending IConfigurationElement[] config = RegistryFactory.getRegistry().getConfigurationElementsFor(INJECTOR_ID); ListSortedMap<Integer, IConfigurationElement> sorted = new ArrayListTreeMap<Integer, IConfigurationElement>(new Comparator<Integer>() { @Override public int compare(Integer first, Integer second) { //reverse the order: return -first.compareTo(second); } }); for (IConfigurationElement element : config) { int priority = ExtensionPointHelper.getIntegerForProperty(element, "priority", 0); //$NON-NLS-1$ sorted.putSingle(priority, element); } //next iterate through them in sorted order for (List<IConfigurationElement> elements : sorted.values()) { for (IConfigurationElement element : elements) { try { boolean bind = "bind".equals(element.getName()); //$NON-NLS-1$ boolean inject = "inject".equals(element.getName()); //$NON-NLS-1$ boolean injectable = "injectable".equals(element.getName()); //$NON-NLS-1$ if (bind) { Class<?> implementationClass = ExtensionPointHelper.getClassForProperty(element, "class"); //$NON-NLS-1$ Class<?> bindingClass = ExtensionPointHelper.getClassForProperty(element, "binding"); //$NON-NLS-1$ InjectorFactory.getDefault().addBinding(bindingClass).implementedBy(implementationClass); } else if (inject || injectable) { Object object = element.createExecutableExtension("class"); //$NON-NLS-1$ ContextInjectionFactory.inject(object, context); if (inject) { IConfigurationElement[] types = element.getChildren("type"); //$NON-NLS-1$ for (IConfigurationElement type : types) { @SuppressWarnings("unchecked") Class<Object> c = (Class<Object>) ExtensionPointHelper.getClassForProperty(type, "class"); //$NON-NLS-1$ context.set(c, c.cast(object)); } IConfigurationElement[] names = element.getChildren("name"); //$NON-NLS-1$ for (IConfigurationElement name : names) { String n = name.getAttribute("value"); //$NON-NLS-1$ context.set(n, object); } if (types.length == 0 && names.length == 0) { @SuppressWarnings("unchecked") Class<Object> c = (Class<Object>) object.getClass(); context.set(c, object); } } } else { throw new IllegalArgumentException("Unknown injectable child: " + element.getName()); //$NON-NLS-1$ } } catch (Exception e) { logger.error("Error processing injectable", e); //$NON-NLS-1$ } } } } }