SOLR-4136: followup: fix getBaseUrlForNodeName to never including trailing slash when using the root context, and harden generateNodeName to not trust the caller as far as leading/trailing slashes

git-svn-id: https://svn.apache.org/repos/asf/lucene/dev/trunk@1424755 13f79535-47bb-0310-9956-ffa450edef68
This commit is contained in:
Chris M. Hostetter 2012-12-20 23:26:08 +00:00
parent dd858fe20b
commit d34e50995a
3 changed files with 59 additions and 20 deletions

View File

@ -142,17 +142,12 @@ public final class ZkController {
TimeoutException, IOException {
if (cc == null) throw new IllegalArgumentException("CoreContainer cannot be null.");
this.cc = cc;
if (localHostContext.startsWith("/")) {
// be forgiving and strip this off
// this allows us to support users specifying hostContext="/" in
// solr.xml to indicate the root context, instead of hostContext=""
// which means the default of "solr"
localHostContext = localHostContext.substring(1);
}
if (localHostContext.endsWith("/")) {
// be extra nice
localHostContext = localHostContext.substring(0,localHostContext.length()-1);
}
// be forgiving and strip this off leading/trailing slashes
// this allows us to support users specifying hostContext="/" in
// solr.xml to indicate the root context, instead of hostContext=""
// which means the default of "solr"
localHostContext = trimLeadingAndTrailingSlashes(localHostContext);
updateShardHandler = new UpdateShardHandler(distribUpdateConnTimeout, distribUpdateSoTimeout);
@ -1313,9 +1308,9 @@ public final class ZkController {
/**
* Returns the nodeName that should be used based on the specified properties.
*
* @param hostName - must not be the empty string
* @param hostPort - must consist only of digits, must not be the empty string
* @param hostContext - should not begin or end with a slash, may be the empty string to denote the root context
* @param hostName - must not be null or the empty string
* @param hostPort - must consist only of digits, must not be null or the empty string
* @param hostContext - should not begin or end with a slash (leading/trailin slashes will be ignored), must not be null, may be the empty string to denote the root context
* @lucene.experimental
* @see SolrZkClient#getBaseUrlForNodeName
*/
@ -1324,9 +1319,27 @@ public final class ZkController {
final String hostContext) {
try {
return hostName + ':' + hostPort + '_' +
URLEncoder.encode(hostContext, "UTF-8");
URLEncoder.encode(trimLeadingAndTrailingSlashes(hostContext), "UTF-8");
} catch (UnsupportedEncodingException e) {
throw new IllegalStateException("JVM Does not seem to support UTF-8", e);
}
}
/**
* utilitiy method fro trimming and leading and/or trailing slashes from
* it's input. May return the empty string. May return null if and only
* if the input is null.
*/
private static String trimLeadingAndTrailingSlashes(final String in) {
if (null == in) return in;
String out = in;
if (out.startsWith("/")) {
out = out.substring(1);
}
if (out.endsWith("/")) {
out = out.substring(0,out.length()-1);
}
return out;
}
}

View File

@ -53,10 +53,22 @@ public class ZkControllerTest extends SolrTestCaseJ4 {
// nodeName from parts
assertEquals("localhost:8888_solr",
ZkController.generateNodeName("localhost", "8888", "solr"));
assertEquals("localhost:8888_", // root context
assertEquals("localhost:8888_solr",
ZkController.generateNodeName("localhost", "8888", "/solr"));
assertEquals("localhost:8888_solr",
ZkController.generateNodeName("localhost", "8888", "/solr/"));
// root context
assertEquals("localhost:8888_",
ZkController.generateNodeName("localhost", "8888", ""));
assertEquals("localhost:8888_",
ZkController.generateNodeName("localhost", "8888", "/"));
// subdir
assertEquals("foo-bar:77_solr%2Fsub_dir",
ZkController.generateNodeName("foo-bar", "77", "solr/sub_dir"));
assertEquals("foo-bar:77_solr%2Fsub_dir",
ZkController.generateNodeName("foo-bar", "77", "/solr/sub_dir"));
assertEquals("foo-bar:77_solr%2Fsub_dir",
ZkController.generateNodeName("foo-bar", "77", "/solr/sub_dir/"));
// setup a SolrZkClient to do some getBaseUrlForNodeName testing
String zkDir = dataDir.getAbsolutePath() + File.separator
@ -75,27 +87,41 @@ public class ZkControllerTest extends SolrTestCaseJ4 {
// getBaseUrlForNodeName
assertEquals("http://zzz.xxx:1234/solr",
zkClient.getBaseUrlForNodeName("zzz.xxx:1234_solr"));
assertEquals("http://xxx:99/",
assertEquals("http://xxx:99",
zkClient.getBaseUrlForNodeName("xxx:99_"));
assertEquals("http://foo-bar.baz.org:9999/some_dir",
zkClient.getBaseUrlForNodeName("foo-bar.baz.org:9999_some_dir"));
assertEquals("http://foo-bar.baz.org:9999/solr/sub_dir",
zkClient.getBaseUrlForNodeName("foo-bar.baz.org:9999_solr%2Fsub_dir"));
// generateNodeName + getBaseUrlForNodeName
assertEquals("http://foo:9876/solr",
zkClient.getBaseUrlForNodeName
(ZkController.generateNodeName("foo","9876","solr")));
assertEquals("http://foo:9876/solr",
zkClient.getBaseUrlForNodeName
(ZkController.generateNodeName("foo","9876","/solr")));
assertEquals("http://foo:9876/solr",
zkClient.getBaseUrlForNodeName
(ZkController.generateNodeName("foo","9876","/solr/")));
assertEquals("http://foo.bar.com:9876/solr/sub_dir",
zkClient.getBaseUrlForNodeName
(ZkController.generateNodeName("foo.bar.com","9876","solr/sub_dir")));
assertEquals("http://foo-bar:9876/",
assertEquals("http://foo.bar.com:9876/solr/sub_dir",
zkClient.getBaseUrlForNodeName
(ZkController.generateNodeName("foo.bar.com","9876","/solr/sub_dir/")));
assertEquals("http://foo-bar:9876",
zkClient.getBaseUrlForNodeName
(ZkController.generateNodeName("foo-bar","9876","")));
assertEquals("http://foo-bar:9876",
zkClient.getBaseUrlForNodeName
(ZkController.generateNodeName("foo-bar","9876","/")));
assertEquals("http://foo-bar.com:80/some_dir",
zkClient.getBaseUrlForNodeName
(ZkController.generateNodeName("foo-bar.com","80","some_dir")));
assertEquals("http://foo-bar.com:80/some_dir",
zkClient.getBaseUrlForNodeName
(ZkController.generateNodeName("foo-bar.com","80","/some_dir")));
} finally {
zkClient.close();
}

View File

@ -484,7 +484,7 @@ public class SolrZkClient {
try {
final String path = URLDecoder.decode(nodeName.substring(1+_offset),
"UTF-8");
return "http://" + hostAndPort + "/" + path;
return "http://" + hostAndPort + (path.isEmpty() ? "" : ("/" + path));
} catch (UnsupportedEncodingException e) {
throw new IllegalStateException("JVM Does not seem to support UTF-8", e);
}