From b6c3b93a30b5c929ae288f9e2f6b9d3232bb34ea Mon Sep 17 00:00:00 2001 From: Nicola Fulvio Calabria <nicola.calabria@inaf.it> Date: Mon, 30 Aug 2021 20:45:17 +0200 Subject: [PATCH] Added request-payload URI consistency check for SetNodeController --- .../inaf/oats/vospace/BaseNodeController.java | 18 +++++++++++++-- .../oats/vospace/CreateNodeController.java | 11 +-------- .../inaf/oats/vospace/SetNodeController.java | 3 +++ .../oats/vospace/SetNodeControllerTest.java | 23 +++++++++++++++++++ 4 files changed, 43 insertions(+), 12 deletions(-) diff --git a/src/main/java/it/inaf/oats/vospace/BaseNodeController.java b/src/main/java/it/inaf/oats/vospace/BaseNodeController.java index 1b317c3..81e2a8b 100644 --- a/src/main/java/it/inaf/oats/vospace/BaseNodeController.java +++ b/src/main/java/it/inaf/oats/vospace/BaseNodeController.java @@ -10,8 +10,10 @@ import it.inaf.oats.vospace.exception.InvalidArgumentException; import it.inaf.oats.vospace.exception.InvalidURIException; import javax.servlet.http.HttpServletRequest; import net.ivoa.xml.vospace.v2.LinkNode; +import net.ivoa.xml.vospace.v2.Node; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.beans.factory.annotation.Value; +import static org.springframework.web.servlet.function.RequestPredicates.path; public abstract class BaseNodeController { @@ -19,8 +21,8 @@ public abstract class BaseNodeController { private HttpServletRequest servletRequest; @Value("${vospace-authority}") - protected String authority; - + protected String authority; + protected String getPath() { String requestURL = servletRequest.getRequestURL().toString(); try { @@ -34,6 +36,18 @@ public abstract class BaseNodeController { return NodeUtils.getParentPath(path); } + protected void validateAndCheckPayloadURIConsistence(Node node) { + // Get Node path (and validates it too) + String decodedURIPathFromNode = URIUtils.returnVosPathFromNodeURI(node.getUri(), this.authority); + + // Check if payload URI is consistent with http request + String requestPath = this.getPath(); + if (!decodedURIPathFromNode.equals(this.getPath())) { + throw new InvalidURIException(decodedURIPathFromNode, requestPath); + } + + } + protected void validateInternalLinkNode(LinkNode linkNode) { String target = linkNode.getTarget(); // I validate it here to add context easily diff --git a/src/main/java/it/inaf/oats/vospace/CreateNodeController.java b/src/main/java/it/inaf/oats/vospace/CreateNodeController.java index e115d15..4cd2860 100644 --- a/src/main/java/it/inaf/oats/vospace/CreateNodeController.java +++ b/src/main/java/it/inaf/oats/vospace/CreateNodeController.java @@ -33,16 +33,7 @@ public class CreateNodeController extends BaseNodeController { String path = getPath(); LOG.debug("createNodeController called for node with URI {} and PATH {}", node.getUri(), path); - - // Get Node path (and validates it too) - String decodedURIPathFromNode = URIUtils.returnVosPathFromNodeURI(node.getUri(), this.authority); - - LOG.debug("createNodeController URI: {} decoded as {}", node.getUri(), decodedURIPathFromNode); - - // Check if payload URI is consistent with http request - if (!decodedURIPathFromNode.equals(path)) { - throw new InvalidURIException(decodedURIPathFromNode, path); - } + this.validateAndCheckPayloadURIConsistence(node); // validate format of input node this.validateInputNode(node); diff --git a/src/main/java/it/inaf/oats/vospace/SetNodeController.java b/src/main/java/it/inaf/oats/vospace/SetNodeController.java index 88621d4..36b2957 100644 --- a/src/main/java/it/inaf/oats/vospace/SetNodeController.java +++ b/src/main/java/it/inaf/oats/vospace/SetNodeController.java @@ -42,6 +42,9 @@ public class SetNodeController extends BaseNodeController { String path = getPath(); LOG.debug("setNode called for path {}", path); + + // Validate and check payload node URI consistence with request + this.validateAndCheckPayloadURIConsistence(node); //The service SHALL throw a HTTP 404 status code including a NodeNotFound //fault in the entity-body if the target Node does not exist diff --git a/src/test/java/it/inaf/oats/vospace/SetNodeControllerTest.java b/src/test/java/it/inaf/oats/vospace/SetNodeControllerTest.java index 00221be..c3cce78 100644 --- a/src/test/java/it/inaf/oats/vospace/SetNodeControllerTest.java +++ b/src/test/java/it/inaf/oats/vospace/SetNodeControllerTest.java @@ -129,7 +129,30 @@ public class SetNodeControllerTest { .andDo(print()) .andExpect(status().isForbidden()); } + + /* Test case: + request and payload URIs don't match + Forbidden. + */ + @Test + public void testRequestPayloadURIMismatch() throws Exception { + String requestBody = getResourceFileContent("modify-data-node-1_type.xml"); + + // Create node + when(nodeDao.listNode(eq("/"))) + .thenReturn(Optional.of(getContainerParentNode("/"))); + when(nodeDao.listNode(eq("/mydata1"))).thenReturn(Optional.of(getWritableDataNode("/mydata1"))); + + mockMvc.perform(post("/nodes/mydataPippo1") + .header("Authorization", "Bearer user2_token") + .content(requestBody) + .contentType(MediaType.APPLICATION_XML) + .accept(MediaType.APPLICATION_XML)) + .andDo(print()) + .andExpect(status().isBadRequest()); + } + /* Test case: try to add accepted views to a node without views. Forbidden -- GitLab