This is an automated email from the ASF dual-hosted git repository. markt pushed a commit to branch 10.1.x in repository https://gitbox.apache.org/repos/asf/tomcat.git
commit 0937137ca58f9b0b034f1d5a2e56a8cbf9ff1571 Author: Mark Thomas <ma...@apache.org> AuthorDate: Thu Dec 12 17:35:33 2024 +0000 Expand the precondition tests to include PUT --- .../apache/catalina/servlets/DefaultServlet.java | 13 ++--- .../apache/tomcat/util/http/parser/EntityTag.java | 11 ++-- ...efaultServletRfc9110Section13Parameterized.java | 63 +++++++++++++++++----- 3 files changed, 64 insertions(+), 23 deletions(-) diff --git a/java/org/apache/catalina/servlets/DefaultServlet.java b/java/org/apache/catalina/servlets/DefaultServlet.java index a9f9c9e40c..fd9710ff19 100644 --- a/java/org/apache/catalina/servlets/DefaultServlet.java +++ b/java/org/apache/catalina/servlets/DefaultServlet.java @@ -610,6 +610,10 @@ public class DefaultServlet extends HttpServlet { return; } + if (!checkIfHeaders(req, resp, resource)) { + return; + } + InputStream resourceInputStream = null; try { @@ -2153,11 +2157,6 @@ public class DefaultServlet extends HttpServlet { return true; } String resourceETag = generateETag(resource); - if (resourceETag == null) { - // if a current representation for the target resource is not present - response.sendError(HttpServletResponse.SC_PRECONDITION_FAILED); - return false; - } boolean hasAsteriskValue = false;// check existence of special header value '*' int headerCount = 0; @@ -2166,7 +2165,9 @@ public class DefaultServlet extends HttpServlet { String headerValue = headerValues.nextElement(); if ("*".equals(headerValue)) { hasAsteriskValue = true; - conditionSatisfied = true; + if (resourceETag != null) { + conditionSatisfied = true; + } } else { // RFC 7232 requires strong comparison for If-Match headers Boolean matched = EntityTag.compareEntityTag(new StringReader(headerValue), false, resourceETag); diff --git a/java/org/apache/tomcat/util/http/parser/EntityTag.java b/java/org/apache/tomcat/util/http/parser/EntityTag.java index 132b480ca3..096e193cf7 100644 --- a/java/org/apache/tomcat/util/http/parser/EntityTag.java +++ b/java/org/apache/tomcat/util/http/parser/EntityTag.java @@ -35,17 +35,20 @@ public class EntityTag { */ public static Boolean compareEntityTag(StringReader input, boolean compareWeak, String resourceETag) throws IOException { + + Boolean result = Boolean.FALSE; + // The resourceETag may be weak so to do weak comparison remove /W // before comparison String comparisonETag; - if (compareWeak && resourceETag.startsWith("W/")) { + if (resourceETag == null) { + comparisonETag = null; + } else if (compareWeak && resourceETag.startsWith("W/")) { comparisonETag = resourceETag.substring(2); } else { comparisonETag = resourceETag; } - Boolean result = Boolean.FALSE; - while (true) { boolean strong = false; HttpParser.skipLws(input); @@ -71,7 +74,7 @@ public class EntityTag { } if (strong || compareWeak) { - if (comparisonETag.equals(value)) { + if (value.equals(comparisonETag)) { result = Boolean.TRUE; } } diff --git a/test/org/apache/catalina/servlets/TestDefaultServletRfc9110Section13Parameterized.java b/test/org/apache/catalina/servlets/TestDefaultServletRfc9110Section13Parameterized.java index b9b5953d42..43c94ead71 100644 --- a/test/org/apache/catalina/servlets/TestDefaultServletRfc9110Section13Parameterized.java +++ b/test/org/apache/catalina/servlets/TestDefaultServletRfc9110Section13Parameterized.java @@ -28,6 +28,8 @@ import java.util.List; import java.util.Map; import java.util.Map.Entry; +import jakarta.servlet.http.HttpServletResponse; + import org.junit.Assert; import org.junit.Test; import org.junit.runner.RunWith; @@ -117,12 +119,15 @@ public class TestDefaultServletRfc9110Section13Parameterized extends TomcatBaseT // RFC 9110, Section 13.2.2, Step 3, HEAD: If-None-Match with and without If-Modified-Since for (DatePrecondition dateCondition : DatePrecondition.values()) { - parameterSets.add(new Object[] { useStrongEtag, task, null, null, EtagPrecondition.ALL, - dateCondition, null, null, Boolean.FALSE, task.equals(Task.POST_INDEX_HTML) ? SC_412 : SC_304 }); - parameterSets.add(new Object[] { useStrongEtag, task, null, null, EtagPrecondition.EXACTLY, - dateCondition, null, null, Boolean.FALSE, task.equals(Task.POST_INDEX_HTML) ? SC_412 : SC_304 }); - parameterSets.add(new Object[] { useStrongEtag, task, null, null, EtagPrecondition.IN, - dateCondition, null, null, Boolean.FALSE, task.equals(Task.POST_INDEX_HTML) ? SC_412 : SC_304 }); + parameterSets + .add(new Object[] { useStrongEtag, task, null, null, EtagPrecondition.ALL, dateCondition, + null, null, Boolean.FALSE, task.equals(Task.POST_INDEX_HTML) ? SC_412 : SC_304 }); + parameterSets.add( + new Object[] { useStrongEtag, task, null, null, EtagPrecondition.EXACTLY, dateCondition, + null, null, Boolean.FALSE, task.equals(Task.POST_INDEX_HTML) ? SC_412 : SC_304 }); + parameterSets + .add(new Object[] { useStrongEtag, task, null, null, EtagPrecondition.IN, dateCondition, + null, null, Boolean.FALSE, task.equals(Task.POST_INDEX_HTML) ? SC_412 : SC_304 }); parameterSets.add(new Object[] { useStrongEtag, task, null, null, EtagPrecondition.NOT_IN, dateCondition, null, null, Boolean.FALSE, SC_200 }); parameterSets.add(new Object[] { useStrongEtag, task, null, null, EtagPrecondition.INVALID, @@ -224,17 +229,48 @@ public class TestDefaultServletRfc9110Section13Parameterized extends TomcatBaseT DatePrecondition.MULTI_IN_REV, Boolean.FALSE, SC_200 }); parameterSets.add(new Object[] { useStrongEtag, Task.GET_INDEX_HTML, null, null, null, null, null, DatePrecondition.INVALID, Boolean.FALSE, SC_200 }); + + // PUT tests + parameterSets.add(new Object[] { useStrongEtag, Task.PUT_EXIST_TXT, null, null, null, null, null, null, + Boolean.FALSE, SC_204 }); + parameterSets.add(new Object[] { useStrongEtag, Task.PUT_EXIST_TXT, EtagPrecondition.ALL, null, null, null, + null, null, Boolean.FALSE, SC_204 }); + parameterSets.add(new Object[] { useStrongEtag, Task.PUT_EXIST_TXT, EtagPrecondition.EXACTLY, null, null, + null, null, null, Boolean.FALSE, useStrongEtag.booleanValue() ? SC_204 : SC_412 }); + parameterSets.add(new Object[] { useStrongEtag, Task.PUT_EXIST_TXT, EtagPrecondition.IN, null, null, null, + null, null, Boolean.FALSE, useStrongEtag.booleanValue() ? SC_204 : SC_412 }); + parameterSets.add(new Object[] { useStrongEtag, Task.PUT_EXIST_TXT, EtagPrecondition.NOT_IN, null, null, + null, null, null, Boolean.FALSE, SC_412 }); + parameterSets.add(new Object[] { useStrongEtag, Task.PUT_EXIST_TXT, EtagPrecondition.INVALID, null, null, + null, null, null, Boolean.FALSE, SC_400 }); + parameterSets.add(new Object[] { useStrongEtag, Task.PUT_EXIST_TXT, EtagPrecondition.INVALID_ALL_PLUS_OTHER, + null, null, null, null, null, Boolean.FALSE, SC_400 }); + + parameterSets.add(new Object[] { useStrongEtag, Task.PUT_NEW_TXT, null, null, null, null, null, null, + Boolean.FALSE, SC_201 }); + parameterSets.add(new Object[] { useStrongEtag, Task.PUT_NEW_TXT, EtagPrecondition.ALL, null, null, null, + null, null, Boolean.FALSE, SC_412 }); + parameterSets.add(new Object[] { useStrongEtag, Task.PUT_NEW_TXT, EtagPrecondition.IN, null, null, null, + null, null, Boolean.FALSE, SC_412 }); + parameterSets.add(new Object[] { useStrongEtag, Task.PUT_NEW_TXT, EtagPrecondition.NOT_IN, null, null, null, + null, null, Boolean.FALSE, SC_412 }); + parameterSets.add(new Object[] { useStrongEtag, Task.PUT_NEW_TXT, EtagPrecondition.INVALID, null, null, + null, null, null, Boolean.FALSE, SC_400 }); + parameterSets.add(new Object[] { useStrongEtag, Task.PUT_NEW_TXT, EtagPrecondition.INVALID_ALL_PLUS_OTHER, + null, null, null, null, null, Boolean.FALSE, SC_400 }); } return parameterSets; } - private static Integer SC_200 = Integer.valueOf(200); - private static Integer SC_206 = Integer.valueOf(206); - private static Integer SC_304 = Integer.valueOf(304); - private static Integer SC_400 = Integer.valueOf(400); - private static Integer SC_412 = Integer.valueOf(412); + private static Integer SC_200 = Integer.valueOf(HttpServletResponse.SC_OK); + private static Integer SC_201 = Integer.valueOf(HttpServletResponse.SC_CREATED); + private static Integer SC_204 = Integer.valueOf(HttpServletResponse.SC_NO_CONTENT); + private static Integer SC_206 = Integer.valueOf(HttpServletResponse.SC_PARTIAL_CONTENT); + private static Integer SC_304 = Integer.valueOf(HttpServletResponse.SC_NOT_MODIFIED); + private static Integer SC_400 = Integer.valueOf(HttpServletResponse.SC_BAD_REQUEST); + private static Integer SC_412 = Integer.valueOf(HttpServletResponse.SC_PRECONDITION_FAILED); private enum HTTP_METHOD { @@ -337,7 +373,8 @@ public class TestDefaultServletRfc9110Section13Parameterized extends TomcatBaseT break; case IN: headerValues.add("\"1a2b3c4d\""); - headerValues.add(weakETag + "," + strongETag + ",W/\"*\""); + headerValues.add((weakETag != null ? weakETag + "," : "") + + (strongETag != null ? strongETag + "," : "") + "W/\"*\""); headerValues.add("\"abcdefg\""); break; case NOT_IN: @@ -467,7 +504,7 @@ public class TestDefaultServletRfc9110Section13Parameterized extends TomcatBaseT Wrapper w = Tomcat.addServlet(ctxt, "default", DefaultServlet.class.getName()); w.addInitParameter("readonly", "false"); - w.addInitParameter("allowPartialPut", Boolean.toString(true)); + w.addInitParameter("allowPartialPut", "true"); w.addInitParameter("useStrongETags", Boolean.toString(useStrongETags)); ctxt.addServletMappingDecoded("/", "default"); --------------------------------------------------------------------- To unsubscribe, e-mail: dev-unsubscr...@tomcat.apache.org For additional commands, e-mail: dev-h...@tomcat.apache.org