Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add collectInfo command #10596

Merged
merged 35 commits into from Feb 13, 2020
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
35 commits
Select commit Hold shift + click to select a range
42e6bbf
init commit of basic functions
jiacheliu3 Dec 9, 2019
f397c73
this compiles
jiacheliu3 Dec 9, 2019
c53705e
added features and compiles
jiacheliu3 Dec 10, 2019
0878687
more functions and unit tests
jiacheliu3 Dec 11, 2019
dfd7d45
Delegate changes to ShellUtils
jiacheliu3 Dec 16, 2019
fc2d17e
Apply new SSH and SCP utils
jiacheliu3 Jan 29, 2020
47cff23
update tar utils
jiacheliu3 Jan 29, 2020
5dfec6e
rewrite util for generate tar.gz files
jiacheliu3 Jan 30, 2020
172ed2f
passed basic unit tests
jiacheliu3 Feb 1, 2020
39d3973
include unit tests
jiacheliu3 Feb 1, 2020
7e2f259
basic tests on infoBundle
jiacheliu3 Feb 5, 2020
eac848b
tarball only needed files
jiacheliu3 Feb 5, 2020
dab029b
checkstyle errors for code
jiacheliu3 Feb 5, 2020
05cb6ef
review refs and unit test
jiacheliu3 Feb 5, 2020
69cb55e
refactored workDir check and removed -f option
jiacheliu3 Feb 6, 2020
de32931
updated unit tests
jiacheliu3 Feb 6, 2020
7f7a8e9
ShellCommand license
jiacheliu3 Feb 6, 2020
98ea364
resolve requested changes
jiacheliu3 Feb 7, 2020
62a2d8f
resolve comments
jiacheliu3 Feb 9, 2020
a8ace50
async tarball collection
jiacheliu3 Feb 10, 2020
fe7e724
shell command failure does not fail CollectInfo command
jiacheliu3 Feb 10, 2020
97e35f1
remove unnecessary unit test
jiacheliu3 Feb 10, 2020
cf11de4
update command
jiacheliu3 Feb 10, 2020
1c39708
infoBundle -> collectInfo
jiacheliu3 Feb 11, 2020
ba10d77
no empty tarball
jiacheliu3 Feb 11, 2020
4933799
moved AlluxioTestDirectory back
jiacheliu3 Feb 11, 2020
33fd0d5
spotbugs is great
jiacheliu3 Feb 12, 2020
54ad2e2
resolve comments
jiacheliu3 Feb 12, 2020
b821e43
config thread num
jiacheliu3 Feb 12, 2020
b7d9d1d
merge CollectInfoAll into CollectInfo with --local option
jiacheliu3 Feb 12, 2020
2209241
add doc
jiacheliu3 Feb 12, 2020
0a9ff3d
checkstyle
jiacheliu3 Feb 12, 2020
cd6b2c8
try sudo for jps and jstack
jiacheliu3 Feb 13, 2020
418a318
spotbug
jiacheliu3 Feb 13, 2020
7612580
correct test
jiacheliu3 Feb 13, 2020
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
5 changes: 5 additions & 0 deletions bin/alluxio
Expand Up @@ -264,6 +264,11 @@ function main {
ALLUXIO_SHELL_JAVA_OPTS+=" -Dalluxio.conf.validation.enabled=false"
runJavaClass "$@"
;;
"collectInfo")
CLASS="alluxio.cli.bundler.CollectInfo"
CLASSPATH=${ALLUXIO_CLIENT_CLASSPATH}
runJavaClass "$@"
;;
"job")
CLASS="alluxio.cli.job.JobShell"
CLASSPATH=${ALLUXIO_CLIENT_CLASSPATH}
Expand Down
36 changes: 36 additions & 0 deletions core/common/src/main/java/alluxio/cli/CommandUtils.java
Expand Up @@ -18,10 +18,17 @@
import org.apache.commons.cli.CommandLine;
import org.reflections.Reflections;

import java.io.IOException;
import java.lang.reflect.Modifier;
import java.nio.charset.StandardCharsets;
import java.nio.file.Files;
import java.nio.file.Paths;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

import javax.annotation.Nullable;
import javax.annotation.concurrent.ThreadSafe;

/**
Expand Down Expand Up @@ -104,4 +111,33 @@ public static void checkNumOfArgsNoMoreThan(Command cmd, CommandLine cl, int n)
.getMessage(cmd.getCommandName(), n, cl.getArgs().length));
}
}

/**
* Reads a list of nodes from given file name ignoring comments and empty lines.
* Can be used to read conf/workers or conf/masters.
* @param confDir directory that holds the configuration
* @param fileName name of a file that contains the list of the nodes
* @return list of the node names, null when file fails to read
*/
@Nullable
public static List<String> readNodeList(String confDir, String fileName) {
List<String> lines;
try {
lines = Files.readAllLines(Paths.get(confDir, fileName), StandardCharsets.UTF_8);
} catch (IOException e) {
System.err.format("Failed to read file %s/%s. Ignored.", confDir, fileName);
return new ArrayList<>();
}

List<String> nodes = new ArrayList<>();
for (String line : lines) {
String node = line.trim();
if (node.startsWith("#") || node.length() == 0) {
continue;
}
nodes.add(node);
}

return nodes;
}
jiacheliu3 marked this conversation as resolved.
Show resolved Hide resolved
}
39 changes: 33 additions & 6 deletions core/common/src/main/java/alluxio/shell/CommandReturn.java
Expand Up @@ -11,11 +11,14 @@

package alluxio.shell;

import java.util.Arrays;

/**
* Object representation of a command execution.
*/
public class CommandReturn {
private int mExitCode;
private String[] mCmd;
private String mOutput;

/**
Expand All @@ -26,16 +29,22 @@ public class CommandReturn {
*/
public CommandReturn(int code, String output) {
mExitCode = code;
mCmd = new String[]{};
mOutput = output;
}

/**
* Gets the stdout content.
* Creates object from the contents.
* Copy the command array.
*
* @return stdout content
* @param code exit code
* @param cmd the command executed
* @param output stdout content
*/
public String getOutput() {
return mOutput;
public CommandReturn(int code, String[] cmd, String output) {
mExitCode = code;
mCmd = Arrays.copyOfRange(cmd, 0, cmd.length);
mOutput = output;
}

/**
Expand All @@ -47,14 +56,32 @@ public int getExitCode() {
return mExitCode;
}

/**
* Gets the command run.
*
* @return the command
* */
public String[] getCmd() {
return mCmd;
}

/**
* Gets the stdout content.
*
* @return stdout content
*/
public String getOutput() {
return mOutput;
}

/**
* Formats the object to more readable format.
* This is not done in toString() because stdout and stderr may be long.
*
* @return pretty formatted output
*/
public String getFormattedOutput() {
return String.format("StatusCode:%s%nOutput:%n%s", getExitCode(),
getOutput());
return String.format("ExitCode:%s%nCommand:%s%nOutput:%n%s", getExitCode(),
Arrays.toString(getCmd()), getOutput());
}
}
37 changes: 33 additions & 4 deletions core/common/src/main/java/alluxio/shell/ShellCommand.java
Expand Up @@ -99,15 +99,20 @@ public String run() throws IOException {
/**
* Runs a command and returns its output and exit code in Object.
* Preserves the output when the execution fails.
* If the command execution fails (not by an interrupt),
* try to wrap the Exception in the {@link CommandReturn}.
* Stderr is redirected to stdout.
*
* @return {@link CommandReturn} object representation of stdout, stderr and exit code
*/
public CommandReturn runWithOutput() throws IOException {
Process process = new ProcessBuilder(mCommand).redirectErrorStream(true).start();
Process process = null;
BufferedReader inReader = null;
try {
process = new ProcessBuilder(mCommand).redirectErrorStream(true).start();
inReader =
new BufferedReader(new InputStreamReader(process.getInputStream()));

try (BufferedReader inReader =
new BufferedReader(new InputStreamReader(process.getInputStream()))) {
// read the output of the command
StringBuilder stdout = new StringBuilder();
String outLine = inReader.readLine();
Expand All @@ -125,7 +130,7 @@ public CommandReturn runWithOutput() throws IOException {
exitCode, Arrays.toString(mCommand)));
}

CommandReturn cr = new CommandReturn(exitCode, stdout.toString());
CommandReturn cr = new CommandReturn(exitCode, mCommand, stdout.toString());

// destroy the process
if (process != null) {
Expand All @@ -136,10 +141,34 @@ public CommandReturn runWithOutput() throws IOException {
} catch (InterruptedException e) {
Thread.currentThread().interrupt();
throw new IOException(e);
} catch (Exception e) {
return new CommandReturn(1, String.format("Command %s failed, exception is %s",
Arrays.toString(mCommand), e.getMessage()));
} finally {
if (inReader != null) {
inReader.close();
}
if (process != null) {
process.destroy();
}
}
}

/**
* Converts the command to string repr.
*
* @return the shell command
* */
public String toString() {
return Arrays.toString(mCommand);
}

/**
* Gets the command. The original array is immutable.
*
* @return a copy of the command string array
* */
public String[] getCommand() {
return Arrays.copyOfRange(mCommand, 0, mCommand.length);
}
}
18 changes: 18 additions & 0 deletions core/common/src/main/java/alluxio/util/ShellUtils.java
Expand Up @@ -240,5 +240,23 @@ public static CommandReturn scpCommandWithOutput(
return new ScpCommand(hostname, fromFile, toFile, isDir).runWithOutput();
}

/**
* Executes a shell command.
* If it fails, try the backup command.
*
* @param cmd the primary command
* @param backupCmd a backup option
* @return the {@link CommandReturn} with combined output
*/
public static CommandReturn execCmdWithBackup(ShellCommand cmd, ShellCommand backupCmd)
throws IOException {
CommandReturn cr = cmd.runWithOutput();
// If the command works or there is no backup option, return
if (cr.getExitCode() == 0 || backupCmd == null) {
return cr;
}
return backupCmd.runWithOutput();
}

private ShellUtils() {} // prevent instantiation
}
10 changes: 5 additions & 5 deletions core/common/src/test/java/alluxio/shell/ShellCommandTest.java
Expand Up @@ -93,13 +93,13 @@ public void execCommandTolerateFailureFailed() throws Exception {
public void execCommandTolerateFailureInvalidCommand() throws Exception {
// create temp file
File testDir = AlluxioTestDirectory.createTemporaryDirectory("command");

// if there's no such command there will be IOException
mExceptionRule.expect(IOException.class);
mExceptionRule.expectMessage("No such file or directory");
// For a non-existent command the command return contains the err msg
String[] testCommandExcept = new String[]{"lsa",
String.format("%s", testDir.getAbsolutePath())};
// lsa is not a valid executable
new ShellCommand(testCommandExcept).runWithOutput();
CommandReturn crf = new ShellCommand(testCommandExcept).runWithOutput();
System.out.println(crf.getFormattedOutput());
assertNotEquals(0, crf.getExitCode());
assertTrue(crf.getOutput().contains("No such file or directory"));
}
}
24 changes: 2 additions & 22 deletions core/server/common/src/main/java/alluxio/cli/validation/Utils.java
Expand Up @@ -11,6 +11,7 @@

package alluxio.cli.validation;

import alluxio.cli.CommandUtils;
import alluxio.conf.ServerConfiguration;
import alluxio.conf.PropertyKey;
import alluxio.util.ShellUtils;
Expand All @@ -22,10 +23,6 @@
import java.io.IOException;
import java.io.InputStreamReader;
import java.net.Socket;
import java.nio.charset.StandardCharsets;
import java.nio.file.Files;
import java.nio.file.Paths;
import java.util.ArrayList;
import java.util.List;

import javax.annotation.Nullable;
Expand Down Expand Up @@ -83,24 +80,7 @@ public static boolean isAlluxioRunning(String className) {
@Nullable
public static List<String> readNodeList(String fileName) {
String confDir = ServerConfiguration.get(PropertyKey.CONF_DIR);
List<String> lines;
try {
lines = Files.readAllLines(Paths.get(confDir, fileName), StandardCharsets.UTF_8);
} catch (IOException e) {
System.err.format("Failed to read file %s/%s.%n", confDir, fileName);
return null;
}

List<String> nodes = new ArrayList<>();
for (String line : lines) {
String node = line.trim();
if (node.startsWith("#") || node.length() == 0) {
continue;
}
nodes.add(node);
}

return nodes;
return CommandUtils.readNodeList(confDir, fileName);
}

/**
Expand Down
4 changes: 4 additions & 0 deletions shell/pom.xml
Expand Up @@ -81,5 +81,9 @@
<artifactId>alluxio-job-client</artifactId>
<version>${project.version}</version>
</dependency>
<dependency>
<groupId>org.apache.commons</groupId>
<artifactId>commons-compress</artifactId>
</dependency>
</dependencies>
</project>