|
@@ -23,12 +23,7 @@ import java.io.OutputStreamWriter;
|
|
|
import java.io.PrintWriter;
|
|
|
import java.nio.charset.Charset;
|
|
|
import java.text.DecimalFormat;
|
|
|
-import java.util.Collection;
|
|
|
-import java.util.Collections;
|
|
|
-import java.util.EnumSet;
|
|
|
-import java.util.HashSet;
|
|
|
-import java.util.List;
|
|
|
-import java.util.Set;
|
|
|
+import java.util.*;
|
|
|
|
|
|
import org.apache.commons.cli.CommandLine;
|
|
|
import org.apache.commons.cli.GnuParser;
|
|
@@ -54,6 +49,7 @@ import org.apache.hadoop.yarn.api.records.ContainerReport;
|
|
|
import org.apache.hadoop.yarn.api.records.Priority;
|
|
|
import org.apache.hadoop.yarn.api.records.SignalContainerCommand;
|
|
|
import org.apache.hadoop.yarn.api.records.YarnApplicationState;
|
|
|
+import org.apache.hadoop.yarn.client.api.AppAdminClient;
|
|
|
import org.apache.hadoop.yarn.exceptions.ApplicationAttemptNotFoundException;
|
|
|
import org.apache.hadoop.yarn.exceptions.ApplicationNotFoundException;
|
|
|
import org.apache.hadoop.yarn.exceptions.ContainerNotFoundException;
|
|
@@ -85,6 +81,7 @@ public class ApplicationCLI extends YarnCLI {
|
|
|
"%30s\t%20s\t%20s\t%20s\t%20s\t%20s\t%35s"
|
|
|
+ System.getProperty("line.separator");
|
|
|
|
|
|
+ public static final String APP = "app";
|
|
|
public static final String APPLICATION = "application";
|
|
|
public static final String APPLICATION_ATTEMPT = "applicationattempt";
|
|
|
public static final String CONTAINER = "container";
|
|
@@ -93,22 +90,52 @@ public class ApplicationCLI extends YarnCLI {
|
|
|
public static final String UPDATE_LIFETIME = "updateLifetime";
|
|
|
public static final String CHANGE_APPLICATION_QUEUE = "changeQueue";
|
|
|
|
|
|
+ // app admin options
|
|
|
+ public static final String LAUNCH_CMD = "launch";
|
|
|
+ public static final String STOP_CMD = "stop";
|
|
|
+ public static final String START_CMD = "start";
|
|
|
+ public static final String SAVE_CMD = "save";
|
|
|
+ public static final String DESTROY_CMD = "destroy";
|
|
|
+ public static final String FLEX_CMD = "flex";
|
|
|
+ public static final String COMPONENT = "component";
|
|
|
+ public static final String ENABLE_FAST_LAUNCH = "enableFastLaunch";
|
|
|
+
|
|
|
+ private static String firstArg = null;
|
|
|
+
|
|
|
private boolean allAppStates;
|
|
|
|
|
|
public static void main(String[] args) throws Exception {
|
|
|
ApplicationCLI cli = new ApplicationCLI();
|
|
|
cli.setSysOutPrintStream(System.out);
|
|
|
cli.setSysErrPrintStream(System.err);
|
|
|
- int res = ToolRunner.run(cli, args);
|
|
|
+ int res = ToolRunner.run(cli, preProcessArgs(args));
|
|
|
cli.stop();
|
|
|
System.exit(res);
|
|
|
}
|
|
|
|
|
|
+ @VisibleForTesting
|
|
|
+ public static String[] preProcessArgs(String[] args) {
|
|
|
+ if (args.length > 0) {
|
|
|
+ // first argument (app|application|applicationattempt|container) must
|
|
|
+ // be stripped off for GenericOptionsParser to work
|
|
|
+ firstArg = args[0];
|
|
|
+ return Arrays.copyOfRange(args, 1, args.length);
|
|
|
+ } else {
|
|
|
+ return args;
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
@Override
|
|
|
public int run(String[] args) throws Exception {
|
|
|
Options opts = new Options();
|
|
|
String title = null;
|
|
|
- if (args.length > 0 && args[0].equalsIgnoreCase(APPLICATION)) {
|
|
|
+ if (firstArg != null) {
|
|
|
+ title = firstArg;
|
|
|
+ } else if (args.length > 0) {
|
|
|
+ title = args[0];
|
|
|
+ }
|
|
|
+ if (title != null && (title.equalsIgnoreCase(APPLICATION) || title
|
|
|
+ .equalsIgnoreCase(APP))) {
|
|
|
title = APPLICATION;
|
|
|
opts.addOption(STATUS_CMD, true,
|
|
|
"Prints the status of the application.");
|
|
@@ -168,8 +195,52 @@ public class ApplicationCLI extends YarnCLI {
|
|
|
opts.getOption(UPDATE_PRIORITY).setArgName("Priority");
|
|
|
opts.getOption(UPDATE_LIFETIME).setArgName("Timeout");
|
|
|
opts.getOption(CHANGE_APPLICATION_QUEUE).setArgName("Queue Name");
|
|
|
- } else if (args.length > 0 && args[0].equalsIgnoreCase(APPLICATION_ATTEMPT)) {
|
|
|
- title = APPLICATION_ATTEMPT;
|
|
|
+ opts.addOption(LAUNCH_CMD, true, "Launches application from " +
|
|
|
+ "specification file (saves specification and starts application). " +
|
|
|
+ "Options -updateLifetime and -changeQueue can be specified to alter" +
|
|
|
+ " the values provided in the file. Supports -appTypes option to " +
|
|
|
+ "specify which client implementation to use.");
|
|
|
+ opts.addOption(STOP_CMD, true, "Stops application gracefully (may be " +
|
|
|
+ "started again later). If name is provided, appType must be " +
|
|
|
+ "provided unless it is the default yarn-service. If ID is provided," +
|
|
|
+ " the appType will be looked up. Supports -appTypes option to " +
|
|
|
+ "specify which client implementation to use.");
|
|
|
+ opts.addOption(START_CMD, true, "Starts a previously saved " +
|
|
|
+ "application. Supports -appTypes option to specify which client " +
|
|
|
+ "implementation to use.");
|
|
|
+ opts.addOption(SAVE_CMD, true, "Saves specification file for " +
|
|
|
+ "an application. Options -updateLifetime and -changeQueue can be " +
|
|
|
+ "specified to alter the values provided in the file. Supports " +
|
|
|
+ "-appTypes option to specify which client implementation to use.");
|
|
|
+ opts.addOption(DESTROY_CMD, true, "Destroys a saved application " +
|
|
|
+ "specification and removes all application data permanently. " +
|
|
|
+ "Supports -appTypes option to specify which client implementation " +
|
|
|
+ "to use.");
|
|
|
+ opts.addOption(FLEX_CMD, true, "Changes number of " +
|
|
|
+ "running containers for a component of an application / " +
|
|
|
+ "long-running service. Requires -component option. If name is " +
|
|
|
+ "provided, appType must be provided unless it is the default " +
|
|
|
+ "yarn-service. If ID is provided, the appType will be looked up. " +
|
|
|
+ "Supports -appTypes option to specify which client implementation " +
|
|
|
+ "to use.");
|
|
|
+ opts.addOption(COMPONENT, true, "Works with -flex option to change " +
|
|
|
+ "the number of components/containers running for an application / " +
|
|
|
+ "long-running service. Supports absolute or relative changes, such " +
|
|
|
+ "as +1, 2, or -3.");
|
|
|
+ opts.addOption(ENABLE_FAST_LAUNCH, false, "Uploads AM dependencies " +
|
|
|
+ "to HDFS to make future launches faster. Supports -appTypes option" +
|
|
|
+ " to specify which client implementation to use.");
|
|
|
+ opts.getOption(LAUNCH_CMD).setArgName("Application Name> <File Name");
|
|
|
+ opts.getOption(LAUNCH_CMD).setArgs(2);
|
|
|
+ opts.getOption(START_CMD).setArgName("Application Name");
|
|
|
+ opts.getOption(STOP_CMD).setArgName("Application Name or ID");
|
|
|
+ opts.getOption(SAVE_CMD).setArgName("Application Name> <File Name");
|
|
|
+ opts.getOption(SAVE_CMD).setArgs(2);
|
|
|
+ opts.getOption(DESTROY_CMD).setArgName("Application Name");
|
|
|
+ opts.getOption(FLEX_CMD).setArgName("Application Name or ID");
|
|
|
+ opts.getOption(COMPONENT).setArgName("Component Name> <Count");
|
|
|
+ opts.getOption(COMPONENT).setArgs(2);
|
|
|
+ } else if (title != null && title.equalsIgnoreCase(APPLICATION_ATTEMPT)) {
|
|
|
opts.addOption(STATUS_CMD, true,
|
|
|
"Prints the status of the application attempt.");
|
|
|
opts.addOption(LIST_CMD, true,
|
|
@@ -179,8 +250,7 @@ public class ApplicationCLI extends YarnCLI {
|
|
|
opts.getOption(STATUS_CMD).setArgName("Application Attempt ID");
|
|
|
opts.getOption(LIST_CMD).setArgName("Application ID");
|
|
|
opts.getOption(FAIL_CMD).setArgName("Application Attempt ID");
|
|
|
- } else if (args.length > 0 && args[0].equalsIgnoreCase(CONTAINER)) {
|
|
|
- title = CONTAINER;
|
|
|
+ } else if (title != null && title.equalsIgnoreCase(CONTAINER)) {
|
|
|
opts.addOption(STATUS_CMD, true,
|
|
|
"Prints the status of the container.");
|
|
|
opts.addOption(LIST_CMD, true,
|
|
@@ -205,23 +275,53 @@ public class ApplicationCLI extends YarnCLI {
|
|
|
printUsage(title, opts);
|
|
|
return exitCode;
|
|
|
}
|
|
|
+ String[] unparsedArgs = cliParser.getArgs();
|
|
|
+ if (firstArg == null) {
|
|
|
+ if (unparsedArgs.length != 1) {
|
|
|
+ printUsage(title, opts);
|
|
|
+ return exitCode;
|
|
|
+ }
|
|
|
+ } else {
|
|
|
+ if (unparsedArgs.length != 0) {
|
|
|
+ printUsage(title, opts);
|
|
|
+ return exitCode;
|
|
|
+ }
|
|
|
+ }
|
|
|
|
|
|
if (cliParser.hasOption(STATUS_CMD)) {
|
|
|
- if (args.length != 3) {
|
|
|
+ if (hasAnyOtherCLIOptions(cliParser, opts, STATUS_CMD)) {
|
|
|
printUsage(title, opts);
|
|
|
return exitCode;
|
|
|
}
|
|
|
- if (args[0].equalsIgnoreCase(APPLICATION)) {
|
|
|
- exitCode = printApplicationReport(cliParser.getOptionValue(STATUS_CMD));
|
|
|
- } else if (args[0].equalsIgnoreCase(APPLICATION_ATTEMPT)) {
|
|
|
+ if (title.equalsIgnoreCase(APPLICATION) ||
|
|
|
+ title.equalsIgnoreCase(APP)) {
|
|
|
+ ApplicationReport report = printApplicationReport(cliParser
|
|
|
+ .getOptionValue(STATUS_CMD));
|
|
|
+ if (report == null) {
|
|
|
+ exitCode = -1;
|
|
|
+ } else {
|
|
|
+ exitCode = 0;
|
|
|
+ String appType = report.getApplicationType();
|
|
|
+ try {
|
|
|
+ AppAdminClient client = AppAdminClient.createAppAdminClient(appType,
|
|
|
+ getConf());
|
|
|
+ sysout.println("Detailed Application Status :");
|
|
|
+ sysout.println(client.getStatusString(cliParser.getOptionValue(
|
|
|
+ STATUS_CMD)));
|
|
|
+ } catch (IllegalArgumentException e) {
|
|
|
+ // app type does not have app admin client implementation
|
|
|
+ }
|
|
|
+ }
|
|
|
+ } else if (title.equalsIgnoreCase(APPLICATION_ATTEMPT)) {
|
|
|
exitCode = printApplicationAttemptReport(cliParser
|
|
|
.getOptionValue(STATUS_CMD));
|
|
|
- } else if (args[0].equalsIgnoreCase(CONTAINER)) {
|
|
|
+ } else if (title.equalsIgnoreCase(CONTAINER)) {
|
|
|
exitCode = printContainerReport(cliParser.getOptionValue(STATUS_CMD));
|
|
|
}
|
|
|
return exitCode;
|
|
|
} else if (cliParser.hasOption(LIST_CMD)) {
|
|
|
- if (args[0].equalsIgnoreCase(APPLICATION)) {
|
|
|
+ if (title.equalsIgnoreCase(APPLICATION) ||
|
|
|
+ title.equalsIgnoreCase(APP)) {
|
|
|
allAppStates = false;
|
|
|
Set<String> appTypes = new HashSet<String>();
|
|
|
if (cliParser.hasOption(APP_TYPE_CMD)) {
|
|
@@ -272,21 +372,21 @@ public class ApplicationCLI extends YarnCLI {
|
|
|
}
|
|
|
}
|
|
|
listApplications(appTypes, appStates, appTags);
|
|
|
- } else if (args[0].equalsIgnoreCase(APPLICATION_ATTEMPT)) {
|
|
|
- if (args.length != 3) {
|
|
|
+ } else if (title.equalsIgnoreCase(APPLICATION_ATTEMPT)) {
|
|
|
+ if (hasAnyOtherCLIOptions(cliParser, opts, LIST_CMD)) {
|
|
|
printUsage(title, opts);
|
|
|
return exitCode;
|
|
|
}
|
|
|
listApplicationAttempts(cliParser.getOptionValue(LIST_CMD));
|
|
|
- } else if (args[0].equalsIgnoreCase(CONTAINER)) {
|
|
|
- if (args.length != 3) {
|
|
|
+ } else if (title.equalsIgnoreCase(CONTAINER)) {
|
|
|
+ if (hasAnyOtherCLIOptions(cliParser, opts, LIST_CMD)) {
|
|
|
printUsage(title, opts);
|
|
|
return exitCode;
|
|
|
}
|
|
|
listContainers(cliParser.getOptionValue(LIST_CMD));
|
|
|
}
|
|
|
} else if (cliParser.hasOption(KILL_CMD)) {
|
|
|
- if (args.length < 3 || hasAnyOtherCLIOptions(cliParser, opts, KILL_CMD)) {
|
|
|
+ if (hasAnyOtherCLIOptions(cliParser, opts, KILL_CMD)) {
|
|
|
printUsage(title, opts);
|
|
|
return exitCode;
|
|
|
}
|
|
@@ -299,7 +399,7 @@ public class ApplicationCLI extends YarnCLI {
|
|
|
moveApplicationAcrossQueues(cliParser.getOptionValue(MOVE_TO_QUEUE_CMD),
|
|
|
cliParser.getOptionValue(QUEUE_CMD));
|
|
|
} else if (cliParser.hasOption(FAIL_CMD)) {
|
|
|
- if (!args[0].equalsIgnoreCase(APPLICATION_ATTEMPT)) {
|
|
|
+ if (!title.equalsIgnoreCase(APPLICATION_ATTEMPT)) {
|
|
|
printUsage(title, opts);
|
|
|
return exitCode;
|
|
|
}
|
|
@@ -314,6 +414,103 @@ public class ApplicationCLI extends YarnCLI {
|
|
|
}
|
|
|
updateApplicationPriority(cliParser.getOptionValue(APP_ID),
|
|
|
cliParser.getOptionValue(UPDATE_PRIORITY));
|
|
|
+ } else if (cliParser.hasOption(SIGNAL_CMD)) {
|
|
|
+ if (hasAnyOtherCLIOptions(cliParser, opts, SIGNAL_CMD)) {
|
|
|
+ printUsage(title, opts);
|
|
|
+ return exitCode;
|
|
|
+ }
|
|
|
+ final String[] signalArgs = cliParser.getOptionValues(SIGNAL_CMD);
|
|
|
+ final String containerId = signalArgs[0];
|
|
|
+ SignalContainerCommand command =
|
|
|
+ SignalContainerCommand.OUTPUT_THREAD_DUMP;
|
|
|
+ if (signalArgs.length == 2) {
|
|
|
+ command = SignalContainerCommand.valueOf(signalArgs[1]);
|
|
|
+ }
|
|
|
+ signalToContainer(containerId, command);
|
|
|
+ } else if (cliParser.hasOption(LAUNCH_CMD)) {
|
|
|
+ if (hasAnyOtherCLIOptions(cliParser, opts, LAUNCH_CMD, APP_TYPE_CMD,
|
|
|
+ UPDATE_LIFETIME, CHANGE_APPLICATION_QUEUE)) {
|
|
|
+ printUsage(title, opts);
|
|
|
+ return exitCode;
|
|
|
+ }
|
|
|
+ String appType = getSingleAppTypeFromCLI(cliParser);
|
|
|
+ Long lifetime = null;
|
|
|
+ if (cliParser.hasOption(UPDATE_LIFETIME)) {
|
|
|
+ lifetime = Long.parseLong(cliParser.getOptionValue(UPDATE_LIFETIME));
|
|
|
+ }
|
|
|
+ String queue = null;
|
|
|
+ if (cliParser.hasOption(CHANGE_APPLICATION_QUEUE)) {
|
|
|
+ queue = cliParser.getOptionValue(CHANGE_APPLICATION_QUEUE);
|
|
|
+ }
|
|
|
+ String[] nameAndFile = cliParser.getOptionValues(LAUNCH_CMD);
|
|
|
+ return AppAdminClient.createAppAdminClient(appType, getConf())
|
|
|
+ .actionLaunch(nameAndFile[1], nameAndFile[0], lifetime, queue);
|
|
|
+ } else if (cliParser.hasOption(STOP_CMD)) {
|
|
|
+ if (hasAnyOtherCLIOptions(cliParser, opts, STOP_CMD, APP_TYPE_CMD)) {
|
|
|
+ printUsage(title, opts);
|
|
|
+ return exitCode;
|
|
|
+ }
|
|
|
+ String[] appNameAndType = getAppNameAndType(cliParser, STOP_CMD);
|
|
|
+ return AppAdminClient.createAppAdminClient(appNameAndType[1], getConf())
|
|
|
+ .actionStop(appNameAndType[0]);
|
|
|
+ } else if (cliParser.hasOption(START_CMD)) {
|
|
|
+ if (hasAnyOtherCLIOptions(cliParser, opts, START_CMD, APP_TYPE_CMD)) {
|
|
|
+ printUsage(title, opts);
|
|
|
+ return exitCode;
|
|
|
+ }
|
|
|
+ String appType = getSingleAppTypeFromCLI(cliParser);
|
|
|
+ return AppAdminClient.createAppAdminClient(appType, getConf())
|
|
|
+ .actionStart(cliParser.getOptionValue(START_CMD));
|
|
|
+ } else if (cliParser.hasOption(SAVE_CMD)) {
|
|
|
+ if (hasAnyOtherCLIOptions(cliParser, opts, SAVE_CMD, APP_TYPE_CMD,
|
|
|
+ UPDATE_LIFETIME, CHANGE_APPLICATION_QUEUE)) {
|
|
|
+ printUsage(title, opts);
|
|
|
+ return exitCode;
|
|
|
+ }
|
|
|
+ String appType = getSingleAppTypeFromCLI(cliParser);
|
|
|
+ Long lifetime = null;
|
|
|
+ if (cliParser.hasOption(UPDATE_LIFETIME)) {
|
|
|
+ lifetime = Long.parseLong(cliParser.getOptionValue(UPDATE_LIFETIME));
|
|
|
+ }
|
|
|
+ String queue = null;
|
|
|
+ if (cliParser.hasOption(CHANGE_APPLICATION_QUEUE)) {
|
|
|
+ queue = cliParser.getOptionValue(CHANGE_APPLICATION_QUEUE);
|
|
|
+ }
|
|
|
+ String[] nameAndFile = cliParser.getOptionValues(SAVE_CMD);
|
|
|
+ return AppAdminClient.createAppAdminClient(appType, getConf())
|
|
|
+ .actionSave(nameAndFile[1], nameAndFile[0], lifetime, queue);
|
|
|
+ } else if (cliParser.hasOption(DESTROY_CMD)) {
|
|
|
+ if (hasAnyOtherCLIOptions(cliParser, opts, DESTROY_CMD, APP_TYPE_CMD)) {
|
|
|
+ printUsage(title, opts);
|
|
|
+ return exitCode;
|
|
|
+ }
|
|
|
+ String appType = getSingleAppTypeFromCLI(cliParser);
|
|
|
+ return AppAdminClient.createAppAdminClient(appType, getConf())
|
|
|
+ .actionDestroy(cliParser.getOptionValue(DESTROY_CMD));
|
|
|
+ } else if (cliParser.hasOption(FLEX_CMD)) {
|
|
|
+ if (!cliParser.hasOption(COMPONENT) ||
|
|
|
+ hasAnyOtherCLIOptions(cliParser, opts, FLEX_CMD, COMPONENT,
|
|
|
+ APP_TYPE_CMD)) {
|
|
|
+ printUsage(title, opts);
|
|
|
+ return exitCode;
|
|
|
+ }
|
|
|
+ String[] rawCounts = cliParser.getOptionValues(COMPONENT);
|
|
|
+ Map<String, String> counts = new HashMap<>(rawCounts.length/2);
|
|
|
+ for (int i = 0; i < rawCounts.length - 1; i+=2) {
|
|
|
+ counts.put(rawCounts[i], rawCounts[i+1]);
|
|
|
+ }
|
|
|
+ String[] appNameAndType = getAppNameAndType(cliParser, FLEX_CMD);
|
|
|
+ return AppAdminClient.createAppAdminClient(appNameAndType[1], getConf())
|
|
|
+ .actionFlex(appNameAndType[0], counts);
|
|
|
+ } else if (cliParser.hasOption(ENABLE_FAST_LAUNCH)) {
|
|
|
+ String appType = getSingleAppTypeFromCLI(cliParser);
|
|
|
+ if (hasAnyOtherCLIOptions(cliParser, opts, ENABLE_FAST_LAUNCH,
|
|
|
+ APP_TYPE_CMD)) {
|
|
|
+ printUsage(title, opts);
|
|
|
+ return exitCode;
|
|
|
+ }
|
|
|
+ return AppAdminClient.createAppAdminClient(appType, getConf())
|
|
|
+ .enableFastLaunch();
|
|
|
} else if (cliParser.hasOption(UPDATE_LIFETIME)) {
|
|
|
if (!cliParser.hasOption(APP_ID)) {
|
|
|
printUsage(title, opts);
|
|
@@ -332,19 +529,6 @@ public class ApplicationCLI extends YarnCLI {
|
|
|
}
|
|
|
moveApplicationAcrossQueues(cliParser.getOptionValue(APP_ID),
|
|
|
cliParser.getOptionValue(CHANGE_APPLICATION_QUEUE));
|
|
|
- } else if (cliParser.hasOption(SIGNAL_CMD)) {
|
|
|
- if (args.length < 3 || args.length > 4) {
|
|
|
- printUsage(title, opts);
|
|
|
- return exitCode;
|
|
|
- }
|
|
|
- final String[] signalArgs = cliParser.getOptionValues(SIGNAL_CMD);
|
|
|
- final String containerId = signalArgs[0];
|
|
|
- SignalContainerCommand command =
|
|
|
- SignalContainerCommand.OUTPUT_THREAD_DUMP;
|
|
|
- if (signalArgs.length == 2) {
|
|
|
- command = SignalContainerCommand.valueOf(signalArgs[1]);
|
|
|
- }
|
|
|
- signalToContainer(containerId, command);
|
|
|
} else {
|
|
|
syserr.println("Invalid Command Usage : ");
|
|
|
printUsage(title, opts);
|
|
@@ -352,6 +536,47 @@ public class ApplicationCLI extends YarnCLI {
|
|
|
return 0;
|
|
|
}
|
|
|
|
|
|
+ private ApplicationReport getApplicationReport(ApplicationId applicationId)
|
|
|
+ throws IOException, YarnException {
|
|
|
+ ApplicationReport appReport = null;
|
|
|
+ try {
|
|
|
+ appReport = client.getApplicationReport(applicationId);
|
|
|
+ } catch (ApplicationNotFoundException e) {
|
|
|
+ throw new YarnException("Application with id '" + applicationId
|
|
|
+ + "' doesn't exist in RM or Timeline Server.");
|
|
|
+ }
|
|
|
+ return appReport;
|
|
|
+ }
|
|
|
+
|
|
|
+ private String[] getAppNameAndType(CommandLine cliParser, String option)
|
|
|
+ throws IOException, YarnException {
|
|
|
+ String applicationIdOrName = cliParser.getOptionValue(option);
|
|
|
+ try {
|
|
|
+ ApplicationId id = ApplicationId.fromString(applicationIdOrName);
|
|
|
+ ApplicationReport report = getApplicationReport(id);
|
|
|
+ return new String[]{report.getName(), report.getApplicationType()};
|
|
|
+ } catch (IllegalArgumentException e) {
|
|
|
+ // assume CLI option provided the app name
|
|
|
+ // and read appType from command line since id wasn't provided
|
|
|
+ String appType = getSingleAppTypeFromCLI(cliParser);
|
|
|
+ return new String[]{applicationIdOrName, appType};
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ private static String getSingleAppTypeFromCLI(CommandLine cliParser) {
|
|
|
+ if (cliParser.hasOption(APP_TYPE_CMD)) {
|
|
|
+ String[] types = cliParser.getOptionValues(APP_TYPE_CMD);
|
|
|
+ if (types != null) {
|
|
|
+ for (String type : types) {
|
|
|
+ if (!type.trim().isEmpty()) {
|
|
|
+ return StringUtils.toLowerCase(type).trim();
|
|
|
+ }
|
|
|
+ }
|
|
|
+ }
|
|
|
+ }
|
|
|
+ return AppAdminClient.DEFAULT_TYPE;
|
|
|
+ }
|
|
|
+
|
|
|
private void updateApplicationTimeout(String applicationId,
|
|
|
ApplicationTimeoutType timeoutType, long timeoutInSec)
|
|
|
throws YarnException, IOException {
|
|
@@ -572,7 +797,7 @@ public class ApplicationCLI extends YarnCLI {
|
|
|
/**
|
|
|
* Kills applications with the application id as appId
|
|
|
*
|
|
|
- * @param Array of applicationIds
|
|
|
+ * @param applicationIds Array of applicationIds
|
|
|
* @return errorCode
|
|
|
* @throws YarnException
|
|
|
* @throws IOException
|
|
@@ -663,10 +888,10 @@ public class ApplicationCLI extends YarnCLI {
|
|
|
* Prints the application report for an application id.
|
|
|
*
|
|
|
* @param applicationId
|
|
|
- * @return exitCode
|
|
|
+ * @return ApplicationReport
|
|
|
* @throws YarnException
|
|
|
*/
|
|
|
- private int printApplicationReport(String applicationId)
|
|
|
+ private ApplicationReport printApplicationReport(String applicationId)
|
|
|
throws YarnException, IOException {
|
|
|
ApplicationReport appReport = null;
|
|
|
try {
|
|
@@ -675,7 +900,7 @@ public class ApplicationCLI extends YarnCLI {
|
|
|
} catch (ApplicationNotFoundException e) {
|
|
|
sysout.println("Application with id '" + applicationId
|
|
|
+ "' doesn't exist in RM or Timeline Server.");
|
|
|
- return -1;
|
|
|
+ return null;
|
|
|
}
|
|
|
// Use PrintWriter.println, which uses correct platform line ending.
|
|
|
ByteArrayOutputStream baos = new ByteArrayOutputStream();
|
|
@@ -739,11 +964,11 @@ public class ApplicationCLI extends YarnCLI {
|
|
|
+ "' doesn't exist in RM.");
|
|
|
appReportStr.close();
|
|
|
sysout.println(baos.toString("UTF-8"));
|
|
|
- return -1;
|
|
|
+ return null;
|
|
|
}
|
|
|
appReportStr.close();
|
|
|
sysout.println(baos.toString("UTF-8"));
|
|
|
- return 0;
|
|
|
+ return appReport;
|
|
|
}
|
|
|
|
|
|
private void printResourceUsage(PrintWriter appReportStr,
|
|
@@ -856,11 +1081,12 @@ public class ApplicationCLI extends YarnCLI {
|
|
|
|
|
|
@SuppressWarnings("unchecked")
|
|
|
private boolean hasAnyOtherCLIOptions(CommandLine cliParser, Options opts,
|
|
|
- String excludeOption) {
|
|
|
+ String... excludeOptions) {
|
|
|
Collection<Option> ops = opts.getOptions();
|
|
|
+ Set<String> excludeSet = new HashSet<>(Arrays.asList(excludeOptions));
|
|
|
for (Option op : ops) {
|
|
|
- // Skip exclude option from the option list
|
|
|
- if (op.getOpt().equals(excludeOption)) {
|
|
|
+ // Skip exclude options from the option list
|
|
|
+ if (excludeSet.contains(op.getOpt())) {
|
|
|
continue;
|
|
|
}
|
|
|
if (cliParser.hasOption(op.getOpt())) {
|