HDDS-289. Volume and Bucket name should not contain a delimiter ('/'). Contributed by chencan.

This commit is contained in:
Hanisha Koneru 2018-09-28 11:24:42 -07:00
parent 3c798c1e3c
commit 72891fc9be
7 changed files with 108 additions and 36 deletions

View File

@ -17,6 +17,7 @@
*/ */
package org.apache.hadoop.ozone.ozShell; package org.apache.hadoop.ozone.ozShell;
import com.google.common.base.Strings;
import java.io.ByteArrayOutputStream; import java.io.ByteArrayOutputStream;
import java.io.File; import java.io.File;
import java.io.FileInputStream; import java.io.FileInputStream;
@ -31,7 +32,7 @@ import java.util.List;
import java.util.Random; import java.util.Random;
import java.util.UUID; import java.util.UUID;
import java.util.stream.Collectors; import java.util.stream.Collectors;
import org.apache.commons.lang3.RandomStringUtils;
import org.apache.hadoop.fs.FileUtil; import org.apache.hadoop.fs.FileUtil;
import org.apache.hadoop.hdds.cli.MissingSubcommandException; import org.apache.hadoop.hdds.cli.MissingSubcommandException;
import org.apache.hadoop.hdds.client.ReplicationFactor; import org.apache.hadoop.hdds.client.ReplicationFactor;
@ -60,17 +61,9 @@ import org.apache.hadoop.ozone.web.response.KeyInfo;
import org.apache.hadoop.ozone.web.response.VolumeInfo; import org.apache.hadoop.ozone.web.response.VolumeInfo;
import org.apache.hadoop.ozone.web.utils.JsonUtils; import org.apache.hadoop.ozone.web.utils.JsonUtils;
import org.apache.hadoop.test.GenericTestUtils; import org.apache.hadoop.test.GenericTestUtils;
import com.google.common.base.Strings;
import org.apache.commons.lang3.RandomStringUtils;
import static org.apache.hadoop.ozone.OzoneConfigKeys.OZONE_REPLICATION;
import org.junit.After; import org.junit.After;
import org.junit.AfterClass; import org.junit.AfterClass;
import org.junit.Assert; import org.junit.Assert;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertNotNull;
import static org.junit.Assert.assertTrue;
import static org.junit.Assert.fail;
import org.junit.Before; import org.junit.Before;
import org.junit.BeforeClass; import org.junit.BeforeClass;
import org.junit.Rule; import org.junit.Rule;
@ -87,6 +80,12 @@ import picocli.CommandLine.ParameterException;
import picocli.CommandLine.ParseResult; import picocli.CommandLine.ParseResult;
import picocli.CommandLine.RunLast; import picocli.CommandLine.RunLast;
import static org.apache.hadoop.ozone.OzoneConfigKeys.OZONE_REPLICATION;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertNotNull;
import static org.junit.Assert.assertTrue;
import static org.junit.Assert.fail;
/** /**
* This test class specified for testing Ozone shell command. * This test class specified for testing Ozone shell command.
*/ */
@ -211,8 +210,7 @@ public class TestOzoneShell {
testCreateVolume("/////", "Volume name is required " + testCreateVolume("/////", "Volume name is required " +
"to create a volume"); "to create a volume");
testCreateVolume("/////vol/123", testCreateVolume("/////vol/123",
"Bucket or Volume name has " + "Invalid volume name. Delimiters (/) not allowed in volume name");
"an unsupported character : /");
} }
private void testCreateVolume(String volumeName, String errorMsg) private void testCreateVolume(String volumeName, String errorMsg)
@ -305,6 +303,12 @@ public class TestOzoneShell {
assertTrue(output.contains("createdOn") assertTrue(output.contains("createdOn")
&& output.contains(OzoneConsts.OZONE_TIME_ZONE)); && output.contains(OzoneConsts.OZONE_TIME_ZONE));
// test infoVolume with invalid volume name
args = new String[] {"volume", "info",
url + "/" + volumeName + "/invalid-name"};
executeWithError(shell, args, "Invalid volume name. " +
"Delimiters (/) not allowed in volume name");
// get info for non-exist volume // get info for non-exist volume
args = new String[] {"volume", "info", url + "/invalid-volume"}; args = new String[] {"volume", "info", url + "/invalid-volume"};
executeWithError(shell, args, "VOLUME_NOT_FOUND"); executeWithError(shell, args, "VOLUME_NOT_FOUND");
@ -563,8 +567,13 @@ public class TestOzoneShell {
// test create a bucket in a non-exist volume // test create a bucket in a non-exist volume
args = new String[] {"bucket", "create", args = new String[] {"bucket", "create",
url + "/invalid-volume/" + bucketName}; url + "/invalid-volume/" + bucketName};
executeWithError(shell, args, "Info Volume failed, error:VOLUME_NOT_FOUND"); executeWithError(shell, args, "Info Volume failed, error:VOLUME_NOT_FOUND");
// test createBucket with invalid bucket name
args = new String[] {"bucket", "create",
url + "/" + vol.getName() + "/" + bucketName + "/invalid-name"};
executeWithError(shell, args,
"Invalid bucket name. Delimiters (/) not allowed in bucket name");
} }
@Test @Test
@ -618,6 +627,12 @@ public class TestOzoneShell {
assertTrue(output.contains("createdOn") assertTrue(output.contains("createdOn")
&& output.contains(OzoneConsts.OZONE_TIME_ZONE)); && output.contains(OzoneConsts.OZONE_TIME_ZONE));
// test infoBucket with invalid bucket name
args = new String[] {"bucket", "info",
url + "/" + vol.getName() + "/" + bucketName + "/invalid-name"};
executeWithError(shell, args,
"Invalid bucket name. Delimiters (/) not allowed in bucket name");
// test get info from a non-exist bucket // test get info from a non-exist bucket
args = new String[] {"bucket", "info", args = new String[] {"bucket", "info",
url + "/" + vol.getName() + "/invalid-bucket" + bucketName}; url + "/" + vol.getName() + "/invalid-bucket" + bucketName};
@ -688,8 +703,14 @@ public class TestOzoneShell {
assertNotNull(bucket); assertNotNull(bucket);
} }
// test -length option // test listBucket with invalid volume name
String[] args = new String[] {"bucket", "list", String[] args = new String[] {"bucket", "list",
url + "/" + vol.getName() + "/invalid-name"};
executeWithError(shell, args, "Invalid volume name. " +
"Delimiters (/) not allowed in volume name");
// test -length option
args = new String[] {"bucket", "list",
url + "/" + vol.getName(), "--length", "100"}; url + "/" + vol.getName(), "--length", "100"};
execute(shell, args); execute(shell, args);
commandOutput = out.toString(); commandOutput = out.toString();
@ -954,8 +975,14 @@ public class TestOzoneShell {
keyOutputStream.close(); keyOutputStream.close();
} }
// test -length option // test listKey with invalid bucket name
String[] args = new String[] {"key", "list", String[] args = new String[] {"key", "list",
url + "/" + volumeName + "/" + bucketName + "/invalid-name"};
executeWithError(shell, args, "Invalid bucket name. " +
"Delimiters (/) not allowed in bucket name");
// test -length option
args = new String[] {"key", "list",
url + "/" + volumeName + "/" + bucketName, "--length", "100"}; url + "/" + volumeName + "/" + bucketName, "--length", "100"};
execute(shell, args); execute(shell, args);
commandOutput = out.toString(); commandOutput = out.toString();

View File

@ -50,9 +50,16 @@ public class CreateBucketHandler extends Handler {
URI ozoneURI = verifyURI(uri); URI ozoneURI = verifyURI(uri);
Path path = Paths.get(ozoneURI.getPath()); Path path = Paths.get(ozoneURI.getPath());
if (path.getNameCount() < 2) { int pathNameCount = path.getNameCount();
throw new OzoneClientException( if (pathNameCount != 2) {
"volume and bucket name required in createBucket"); String errorMessage;
if (pathNameCount < 2) {
errorMessage = "volume and bucket name required in createBucket";
} else {
errorMessage = "Invalid bucket name. Delimiters (/) not allowed in " +
"bucket name";
}
throw new OzoneClientException(errorMessage);
} }
String volumeName = path.getName(0).toString(); String volumeName = path.getName(0).toString();

View File

@ -50,10 +50,16 @@ public class InfoBucketHandler extends Handler {
String volumeName, bucketName; String volumeName, bucketName;
URI ozoneURI = verifyURI(uri); URI ozoneURI = verifyURI(uri);
Path path = Paths.get(ozoneURI.getPath()); Path path = Paths.get(ozoneURI.getPath());
int pathNameCount = path.getNameCount();
if (path.getNameCount() < 2) { if (pathNameCount != 2) {
throw new OzoneClientException( String errorMessage;
"volume and bucket name required in info Bucket"); if (pathNameCount < 2) {
errorMessage = "volume and bucket name required in infoBucket";
} else {
errorMessage = "Invalid bucket name. Delimiters (/) not allowed in " +
"bucket name";
}
throw new OzoneClientException(errorMessage);
} }
volumeName = path.getName(0).toString(); volumeName = path.getName(0).toString();

View File

@ -71,8 +71,16 @@ public class ListBucketHandler extends Handler {
URI ozoneURI = verifyURI(uri); URI ozoneURI = verifyURI(uri);
Path path = Paths.get(ozoneURI.getPath()); Path path = Paths.get(ozoneURI.getPath());
if (path.getNameCount() < 1) { int pathNameCount = path.getNameCount();
throw new OzoneClientException("volume is required in listBucket"); if (pathNameCount != 1) {
String errorMessage;
if (pathNameCount < 1) {
errorMessage = "volume is required in listBucket";
} else {
errorMessage = "Invalid volume name. Delimiters (/) not allowed in " +
"volume name";
}
throw new OzoneClientException(errorMessage);
} }
if (maxBuckets < 1) { if (maxBuckets < 1) {

View File

@ -71,9 +71,16 @@ public class ListKeyHandler extends Handler {
URI ozoneURI = verifyURI(uri); URI ozoneURI = verifyURI(uri);
Path path = Paths.get(ozoneURI.getPath()); Path path = Paths.get(ozoneURI.getPath());
if (path.getNameCount() < 2) { int pathNameCount = path.getNameCount();
throw new OzoneClientException( if (pathNameCount != 2) {
"volume/bucket is required in listKey"); String errorMessage;
if (pathNameCount < 2) {
errorMessage = "volume/bucket is required in listKey";
} else {
errorMessage = "Invalid bucket name. Delimiters (/) not allowed in " +
"bucket name";
}
throw new OzoneClientException(errorMessage);
} }
if (maxKeys < 1) { if (maxKeys < 1) {

View File

@ -19,6 +19,8 @@
package org.apache.hadoop.ozone.web.ozShell.volume; package org.apache.hadoop.ozone.web.ozShell.volume;
import java.net.URI; import java.net.URI;
import java.nio.file.Path;
import java.nio.file.Paths;
import org.apache.hadoop.ozone.client.OzoneClientException; import org.apache.hadoop.ozone.client.OzoneClientException;
import org.apache.hadoop.ozone.client.OzoneClientUtils; import org.apache.hadoop.ozone.client.OzoneClientUtils;
@ -64,15 +66,20 @@ public class CreateVolumeHandler extends Handler {
public Void call() throws Exception { public Void call() throws Exception {
URI ozoneURI = verifyURI(uri); URI ozoneURI = verifyURI(uri);
Path path = Paths.get(ozoneURI.getPath());
// we need to skip the slash in the URI path int pathNameCount = path.getNameCount();
// getPath returns /volumeName needs to remove the initial slash. if (pathNameCount != 1) {
String volumeName = ozoneURI.getPath().replaceAll("^/+", ""); String errorMessage;
if (volumeName.isEmpty()) { if (pathNameCount < 1) {
throw new OzoneClientException( errorMessage = "Volume name is required to create a volume";
"Volume name is required to create a volume"); } else {
errorMessage = "Invalid volume name. Delimiters (/) not allowed in " +
"volume name";
}
throw new OzoneClientException(errorMessage);
} }
String volumeName = ozoneURI.getPath().replaceAll("^/+", "");
if (isVerbose()) { if (isVerbose()) {
System.out.printf("Volume name : %s%n", volumeName); System.out.printf("Volume name : %s%n", volumeName);
} }

View File

@ -19,6 +19,8 @@
package org.apache.hadoop.ozone.web.ozShell.volume; package org.apache.hadoop.ozone.web.ozShell.volume;
import java.net.URI; import java.net.URI;
import java.nio.file.Path;
import java.nio.file.Paths;
import org.apache.hadoop.ozone.client.OzoneClientException; import org.apache.hadoop.ozone.client.OzoneClientException;
import org.apache.hadoop.ozone.client.OzoneClientUtils; import org.apache.hadoop.ozone.client.OzoneClientUtils;
@ -47,9 +49,17 @@ public class InfoVolumeHandler extends Handler{
public Void call() throws Exception { public Void call() throws Exception {
URI ozoneURI = verifyURI(uri); URI ozoneURI = verifyURI(uri);
if (ozoneURI.getPath().isEmpty()) { Path path = Paths.get(ozoneURI.getPath());
throw new OzoneClientException( int pathNameCount = path.getNameCount();
"Volume name is required to get info of a volume"); if (pathNameCount != 1) {
String errorMessage;
if (pathNameCount < 1) {
errorMessage = "Volume name is required to get info of a volume";
} else {
errorMessage = "Invalid volume name. Delimiters (/) not allowed in " +
"volume name";
}
throw new OzoneClientException(errorMessage);
} }
// we need to skip the slash in the URI path // we need to skip the slash in the URI path