YARN-107. Fixed ResourceManager and clients to better handle forceKillApplication on non-running and finished applications. Contributed by Xuan Gong.
git-svn-id: https://svn.apache.org/repos/asf/hadoop/common/trunk@1514918 13f79535-47bb-0310-9956-ffa450edef68
This commit is contained in:
parent
52f0259502
commit
1ad3fe4633
|
@ -70,6 +70,10 @@ Release 2.1.1-beta - UNRELEASED
|
|||
|
||||
YARN-337. RM handles killed application tracking URL poorly (jlowe)
|
||||
|
||||
YARN-107. Fixed ResourceManager and clients to better handle
|
||||
forceKillApplication on non-running and finished applications. (Xuan Gong
|
||||
via vinodkv)
|
||||
|
||||
Release 2.1.0-beta - 2013-08-22
|
||||
|
||||
INCOMPATIBLE CHANGES
|
||||
|
|
|
@ -35,6 +35,7 @@ import org.apache.hadoop.classification.InterfaceStability.Unstable;
|
|||
import org.apache.hadoop.util.ToolRunner;
|
||||
import org.apache.hadoop.yarn.api.records.ApplicationId;
|
||||
import org.apache.hadoop.yarn.api.records.ApplicationReport;
|
||||
import org.apache.hadoop.yarn.api.records.YarnApplicationState;
|
||||
import org.apache.hadoop.yarn.exceptions.YarnException;
|
||||
import org.apache.hadoop.yarn.util.ConverterUtils;
|
||||
|
||||
|
@ -164,9 +165,16 @@ public class ApplicationCLI extends YarnCLI {
|
|||
private void killApplication(String applicationId)
|
||||
throws YarnException, IOException {
|
||||
ApplicationId appId = ConverterUtils.toApplicationId(applicationId);
|
||||
ApplicationReport appReport = client.getApplicationReport(appId);
|
||||
if (appReport.getYarnApplicationState() == YarnApplicationState.FINISHED
|
||||
|| appReport.getYarnApplicationState() == YarnApplicationState.KILLED
|
||||
|| appReport.getYarnApplicationState() == YarnApplicationState.FAILED) {
|
||||
sysout.println("Application " + applicationId + " has already finished ");
|
||||
} else {
|
||||
sysout.println("Killing application " + applicationId);
|
||||
client.killApplication(appId);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Prints the application report for an application id.
|
||||
|
|
|
@ -26,6 +26,7 @@ import static org.mockito.Mockito.spy;
|
|||
import static org.mockito.Mockito.times;
|
||||
import static org.mockito.Mockito.verify;
|
||||
import static org.mockito.Mockito.when;
|
||||
import static org.mockito.Mockito.doThrow;
|
||||
|
||||
import java.io.ByteArrayOutputStream;
|
||||
import java.io.PrintStream;
|
||||
|
@ -320,10 +321,44 @@ public class TestYarnCLI {
|
|||
public void testKillApplication() throws Exception {
|
||||
ApplicationCLI cli = createAndGetAppCLI();
|
||||
ApplicationId applicationId = ApplicationId.newInstance(1234, 5);
|
||||
|
||||
ApplicationReport newApplicationReport2 = ApplicationReport.newInstance(
|
||||
applicationId, ApplicationAttemptId.newInstance(applicationId, 1),
|
||||
"user", "queue", "appname", "host", 124, null,
|
||||
YarnApplicationState.FINISHED, "diagnostics", "url", 0, 0,
|
||||
FinalApplicationStatus.SUCCEEDED, null, "N/A", 0.53789f, "YARN", null);
|
||||
when(client.getApplicationReport(any(ApplicationId.class))).thenReturn(
|
||||
newApplicationReport2);
|
||||
int result = cli.run(new String[] { "-kill", applicationId.toString() });
|
||||
assertEquals(0, result);
|
||||
verify(client, times(0)).killApplication(any(ApplicationId.class));
|
||||
verify(sysOut).println(
|
||||
"Application " + applicationId + " has already finished ");
|
||||
|
||||
ApplicationReport newApplicationReport = ApplicationReport.newInstance(
|
||||
applicationId, ApplicationAttemptId.newInstance(applicationId, 1),
|
||||
"user", "queue", "appname", "host", 124, null,
|
||||
YarnApplicationState.RUNNING, "diagnostics", "url", 0, 0,
|
||||
FinalApplicationStatus.SUCCEEDED, null, "N/A", 0.53789f, "YARN", null);
|
||||
when(client.getApplicationReport(any(ApplicationId.class))).thenReturn(
|
||||
newApplicationReport);
|
||||
result = cli.run(new String[] { "-kill", applicationId.toString() });
|
||||
assertEquals(0, result);
|
||||
verify(client).killApplication(any(ApplicationId.class));
|
||||
verify(sysOut).println("Killing application application_1234_0005");
|
||||
|
||||
doThrow(new ApplicationNotFoundException("Application with id '"
|
||||
+ applicationId + "' doesn't exist in RM.")).when(client)
|
||||
.getApplicationReport(applicationId);
|
||||
cli = createAndGetAppCLI();
|
||||
try {
|
||||
cli.run(new String[] { "-kill", applicationId.toString() });
|
||||
Assert.fail();
|
||||
} catch (Exception ex) {
|
||||
Assert.assertTrue(ex instanceof ApplicationNotFoundException);
|
||||
Assert.assertEquals("Application with id '" + applicationId +
|
||||
"' doesn't exist in RM.", ex.getMessage());
|
||||
}
|
||||
}
|
||||
|
||||
@Test
|
||||
|
|
|
@ -353,9 +353,8 @@ public class ClientRMService extends AbstractService implements
|
|||
RMAuditLogger.logFailure(callerUGI.getUserName(),
|
||||
AuditConstants.KILL_APP_REQUEST, "UNKNOWN", "ClientRMService",
|
||||
"Trying to kill an absent application", applicationId);
|
||||
throw RPCUtil
|
||||
.getRemoteException("Trying to kill an absent application "
|
||||
+ applicationId);
|
||||
throw new ApplicationNotFoundException("Trying to kill an absent"
|
||||
+ " application " + applicationId);
|
||||
}
|
||||
|
||||
if (!checkAccess(callerUGI, application.getUser(),
|
||||
|
|
|
@ -51,6 +51,7 @@ import org.apache.hadoop.yarn.api.protocolrecords.GetApplicationReportResponse;
|
|||
import org.apache.hadoop.yarn.api.protocolrecords.GetClusterNodesRequest;
|
||||
import org.apache.hadoop.yarn.api.protocolrecords.GetQueueInfoRequest;
|
||||
import org.apache.hadoop.yarn.api.protocolrecords.GetQueueInfoResponse;
|
||||
import org.apache.hadoop.yarn.api.protocolrecords.KillApplicationRequest;
|
||||
import org.apache.hadoop.yarn.api.protocolrecords.RenewDelegationTokenRequest;
|
||||
import org.apache.hadoop.yarn.api.protocolrecords.SubmitApplicationRequest;
|
||||
import org.apache.hadoop.yarn.api.records.ApplicationAccessType;
|
||||
|
@ -197,6 +198,27 @@ public class TestClientRMService {
|
|||
}
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testForceKillApplication() throws YarnException {
|
||||
RMContext rmContext = mock(RMContext.class);
|
||||
when(rmContext.getRMApps()).thenReturn(
|
||||
new ConcurrentHashMap<ApplicationId, RMApp>());
|
||||
ClientRMService rmService = new ClientRMService(rmContext, null, null,
|
||||
null, null);
|
||||
ApplicationId applicationId =
|
||||
BuilderUtils.newApplicationId(System.currentTimeMillis(), 0);
|
||||
KillApplicationRequest request =
|
||||
KillApplicationRequest.newInstance(applicationId);
|
||||
try {
|
||||
rmService.forceKillApplication(request);
|
||||
Assert.fail();
|
||||
} catch (ApplicationNotFoundException ex) {
|
||||
Assert.assertEquals(ex.getMessage(),
|
||||
"Trying to kill an absent " +
|
||||
"application " + request.getApplicationId());
|
||||
}
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testGetQueueInfo() throws Exception {
|
||||
YarnScheduler yarnScheduler = mock(YarnScheduler.class);
|
||||
|
|
Loading…
Reference in New Issue