HDDS-438. 'ozone oz' should print usage when command or sub-command is missing. Contributed by Dinesh Chitlangia.
This commit is contained in:
parent
f1a893fdbc
commit
a12f12f1af
|
@ -67,11 +67,14 @@ public class GenericCli implements Callable<Void>, GenericParentCommand {
|
||||||
} else {
|
} else {
|
||||||
System.err.println(error.getMessage().split("\n")[0]);
|
System.err.println(error.getMessage().split("\n")[0]);
|
||||||
}
|
}
|
||||||
|
if(error instanceof MissingSubcommandException){
|
||||||
|
System.err.println(((MissingSubcommandException) error).getUsage());
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public Void call() throws Exception {
|
public Void call() throws Exception {
|
||||||
throw new MissingSubcommandException();
|
throw new MissingSubcommandException(cmd.getUsageMessage());
|
||||||
}
|
}
|
||||||
|
|
||||||
public OzoneConfiguration createOzoneConfiguration() {
|
public OzoneConfiguration createOzoneConfiguration() {
|
||||||
|
|
|
@ -22,8 +22,14 @@ package org.apache.hadoop.hdds.cli;
|
||||||
*/
|
*/
|
||||||
public class MissingSubcommandException extends RuntimeException {
|
public class MissingSubcommandException extends RuntimeException {
|
||||||
|
|
||||||
public MissingSubcommandException() {
|
private String usage;
|
||||||
super("Please select a subcommand");
|
|
||||||
|
public MissingSubcommandException(String usage) {
|
||||||
|
super("Incomplete command");
|
||||||
|
this.usage = usage;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public String getUsage() {
|
||||||
|
return usage;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -33,6 +33,7 @@ import java.util.UUID;
|
||||||
import java.util.stream.Collectors;
|
import java.util.stream.Collectors;
|
||||||
|
|
||||||
import org.apache.hadoop.fs.FileUtil;
|
import org.apache.hadoop.fs.FileUtil;
|
||||||
|
import org.apache.hadoop.hdds.cli.MissingSubcommandException;
|
||||||
import org.apache.hadoop.hdds.client.ReplicationFactor;
|
import org.apache.hadoop.hdds.client.ReplicationFactor;
|
||||||
import org.apache.hadoop.hdds.conf.OzoneConfiguration;
|
import org.apache.hadoop.hdds.conf.OzoneConfiguration;
|
||||||
import org.apache.hadoop.hdds.protocol.proto.HddsProtos;
|
import org.apache.hadoop.hdds.protocol.proto.HddsProtos;
|
||||||
|
@ -236,10 +237,10 @@ public class TestOzoneShell {
|
||||||
assertEquals(userName, volumeInfo.getOwner());
|
assertEquals(userName, volumeInfo.getOwner());
|
||||||
}
|
}
|
||||||
|
|
||||||
private void execute(Shell shell, String[] args) {
|
private void execute(Shell ozoneShell, String[] args) {
|
||||||
List<String> arguments = new ArrayList(Arrays.asList(args));
|
List<String> arguments = new ArrayList(Arrays.asList(args));
|
||||||
LOG.info("Executing shell command with args {}", arguments);
|
LOG.info("Executing shell command with args {}", arguments);
|
||||||
CommandLine cmd = shell.getCmd();
|
CommandLine cmd = ozoneShell.getCmd();
|
||||||
|
|
||||||
IExceptionHandler2<List<Object>> exceptionHandler =
|
IExceptionHandler2<List<Object>> exceptionHandler =
|
||||||
new IExceptionHandler2<List<Object>>() {
|
new IExceptionHandler2<List<Object>>() {
|
||||||
|
@ -309,6 +310,29 @@ public class TestOzoneShell {
|
||||||
executeWithError(shell, args, "VOLUME_NOT_FOUND");
|
executeWithError(shell, args, "VOLUME_NOT_FOUND");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void testShellIncompleteCommand() throws Exception {
|
||||||
|
LOG.info("Running testShellIncompleteCommand");
|
||||||
|
String expectedError = "Incomplete command";
|
||||||
|
String[] args = new String[] {}; //executing 'ozone oz'
|
||||||
|
|
||||||
|
executeWithError(shell, args, expectedError,
|
||||||
|
"Usage: ozone oz [-hV] [--verbose] [-D=<String=String>]..." +
|
||||||
|
" [COMMAND]");
|
||||||
|
|
||||||
|
args = new String[] {"volume"}; //executing 'ozone oz volume'
|
||||||
|
executeWithError(shell, args, expectedError,
|
||||||
|
"Usage: ozone oz volume [-hV] [COMMAND]");
|
||||||
|
|
||||||
|
args = new String[] {"bucket"}; //executing 'ozone oz bucket'
|
||||||
|
executeWithError(shell, args, expectedError,
|
||||||
|
"Usage: ozone oz bucket [-hV] [COMMAND]");
|
||||||
|
|
||||||
|
args = new String[] {"key"}; //executing 'ozone oz key'
|
||||||
|
executeWithError(shell, args, expectedError,
|
||||||
|
"Usage: ozone oz key [-hV] [COMMAND]");
|
||||||
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
public void testUpdateVolume() throws Exception {
|
public void testUpdateVolume() throws Exception {
|
||||||
LOG.info("Running testUpdateVolume");
|
LOG.info("Running testUpdateVolume");
|
||||||
|
@ -352,13 +376,13 @@ public class TestOzoneShell {
|
||||||
* Execute command, assert exeception message and returns true if error
|
* Execute command, assert exeception message and returns true if error
|
||||||
* was thrown.
|
* was thrown.
|
||||||
*/
|
*/
|
||||||
private void executeWithError(Shell shell, String[] args,
|
private void executeWithError(Shell ozoneShell, String[] args,
|
||||||
String expectedError) {
|
String expectedError) {
|
||||||
if (Strings.isNullOrEmpty(expectedError)) {
|
if (Strings.isNullOrEmpty(expectedError)) {
|
||||||
execute(shell, args);
|
execute(ozoneShell, args);
|
||||||
} else {
|
} else {
|
||||||
try {
|
try {
|
||||||
execute(shell, args);
|
execute(ozoneShell, args);
|
||||||
fail("Exception is expected from command execution " + Arrays
|
fail("Exception is expected from command execution " + Arrays
|
||||||
.asList(args));
|
.asList(args));
|
||||||
} catch (Exception ex) {
|
} catch (Exception ex) {
|
||||||
|
@ -378,6 +402,41 @@ public class TestOzoneShell {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Execute command, assert exception message and returns true if error
|
||||||
|
* was thrown and contains the specified usage string.
|
||||||
|
*/
|
||||||
|
private void executeWithError(Shell ozoneShell, String[] args,
|
||||||
|
String expectedError, String usage) {
|
||||||
|
if (Strings.isNullOrEmpty(expectedError)) {
|
||||||
|
execute(ozoneShell, args);
|
||||||
|
} else {
|
||||||
|
try {
|
||||||
|
execute(ozoneShell, args);
|
||||||
|
fail("Exception is expected from command execution " + Arrays
|
||||||
|
.asList(args));
|
||||||
|
} catch (Exception ex) {
|
||||||
|
if (!Strings.isNullOrEmpty(expectedError)) {
|
||||||
|
Throwable exceptionToCheck = ex;
|
||||||
|
if (exceptionToCheck.getCause() != null) {
|
||||||
|
exceptionToCheck = exceptionToCheck.getCause();
|
||||||
|
}
|
||||||
|
Assert.assertTrue(
|
||||||
|
String.format(
|
||||||
|
"Error of shell code doesn't contain the " +
|
||||||
|
"exception [%s] in [%s]",
|
||||||
|
expectedError, exceptionToCheck.getMessage()),
|
||||||
|
exceptionToCheck.getMessage().contains(expectedError));
|
||||||
|
Assert.assertTrue(
|
||||||
|
exceptionToCheck instanceof MissingSubcommandException);
|
||||||
|
Assert.assertTrue(
|
||||||
|
((MissingSubcommandException)exceptionToCheck)
|
||||||
|
.getUsage().contains(usage));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
public void testListVolume() throws Exception {
|
public void testListVolume() throws Exception {
|
||||||
LOG.info("Running testListVolume");
|
LOG.info("Running testListVolume");
|
||||||
|
|
|
@ -49,7 +49,8 @@ public class BucketCommands implements GenericParentCommand, Callable<Void> {
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public Void call() throws Exception {
|
public Void call() throws Exception {
|
||||||
throw new MissingSubcommandException();
|
throw new MissingSubcommandException(
|
||||||
|
this.shell.getCmd().getSubcommands().get("bucket").getUsageMessage());
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
|
|
@ -49,7 +49,8 @@ public class KeyCommands implements GenericParentCommand, Callable<Void> {
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public Void call() throws Exception {
|
public Void call() throws Exception {
|
||||||
throw new MissingSubcommandException();
|
throw new MissingSubcommandException(
|
||||||
|
this.shell.getCmd().getSubcommands().get("key").getUsageMessage());
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
|
|
@ -50,7 +50,8 @@ public class VolumeCommands implements GenericParentCommand, Callable<Void> {
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public Void call() throws Exception {
|
public Void call() throws Exception {
|
||||||
throw new MissingSubcommandException();
|
throw new MissingSubcommandException(
|
||||||
|
this.shell.getCmd().getSubcommands().get("volume").getUsageMessage());
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
|
Loading…
Reference in New Issue