YARN-3239. WebAppProxy does not support a final tracking url which has query fragments and params. Contributed by Jian He

(cherry picked from commit 1a68fc4346)

(cherry picked from commit 257087417e)
(cherry picked from commit 49468108c203bf093acdc93c1798d90c480c3a17)
This commit is contained in:
Jason Lowe 2015-02-25 16:14:34 +00:00 committed by Vinod Kumar Vavilapalli
parent 406ec495bb
commit a4b8897b30
3 changed files with 41 additions and 8 deletions

View File

@ -85,6 +85,9 @@ Release 2.6.1 - UNRELEASED
YARN-3238. Connection timeouts to nodemanagers are retried at
multiple levels (Jason Lowe via xgong)
YARN-3239. WebAppProxy does not support a final tracking url which has
query fragments and params (Jian He via jlowe)
Release 2.6.0 - 2014-11-18
INCOMPATIBLE CHANGES

View File

@ -36,6 +36,7 @@ import javax.servlet.http.Cookie;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.ws.rs.core.UriBuilder;
import org.apache.commons.httpclient.Header;
import org.apache.commons.httpclient.HostConfiguration;
@ -58,6 +59,8 @@ import org.apache.hadoop.yarn.util.TrackingUriPlugin;
import org.apache.hadoop.yarn.webapp.MimeType;
import org.apache.hadoop.yarn.webapp.hamlet.Hamlet;
import org.apache.hadoop.yarn.webapp.util.WebAppUtils;
import org.apache.http.NameValuePair;
import org.apache.http.client.utils.URLEncodedUtils;
public class WebAppProxyServlet extends HttpServlet {
private static final long serialVersionUID = 1L;
@ -322,13 +325,19 @@ public class WebAppProxyServlet extends HttpServlet {
req.getQueryString(), true), runningUser, id);
return;
}
URI toFetch = new URI(trackingUri.getScheme(),
trackingUri.getAuthority(),
StringHelper.ujoin(trackingUri.getPath(), rest), req.getQueryString(),
null);
LOG.info(req.getRemoteUser()+" is accessing unchecked "+toFetch+
" which is the app master GUI of "+appId+" owned by "+runningUser);
// Append the user-provided path and query parameter to the original
// tracking url.
List<NameValuePair> queryPairs =
URLEncodedUtils.parse(req.getQueryString(), null);
UriBuilder builder = UriBuilder.fromUri(trackingUri);
for (NameValuePair pair : queryPairs) {
builder.queryParam(pair.getName(), pair.getValue());
}
URI toFetch = builder.path(rest).build();
LOG.info(remoteUser+" is accessing unchecked "+toFetch+
" which is the app master GUI of "+appId+" owned by "+runningUser);
switch(applicationReport.getYarnApplicationState()) {
case KILLED:

View File

@ -84,7 +84,7 @@ public class TestWebAppProxyServlet {
Context context = new Context();
context.setContextPath("/foo");
server.setHandler(context);
context.addServlet(new ServletHolder(TestServlet.class), "/bar/");
context.addServlet(new ServletHolder(TestServlet.class), "/bar");
server.getConnectors()[0].setHost("localhost");
server.start();
originalPort = server.getConnectors()[0].getLocalPort();
@ -183,6 +183,19 @@ public class TestWebAppProxyServlet {
proxyConn.setRequestProperty("Cookie", "checked_application_0_0000=true");
proxyConn.connect();
assertEquals(HttpURLConnection.HTTP_OK, proxyConn.getResponseCode());
// test user-provided path and query parameter can be appended to the
// original tracking url
appReportFetcher.answer = 5;
URL clientUrl = new URL("http://localhost:" + proxyPort
+ "/proxy/application_00_0/test/tez?x=y&h=p");
proxyConn = (HttpURLConnection) clientUrl.openConnection();
proxyConn.connect();
LOG.info("" + proxyConn.getURL());
LOG.info("ProxyConn.getHeaderField(): " + proxyConn.getHeaderField("Location"));
assertEquals("http://localhost:" + originalPort
+ "/foo/bar/test/tez?a=b&x=y&h=p#main", proxyConn.getURL().toString());
} finally {
proxy.close();
}
@ -352,6 +365,14 @@ public class TestWebAppProxyServlet {
return result;
} else if (answer == 4) {
throw new ApplicationNotFoundException("Application is not found");
} else if (answer == 5) {
// test user-provided path and query parameter can be appended to the
// original tracking url
ApplicationReport result = getDefaultApplicationReport(appId);
result.setOriginalTrackingUrl("localhost:" + originalPort
+ "/foo/bar?a=b#main");
result.setYarnApplicationState(YarnApplicationState.FINISHED);
return result;
}
return null;
}