cn.org.once.cstack.initializer.CloudUnitApplicationContext.java Source code

Java tutorial

Introduction

Here is the source code for cn.org.once.cstack.initializer.CloudUnitApplicationContext.java

Source

/*
 * LICENCE : CloudUnit is available under the GNU Affero General Public License : https://gnu.org/licenses/agpl.html
 * but CloudUnit is licensed too under a standard commercial license.
 * Please contact our sales team if you would like to discuss the specifics of our Enterprise license.
 * If you are not sure whether the AGPL is right for you,
 * you can always test our software under the AGPL and inspect the source code before you contact us
 * about purchasing a commercial license.
 *
 * LEGAL TERMS : "CloudUnit" is a registered trademark of Treeptik and can't be used to endorse
 * or promote products derived from this project without prior written permission from Treeptik.
 * Products or services derived from this software may not be called "CloudUnit"
 * nor may "Treeptik" or similar confusing terms appear in their names without prior written permission.
 * For any questions, contact us : contact@treeptik.fr
 */

package cn.org.once.cstack.initializer;

import com.fasterxml.jackson.databind.ObjectMapper;
import com.fasterxml.jackson.datatype.hibernate4.Hibernate4Module;
import com.spotify.docker.client.DefaultDockerClient;
import com.spotify.docker.client.DockerCertificates;
import com.spotify.docker.client.DockerClient;
import cn.org.once.cstack.config.EmailActiveCondition;
import cn.org.once.cstack.docker.core.DockerCloudUnitClient;
import cn.org.once.cstack.docker.core.SimpleDockerDriver;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.context.MessageSource;
import org.springframework.context.annotation.*;
import org.springframework.context.support.PropertySourcesPlaceholderConfigurer;
import org.springframework.context.support.ResourceBundleMessageSource;
import org.springframework.core.io.ClassPathResource;
import org.springframework.core.io.FileSystemResource;
import org.springframework.core.io.Resource;
import org.springframework.http.converter.HttpMessageConverter;
import org.springframework.http.converter.json.MappingJackson2HttpMessageConverter;
import org.springframework.mail.javamail.JavaMailSender;
import org.springframework.mail.javamail.JavaMailSenderImpl;
import org.springframework.web.multipart.MultipartResolver;
import org.springframework.web.multipart.commons.CommonsMultipartResolver;
import org.springframework.web.servlet.View;
import org.springframework.web.servlet.ViewResolver;
import org.springframework.web.servlet.config.annotation.DefaultServletHandlerConfigurer;
import org.springframework.web.servlet.config.annotation.EnableWebMvc;
import org.springframework.web.servlet.config.annotation.ResourceHandlerRegistry;
import org.springframework.web.servlet.config.annotation.WebMvcConfigurerAdapter;
import org.springframework.web.servlet.i18n.SessionLocaleResolver;
import org.springframework.web.servlet.view.ContentNegotiatingViewResolver;
import org.springframework.web.servlet.view.JstlView;
import org.springframework.web.servlet.view.UrlBasedViewResolver;
import org.springframework.web.servlet.view.json.MappingJackson2JsonView;

import javax.annotation.PostConstruct;
import java.io.File;
import java.io.IOException;
import java.nio.file.Paths;
import java.util.ArrayList;
import java.util.List;
import java.util.Locale;
import java.util.Properties;

@EnableAspectJAutoProxy
@Configuration
@EnableWebMvc
@ComponentScan(basePackages = { "cn.org.once.cstack.controller", "cn.org.once.cstack.dao",
        "cn.org.once.cstack.docker", "cn.org.once.cstack.docker.model", "cn.org.once.cstack.config",
        "cn.org.once.cstack.exception", "cn.org.once.cstack.model", "cn.org.once.cstack.service",
        "cn.org.once.cstack.service.impl", "cn.org.once.cstack.utils", "cn.org.once.cstack.aspects",
        "cn.org.once.cstack.manager", "cn.org.once.cstack.manager.impl", "cn.org.once.cstack.schedule",
        "cn.org.once.cstack.schedule.tasks", "cn.org.once.cstack.logs" })
@PropertySource({ "classpath:/application.properties" })
@PropertySource({ "classpath:/maven.properties" })
public class CloudUnitApplicationContext extends WebMvcConfigurerAdapter {

    // Allow for longer running Docker commands, esp. database scripts.
    private static final int READ_TIMEOUT_MILLIS = 1 * 60 * 1000;

    // Max file size
    private static final int MAX_UPLOAD_SIZE = 300 * 1000 * 1000;

    private final static Logger logger = LoggerFactory.getLogger(CloudUnitApplicationContext.class);

    @Value("${cloudunit.instance.name}")
    private String cuInstanceName;

    @PostConstruct
    public void getCuINstanceName() {
        logger.info("CloudUnit instance name: {}", cuInstanceName);
    }

    @Bean
    @Profile("vagrant")
    public static PropertySourcesPlaceholderConfigurer properties() throws Exception {
        String file = "application-vagrant.properties";
        PropertySourcesPlaceholderConfigurer pspc = new PropertySourcesPlaceholderConfigurer();
        pspc.setLocations(getResources(file));
        pspc.setIgnoreUnresolvablePlaceholders(true);
        pspc.setLocalOverride(true);
        return pspc;
    }

    @Bean
    @Profile("production")
    public static PropertySourcesPlaceholderConfigurer propertiesForProduction() throws Exception {
        String file = "application-production.properties";
        PropertySourcesPlaceholderConfigurer pspc = new PropertySourcesPlaceholderConfigurer();
        pspc.setLocations(getResources(file));
        pspc.setIgnoreUnresolvablePlaceholders(true);
        pspc.setLocalOverride(true);
        return pspc;
    }

    @Bean
    @Profile("vagrant-demo")
    public static PropertySourcesPlaceholderConfigurer propertiesForDemo() throws Exception {
        String file = "application-vagrant-demo.properties";
        PropertySourcesPlaceholderConfigurer pspc = new PropertySourcesPlaceholderConfigurer();
        pspc.setLocations(getResources(file));
        pspc.setIgnoreUnresolvablePlaceholders(true);
        pspc.setLocalOverride(true);
        return pspc;
    }

    @Bean
    @Profile("integration")
    public static PropertySourcesPlaceholderConfigurer propertiesForIntegration() throws Exception {
        String file = "application-integration-local.properties";

        String envIntegration = System.getenv("CLOUDUNIT_JENKINS_CI");
        if ("true".equalsIgnoreCase(envIntegration)) {
            file = "application-integration.properties";
        }

        PropertySourcesPlaceholderConfigurer pspc = new PropertySourcesPlaceholderConfigurer();
        pspc.setLocations(getResources(file));
        pspc.setIgnoreUnresolvablePlaceholders(true);
        pspc.setLocalOverride(true);
        return pspc;
    }

    @Bean
    @Profile("test")
    public static PropertySourcesPlaceholderConfigurer propertiesForTest() throws Exception {
        PropertySourcesPlaceholderConfigurer pspc = new PropertySourcesPlaceholderConfigurer();
        Resource[] resources = new Resource[] { new ClassPathResource("application-test.properties") };
        pspc.setLocations(resources);
        pspc.setIgnoreUnresolvablePlaceholders(true);
        pspc.setLocalOverride(true);
        return pspc;
    }

    @Bean
    public ViewResolver contentNegotiatingViewResolver() {
        logger.debug("Configuring the ContentNegotiatingViewResolver");
        ContentNegotiatingViewResolver viewResolver = new ContentNegotiatingViewResolver();
        List<ViewResolver> viewResolvers = new ArrayList<ViewResolver>();

        UrlBasedViewResolver urlBasedViewResolver = new UrlBasedViewResolver();
        urlBasedViewResolver.setViewClass(JstlView.class);
        urlBasedViewResolver.setSuffix(".html");
        viewResolvers.add(urlBasedViewResolver);

        viewResolver.setViewResolvers(viewResolvers);

        List<View> defaultViews = new ArrayList<View>();
        defaultViews.add(new MappingJackson2JsonView());
        viewResolver.setDefaultViews(defaultViews);

        return viewResolver;
    }

    @Override
    public void addResourceHandlers(ResourceHandlerRegistry registry) {
        registry.addResourceHandler("/resources/**").addResourceLocations("/resources/");
    }

    @Override
    public void configureDefaultServletHandling(DefaultServletHandlerConfigurer configurer) {
        configurer.enable();
    }

    private MappingJackson2HttpMessageConverter jacksonMessageConverter() {
        MappingJackson2HttpMessageConverter messageConverter = new MappingJackson2HttpMessageConverter();
        ObjectMapper mapper = new ObjectMapper();
        mapper.registerModule(new Hibernate4Module().enable(Hibernate4Module.Feature.USE_TRANSIENT_ANNOTATION));
        messageConverter.setObjectMapper(mapper);
        return messageConverter;
    }

    @Override
    public void configureMessageConverters(List<HttpMessageConverter<?>> converters) {
        converters.add(jacksonMessageConverter());
        super.configureMessageConverters(converters);
    }

    @Bean
    public SessionLocaleResolver localeResolver() {
        SessionLocaleResolver localeResolver = new SessionLocaleResolver();
        localeResolver.setDefaultLocale(Locale.ENGLISH);
        return localeResolver;
    }

    @Bean
    public MessageSource messageSource() {
        ResourceBundleMessageSource messageSource = new ResourceBundleMessageSource();
        messageSource.setBasename("message");
        return messageSource;
    }

    @Bean
    public MultipartResolver multipartResolver() {
        CommonsMultipartResolver multipartResolver = new CommonsMultipartResolver();
        multipartResolver.setMaxUploadSize(MAX_UPLOAD_SIZE);
        return multipartResolver;
    }

    @Bean
    public DockerCloudUnitClient dockerCloudUnitClient(@Value("${docker.endpoint.mode}") String endpoint,
            @Value("${docker.socket.location}") String dockerSocketLocation,
            @Value("${docker.certs.dir.path:}") String certPathDirectory) {
        boolean useUnixSocket = endpoint.equalsIgnoreCase("unix");
        logger.info("Socket mode : " + (useUnixSocket ? "unix" : "tcp"));
        DockerCloudUnitClient dockerCloudUnitClient = new DockerCloudUnitClient();
        if (useUnixSocket) {
            dockerCloudUnitClient.setDriver(new SimpleDockerDriver(true, endpoint, dockerSocketLocation, null));
        } else {
            dockerCloudUnitClient
                    .setDriver(new SimpleDockerDriver(false, endpoint, dockerSocketLocation, certPathDirectory));
        }
        return dockerCloudUnitClient;
    }

    @Bean
    public DockerClient dockerClient(@Value("${docker.endpoint.mode}") String endpoint,
            @Value("${docker.socket.location}") String dockerSocketLocation,
            @Value("${docker.certs.dir.path}") String certPathDirectory) {
        com.spotify.docker.client.DockerClient dockerClient = null;
        boolean useUnixSocket = endpoint.equalsIgnoreCase("unix");
        boolean useTLS = endpoint.equalsIgnoreCase("https");
        logger.info("Socket mode : " + (useUnixSocket ? "unix" : "tcp"));
        logger.info("Socket TLS : " + (useTLS ? "yes" : "no"));
        try {
            if (useUnixSocket) {
                dockerClient = DefaultDockerClient.fromEnv().build();
            } else {
                if (useTLS) {
                    final DockerCertificates certs = new DockerCertificates(Paths.get(certPathDirectory));
                    dockerClient = DefaultDockerClient.builder().uri("https://" + dockerSocketLocation)
                            .dockerCertificates(certs).build();
                } else {
                    dockerClient = DefaultDockerClient.builder().uri("http://" + dockerSocketLocation).build();
                }
            }
        } catch (Exception e) {
            logger.error("cannot instance docker client : ", e);
        }
        return dockerClient;
    }

    @Bean
    @Conditional(value = EmailActiveCondition.class)
    public JavaMailSender mailSender(@Value("${email.host}") String host, @Value("${email.port}") Integer port,
            @Value("${email.protocol}") String protocol, @Value("${email.username}") String username,
            @Value("${email.password}") String password) throws IOException {
        JavaMailSenderImpl mailSender = new JavaMailSenderImpl();
        mailSender.setHost(host);
        mailSender.setPort(port);
        mailSender.setProtocol(protocol);
        mailSender.setUsername(username);
        mailSender.setPassword(password);
        mailSender.setJavaMailProperties(javaMailProperties());
        return mailSender;
    }

    private Properties javaMailProperties() throws IOException {
        Properties properties = new Properties();
        return properties;
    }

    @Bean
    @Profile("integration")
    public ObjectMapper objectMapper() {
        return new ObjectMapper();
    }

    /**
     * Get Resources to load for CloudUnit Context.
     *
     * @param profileProperties The filename of the profile properties.
     * @return An array of Resource.
     * The array will have at least the profileProperties given by parameter, and eventually a custom
     * configuration file if found in the {@code $HOME/.cloudunit/} repertory.
     */
    private static Resource[] getResources(String profileProperties) {
        final File customFile = new File(System.getProperty("user.home") + "/.cloudunit/configuration.properties");
        Resource[] resources = null;

        if (customFile.exists()) {
            logger.warn("Custom file configuration found ! : {}", customFile.getAbsolutePath());

            resources = new Resource[] { new ClassPathResource(profileProperties),
                    new FileSystemResource(customFile) };
        } else {
            logger.warn(customFile.getAbsolutePath() + " is missing. Needed for production !");
            resources = new Resource[] { new ClassPathResource(profileProperties), };
        }
        return resources;
    }

}