Java tutorial
/** * Copyright (c) 2010-2015, openHAB.org and others. * * 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 */ package org.openhab.io.cv; import java.util.Dictionary; import java.util.HashMap; import java.util.HashSet; import java.util.Hashtable; import java.util.Map; import java.util.Set; import javax.servlet.ServletException; import javax.ws.rs.ApplicationPath; import org.apache.commons.lang.StringUtils; import org.atmosphere.cpr.AtmosphereServlet; import org.openhab.core.events.EventPublisher; import org.openhab.core.items.ItemRegistry; import org.openhab.io.cv.internal.resources.LoginResource; import org.openhab.core.persistence.PersistenceService; import org.openhab.core.persistence.QueryablePersistenceService; import org.openhab.io.cv.internal.resources.ReadResource; import org.openhab.io.cv.internal.resources.RrdResource; import org.openhab.io.cv.internal.resources.WriteResource; import org.openhab.io.net.http.SecureHttpContext; import org.openhab.io.servicediscovery.DiscoveryService; import org.openhab.io.servicediscovery.ServiceDescription; import org.openhab.model.core.ModelRepository; import org.openhab.ui.items.ItemUIRegistry; import org.osgi.framework.BundleContext; import org.osgi.framework.FrameworkUtil; import org.osgi.service.http.HttpContext; import org.osgi.service.http.HttpService; import org.osgi.service.http.NamespaceException; import org.slf4j.Logger; import org.slf4j.LoggerFactory; import com.sun.jersey.api.core.PackagesResourceConfig; import com.sun.jersey.core.util.FeaturesAndProperties; /** * This is the main component of the Cometvisu API; it gets all required services injected, * registers itself as a servlet on the HTTP service and adds the different rest resources * to this service. * * @author Tobias Brutigam * @since 1.4.0 */ @ApplicationPath(CVApplication.CV_SERVLET_ALIAS) public class CVApplication extends PackagesResourceConfig { public static final String CV_SERVLET_ALIAS = "/services/cv"; private static final Logger logger = LoggerFactory.getLogger(CVApplication.class); private int httpSSLPort; private int httpPort; private HttpService httpService; private DiscoveryService discoveryService; static private EventPublisher eventPublisher; static private ItemUIRegistry itemUIRegistry; static public ModelRepository modelRepository; static protected Map<String, QueryablePersistenceService> persistenceServices = new HashMap<String, QueryablePersistenceService>(); public CVApplication() { super("org.openhab.io.cv.internal.resources"); } public void setHttpService(HttpService httpService) { this.httpService = httpService; } public void unsetHttpService(HttpService httpService) { this.httpService = null; } public void setEventPublisher(EventPublisher eventPublisher) { CVApplication.eventPublisher = eventPublisher; } public void unsetEventPublisher(EventPublisher eventPublisher) { CVApplication.eventPublisher = null; } static public EventPublisher getEventPublisher() { return CVApplication.eventPublisher; } public void setItemUIRegistry(ItemUIRegistry itemUIRegistry) { CVApplication.itemUIRegistry = itemUIRegistry; } public void unsetItemUIRegistry(ItemRegistry itemUIRegistry) { CVApplication.itemUIRegistry = null; } static public ItemUIRegistry getItemUIRegistry() { return CVApplication.itemUIRegistry; } public void setModelRepository(ModelRepository modelRepository) { CVApplication.modelRepository = modelRepository; } public void unsetModelRepository(ModelRepository modelRepository) { CVApplication.modelRepository = null; } static public ModelRepository getModelRepository() { return CVApplication.modelRepository; } public void setDiscoveryService(DiscoveryService discoveryService) { this.discoveryService = discoveryService; } public void unsetDiscoveryService(DiscoveryService discoveryService) { this.discoveryService = null; } public void addPersistenceService(PersistenceService service) { if (service instanceof QueryablePersistenceService) persistenceServices.put(service.getName(), (QueryablePersistenceService) service); } public void removePersistenceService(PersistenceService service) { persistenceServices.remove(service.getName()); } static public Map<String, QueryablePersistenceService> getPersistenceServices() { return persistenceServices; } public void activate() { try { // we need to call the activator ourselves as this bundle is included in the lib folder com.sun.jersey.core.osgi.Activator jerseyActivator = new com.sun.jersey.core.osgi.Activator(); BundleContext bundleContext = FrameworkUtil.getBundle(this.getClass()).getBundleContext(); try { jerseyActivator.start(bundleContext); } catch (Exception e) { logger.error("Could not start Jersey framework", e); } httpPort = Integer.parseInt(bundleContext.getProperty("jetty.port")); httpSSLPort = Integer.parseInt(bundleContext.getProperty("jetty.port.ssl")); httpService.registerServlet(CV_SERVLET_ALIAS, new AtmosphereServlet(), getJerseyServletParams(), createHttpContext()); logger.info("Started Cometvisu API at " + CV_SERVLET_ALIAS); if (discoveryService != null) { discoveryService.registerService(getDefaultServiceDescription()); discoveryService.registerService(getSSLServiceDescription()); } } catch (ServletException se) { throw new RuntimeException(se); } catch (NamespaceException se) { throw new RuntimeException(se); } } public void deactivate() { if (this.httpService != null) { httpService.unregister(CV_SERVLET_ALIAS); logger.info("Stopped CometVisu API"); } if (discoveryService != null) { discoveryService.unregisterService(getDefaultServiceDescription()); discoveryService.unregisterService(getSSLServiceDescription()); } } /** * Creates a {@link SecureHttpContext} which handles the security for this * Servlet * @return a {@link SecureHttpContext} */ protected HttpContext createHttpContext() { HttpContext defaultHttpContext = httpService.createDefaultHttpContext(); return new SecureHttpContext(defaultHttpContext, "openHAB.org"); } @Override public Set<Class<?>> getClasses() { Set<Class<?>> result = new HashSet<Class<?>>(); result.add(LoginResource.class); result.add(ReadResource.class); result.add(WriteResource.class); result.add(RrdResource.class); return result; } private Dictionary<String, String> getJerseyServletParams() { Dictionary<String, String> jerseyServletParams = new Hashtable<String, String>(); jerseyServletParams.put("javax.ws.rs.Application", CVApplication.class.getName()); jerseyServletParams.put("org.atmosphere.core.servlet-mapping", CV_SERVLET_ALIAS + "/*"); jerseyServletParams.put("org.atmosphere.useWebSocket", "true"); jerseyServletParams.put("org.atmosphere.useNative", "true"); jerseyServletParams.put("org.atmosphere.cpr.AtmosphereInterceptor.disableDefaults", "true"); // use the default interceptors without PaddingAtmosphereInterceptor // see: https://groups.google.com/forum/#!topic/openhab/Z-DVBXdNiYE final String[] interceptors = { "org.atmosphere.interceptor.CacheHeadersInterceptor", "org.atmosphere.interceptor.AndroidAtmosphereInterceptor", "org.atmosphere.interceptor.SSEAtmosphereInterceptor", "org.atmosphere.interceptor.JSONPAtmosphereInterceptor", "org.atmosphere.interceptor.JavaScriptProtocol", "org.atmosphere.interceptor.OnDisconnectInterceptor" }; jerseyServletParams.put("org.atmosphere.cpr.AtmosphereInterceptor", StringUtils.join(interceptors, ",")); jerseyServletParams.put("org.atmosphere.cpr.broadcasterLifeCyclePolicy", "IDLE_DESTROY"); jerseyServletParams.put("org.atmosphere.cpr.CometSupport.maxInactiveActivity", "300000"); jerseyServletParams.put("com.sun.jersey.spi.container.ResourceFilter", "org.atmosphere.core.AtmosphereFilter"); // The BroadcasterCache is set in ResourceStateChangeListener.registerItems(), because otherwise // it gets somehow overridden by other registered servlets (e.g. the REST-bundle) // the other advantage of this solution is, that the BroadcasterCache class does not need to be exported by this package // jerseyServletParams.put("org.atmosphere.cpr.broadcasterCacheClass", "org.openhab.io.cv.internal.cache.CVBroadcasterCache"); // required because of bug http://java.net/jira/browse/JERSEY-361 jerseyServletParams.put(FeaturesAndProperties.FEATURE_XMLROOTELEMENT_PROCESSING, "true"); return jerseyServletParams; } private ServiceDescription getDefaultServiceDescription() { Hashtable<String, String> serviceProperties = new Hashtable<String, String>(); serviceProperties.put("uri", CV_SERVLET_ALIAS); return new ServiceDescription("_openhab-cv-server._tcp.local.", "openHAB-CV", httpPort, serviceProperties); } private ServiceDescription getSSLServiceDescription() { ServiceDescription description = getDefaultServiceDescription(); description.serviceType = "_openhab-cv-server-ssl._tcp.local."; description.serviceName = "openHAB-CV-ssl"; description.servicePort = httpSSLPort; return description; } }