diff --git hadoop-yarn-project/hadoop-yarn/hadoop-yarn-api/src/main/java/org/apache/hadoop/yarn/api/protocolrecords/FinishApplicationMasterRequest.java hadoop-yarn-project/hadoop-yarn/hadoop-yarn-api/src/main/java/org/apache/hadoop/yarn/api/protocolrecords/FinishApplicationMasterRequest.java index 3c72568..d0dba7f 100644 --- hadoop-yarn-project/hadoop-yarn/hadoop-yarn-api/src/main/java/org/apache/hadoop/yarn/api/protocolrecords/FinishApplicationMasterRequest.java +++ hadoop-yarn-project/hadoop-yarn/hadoop-yarn-api/src/main/java/org/apache/hadoop/yarn/api/protocolrecords/FinishApplicationMasterRequest.java @@ -101,6 +101,7 @@ public static FinishApplicationMasterRequest newInstance( /** * Set the tracking URLfor the ApplicationMaster + * Empty, null, "N/A" strings are all valid besides a real URL * This url if contains scheme then that will be used by resource manager * web application proxy otherwise it will default to http. * @param url tracking URLfor the diff --git hadoop-yarn-project/hadoop-yarn/hadoop-yarn-api/src/main/java/org/apache/hadoop/yarn/api/protocolrecords/RegisterApplicationMasterRequest.java hadoop-yarn-project/hadoop-yarn/hadoop-yarn-api/src/main/java/org/apache/hadoop/yarn/api/protocolrecords/RegisterApplicationMasterRequest.java index 05668dd..3d7901f 100644 --- hadoop-yarn-project/hadoop-yarn/hadoop-yarn-api/src/main/java/org/apache/hadoop/yarn/api/protocolrecords/RegisterApplicationMasterRequest.java +++ hadoop-yarn-project/hadoop-yarn/hadoop-yarn-api/src/main/java/org/apache/hadoop/yarn/api/protocolrecords/RegisterApplicationMasterRequest.java @@ -113,6 +113,7 @@ public static RegisterApplicationMasterRequest newInstance(String host, /** * Set the tracking URL for the ApplicationMaster. + * Empty, null, "N/A" strings are all values besides a real URL * This url if contains scheme then that will be used by resource manager * web application proxy otherwise it will default to http. * @param trackingUrl tracking URL for the diff --git hadoop-yarn-project/hadoop-yarn/hadoop-yarn-server/hadoop-yarn-server-resourcemanager/src/main/java/org/apache/hadoop/yarn/server/resourcemanager/rmapp/attempt/RMAppAttemptImpl.java hadoop-yarn-project/hadoop-yarn/hadoop-yarn-server/hadoop-yarn-server-resourcemanager/src/main/java/org/apache/hadoop/yarn/server/resourcemanager/rmapp/attempt/RMAppAttemptImpl.java index c31f4ed..40eafec 100644 --- hadoop-yarn-project/hadoop-yarn/hadoop-yarn-server/hadoop-yarn-server-resourcemanager/src/main/java/org/apache/hadoop/yarn/server/resourcemanager/rmapp/attempt/RMAppAttemptImpl.java +++ hadoop-yarn-project/hadoop-yarn/hadoop-yarn-server/hadoop-yarn-server-resourcemanager/src/main/java/org/apache/hadoop/yarn/server/resourcemanager/rmapp/attempt/RMAppAttemptImpl.java @@ -995,7 +995,12 @@ public void transition(RMAppAttemptImpl appAttempt, = (RMAppAttemptRegistrationEvent) event; appAttempt.host = registrationEvent.getHost(); appAttempt.rpcPort = registrationEvent.getRpcport(); - appAttempt.origTrackingUrl = registrationEvent.getTrackingurl(); + String url = registrationEvent.getTrackingurl(); + if (url == null || url.trim().isEmpty()) { + appAttempt.origTrackingUrl = "N/A"; + } else { + appAttempt.origTrackingUrl = url; + } appAttempt.proxiedTrackingUrl = appAttempt.generateProxyUriWithoutScheme(appAttempt.origTrackingUrl); @@ -1115,7 +1120,7 @@ public void transition(RMAppAttemptImpl appAttempt, } } - private static final class AMUnregisteredTransition implements + static final class AMUnregisteredTransition implements MultipleArcTransition { @Override @@ -1130,7 +1135,12 @@ public RMAppAttemptState transition(RMAppAttemptImpl appAttempt, RMAppAttemptUnregistrationEvent unregisterEvent = (RMAppAttemptUnregistrationEvent) event; appAttempt.diagnostics.append(unregisterEvent.getDiagnostics()); - appAttempt.origTrackingUrl = unregisterEvent.getTrackingUrl(); + String url = unregisterEvent.getTrackingUrl(); + if (url == null || url.trim().isEmpty()) { + appAttempt.origTrackingUrl = "N/A"; + } else { + appAttempt.origTrackingUrl = url; + } appAttempt.proxiedTrackingUrl = appAttempt.generateProxyUriWithoutScheme(appAttempt.origTrackingUrl); appAttempt.finalStatus = unregisterEvent.getFinalApplicationStatus(); diff --git hadoop-yarn-project/hadoop-yarn/hadoop-yarn-server/hadoop-yarn-server-resourcemanager/src/test/java/org/apache/hadoop/yarn/server/resourcemanager/rmapp/attempt/TestRMAppAttemptImpl.java hadoop-yarn-project/hadoop-yarn/hadoop-yarn-server/hadoop-yarn-server-resourcemanager/src/test/java/org/apache/hadoop/yarn/server/resourcemanager/rmapp/attempt/TestRMAppAttemptImpl.java index e69d867..b6b6f55 100644 --- hadoop-yarn-project/hadoop-yarn/hadoop-yarn-server/hadoop-yarn-server-resourcemanager/src/test/java/org/apache/hadoop/yarn/server/resourcemanager/rmapp/attempt/TestRMAppAttemptImpl.java +++ hadoop-yarn-project/hadoop-yarn/hadoop-yarn-server/hadoop-yarn-server-resourcemanager/src/test/java/org/apache/hadoop/yarn/server/resourcemanager/rmapp/attempt/TestRMAppAttemptImpl.java @@ -21,33 +21,54 @@ import org.apache.hadoop.yarn.api.records.ApplicationAttemptId; import org.apache.hadoop.yarn.api.records.ApplicationId; import org.apache.hadoop.yarn.api.records.ApplicationSubmissionContext; +import org.apache.hadoop.yarn.api.records.FinalApplicationStatus; import org.apache.hadoop.yarn.conf.YarnConfiguration; import org.apache.hadoop.yarn.event.Dispatcher; import org.apache.hadoop.yarn.event.EventHandler; import org.apache.hadoop.yarn.server.resourcemanager.RMContext; import org.apache.hadoop.yarn.server.resourcemanager.rmapp.attempt.event.RMAppAttemptRegistrationEvent; +import org.apache.hadoop.yarn.server.resourcemanager.rmapp.attempt.event.RMAppAttemptUnregistrationEvent; import org.apache.hadoop.yarn.server.webproxy.ProxyUriUtils; import org.junit.Test; import org.mockito.Mockito; +import org.mockito.invocation.InvocationOnMock; +import org.mockito.stubbing.Answer; public class TestRMAppAttemptImpl { - - private void testTrackingUrl(String url, boolean unmanaged) { - ApplicationAttemptId attemptId = ApplicationAttemptId.newInstance + ApplicationAttemptId attemptId; + RMAppAttemptImpl attempt; + + private void setup(boolean unmanaged) { + attemptId = ApplicationAttemptId.newInstance (ApplicationId.newInstance(1, 2), 1); - EventHandler handler = Mockito.mock(EventHandler.class); + EventHandler handler = Mockito.mock(EventHandler.class); Dispatcher dispatcher = Mockito.mock(Dispatcher.class); Mockito.when(dispatcher.getEventHandler()).thenReturn(handler); RMContext rmContext = Mockito.mock(RMContext.class); Mockito.when(rmContext.getDispatcher()).thenReturn(dispatcher); - - ApplicationSubmissionContext appContext = + AMLivelinessMonitor mockAMLivelinessMonitor = + Mockito.mock(AMLivelinessMonitor.class); + Mockito.doAnswer(new Answer() { + + public Object answer(InvocationOnMock invocation) { + return true; + } + }).when(mockAMLivelinessMonitor).unregister(attemptId); + Mockito.when(rmContext.getAMLivelinessMonitor()).thenReturn( + mockAMLivelinessMonitor); + Mockito.when(rmContext.getAMFinishingMonitor()).thenReturn( + mockAMLivelinessMonitor); + ApplicationSubmissionContext appContext = Mockito.mock(ApplicationSubmissionContext.class); Mockito.when(appContext.getUnmanagedAM()).thenReturn(unmanaged); - - RMAppAttemptImpl attempt = new RMAppAttemptImpl(attemptId, rmContext, null, + + attempt = new RMAppAttemptImpl(attemptId, rmContext, null, null, appContext, new YarnConfiguration(), null); + } + + private void testTrackingUrl(String url, boolean unmanaged) { + setup(unmanaged); RMAppAttemptRegistrationEvent event = Mockito.mock(RMAppAttemptRegistrationEvent.class); Mockito.when(event.getHost()).thenReturn("h"); @@ -74,4 +95,47 @@ public void testTrackingUrlUnmanagedAM() { public void testTrackingUrlManagedAM() { testTrackingUrl("bar:8000/x", false); } + + @Test + public void testOriginalUrl() { + setup(false); + RMAppAttemptRegistrationEvent event = + Mockito.mock(RMAppAttemptRegistrationEvent.class); + Mockito.when(event.getHost()).thenReturn("h"); + Mockito.when(event.getRpcport()).thenReturn(0); + Mockito.when(event.getTrackingurl()).thenReturn(""); + new RMAppAttemptImpl.AMRegisteredTransition().transition(attempt, event); + Assert.assertEquals("N/A", attempt.getOriginalTrackingUrl()); + + Mockito.when(event.getTrackingurl()).thenReturn(null); + new RMAppAttemptImpl.AMRegisteredTransition().transition(attempt, event); + Assert.assertEquals("N/A", attempt.getOriginalTrackingUrl()); + + String url = "fake Url"; + Mockito.when(event.getTrackingurl()).thenReturn(url); + new RMAppAttemptImpl.AMRegisteredTransition().transition(attempt, event); + Assert.assertEquals(url, attempt.getOriginalTrackingUrl()); + + RMAppAttemptUnregistrationEvent unRegistrationEvent = + Mockito.mock(RMAppAttemptUnregistrationEvent.class); + Mockito.when(unRegistrationEvent.getDiagnostics()) + .thenReturn("Diagnostics"); + Mockito.when(unRegistrationEvent.getFinalApplicationStatus()).thenReturn( + FinalApplicationStatus.SUCCEEDED); + Mockito.when(unRegistrationEvent.getTrackingUrl()).thenReturn(""); + new RMAppAttemptImpl.AMUnregisteredTransition().transition(attempt, + unRegistrationEvent); + Assert.assertEquals("N/A", attempt.getOriginalTrackingUrl()); + + Mockito.when(unRegistrationEvent.getTrackingUrl()).thenReturn(null); + new RMAppAttemptImpl.AMUnregisteredTransition().transition(attempt, + unRegistrationEvent); + Assert.assertEquals("N/A", attempt.getOriginalTrackingUrl()); + + url = "fake url2"; + Mockito.when(unRegistrationEvent.getTrackingUrl()).thenReturn(url); + new RMAppAttemptImpl.AMUnregisteredTransition().transition(attempt, + unRegistrationEvent); + Assert.assertEquals(url, attempt.getOriginalTrackingUrl()); + } } diff --git hadoop-yarn-project/hadoop-yarn/hadoop-yarn-server/hadoop-yarn-server-resourcemanager/src/test/java/org/apache/hadoop/yarn/server/resourcemanager/rmapp/attempt/TestRMAppAttemptTransitions.java hadoop-yarn-project/hadoop-yarn/hadoop-yarn-server/hadoop-yarn-server-resourcemanager/src/test/java/org/apache/hadoop/yarn/server/resourcemanager/rmapp/attempt/TestRMAppAttemptTransitions.java index 39c6337..5aa8b22 100644 --- hadoop-yarn-project/hadoop-yarn/hadoop-yarn-server/hadoop-yarn-server-resourcemanager/src/test/java/org/apache/hadoop/yarn/server/resourcemanager/rmapp/attempt/TestRMAppAttemptTransitions.java +++ hadoop-yarn-project/hadoop-yarn/hadoop-yarn-server/hadoop-yarn-server-resourcemanager/src/test/java/org/apache/hadoop/yarn/server/resourcemanager/rmapp/attempt/TestRMAppAttemptTransitions.java @@ -30,14 +30,18 @@ import static org.mockito.Mockito.when; import static org.mockito.Mockito.spy; +import java.net.URI; +import java.net.URISyntaxException; import java.util.Arrays; import java.util.Collection; import java.util.Collections; import java.util.List; +import org.apache.commons.lang.StringUtils; import org.apache.commons.logging.Log; import org.apache.commons.logging.LogFactory; import org.apache.hadoop.conf.Configuration; +import org.apache.hadoop.http.HttpConfig; import org.apache.hadoop.security.SecurityUtil; import org.apache.hadoop.security.UserGroupInformation; import org.apache.hadoop.security.UserGroupInformation.AuthenticationMethod; @@ -85,8 +89,10 @@ import org.apache.hadoop.yarn.server.resourcemanager.security.ClientToAMTokenSecretManagerInRM; import org.apache.hadoop.yarn.server.resourcemanager.security.RMContainerTokenSecretManager; import org.apache.hadoop.yarn.server.utils.BuilderUtils; +import org.apache.hadoop.yarn.server.webproxy.ProxyUriUtils; import org.apache.hadoop.yarn.server.resourcemanager.security.NMTokenSecretManagerInRM; import org.junit.After; +import org.junit.Assert; import org.junit.Before; import org.junit.Test; import org.junit.runner.RunWith; @@ -261,8 +267,22 @@ public void tearDown() throws Exception { private String getProxyUrl(RMAppAttempt appAttempt) { - return pjoin(RM_WEBAPP_ADDR, "proxy", - appAttempt.getAppAttemptId().getApplicationId(), ""); + String url = null; + try { + URI trackingUri = + StringUtils.isEmpty(appAttempt.getOriginalTrackingUrl()) ? null : + ProxyUriUtils + .getUriFromAMUrl(appAttempt.getOriginalTrackingUrl()); + String proxy = YarnConfiguration.getProxyHostAndPort(conf); + URI proxyUri = ProxyUriUtils.getUriFromAMUrl(proxy); + URI result = ProxyUriUtils.getProxyUri(trackingUri, proxyUri, + appAttempt.getAppAttemptId().getApplicationId()); + url = result.toASCIIString().substring( + HttpConfig.getSchemePrefix().length()); + } catch (URISyntaxException ex) { + Assert.fail(); + } + return url; } /** @@ -442,7 +462,11 @@ private void testAppAttemptRunningState(Container container, assertEquals(container, applicationAttempt.getMasterContainer()); assertEquals(host, applicationAttempt.getHost()); assertEquals(rpcPort, applicationAttempt.getRpcPort()); - assertEquals(trackingUrl, applicationAttempt.getOriginalTrackingUrl()); + if (trackingUrl != null && trackingUrl.trim().isEmpty()) { + assertEquals("N/A", applicationAttempt.getOriginalTrackingUrl()); + } else { + assertEquals(trackingUrl, applicationAttempt.getOriginalTrackingUrl()); + } if (unmanagedAM) { assertEquals("oldtrackingurl", applicationAttempt.getTrackingUrl()); } else {