diff --git hadoop-yarn-project/hadoop-yarn/hadoop-yarn-client/src/main/java/org/apache/hadoop/yarn/client/cli/LogsCLI.java hadoop-yarn-project/hadoop-yarn/hadoop-yarn-client/src/main/java/org/apache/hadoop/yarn/client/cli/LogsCLI.java index d62ee5e..feb65fb 100644 --- hadoop-yarn-project/hadoop-yarn/hadoop-yarn-client/src/main/java/org/apache/hadoop/yarn/client/cli/LogsCLI.java +++ hadoop-yarn-project/hadoop-yarn/hadoop-yarn-client/src/main/java/org/apache/hadoop/yarn/client/cli/LogsCLI.java @@ -339,8 +339,9 @@ private boolean fetchAllLogFiles(String[] logFiles) { WebResource webResource = webServiceClient .resource(WebAppUtils.getHttpSchemePrefix(conf) + nodeHttpAddress); ClientResponse response = - webResource.path("ws").path("v1").path("node").path("containers") - .path(containerIdStr).accept(MediaType.APPLICATION_XML) + webResource.path("ws").path("v1").path("node").path("containerlogs") + .path("container").path(containerIdStr) + .accept(MediaType.APPLICATION_XML) .get(ClientResponse.class); if (response.getClientResponseStatus().equals(ClientResponse.Status.OK)) { try { diff --git hadoop-yarn-project/hadoop-yarn/hadoop-yarn-server/hadoop-yarn-server-nodemanager/src/main/java/org/apache/hadoop/yarn/server/nodemanager/webapp/NMWebServices.java hadoop-yarn-project/hadoop-yarn/hadoop-yarn-server/hadoop-yarn-server-nodemanager/src/main/java/org/apache/hadoop/yarn/server/nodemanager/webapp/NMWebServices.java index efc0e7e..32df801 100644 --- hadoop-yarn-project/hadoop-yarn/hadoop-yarn-server/hadoop-yarn-server-nodemanager/src/main/java/org/apache/hadoop/yarn/server/nodemanager/webapp/NMWebServices.java +++ hadoop-yarn-project/hadoop-yarn/hadoop-yarn-server/hadoop-yarn-server-nodemanager/src/main/java/org/apache/hadoop/yarn/server/nodemanager/webapp/NMWebServices.java @@ -21,6 +21,8 @@ import java.io.FileInputStream; import java.io.IOException; import java.io.OutputStream; +import java.util.ArrayList; +import java.util.List; import java.util.Map.Entry; import javax.servlet.http.HttpServletRequest; @@ -53,6 +55,7 @@ import org.apache.hadoop.yarn.server.nodemanager.webapp.dao.AppInfo; import org.apache.hadoop.yarn.server.nodemanager.webapp.dao.AppsInfo; import org.apache.hadoop.yarn.server.nodemanager.webapp.dao.ContainerInfo; +import org.apache.hadoop.yarn.server.nodemanager.webapp.dao.ContainerLogsFileInfo; import org.apache.hadoop.yarn.server.nodemanager.webapp.dao.ContainersInfo; import org.apache.hadoop.yarn.server.nodemanager.webapp.dao.NodeInfo; import org.apache.hadoop.yarn.util.ConverterUtils; @@ -194,8 +197,35 @@ public ContainerInfo getNodeContainer(@javax.ws.rs.core.Context .toString(), webapp.name(), hsr.getRemoteUser()); } - + /** + * Returns the name of a container's log file. + * + * @param hsr + * HttpServletRequest + * @param id + * The container ID + * @return + * The name of the container's log files + */ + @GET + @Path("/containerlogs/container/{containerid}") + @Produces({ MediaType.APPLICATION_JSON, MediaType.APPLICATION_XML }) + public ContainerLogsFileInfo getNodeContainerLogFiles( + @javax.ws.rs.core.Context HttpServletRequest hsr, + @PathParam("containerid") String id) { + ContainerId containerId = null; + init(); + try { + containerId = ConverterUtils.toContainerId(id); + } catch (Exception e) { + throw new BadRequestException("invalid container id, " + id); + } + return new ContainerLogsFileInfo(this.nmContext, containerId, + hsr.getRemoteUser()); + } + +/** * Returns the contents of a container's log file in plain text. * * Only works for containers that are still in the NodeManager's memory, so diff --git hadoop-yarn-project/hadoop-yarn/hadoop-yarn-server/hadoop-yarn-server-nodemanager/src/main/java/org/apache/hadoop/yarn/server/nodemanager/webapp/dao/ContainerLogsFileInfo.java hadoop-yarn-project/hadoop-yarn/hadoop-yarn-server/hadoop-yarn-server-nodemanager/src/main/java/org/apache/hadoop/yarn/server/nodemanager/webapp/dao/ContainerLogsFileInfo.java new file mode 100644 index 0000000..1136486 --- /dev/null +++ hadoop-yarn-project/hadoop-yarn/hadoop-yarn-server/hadoop-yarn-server-nodemanager/src/main/java/org/apache/hadoop/yarn/server/nodemanager/webapp/dao/ContainerLogsFileInfo.java @@ -0,0 +1,71 @@ +/** + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package org.apache.hadoop.yarn.server.nodemanager.webapp.dao; + +import java.io.File; +import java.util.ArrayList; +import java.util.List; +import javax.xml.bind.annotation.XmlAccessType; +import javax.xml.bind.annotation.XmlAccessorType; +import javax.xml.bind.annotation.XmlRootElement; +import org.apache.hadoop.yarn.api.records.ContainerId; +import org.apache.hadoop.yarn.server.nodemanager.Context; +import org.apache.hadoop.yarn.server.nodemanager.webapp.ContainerLogsUtils; + +@XmlRootElement +@XmlAccessorType(XmlAccessType.FIELD) +public class ContainerLogsFileInfo { + + protected List containerLogFiles; + + public ContainerLogsFileInfo() { + } // JAXB needs this + + public ContainerLogsFileInfo(final Context nmContext, + final ContainerId containerId, String remoteUser) { + this.containerLogFiles = getContainerLogFiles(containerId, + remoteUser, nmContext); + } + + public List getContainerLogFiles() { + return this.containerLogFiles; + } + + private List getContainerLogFiles(ContainerId id, String remoteUser, + Context nmContext) { + List logFiles = new ArrayList<>(); + try { + List logDirs = + ContainerLogsUtils.getContainerLogDirs(id, remoteUser, nmContext); + for (File containerLogsDir : logDirs) { + File[] logs = containerLogsDir.listFiles(); + if (logs != null) { + for (File log : logs) { + if (log.isFile()) { + logFiles.add(log.getName()); + } + } + } + } + } catch (Exception ye) { + return logFiles; + } + return logFiles; + } +} \ No newline at end of file diff --git hadoop-yarn-project/hadoop-yarn/hadoop-yarn-server/hadoop-yarn-server-nodemanager/src/test/java/org/apache/hadoop/yarn/server/nodemanager/webapp/TestNMWebServices.java hadoop-yarn-project/hadoop-yarn/hadoop-yarn-server/hadoop-yarn-server-nodemanager/src/test/java/org/apache/hadoop/yarn/server/nodemanager/webapp/TestNMWebServices.java index a4305da..6342558 100644 --- hadoop-yarn-project/hadoop-yarn/hadoop-yarn-server/hadoop-yarn-server-nodemanager/src/test/java/org/apache/hadoop/yarn/server/nodemanager/webapp/TestNMWebServices.java +++ hadoop-yarn-project/hadoop-yarn/hadoop-yarn-server/hadoop-yarn-server-nodemanager/src/test/java/org/apache/hadoop/yarn/server/nodemanager/webapp/TestNMWebServices.java @@ -313,12 +313,13 @@ public void testSingleNodesXML() throws JSONException, Exception { } @Test - public void testContainerLogs() throws IOException { + public void testContainerLogs() throws IOException, JSONException { WebResource r = resource(); final ContainerId containerId = BuilderUtils.newContainerId(0, 0, 0, 0); final String containerIdStr = BuilderUtils.newContainerId(0, 0, 0, 0) .toString(); - final ApplicationAttemptId appAttemptId = containerId.getApplicationAttemptId(); + final ApplicationAttemptId appAttemptId = containerId + .getApplicationAttemptId(); final ApplicationId appId = appAttemptId.getApplicationId(); final String appIdStr = appId.toString(); final String filename = "logfile1"; @@ -431,6 +432,14 @@ public void testContainerLogs() throws IOException { .get(ClientResponse.class); responseText = response.getEntity(String.class); assertEquals(logMessage, responseText); + + // Get container log files' name + response = r.path("ws").path("v1").path("node") + .path("containerlogs").path("container").path(containerIdStr) + .accept(MediaType.APPLICATION_JSON).get(ClientResponse.class); + assertEquals(200, response.getStatus()); + JSONObject json = response.getEntity(JSONObject.class); + assertEquals(json.getString("containerLogFiles"), filename); } public void verifyNodesXML(NodeList nodes) throws JSONException, Exception {