| /** |
| * Copyright (c) 2011, 2015 - Lunifera GmbH (Gross Enzersdorf, Austria), Loetz GmbH&Co.KG (69115 Heidelberg, Germany) |
| * All rights reserved. This program and the accompanying materials |
| * are made available under the terms of the Eclipse Public License v1.0 |
| * which accompanies this distribution, and is available at |
| * http://www.eclipse.org/legal/epl-v10.html |
| * |
| * Contributors: |
| * Florian Pirchner - Initial implementation |
| */ |
| package org.eclipse.osbp.runtime.web.vaadin.osgi.webapp; |
| |
| import java.util.ArrayList; |
| import java.util.Collections; |
| import java.util.Hashtable; |
| import java.util.Iterator; |
| import java.util.List; |
| import java.util.Map; |
| import java.util.UUID; |
| import java.util.concurrent.CopyOnWriteArrayList; |
| import java.util.concurrent.locks.Lock; |
| import java.util.concurrent.locks.ReentrantLock; |
| |
| import javax.servlet.ServletException; |
| |
| import org.eclipse.core.runtime.IStatus; |
| import org.eclipse.core.runtime.Status; |
| import org.eclipse.equinox.http.servlet.ExtendedHttpService; |
| import org.eclipse.osbp.runtime.web.vaadin.osgi.Activator; |
| import org.eclipse.osbp.runtime.web.vaadin.osgi.common.IOSGiUiProviderFactory; |
| import org.eclipse.osbp.runtime.web.vaadin.osgi.common.IVaadinApplication; |
| import org.eclipse.osbp.runtime.web.vaadin.osgi.common.VaadinConstants; |
| import org.eclipse.osbp.runtime.web.vaadin.osgi.common.VaadinStatusCodes; |
| import org.eclipse.osbp.runtime.web.vaadin.osgi.servlet.VaadinOSGiServlet; |
| import org.eclipse.osbp.runtime.web.vaadin.osgi.servlet.WebResourcesHttpContext; |
| import org.osgi.framework.BundleContext; |
| import org.osgi.framework.InvalidSyntaxException; |
| import org.osgi.framework.ServiceReference; |
| import org.osgi.service.component.ComponentContext; |
| import org.osgi.service.component.ComponentFactory; |
| import org.osgi.service.http.NamespaceException; |
| import org.osgi.util.tracker.ServiceTracker; |
| import org.slf4j.Logger; |
| import org.slf4j.LoggerFactory; |
| |
| import com.vaadin.server.UIProvider; |
| import com.vaadin.ui.UI; |
| |
| // TODO: Auto-generated Javadoc |
| /** |
| * Default implementation of {@link IVaadinApplication}. |
| */ |
| @SuppressWarnings("deprecation") |
| public class VaadinApplication implements IVaadinApplication { |
| |
| /** The Constant LOGGER. */ |
| private static final Logger LOGGER = LoggerFactory |
| .getLogger(VaadinApplication.class); |
| |
| /** The resource base. */ |
| private final String RESOURCE_BASE = "/VAADIN"; |
| |
| /** The context. */ |
| // OSGi |
| private ComponentContext context; |
| |
| /** The service tracker. */ |
| private HttpServiceTracker serviceTracker; |
| |
| /** The id. */ |
| // properties |
| private String id; |
| |
| /** The status. */ |
| private IStatus status; |
| |
| /** The name. */ |
| private String name = VaadinConstants.DEFAULT_APPLICATION_NAME; |
| |
| /** The ui alias. */ |
| private String uiAlias = VaadinConstants.DEFAULT_UI_ALIAS; |
| |
| /** The widgetset. */ |
| private String widgetset = ""; |
| |
| /** The production mode. */ |
| private boolean productionMode; |
| |
| /** The http application. */ |
| private String httpApplication = ""; |
| |
| /** The ui providers. */ |
| private List<OSGiUIProvider> uiProviders = new ArrayList<OSGiUIProvider>(1); |
| |
| /** The http service. */ |
| private ExtendedHttpService httpService; |
| |
| /** The provider factories. */ |
| private List<IOSGiUiProviderFactory> providerFactories = new CopyOnWriteArrayList<IOSGiUiProviderFactory>(); |
| |
| /** The ui factories. */ |
| private List<UiFactoryWrapper> uiFactories = new CopyOnWriteArrayList<UiFactoryWrapper>(); |
| |
| /** The started. */ |
| // lifecycle |
| private boolean started; |
| |
| /** The access lock. */ |
| private final Lock accessLock = new ReentrantLock(); |
| |
| /** The filter. */ |
| // web |
| // private IniShiroFilter filter; |
| |
| /** The servlet. */ |
| private VaadinOSGiServlet servlet; |
| |
| /** The default context. */ |
| private WebResourcesHttpContext defaultContext; |
| |
| /** The servlet alias. */ |
| private String servletAlias; |
| |
| /** |
| * Called by OSGi-DS. |
| * |
| * @param context |
| * the context |
| * @param properties |
| * the properties |
| */ |
| protected void activate(ComponentContext context, |
| Map<String, Object> properties) { |
| LOGGER.debug("{} started", getName()); |
| this.context = context; |
| this.id = UUID.randomUUID().toString(); |
| |
| modified(context, properties); |
| } |
| |
| /** |
| * Called by OSGi-DS. |
| * |
| * @param context |
| * the context |
| * @param properties |
| * the properties |
| */ |
| protected void deactivate(ComponentContext context, |
| Map<String, Object> properties) { |
| |
| destroy(); |
| |
| this.context = null; |
| |
| LOGGER.debug("{} stopped", getName()); |
| } |
| |
| /** |
| * Called by OSGi-DS if service properties became changed. |
| * |
| * @param context |
| * the context |
| * @param properties |
| * the properties |
| */ |
| protected void modified(ComponentContext context, |
| Map<String, Object> properties) { |
| |
| System.out.println("Update"); |
| LOGGER.debug("Calling update"); |
| |
| try { |
| accessLock.lock(); |
| |
| stop(); |
| |
| id = "NOT SPECIFIED"; |
| if (properties.get(VaadinConstants.EXTERNAL_PID) != null) { |
| id = (String) properties.get(VaadinConstants.EXTERNAL_PID); |
| } |
| |
| String name = VaadinConstants.DEFAULT_APPLICATION_NAME; |
| if (properties.get(VaadinConstants.APPLICATION_NAME) != null) { |
| name = (String) properties |
| .get(VaadinConstants.APPLICATION_NAME); |
| } |
| |
| String httpApplicationName = null; |
| if (properties.get(VaadinConstants.HTTP_APPLICATION_NAME) != null) { |
| httpApplicationName = (String) properties |
| .get(VaadinConstants.HTTP_APPLICATION_NAME); |
| } |
| |
| String widgetsetName = null; |
| if (properties.get(VaadinConstants.WIDGETSET) != null) { |
| widgetsetName = (String) properties |
| .get(VaadinConstants.WIDGETSET); |
| } |
| |
| String uialias = null; |
| if (properties.get(VaadinConstants.UI_ALIAS) != null) { |
| uialias = (String) properties.get(VaadinConstants.UI_ALIAS); |
| } |
| |
| boolean productionMode = false; |
| if (properties.get(VaadinConstants.PRODUCTIONMODE) != null) { |
| productionMode = Boolean.valueOf((String) properties |
| .get(VaadinConstants.PRODUCTIONMODE)); |
| } |
| |
| setName(name); |
| setWidgetSetName(widgetsetName); |
| setHttpApplication(httpApplicationName); |
| setUIAlias(uialias); |
| setProductionMode(productionMode); |
| |
| // create and set the UI provider to the application |
| OSGiUIProvider provider = createUIProvider(); |
| if (provider != null) { |
| addUIProvider(provider); |
| } |
| |
| // properties.put(VaadinConstants.APPLICATION_ID, getId()); |
| |
| // start the application again |
| // |
| start(); |
| |
| LOGGER.debug( |
| "New IVaadinApplication {} deployed on 'http application' {}", |
| getName(), getHttpApplication()); |
| |
| } finally { |
| accessLock.unlock(); |
| } |
| } |
| |
| /** |
| * Creates the UI provider for the given application name. |
| * |
| * @return the OS gi ui provider |
| */ |
| protected OSGiUIProvider createUIProvider() { |
| |
| // iterate all the factories with match application name filter |
| OSGiUIProvider provider = null; |
| for (UiFactoryWrapper factory : uiFactories) { |
| if (name.equals(factory.vaadinApplicationFilter)) { |
| provider = factory.createProvider(name); |
| break; |
| } |
| } |
| |
| // if no UI provider was found, try to find a factory with empty |
| // application name filter |
| if (provider == null) { |
| for (UiFactoryWrapper factory : uiFactories) { |
| if (factory.vaadinApplicationFilter == null) { |
| provider = factory.createProvider(name); |
| break; |
| } |
| } |
| } |
| return provider; |
| } |
| |
| /* (non-Javadoc) |
| * @see org.eclipse.osbp.runtime.web.vaadin.osgi.common.IVaadinApplication#getStatus() |
| */ |
| @Override |
| public IStatus getStatus() { |
| return status != null ? status : Status.OK_STATUS; |
| } |
| |
| /* (non-Javadoc) |
| * @see org.eclipse.osbp.runtime.web.vaadin.osgi.common.IVaadinApplication#getId() |
| */ |
| @Override |
| public String getId() { |
| return id; |
| } |
| |
| /** |
| * Returns the name of that http application. |
| * |
| * @return the name |
| */ |
| @Override |
| public String getName() { |
| return name; |
| } |
| |
| /** |
| * Sets the name of that application. |
| * |
| * @param name |
| * the new name |
| */ |
| protected void setName(String name) { |
| this.name = isStringValid(name) ? name |
| : VaadinConstants.DEFAULT_APPLICATION_NAME; |
| } |
| |
| /* (non-Javadoc) |
| * @see org.eclipse.osbp.runtime.web.vaadin.osgi.common.IVaadinApplication#getUIAlias() |
| */ |
| @Override |
| public String getUIAlias() { |
| return uiAlias; |
| } |
| |
| /** |
| * Sets the alias that is used to access the vaadin UI. |
| * |
| * @param uiAlias |
| * the new UI alias |
| */ |
| protected void setUIAlias(String uiAlias) { |
| this.uiAlias = isStringValid(uiAlias) ? uiAlias |
| : VaadinConstants.DEFAULT_UI_ALIAS; |
| } |
| |
| /* (non-Javadoc) |
| * @see org.eclipse.osbp.runtime.web.vaadin.osgi.common.IVaadinApplication#getHttpApplication() |
| */ |
| @Override |
| public String getHttpApplication() { |
| return httpApplication; |
| } |
| |
| /** |
| * Sets the name of the IHttpApplication that vaadin application |
| * should be deployed at. |
| * |
| * @param httpApplication |
| * the httpApplication to set |
| */ |
| protected void setHttpApplication(String httpApplication) { |
| this.httpApplication = isStringValid(httpApplication) ? httpApplication |
| : ""; |
| } |
| |
| /* (non-Javadoc) |
| * @see org.eclipse.osbp.runtime.web.vaadin.osgi.common.IVaadinApplication#getWidgetSetName() |
| */ |
| @Override |
| public String getWidgetSetName() { |
| return widgetset; |
| } |
| |
| /** |
| * Sets the name of the widgetset. |
| * |
| * @param widgetset |
| * the new widget set name |
| */ |
| protected void setWidgetSetName(String widgetset) { |
| this.widgetset = isStringValid(widgetset) ? widgetset : ""; |
| } |
| |
| /* (non-Javadoc) |
| * @see org.eclipse.osbp.runtime.web.vaadin.osgi.common.IVaadinApplication#isProductionMode() |
| */ |
| @Override |
| public boolean isProductionMode() { |
| return productionMode; |
| } |
| |
| /** |
| * Sets the production mode. |
| * |
| * @param productionMode |
| * the productionMode to set |
| */ |
| protected void setProductionMode(boolean productionMode) { |
| this.productionMode = productionMode; |
| } |
| |
| /** |
| * Returns true if the string is not <code>null</code> and not empty string. |
| * |
| * @param value |
| * the value |
| * @return true, if is string valid |
| */ |
| private boolean isStringValid(String value) { |
| return value != null && !value.trim().equals(""); |
| } |
| |
| /* (non-Javadoc) |
| * @see org.eclipse.osbp.runtime.web.vaadin.osgi.common.IVaadinApplication#isStarted() |
| */ |
| @Override |
| public boolean isStarted() { |
| return started; |
| } |
| |
| /* (non-Javadoc) |
| * @see org.eclipse.osbp.runtime.web.vaadin.osgi.common.IVaadinApplication#isDeployed() |
| */ |
| @Override |
| public boolean isDeployed() { |
| return httpService != null; |
| } |
| |
| /** |
| * Is called to start the application. All resources should be registered |
| * and the http service is registered. |
| */ |
| @Override |
| public void start() { |
| if (started) { |
| LOGGER.debug("HttpApplication {} is already started", getName()); |
| return; |
| } |
| |
| // ensure that only one threas manipulates the contents |
| accessLock.lock(); |
| try { |
| // start the tracker to observe handler |
| try { |
| serviceTracker = new HttpServiceTracker( |
| context.getBundleContext(), this); |
| serviceTracker.open(); |
| } catch (InvalidSyntaxException e) { |
| LOGGER.error("{}", e); |
| setStatus(VaadinStatusCodes.createHttpServiceTracker(e)); |
| |
| // stop the application |
| stop(true); |
| return; |
| } |
| |
| // add all yet existing handler from the tracker |
| ExtendedHttpService httpService = serviceTracker.getService(); |
| if (httpService != null) { |
| try { |
| setHttpService(httpService); |
| } catch (AppException e) { |
| LOGGER.error(String |
| .format("Stopping vaadin application %s since setting http service caused a problem.", |
| getName())); |
| setStatus(VaadinStatusCodes.createSettingHttpService(e)); |
| |
| // stop the application |
| stop(true); |
| return; |
| } |
| } |
| |
| started = true; |
| } finally { |
| accessLock.unlock(); |
| } |
| |
| setStatus(VaadinStatusCodes.OK_STATUS); |
| } |
| |
| /** |
| * Is called by the service tracker to add a new http service. |
| * |
| * @param httpService |
| * the http service |
| */ |
| protected void httpServiceAdded(ExtendedHttpService httpService) { |
| if (!isStarted()) { |
| return; |
| } |
| |
| // ensure that only one threads manipulates the contents |
| accessLock.lock(); |
| try { |
| setHttpService(httpService); |
| } catch (AppException e) { |
| LOGGER.error(String |
| .format("Stopping vaadin application %s since setting http service caused a problem.", |
| getName())); |
| setStatus(VaadinStatusCodes.createSettingHttpService(e)); |
| |
| // stop the application |
| stop(); |
| return; |
| |
| } finally { |
| accessLock.unlock(); |
| } |
| |
| setStatus(VaadinStatusCodes.OK_STATUS); |
| } |
| |
| /** |
| * Is called by the service tracker to remove a registered http service. |
| * |
| * @param httpService |
| * the http service |
| */ |
| protected void httpServiceRemoved(ExtendedHttpService httpService) { |
| if (!isStarted()) { |
| return; |
| } |
| |
| // ensure that only one threas manipulates the contents |
| accessLock.lock(); |
| try { |
| unsetHttpService(httpService); |
| } finally { |
| accessLock.unlock(); |
| } |
| } |
| |
| /** |
| * Sets the given http service to the internal cache. |
| * |
| * @param httpService |
| * the new http service |
| * @throws AppException |
| * the app exception |
| */ |
| protected void setHttpService(ExtendedHttpService httpService) |
| throws AppException { |
| if (this.httpService != null) { |
| LOGGER.error("HttpService already present. Abort operation!"); |
| return; |
| } |
| |
| this.httpService = httpService; |
| |
| registerWebArtifacts(); |
| } |
| |
| /** |
| * Registers servlets, filters and resources. |
| * |
| * @throws AppException |
| * the app exception |
| */ |
| protected void registerWebArtifacts() throws AppException { |
| Hashtable<String, String> properties = new Hashtable<String, String>(); |
| properties.put(VaadinConstants.EXTERNAL_PID, getId()); |
| properties.put(VaadinConstants.APPLICATION_NAME, getName()); |
| properties.put(VaadinConstants.WIDGETSET, getWidgetSetName()); |
| properties.put("widgetset", getWidgetSetName()); |
| properties.put("productionMode", Boolean.toString(isProductionMode())); |
| |
| servlet = new VaadinOSGiServlet(this); |
| servletAlias = String.format("/%s", getUIAlias()); |
| defaultContext = new WebResourcesHttpContext(Activator |
| .getBundleContext().getBundle()); |
| // filter = new IniShiroFilter(); |
| try { |
| // try { |
| // httpService.registerFilter("/", filter, properties, |
| // defaultContext); |
| // } catch (Exception e) { |
| // LOGGER.error("{}", e); |
| // throw new AppException(e); |
| // } |
| httpService.registerResources(RESOURCE_BASE, RESOURCE_BASE, |
| defaultContext); |
| httpService.registerServlet(servletAlias, servlet, properties, |
| defaultContext); |
| } catch (ServletException e) { |
| LOGGER.error("{}", e); |
| throw new AppException(e); |
| } catch (NamespaceException e) { |
| LOGGER.error("{}", e); |
| throw new AppException(e); |
| } |
| } |
| |
| /** |
| * Sets the current status. |
| * |
| * @param status |
| * the new status |
| */ |
| private void setStatus(IStatus status) { |
| this.status = status; |
| |
| if (status != null && status != VaadinStatusCodes.OK_STATUS) { |
| LOGGER.warn("Status was set to vaadin application {}: {}", |
| getName(), status); |
| } |
| } |
| |
| /** |
| * Unregisters all registered servlets, filters and resources. |
| */ |
| protected void unregisterWebArtifacts() { |
| try { |
| if (servletAlias != null) { |
| httpService.unregister(servletAlias); |
| } |
| } catch (Exception e) { |
| // May throw exception if http service was stopped by |
| // tracker.close() |
| LOGGER.info("{}", e.getMessage()); |
| } finally { |
| servletAlias = null; |
| servlet = null; |
| } |
| |
| // try { |
| // if (filter != null) { |
| // httpService.unregisterFilter(filter); |
| // } |
| // } catch (Exception e) { |
| // LOGGER.info("{}", e.getMessage()); |
| // } finally { |
| // filter = null; |
| // } |
| |
| try { |
| httpService.unregister(RESOURCE_BASE); |
| } catch (Exception e) { |
| LOGGER.info("{}", e.getMessage()); |
| } finally { |
| } |
| } |
| |
| /** |
| * Removes the given http service from the internal cache. |
| * |
| * @param httpService |
| * the http service |
| */ |
| protected void unsetHttpService(ExtendedHttpService httpService) { |
| if (this.httpService == null) { |
| LOGGER.error("HttpService can not be unset! No instance set yet!"); |
| return; |
| } |
| |
| if (this.httpService != httpService) { |
| LOGGER.error("Tries to unset different http service. Operation aborted."); |
| return; |
| } |
| |
| // unregister all registered artifacts |
| unregisterWebArtifacts(); |
| |
| this.httpService = null; |
| } |
| |
| /** |
| * Is called to stop the application. All resources should be unregistered |
| * and the http service will become disposed. |
| */ |
| @Override |
| public void stop() { |
| stop(false); |
| } |
| |
| /** |
| * Stops the application. If true, then the started state will no be |
| * checked. |
| * |
| * @param force |
| * the force |
| */ |
| protected void stop(boolean force) { |
| if (!force && !started) { |
| LOGGER.debug("HttpApplication {} not started", getName()); |
| return; |
| } |
| |
| // ensure that only one threads manipulates the contents |
| accessLock.lock(); |
| try { |
| if (serviceTracker != null) { |
| serviceTracker.close(); |
| serviceTracker = null; |
| } |
| |
| } finally { |
| accessLock.unlock(); |
| started = false; |
| } |
| } |
| |
| /** |
| * Destroys the http application. |
| */ |
| public void destroy() { |
| try { |
| accessLock.lock(); |
| if (isStarted()) { |
| stop(); |
| } |
| |
| uiProviders = null; |
| |
| } finally { |
| accessLock.unlock(); |
| } |
| } |
| |
| /** |
| * Adds a new {@link UIProvider} to the web application. |
| * |
| * @param provider |
| * the provider |
| */ |
| protected void addUIProvider(OSGiUIProvider provider) { |
| if (!uiProviders.contains(provider)) { |
| uiProviders.add(provider); |
| } |
| } |
| |
| /** |
| * Removes an {@link UIProvider} from the web application. |
| * |
| * @param provider |
| * the provider |
| */ |
| protected void removeUIProvider(OSGiUIProvider provider) { |
| if (!isActive()) { |
| // component deactivated |
| return; |
| } |
| |
| uiProviders.remove(provider); |
| } |
| |
| /** |
| * Removes an {@link UIProvider} for the given component factory that is |
| * used created UI instances. |
| * |
| * @param uiFactory |
| * the ui factory |
| */ |
| protected void removeUIProviderForFactory(ComponentFactory uiFactory) { |
| if (!isActive()) { |
| return; |
| } |
| |
| for (Iterator<OSGiUIProvider> iterator = uiProviders.iterator(); iterator |
| .hasNext();) { |
| OSGiUIProvider provider = iterator.next(); |
| if (provider.getUIFactory() == uiFactory) { |
| iterator.remove(); |
| } |
| } |
| } |
| |
| /** |
| * Returns true if the component is active. |
| * |
| * @return true, if is active |
| */ |
| private boolean isActive() { |
| return context != null; |
| } |
| |
| /* (non-Javadoc) |
| * @see org.eclipse.osbp.runtime.web.vaadin.osgi.common.IVaadinApplication#getUiProviders() |
| */ |
| @Override |
| public List<OSGiUIProvider> getUiProviders() { |
| return Collections.unmodifiableList(uiProviders); |
| } |
| |
| /** |
| * Creates a filter string. |
| * |
| * @param httpApplication |
| * the http application |
| * @return the string |
| */ |
| private String createHttpServiceFilterString(String httpApplication) { |
| String filterString = null; |
| if (httpApplication != null && !httpApplication.equals("")) { |
| filterString = String |
| .format("(&(objectClass=org.eclipse.equinox.http.servlet.ExtendedHttpService)(osbp.http.name=%s))", |
| httpApplication); |
| } else { |
| filterString = String |
| .format("(objectClass=org.eclipse.equinox.http.servlet.ExtendedHttpService)", |
| httpApplication); |
| } |
| return filterString; |
| } |
| |
| /** |
| * Adds the OSGi UI provider factory. |
| * |
| * @param providerFactory |
| * the provider factory |
| */ |
| protected void addUIProviderFactory(IOSGiUiProviderFactory providerFactory) { |
| providerFactories.add(providerFactory); |
| } |
| |
| /** |
| * Removes the OSGi UI provider factory. |
| * |
| * @param providerFactory |
| * the provider factory |
| */ |
| protected void removeUIProviderFactory( |
| IOSGiUiProviderFactory providerFactory) { |
| if (!isActive()) { |
| // component deactivated |
| return; |
| } |
| providerFactories.remove(providerFactory); |
| } |
| |
| /** |
| * Called by OSGi-DS and adds a component factory that is used to create |
| * instances of UIs. |
| * |
| * @param reference |
| * the reference |
| */ |
| protected void addUIFactory(ServiceReference<ComponentFactory> reference) { |
| try { |
| accessLock.lock(); |
| |
| LOGGER.debug("Adding ui factory"); |
| |
| // parse the target of service |
| // |
| String name = (String) reference.getProperty("component.factory"); |
| String[] tokens = name.split("/"); |
| if (tokens.length != 2) { |
| LOGGER.error( |
| "UiFactory {} does not meet syntax. (org.eclipse.osbp.web.vaadin.UI/[uiclass]@[vaadinApp]) Eg: org.eclipse.osbp.web.vaadin.UI/org.eclipse.osbp.examples.runtime.web.vaadin.standalone.Vaadin7StandaloneDemoUI@StandaloneDemo", |
| name); |
| return; |
| } |
| |
| String uiClassName; |
| String vaadinApplication; |
| String[] innerTokens = tokens[1].split("@"); |
| if (innerTokens.length == 1) { |
| uiClassName = innerTokens[0]; |
| vaadinApplication = null; |
| } else { |
| uiClassName = innerTokens[0]; |
| vaadinApplication = innerTokens[1]; |
| } |
| |
| // register factory internally |
| // |
| uiFactories.add(new UiFactoryWrapper(vaadinApplication, |
| uiClassName, reference)); |
| |
| } finally { |
| accessLock.unlock(); |
| } |
| } |
| |
| /** |
| * Called by OSGi-DS and removes a component factory that is used to create |
| * instances of UIs. |
| * |
| * @param factory |
| * the factory |
| * @param properties |
| * the properties |
| */ |
| protected void removeUIFactory(ComponentFactory factory, |
| Map<String, Object> properties) { |
| try { |
| accessLock.lock(); |
| removeUIProviderForFactory(factory); |
| } finally { |
| accessLock.unlock(); |
| } |
| } |
| |
| /** |
| * Update the web application with the new UI provider. |
| * |
| * @param uiProvider |
| * the ui provider |
| */ |
| private void uiProviderAdded(OSGiUIProvider uiProvider) { |
| try { |
| accessLock.lock(); |
| if (uiProvider.getVaadinApplication() == null) { |
| addUIProvider(uiProvider); |
| } else { |
| if (uiProvider.getVaadinApplication().equals(getName())) { |
| addUIProvider(uiProvider); |
| } |
| } |
| } finally { |
| accessLock.unlock(); |
| } |
| } |
| |
| /** |
| * A wrapper class to keep information about pending factory. Pending means |
| * that the service was not activated yet. |
| */ |
| private class UiFactoryWrapper { |
| |
| /** The vaadin application filter. */ |
| private final String vaadinApplicationFilter; |
| |
| /** The reference. */ |
| private final ServiceReference<ComponentFactory> reference; |
| |
| /** The ui class name. */ |
| private final String uiClassName; |
| |
| /** |
| * Instantiates a new ui factory wrapper. |
| * |
| * @param vaadinApplicationFilter |
| * the vaadin application filter |
| * @param uiClassName |
| * the ui class name |
| * @param reference |
| * the reference |
| */ |
| public UiFactoryWrapper(String vaadinApplicationFilter, |
| String uiClassName, ServiceReference<ComponentFactory> reference) { |
| super(); |
| this.vaadinApplicationFilter = vaadinApplicationFilter; |
| this.uiClassName = uiClassName; |
| this.reference = reference; |
| } |
| |
| /** |
| * Creates the provider. |
| * |
| * @param vaadinApplication |
| * the vaadin application |
| * @return the OS gi ui provider |
| */ |
| @SuppressWarnings("unchecked") |
| public OSGiUIProvider createProvider(String vaadinApplication) { |
| if (vaadinApplicationFilter != null |
| && !vaadinApplicationFilter.equals(vaadinApplication)) { |
| return null; |
| } |
| |
| ComponentFactory uiFactory = reference.getBundle() |
| .getBundleContext().getService(reference); |
| |
| Class<? extends UI> uiClass = null; |
| try { |
| uiClass = (Class<? extends UI>) reference.getBundle() |
| .loadClass(uiClassName); |
| } catch (ClassNotFoundException e) { |
| throw new IllegalStateException(e); |
| } |
| |
| // iterates all UI provider factories to find a proper UI provider |
| OSGiUIProvider uiProvider = null; |
| for (IOSGiUiProviderFactory providerFactory : providerFactories) { |
| uiProvider = providerFactory.createUiProvider( |
| vaadinApplication, uiClass); |
| if (uiProvider == null) { |
| continue; |
| } |
| uiProvider.setUIFactory(uiFactory); |
| break; |
| } |
| |
| // If no provider was found for the given vaadin application, then |
| // add a default one |
| if (uiProvider == null) { |
| uiProvider = new OSGiUIProvider(vaadinApplication, uiClass); |
| uiProvider.setUIFactory(uiFactory); |
| } |
| |
| // handle added UI provider |
| uiProviderAdded(uiProvider); |
| |
| return uiProvider; |
| } |
| } |
| |
| /** |
| * The Class HttpServiceTracker. |
| */ |
| public class HttpServiceTracker extends |
| ServiceTracker<ExtendedHttpService, ExtendedHttpService> { |
| |
| /** The logger. */ |
| @SuppressWarnings("unused") |
| private Logger logger = LoggerFactory |
| .getLogger(HttpServiceTracker.class); |
| |
| /** |
| * Instantiates a new http service tracker. |
| * |
| * @param ctx |
| * the ctx |
| * @param webApplication |
| * the web application |
| * @throws InvalidSyntaxException |
| * the invalid syntax exception |
| */ |
| public HttpServiceTracker(BundleContext ctx, |
| IVaadinApplication webApplication) |
| throws InvalidSyntaxException { |
| super(ctx, ctx |
| .createFilter(createHttpServiceFilterString(webApplication |
| .getHttpApplication())), null); |
| } |
| |
| /* (non-Javadoc) |
| * @see org.osgi.util.tracker.ServiceTracker#addingService(org.osgi.framework.ServiceReference) |
| */ |
| @Override |
| public ExtendedHttpService addingService( |
| ServiceReference<ExtendedHttpService> reference) { |
| ExtendedHttpService service = super.addingService(reference); |
| |
| VaadinApplication.this.httpServiceAdded(service); |
| |
| return service; |
| } |
| |
| /* (non-Javadoc) |
| * @see org.osgi.util.tracker.ServiceTracker#removedService(org.osgi.framework.ServiceReference, java.lang.Object) |
| */ |
| @Override |
| public void removedService( |
| ServiceReference<ExtendedHttpService> reference, |
| ExtendedHttpService service) { |
| super.removedService(reference, service); |
| |
| VaadinApplication.this.httpServiceRemoved(service); |
| } |
| } |
| |
| } |