Merge "Bug 116 - Revisit SanityTest"
[controller.git] / opendaylight / commons / controller-maven-plugin / src / main / java / org / opendaylight / controller / maven / plugin / AbstractControllerMojo.java
1 /*
2  * Copyright (c) 2013 Cisco Systems, Inc. and others.  All rights reserved.
3  *
4  * This program and the accompanying materials are made available under the
5  * terms of the Eclipse Public License v1.0 which accompanies this distribution,
6  * and is available at http://www.eclipse.org/legal/epl-v10.html
7  */
8
9 package org.opendaylight.controller.maven.plugin;
10
11 import java.io.File;
12 import java.io.IOException;
13 import java.net.HttpURLConnection;
14 import java.net.MalformedURLException;
15 import java.net.URL;
16 import java.util.ArrayList;
17 import java.util.Enumeration;
18 import java.util.List;
19 import java.util.Map;
20 import java.util.Properties;
21
22 import org.apache.maven.plugin.AbstractMojo;
23 import org.apache.maven.plugin.MojoExecutionException;
24 import org.apache.maven.plugin.MojoFailureException;
25 import org.apache.maven.plugins.annotations.Parameter;
26
27 import org.opendaylight.controller.maven.plugin.util.JavaProcess;
28 import org.opendaylight.controller.maven.plugin.util.ProcessMonitor;
29
30 /**
31  * Base controller mojo which handles common operations
32  */
33 public abstract class AbstractControllerMojo extends AbstractMojo {
34     public static final String OS_NAME = System.getProperty("os.name");
35     public static final boolean WIN = OS_NAME.toUpperCase().contains("WINDOWS");
36     public static final String JAVA_HOME = "JAVA_HOME";
37     public static final boolean skip = Boolean.getBoolean("controller.startup.skip");
38     public static final String MAIN_CLASS = "org.eclipse.equinox.launcher.Main";
39     public static final String CTRL_PROP = "opendaylight.controller";
40
41     /**
42      * The home directory where controller is installed
43      */
44     @Parameter( required = false )
45     protected File controllerHome;
46
47     /**
48      * The address on which controller is listening
49      */
50     @Parameter( defaultValue = "localhost")
51     protected String controllerHost;
52
53     /**
54      * The admin web port
55      */
56     @Parameter( defaultValue = "8080")
57     protected int controllerWebPort;
58
59     /**
60      * The openflow port
61      */
62     @Parameter( defaultValue = "6633")
63     protected int controllerOFPort;
64
65     /**
66      * Additional environment variables passed when starting the controller
67      * process.
68      */
69     @Parameter(required = false)
70     protected Properties controllerShellVariables;
71
72     /**
73      * The script name to invoke
74      */
75     @Parameter(required = false)
76     protected String controllerStartScriptName;
77
78     /**
79      * The username
80      */
81     @Parameter(required = false)
82     protected String controllerUsername;
83
84     /**
85      * The password
86      */
87     @Parameter(required = false)
88     protected String controllerPassword;
89
90     /**
91      * pidFile location
92      */
93     @Parameter(required = false)
94     protected File pidFile;
95
96     protected final ProcessMonitor procMon = ProcessMonitor.load();
97
98     public abstract void start() throws MojoExecutionException, MojoFailureException;
99
100     public void execute() throws MojoExecutionException, MojoFailureException {
101         if (skip) return;
102         validateArgs();
103         start();
104     }
105
106     protected URL getWebUrl() {
107       try {
108         return new URL("http", controllerHost, controllerWebPort, "/");
109       } catch (MalformedURLException e) {
110         throw new IllegalArgumentException(
111             "controller host:port is Malformed: " + controllerHost + " " + controllerWebPort, e);
112       }
113
114     }
115
116     protected void validateArgs() throws IllegalArgumentException {
117         // System property and environment variable override the default setting
118         String odlHome = System.getProperty("controllerHome");
119         if (odlHome != null) {
120           controllerHome = new File(odlHome);
121         }
122         if (controllerHome == null) {
123             getLog().error("controllerHome cannot be determined from controllerHome "
124                 + "property or ONE_HOME env variable");
125             throw new IllegalArgumentException("controllerHome cannot be determined.");
126         }
127         if (!controllerHome.exists()) {
128             throw new IllegalArgumentException(
129                     "controllerHome does not exist: " + controllerHome);
130         }
131        if (controllerUsername == null) {
132             controllerUsername = System.getProperty("controllerUsername");
133         }
134         if (controllerPassword == null) {
135             controllerPassword= System.getProperty("controllerPassword");
136         }
137         URL u = getWebUrl();
138         getLog().info("Controller Home       : " + controllerHome);
139         getLog().info("Controller Url        : " + u);
140         getLog().info("Controller credentials: " + controllerUsername
141                 + "/" + controllerPassword);
142     }
143
144     protected Process invokeScript(List<String> args, String log)
145             throws MojoFailureException, MojoExecutionException
146     {
147         ProcessBuilder pb = new ProcessBuilder();
148         List<String> cmd = new ArrayList<String>();
149         cmd.add(getScript());
150         if (args != null) {
151             for (String s : args) {
152                 // on windows args containing equals symbols need to be quoted
153                 if (WIN && s.contains("=") && !s.startsWith("\"")) {
154                   cmd.add("\"" + s + "\"");
155                 } else {
156                   cmd.add(s);
157                 }
158             }
159         }
160         pb.command(cmd);
161         pb.directory(controllerHome);
162         pb.redirectErrorStream(true);
163         pb.inheritIO();
164         Map<String,String> env = pb.environment();
165         if (controllerShellVariables != null) {
166             for (Enumeration e = controllerShellVariables.propertyNames(); e.hasMoreElements();) {
167                 String n = (String) e.nextElement();
168                 env.put(n, controllerShellVariables.getProperty(n));
169             }
170         }
171         String jh = env.get(JAVA_HOME);
172         if (jh == null) env.put(JAVA_HOME, System.getProperty("java.home"));
173         try {
174             getLog().info("Invoking process " + pb.command());
175             return pb.start();
176         } catch (IOException e) {
177             throw new MojoExecutionException(e.getMessage());
178         }
179     }
180
181     private String getScript() throws MojoFailureException {
182         File script = null;
183         if (controllerStartScriptName != null && !"".equals(controllerStartScriptName) ) {
184             script = new File(controllerStartScriptName);
185             if (!script.exists()) {
186                 // try relative path
187                 script = new File(controllerHome, controllerStartScriptName);
188             }
189             if (script.exists()) return script.getAbsolutePath();
190             throw new MojoFailureException("Script not found: " + controllerStartScriptName);
191         }
192         // try default
193         script = new File(controllerHome, "run." + (WIN ? "bat" : "sh") );
194         if (script.exists()) return script.getAbsolutePath();
195         throw new MojoFailureException("Cannot find a default script to launch.");
196     }
197
198     protected boolean canConnect() {
199         try {
200             URL url = getWebUrl();
201             HttpURLConnection con;
202             con = (HttpURLConnection) url.openConnection();
203             return (con.getResponseCode() > 0);
204         } catch (IOException e) {
205             return false;
206         }
207     }
208
209     public void killControllers() {
210         getLog().info("Checking environment for stray processes.");
211         List<JavaProcess> jvms = procMon.getProcesses(MAIN_CLASS, CTRL_PROP);
212         for (JavaProcess j : jvms) {
213             getLog().info("Killing running process: " + j);
214             ProcessMonitor.kill(j.getPid());
215         }
216         // cleanup pid files
217         getLog().info("Checking left over pid file: " + pidFile);
218         if (pidFile != null && pidFile.exists()) {
219             getLog().info("Cleaning up pid file : " + pidFile);
220             pidFile.delete();
221         }
222     }
223
224     public boolean isControllerRunning() {
225         return !procMon.getProcesses(MAIN_CLASS, CTRL_PROP).isEmpty();
226     }
227
228 }