package org.gcube.smartgears.configuration.application; import static org.gcube.smartgears.utils.Utils.closeSafely; import static org.gcube.smartgears.utils.Utils.unchecked; import java.io.InputStream; import java.lang.reflect.Modifier; import java.util.HashSet; import java.util.LinkedList; import java.util.List; import java.util.ServiceLoader; import java.util.Set; import javax.xml.bind.JAXBContext; import javax.xml.bind.JAXBException; import org.gcube.smartgears.extensions.ApplicationExtension; import org.gcube.smartgears.handlers.application.ApplicationLifecycleHandler; import org.gcube.smartgears.handlers.application.RequestHandler; import org.gcube.smartgears.handlers.application.lifecycle.ProfileManager; import org.gcube.smartgears.handlers.application.request.RequestAccounting; import org.gcube.smartgears.handlers.application.request.RequestValidator; /** * Binds {@link ApplicationConfiguration}s to and from XML serialisations. * * @author Fabio Simeoni * */ public class ApplicationConfigurationBinder { /** * Returns the application configuration from its XML serialisation. * * @param stream the serialisation * @return the configuration * @throws RuntimeException if the serialisation is invalid */ public ApplicationConfiguration bind(InputStream stream) { try { JAXBContext ctx = JAXBContext.newInstance(DefaultApplicationConfiguration.class); return (ApplicationConfiguration) ctx.createUnmarshaller().unmarshal(stream); } catch (JAXBException e) { throw new RuntimeException("invalid service configuration", e); } finally { closeSafely(stream); } } /** * Returns the handlers of the application from their XML serialisation. * * @param stream the serialisation * @return the handlers * @throws RuntimeException if the serialisation is invalid */ public ApplicationHandlers bindHandlers(ClassLoader classLoader) { List requestHandlers = new LinkedList(); //ADDING BASE Handler (order is important) requestHandlers.add(new RequestValidator()); requestHandlers.add(new RequestAccounting()); //TODO scan RequestHAndler form classloader List lifecycleHandlers = new LinkedList(); //ADDING BASE Handler (order is important) lifecycleHandlers.add(new ProfileManager()); //TODO scan ApplicationLifecycleHandler form classloader return new ApplicationHandlers(lifecycleHandlers, requestHandlers); } /** * Returns the extensions of the application from their XML serialisation. * * @param stream the serialisation * @return the extensions * @throws RuntimeException if the serialisation is invalid */ public ApplicationExtensions bindExtensions(InputStream stream) { //collects handler classes Set> classes = scanForExtensions(); try { JAXBContext ctx = JAXBContext.newInstance(classes.toArray(new Class[0])); return (ApplicationExtensions) ctx.createUnmarshaller().unmarshal(stream); } catch (JAXBException e) { throw unchecked(e); } finally { closeSafely(stream); } } private Set> scanForExtensions() throws RuntimeException { @SuppressWarnings("all") ServiceLoader handlerLoader = (ServiceLoader) ServiceLoader.load(ApplicationExtension.class); Set> scanned = new HashSet>(); for (ApplicationExtension handler : handlerLoader) { Class handlerClass = handler.getClass(); if (handlerClass.isInterface() || handlerClass.getModifiers() == Modifier.ABSTRACT) continue; else scanned.add(handlerClass); } //add top-level configuration scanned.add(ApplicationExtensions.class); return scanned; } public void scanForApplicationHandlers(ClassLoader currentClassLoader) { // TODO Auto-generated method stub } }