org.red5.server.service.WarDeployer.java Source code

Java tutorial

Introduction

Here is the source code for org.red5.server.service.WarDeployer.java

Source

package org.red5.server.service;

import java.io.File;
import java.io.FileOutputStream;
import java.io.FilenameFilter;
import java.io.IOException;
import java.io.InputStream;

import javax.management.MBeanServer;
import javax.management.MBeanServerInvocationHandler;
import javax.management.ObjectName;

import org.apache.commons.httpclient.HttpClient;
import org.apache.commons.httpclient.HttpException;
import org.apache.commons.httpclient.HttpMethod;
import org.apache.commons.httpclient.methods.GetMethod;
import org.red5.server.LoaderMBean;
import org.red5.server.api.scheduling.IScheduledJob;
import org.red5.server.api.scheduling.ISchedulingService;
import org.red5.server.jmx.JMXFactory;
import org.red5.server.scheduling.QuartzSchedulingService;
import org.red5.server.stream.ClientBroadcastStream;
import org.red5.server.util.FileUtil;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

/*
 * RED5 Open Source Flash Server - http://www.osflash.org/red5
 * 
 * Copyright (c) 2006-2008 by respective authors (see below). All rights reserved.
 * 
 * This library is free software; you can redistribute it and/or modify it under the 
 * terms of the GNU Lesser General Public License as published by the Free Software 
 * Foundation; either version 2.1 of the License, or (at your option) any later 
 * version. 
 * 
 * This library is distributed in the hope that it will be useful, but WITHOUT ANY 
 * WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A 
 * PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details.
 * 
 * You should have received a copy of the GNU Lesser General Public License along 
 * with this library; if not, write to the Free Software Foundation, Inc., 
 * 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA 
 */

/**
 * This service provides the means to auto-deploy a war. 
 * 
 * @author Paul Gregoire (mondain@gmail.com)
 */
public class WarDeployer {

    private Logger log = LoggerFactory.getLogger(WarDeployer.class);

    private ISchedulingService scheduler;

    //how often to check for wars
    private int checkInterval = 600000; //ten minutes

    //where we deploy from - where the war files are located
    private String deploymentDirectory;

    private static String jobName;

    //that wars are currently being installed
    private static boolean deploying;

    {
        log.info("War deployer service created");
    }

    public void setCheckInterval(int checkInterval) {
        this.checkInterval = checkInterval;
    }

    public int getCheckInterval() {
        return checkInterval;
    }

    public ISchedulingService getScheduler() {
        return scheduler;
    }

    public void setScheduler(ISchedulingService scheduler) {
        this.scheduler = scheduler;
    }

    public String getDeploymentDirectory() {
        return deploymentDirectory;
    }

    public void setDeploymentDirectory(String deploymentDirectory) {
        this.deploymentDirectory = deploymentDirectory;
    }

    public void init() {
        //create the job and schedule it
        jobName = scheduler.addScheduledJobAfterDelay(checkInterval, new DeployJob(), 120000);
        //
        log.debug("Source directory: {}", deploymentDirectory);
        //check the deploy from directory
        File dir = new File(deploymentDirectory);
        if (!dir.exists()) {
            log.warn("Source directory not found");
        } else {
            if (!dir.isDirectory()) {
                log.warn("Source directory is not a directory");
            }
        }
        dir = null;
    }

    public void shutdown() {
        scheduler.removeScheduledJob(jobName);
    }

    /**
     * Returns the LoaderMBean.
     * @return
     */
    public LoaderMBean getLoader() {
        MBeanServer mbs = JMXFactory.getMBeanServer();

        ObjectName oName = JMXFactory.createObjectName("type", "TomcatLoader");

        LoaderMBean proxy = null;
        if (mbs.isRegistered(oName)) {
            proxy = (LoaderMBean) MBeanServerInvocationHandler.newProxyInstance(mbs, oName, LoaderMBean.class,
                    true);
            log.debug("Loader was found");
        } else {
            log.warn("Loader not found");
        }
        return proxy;
    }

    /**
     * Filters directory content
     */
    protected class DirectoryFilter implements FilenameFilter {
        /**
         * Check whether file matches filter rules
         * 
         * @param dir   Directory
         * @param name   File name
         * @return true If file does match filter rules, false otherwise
         */
        public boolean accept(File dir, String name) {
            File f = new File(dir, name);
            log.debug("Filtering: {} name: {}", dir.getName(), name);
            // filter out all but war files
            boolean result = f.getName().endsWith("war");
            //nullify
            f = null;
            return result;
        }
    }

    private class DeployJob implements IScheduledJob {

        public void execute(ISchedulingService service) {
            log.debug("Executing job");
            if (deploying) {
                return;
            }
            deploying = true;
            log.debug("Starting scheduled deployment of wars");

            //short name
            String application = null;
            //file name
            String applicationWarName = null;

            //get webapp location
            String webappsDir = System.getProperty("red5.webapp.root");
            log.debug("Webapp folder: {}", webappsDir);

            //look for web application archives
            File dir = new File(deploymentDirectory);
            //get a list of wars
            File[] files = dir.listFiles(new DirectoryFilter());
            for (File f : files) {
                //get the war name
                applicationWarName = f.getName();

                int dashIndex = applicationWarName.indexOf('-');
                if (dashIndex != -1) {
                    //strip everything except the applications name
                    application = applicationWarName.substring(0, dashIndex);
                } else {
                    //grab every char up to the last '.'
                    application = applicationWarName.substring(0, applicationWarName.lastIndexOf('.'));
                }
                log.debug("Application name: {}", application);

                //setup context
                String contextPath = '/' + application;
                String contextDir = webappsDir + contextPath;

                log.debug("Web context: {} context directory: {}", contextPath, contextDir);

                //verify this is a unique app
                File appDir = new File(webappsDir, application);
                if (appDir.exists()) {
                    if (appDir.isDirectory()) {
                        log.debug("Application directory exists");
                    } else {
                        log.warn("Application destination is not a directory");
                    }
                    log.warn(
                            "Application {} already installed, please un-install before attempting another install",
                            application);
                } else {
                    log.debug("Unwaring and starting...");
                    //un-archive it to app dir
                    FileUtil.unzip(deploymentDirectory + '/' + applicationWarName, contextDir);
                    //get the webapp loader
                    LoaderMBean loader = getLoader();
                    if (loader != null) {
                        //load and start the context
                        loader.startWebApplication(application);
                        //remove the war file
                        File warFile = new File(deploymentDirectory, applicationWarName);
                        if (warFile.delete()) {
                            log.debug("{} was deleted", warFile.getName());
                        } else {
                            log.debug("{} was not deleted", warFile.getName());
                            warFile.deleteOnExit();
                        }
                        warFile = null;
                    }
                }
                appDir = null;
            }
            dir = null;

            //reset sentinel
            deploying = false;
        }

    }

}