| /* |
| * Licensed to the Apache Software Foundation (ASF) under one |
| * or more contributor license agreements. See the NOTICE file |
| * distributed with this work for additional information |
| * regarding copyright ownership. The ASF licenses this file |
| * to you under the Apache License, Version 2.0 (the |
| * "License"); you may not use this file except in compliance |
| * with the License. You may obtain a copy of the License at |
| * |
| * http://www.apache.org/licenses/LICENSE-2.0 |
| * |
| * Unless required by applicable law or agreed to in writing, |
| * software distributed under the License is distributed on an |
| * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY |
| * KIND, either express or implied. See the License for the |
| * specific language governing permissions and limitations |
| * under the License. |
| */ |
| package org.apache.uima.ducc.agent.launcher; |
| |
| import java.net.InetAddress; |
| import java.util.concurrent.ExecutorService; |
| import java.util.concurrent.Executors; |
| import java.util.concurrent.Future; |
| |
| import org.apache.uima.ducc.agent.NodeAgent; |
| import org.apache.uima.ducc.agent.event.ProcessLifecycleObserver; |
| import org.apache.uima.ducc.common.IDuccUser; |
| import org.apache.uima.ducc.common.NodeIdentity; |
| import org.apache.uima.ducc.common.utils.Utils; |
| import org.apache.uima.ducc.common.utils.id.DuccIdFactory; |
| import org.apache.uima.ducc.transport.cmdline.ICommandLine; |
| import org.apache.uima.ducc.transport.cmdline.JavaCommandLine; |
| import org.apache.uima.ducc.transport.event.common.DuccProcess; |
| import org.apache.uima.ducc.transport.event.common.IDuccProcess; |
| import org.apache.uima.ducc.transport.event.common.IDuccProcessType.ProcessType; |
| |
| public class Launcher { |
| private ExecutorService executorService = null; |
| |
| private DuccIdFactory duccIdFactory = new DuccIdFactory(); |
| |
| public Launcher() { |
| executorService = Executors.newCachedThreadPool(); |
| } |
| |
| /** |
| * This method is used to launch multiple Agents on the same physical machine. It allows to scale |
| * up Agents on a single machine to simulate load. Each Agent instance will assume a given name |
| * and IP address. |
| * |
| * @param cmdLine |
| * - defines the command line used to exec Agent process |
| * @param howMany |
| * - how many Agents to exec |
| * @param ip |
| * - initial IP address to assign to first Agent instance. Subsequent Agent instances |
| * will have this IP incremented as in XXX.XXX.XXX.XX+1,XXX.XXX.XXX.XX+2, etc |
| * @param nodeName |
| * - name of the physical machine. The Agents will be assigned this name plus a suffix as |
| * in watson-1, watson-2, etc |
| * @throws Exception |
| */ |
| public void start(ICommandLine cmdLine, int howMany, String ip, String nodeName) |
| throws Exception { |
| // Launch as many agents as requested |
| for (int i = 0; i < howMany; i++) { |
| String host = nodeName; |
| // Append suffix to node name for each Agent instance |
| if (host.indexOf(".") > -1) { |
| String tmp = host.substring(0, host.indexOf(".")); |
| host = tmp + "-" + String.valueOf(i + 1) + host.substring(host.indexOf(".")); |
| } else { |
| host = host + "-" + String.valueOf(i + 1); |
| } |
| launchProcess(host, ip, cmdLine); |
| // Increment IP address for the next Agent |
| int uip = Integer.parseInt(ip.substring(ip.lastIndexOf(".") + 1, ip.length())); |
| ip = ip.substring(0, ip.lastIndexOf(".") + 1).concat(String.valueOf(uip + 1)); |
| } |
| |
| } |
| |
| /** |
| * Submit request to exec a process. The process will be exec'd in a separate thread. |
| * |
| * @param process |
| * @param commandLine |
| * |
| * @throws Exception |
| */ |
| public ManagedProcess launchProcess(NodeAgent agent, NodeIdentity nodeIdentity, |
| IDuccProcess process, ICommandLine commandLine, ProcessLifecycleObserver observer, |
| ManagedProcess managedProcess) throws Exception { |
| // Instantiate executor that will actually exec the process using java's ProcessBuilder |
| DuccCommandExecutor executor = new DuccCommandExecutor(agent, commandLine, |
| nodeIdentity.getCanonicalName(), nodeIdentity.getIp(), managedProcess); |
| Future<?> future = executorService.submit(executor); |
| // if we are launching a process, save the future object returned from Executor above |
| managedProcess.setFuture(future); |
| return managedProcess; |
| } |
| |
| /** |
| * Submit request to exec a process. The process will be exec'd in a separate thread. |
| * |
| * @param process |
| * @param commandLine |
| * |
| * @throws Exception |
| */ |
| public void launchOSCommand(ICommand command) { |
| try { |
| executorService.submit(command); |
| } catch (Exception e) { |
| e.printStackTrace(); |
| } |
| |
| } |
| |
| /** |
| * This method is used for simulation only. It enables launching an agent with a given name and IP |
| * address which are different from a physical node name and IP address. With that multiple agents |
| * can be launched on the same physical machine simulating a cluster of nodes. |
| * |
| */ |
| public void launchProcess(String host, String ip, ICommandLine cmdLine) throws Exception { |
| IDuccProcess process = new DuccProcess(duccIdFactory.next(), new NodeIdentity(ip, host)); |
| process.setProcessType(ProcessType.Pop); |
| ManagedProcess managedProcess = new ManagedProcess(process, cmdLine, true); |
| DuccCommandExecutor executor = new DuccCommandExecutor(cmdLine, host, ip, managedProcess); |
| executorService.submit(executor); |
| } |
| |
| public static void main(String[] args) { |
| try { |
| int howMany = Integer.parseInt(args[0]); // how many agent processes to launch |
| String ip = System.getProperty(IDuccUser.EnvironmentVariable.DUCC_IP.value()); |
| String nodeName = InetAddress.getLocalHost().getHostName(); |
| Launcher launcher = new Launcher(); |
| JavaCommandLine cmdLine = new JavaCommandLine("java"); |
| String duccHome = Utils.findDuccHome(); |
| cmdLine.addOption("-Dducc.deploy.configuration=" + duccHome + "/resources/ducc.properties"); |
| cmdLine.addOption("-Dducc.deploy.components=agent"); |
| cmdLine.addOption("-Djava.library.path=" + duccHome + "/lib/sigar"); |
| cmdLine.addOption("-DDUCC_HOME=" + duccHome); |
| |
| // System.out.println("Spawning with classpath: \n" + System.getProperty("java.class.path")); |
| // cmdLine.setClasspath(duccHome+"/lib/*:" + |
| // duccHome+"/lib/apache-activemq-5.5.0/*:" + |
| // duccHome+"/lib/apache-camel-2.7.1/*:" + |
| // duccHome+"/lib/commons-collections-3.2.1/*:" + |
| // duccHome+"/lib/apache-commons-lang-2.6/*:" + |
| // duccHome+"/lib/apache-log4j-1.2.16/*:" + |
| // duccHome+"/lib/guava-r09/*:" + |
| // duccHome+"/lib/joda-time-1.6/*:" + |
| // duccHome+"/lib/sigar/*:" + |
| // duccHome+"/lib/springframework-3.0.5/*:"); |
| |
| cmdLine.setClasspath(System.getProperty("java.class.path")); |
| cmdLine.setClassName("org.apache.uima.ducc.agent.common.main.DuccService"); |
| launcher.start(cmdLine, howMany, ip, nodeName); |
| } catch (Exception e) { |
| e.printStackTrace(); |
| } |
| } |
| |
| } |