You are viewing a plain text version of this content. The canonical link for it is here.
Posted to dev@tomcat.apache.org by ma...@apache.org on 2021/09/23 21:18:36 UTC
[tomcat] 03/03: Implement the new page/tag directive
errorOnELNotFound
This is an automated email from the ASF dual-hosted git repository.
markt pushed a commit to branch main
in repository https://gitbox.apache.org/repos/asf/tomcat.git
commit 37bc60c9efed390f662afe0a1d12d2ba0d91ada8
Author: Mark Thomas <ma...@apache.org>
AuthorDate: Thu Sep 23 21:09:52 2021 +0100
Implement the new page/tag directive errorOnELNotFound
---
java/jakarta/servlet/jsp/resources/jspxml.dtd | 27 ++--
java/jakarta/servlet/jsp/resources/jspxml.xsd | 1 +
java/org/apache/jasper/compiler/Compiler.java | 4 +
java/org/apache/jasper/compiler/Generator.java | 15 +++
java/org/apache/jasper/compiler/JspConfig.java | 21 ++-
java/org/apache/jasper/compiler/PageInfo.java | 40 ++++++
.../apache/jasper/compiler/TagFileProcessor.java | 3 +-
java/org/apache/jasper/compiler/Validator.java | 15 +++
.../jasper/resources/LocalStrings.properties | 4 +
.../apache/jasper/runtime/JspContextWrapper.java | 9 ++
.../apache/jasper/runtime/JspSourceDirectives.java | 27 ++++
.../org/apache/jasper/runtime/PageContextImpl.java | 6 +
.../util/descriptor/web/JspPropertyGroup.java | 6 +
.../web/JspPropertyGroupDescriptorImpl.java | 12 ++
.../tomcat/util/descriptor/web/WebRuleSet.java | 2 +
test/org/apache/jasper/compiler/TestJspConfig.java | 145 +++++++++++++++++++++
.../jasper/servlet/TestJspCServletContext.java | 2 +-
.../WEB-INF/tags/error-on-el-not-found-false.tag | 18 +++
.../WEB-INF/tags/error-on-el-not-found-true.tag | 18 +++
test/webapp/WEB-INF/web.xml | 8 ++
test/webapp/jsp/errorOnELNotFound/default.jsp | 21 +++
.../jsp/errorOnELNotFound/page-directive-false.jsp | 22 ++++
.../jsp/errorOnELNotFound/page-directive-true.jsp | 22 ++++
.../jsp/errorOnELNotFound/tag-file-false.jsp | 23 ++++
.../webapp/jsp/errorOnELNotFound/tag-file-true.jsp | 23 ++++
.../webapp/jsp/errorOnELNotFound/web-xml-false.jsp | 21 +++
test/webapp/jsp/errorOnELNotFound/web-xml-true.jsp | 21 +++
webapps/docs/changelog.xml | 5 +
28 files changed, 524 insertions(+), 17 deletions(-)
diff --git a/java/jakarta/servlet/jsp/resources/jspxml.dtd b/java/jakarta/servlet/jsp/resources/jspxml.dtd
index c6f0998..a5fcc5f 100644
--- a/java/jakarta/servlet/jsp/resources/jspxml.dtd
+++ b/java/jakarta/servlet/jsp/resources/jspxml.dtd
@@ -94,19 +94,20 @@
<!ELEMENT jsp:directive.page EMPTY>
<!ATTLIST jsp:directive.page
- language CDATA "java"
- extends %ClassName; #IMPLIED
- contentType %Content; "text/html; charset=ISO-8859-1"
- import CDATA #IMPLIED
- session %Bool; "true"
- buffer CDATA "8kb"
- autoFlush %Bool; "true"
- isThreadSafe %Bool; "true"
- info CDATA #IMPLIED
- errorPage %URL; #IMPLIED
- isErrorPage %Bool; "false"
- pageEncoding CDATA #IMPLIED
- isELIgnored %Bool; #IMPLIED
+ language CDATA "java"
+ extends %ClassName; #IMPLIED
+ contentType %Content; "text/html; charset=ISO-8859-1"
+ import CDATA #IMPLIED
+ session %Bool; "true"
+ buffer CDATA "8kb"
+ autoFlush %Bool; "true"
+ isThreadSafe %Bool; "true"
+ info CDATA #IMPLIED
+ errorPage %URL; #IMPLIED
+ isErrorPage %Bool; "false"
+ pageEncoding CDATA #IMPLIED
+ isELIgnored %Bool; #IMPLIED
+ errorOnELNotFound %Bool; "false"
>
<!-- the jsp:directive.include only appears in JSP documents and does
diff --git a/java/jakarta/servlet/jsp/resources/jspxml.xsd b/java/jakarta/servlet/jsp/resources/jspxml.xsd
index 0e5eba0..4cad6bb 100644
--- a/java/jakarta/servlet/jsp/resources/jspxml.xsd
+++ b/java/jakarta/servlet/jsp/resources/jspxml.xsd
@@ -333,6 +333,7 @@
<xsd:attribute name = "errorPage" type = "RelativeURL"/>
<xsd:attribute name = "isErrorPage" default = "false" type = "Bool"/>
<xsd:attribute name = "isELIgnored" type = "Bool"/>
+ <xsd:attribute name = "errorOnELNotFound" default = "false" type = "Bool"/>
</xsd:complexType>
</xsd:element>
diff --git a/java/org/apache/jasper/compiler/Compiler.java b/java/org/apache/jasper/compiler/Compiler.java
index 7da6055..b38edae 100644
--- a/java/org/apache/jasper/compiler/Compiler.java
+++ b/java/org/apache/jasper/compiler/Compiler.java
@@ -132,6 +132,10 @@ public abstract class Compiler {
pageInfo.setELIgnored(JspUtil.booleanValue(jspProperty
.isELIgnored()));
}
+ if (jspProperty.getErrorOnELNotFound() != null) {
+ pageInfo.setErrorOnELNotFound(JspUtil.booleanValue(jspProperty
+ .getErrorOnELNotFound()));
+ }
if (jspProperty.isScriptingInvalid() != null) {
pageInfo.setScriptingInvalid(JspUtil.booleanValue(jspProperty
.isScriptingInvalid()));
diff --git a/java/org/apache/jasper/compiler/Generator.java b/java/org/apache/jasper/compiler/Generator.java
index 61eec0c..2872e01 100644
--- a/java/org/apache/jasper/compiler/Generator.java
+++ b/java/org/apache/jasper/compiler/Generator.java
@@ -700,6 +700,17 @@ class Generator {
out.printil("}");
out.println();
+ // Implement JspSourceDirectives
+ out.printil("public boolean getErrorOnELNotFound() {");
+ out.pushIndent();
+ if (pageInfo.isErrorOnELNotFound()) {
+ out.printil("return true;");
+ } else {
+ out.printil("return false;");
+ }
+ out.popIndent();
+ out.printil("}");
+ out.println();
generateGetters();
generateInit();
@@ -733,6 +744,8 @@ class Generator {
out.println(",");
out.printin(" jakarta.servlet.SingleThreadModel");
}
+ out.println(",");
+ out.printin(" org.apache.jasper.runtime.JspSourceDirectives");
out.println(" {");
out.pushIndent();
@@ -3652,6 +3665,8 @@ class Generator {
out.println(",");
out.printin(" jakarta.servlet.jsp.tagext.DynamicAttributes");
}
+ out.println(",");
+ out.printin(" org.apache.jasper.runtime.JspSourceDirectives");
out.println(" {");
out.pushIndent();
diff --git a/java/org/apache/jasper/compiler/JspConfig.java b/java/org/apache/jasper/compiler/JspConfig.java
index f63109a..7cb3b64 100644
--- a/java/org/apache/jasper/compiler/JspConfig.java
+++ b/java/org/apache/jasper/compiler/JspConfig.java
@@ -46,6 +46,7 @@ public class JspConfig {
private static final String defaultIsXml = null; // unspecified
private String defaultIsELIgnored = null; // unspecified
+ private String defaultErrorOnELNotFound = "false";
private static final String defaultIsScriptingInvalid = null;
private String defaultDeferedSyntaxAllowedAsLiteral = null;
private static final String defaultTrimDirectiveWhitespaces = null;
@@ -96,6 +97,7 @@ public class JspConfig {
JspProperty property = new JspProperty(jspPropertyGroup.getIsXml(),
jspPropertyGroup.getElIgnored(),
+ jspPropertyGroup.getErrorOnELNotFound(),
jspPropertyGroup.getScriptingInvalid(),
jspPropertyGroup.getPageEncoding(),
jspPropertyGroup.getIncludePreludes(),
@@ -164,6 +166,7 @@ public class JspConfig {
processWebDotXml();
defaultJspProperty = new JspProperty(defaultIsXml,
defaultIsELIgnored,
+ defaultErrorOnELNotFound,
defaultIsScriptingInvalid,
null, null, null,
defaultDeferedSyntaxAllowedAsLiteral,
@@ -245,6 +248,7 @@ public class JspConfig {
JspPropertyGroup isXmlMatch = null;
JspPropertyGroup elIgnoredMatch = null;
+ JspPropertyGroup errorOnELNotFoundMatch = null;
JspPropertyGroup scriptingInvalidMatch = null;
JspPropertyGroup pageEncodingMatch = null;
JspPropertyGroup deferedSyntaxAllowedAsLiteralMatch = null;
@@ -296,6 +300,9 @@ public class JspConfig {
if (jp.isELIgnored() != null) {
elIgnoredMatch = selectProperty(elIgnoredMatch, jpg);
}
+ if (jp.getErrorOnELNotFound() != null) {
+ errorOnELNotFoundMatch = selectProperty(errorOnELNotFoundMatch, jpg);
+ }
if (jp.isScriptingInvalid() != null) {
scriptingInvalidMatch =
selectProperty(scriptingInvalidMatch, jpg);
@@ -327,6 +334,7 @@ public class JspConfig {
String isXml = defaultIsXml;
String isELIgnored = defaultIsELIgnored;
+ String errorOnELNotFound = defaultErrorOnELNotFound;
String isScriptingInvalid = defaultIsScriptingInvalid;
String pageEncoding = null;
String isDeferedSyntaxAllowedAsLiteral = defaultDeferedSyntaxAllowedAsLiteral;
@@ -338,6 +346,9 @@ public class JspConfig {
if (isXmlMatch != null) {
isXml = isXmlMatch.getJspProperty().isXml();
}
+ if (errorOnELNotFoundMatch != null) {
+ errorOnELNotFound = errorOnELNotFoundMatch.getJspProperty().getErrorOnELNotFound();
+ }
if (elIgnoredMatch != null) {
isELIgnored = elIgnoredMatch.getJspProperty().isELIgnored();
}
@@ -368,7 +379,7 @@ public class JspConfig {
errorOnUndeclaredNamespaceMatch.getJspProperty().isErrorOnUndeclaredNamespace();
}
- return new JspProperty(isXml, isELIgnored, isScriptingInvalid,
+ return new JspProperty(isXml, isELIgnored, errorOnELNotFound, isScriptingInvalid,
pageEncoding, includePreludes, includeCodas,
isDeferedSyntaxAllowedAsLiteral, isTrimDirectiveWhitespaces,
defaultContentType, buffer, errorOnUndeclaredNamespace);
@@ -448,6 +459,7 @@ public class JspConfig {
private final String isXml;
private final String elIgnored;
+ private final String errorOnELNotFound;
private final String scriptingInvalid;
private final String pageEncoding;
private final Collection<String> includePrelude;
@@ -458,7 +470,7 @@ public class JspConfig {
private final String buffer;
private final String errorOnUndeclaredNamespace;
- public JspProperty(String isXml, String elIgnored,
+ public JspProperty(String isXml, String elIgnored, String errorOnELNotFound,
String scriptingInvalid, String pageEncoding,
Collection<String> includePrelude, Collection<String> includeCoda,
String deferedSyntaxAllowedAsLiteral,
@@ -469,6 +481,7 @@ public class JspConfig {
this.isXml = isXml;
this.elIgnored = elIgnored;
+ this.errorOnELNotFound = errorOnELNotFound;
this.scriptingInvalid = scriptingInvalid;
this.pageEncoding = pageEncoding;
this.includePrelude = includePrelude;
@@ -488,6 +501,10 @@ public class JspConfig {
return elIgnored;
}
+ public String getErrorOnELNotFound() {
+ return errorOnELNotFound;
+ }
+
public String isScriptingInvalid() {
return scriptingInvalid;
}
diff --git a/java/org/apache/jasper/compiler/PageInfo.java b/java/org/apache/jasper/compiler/PageInfo.java
index 464a5c9..5c0a2c0 100644
--- a/java/org/apache/jasper/compiler/PageInfo.java
+++ b/java/org/apache/jasper/compiler/PageInfo.java
@@ -100,6 +100,10 @@ class PageInfo {
// JSP 2.2
private boolean errorOnUndeclaredNamespace = false;
+ // JSP 3.1
+ private String errorOnELNotFoundValue;
+ private boolean errorOnELNotFound = false;
+
private final boolean isTagFile;
PageInfo(BeanRepository beanRepository, JspCompilationContext ctxt) {
@@ -635,6 +639,30 @@ class PageInfo {
isELIgnoredValue = value;
}
+
+ /*
+ * errorOnELNotFound
+ */
+ public void setErrorOnELNotFound(String value, Node n, ErrorDispatcher err,
+ boolean pagedir)
+ throws JasperException {
+
+ if ("true".equalsIgnoreCase(value)) {
+ errorOnELNotFound = true;
+ } else if ("false".equalsIgnoreCase(value)) {
+ errorOnELNotFound = false;
+ } else {
+ if (pagedir) {
+ err.jspError(n, "jsp.error.page.invalid.errorOnELNotFound");
+ } else {
+ err.jspError(n, "jsp.error.tag.invalid.errorOnELNotFound");
+ }
+ }
+
+ errorOnELNotFoundValue = value;
+ }
+
+
/*
* deferredSyntaxAllowedAsLiteral
*/
@@ -691,6 +719,18 @@ class PageInfo {
return isELIgnored;
}
+ public void setErrorOnELNotFound(boolean s) {
+ errorOnELNotFound = s;
+ }
+
+ public String getErrorOnELNotFound() {
+ return errorOnELNotFoundValue;
+ }
+
+ public boolean isErrorOnELNotFound() {
+ return errorOnELNotFound;
+ }
+
public void putNonCustomTagPrefix(String prefix, Mark where) {
nonCustomTagPrefixMap.put(prefix, where);
}
diff --git a/java/org/apache/jasper/compiler/TagFileProcessor.java b/java/org/apache/jasper/compiler/TagFileProcessor.java
index e6a1773..e1ed7c1 100644
--- a/java/org/apache/jasper/compiler/TagFileProcessor.java
+++ b/java/org/apache/jasper/compiler/TagFileProcessor.java
@@ -68,7 +68,8 @@ class TagFileProcessor {
new JspUtil.ValidAttribute("import"),
new JspUtil.ValidAttribute("deferredSyntaxAllowedAsLiteral"), // JSP 2.1
new JspUtil.ValidAttribute("trimDirectiveWhitespaces"), // JSP 2.1
- new JspUtil.ValidAttribute("isELIgnored") };
+ new JspUtil.ValidAttribute("isELIgnored"),
+ new JspUtil.ValidAttribute("errorOnELNotFound") };
private static final JspUtil.ValidAttribute[] attributeDirectiveAttrs = {
new JspUtil.ValidAttribute("name", true),
diff --git a/java/org/apache/jasper/compiler/Validator.java b/java/org/apache/jasper/compiler/Validator.java
index 61bc587..94d0b2c 100644
--- a/java/org/apache/jasper/compiler/Validator.java
+++ b/java/org/apache/jasper/compiler/Validator.java
@@ -82,6 +82,7 @@ class Validator {
new JspUtil.ValidAttribute("contentType"),
new JspUtil.ValidAttribute("pageEncoding"),
new JspUtil.ValidAttribute("isELIgnored"),
+ new JspUtil.ValidAttribute("errorOnELNotFound"),
new JspUtil.ValidAttribute("deferredSyntaxAllowedAsLiteral"),
new JspUtil.ValidAttribute("trimDirectiveWhitespaces")
};
@@ -174,6 +175,13 @@ class Validator {
err.jspError(n, "jsp.error.page.conflict.iselignored",
pageInfo.getIsELIgnored(), value);
}
+ } else if ("errorOnELNotFound".equals(attr)) {
+ if (pageInfo.getErrorOnELNotFound() == null) {
+ pageInfo.setErrorOnELNotFound(value, n, err, true);
+ } else if (!pageInfo.getErrorOnELNotFound().equals(value)) {
+ err.jspError(n, "jsp.error.page.conflict.errorOnELNotFound",
+ pageInfo.getErrorOnELNotFound(), value);
+ }
} else if ("isErrorPage".equals(attr)) {
if (pageInfo.getIsErrorPage() == null) {
pageInfo.setIsErrorPage(value, n, err);
@@ -270,6 +278,13 @@ class Validator {
err.jspError(n, "jsp.error.tag.conflict.iselignored",
pageInfo.getIsELIgnored(), value);
}
+ } else if ("errorOnELNotFound".equals(attr)) {
+ if (pageInfo.getErrorOnELNotFound() == null) {
+ pageInfo.setErrorOnELNotFound(value, n, err, false);
+ } else if (!pageInfo.getErrorOnELNotFound().equals(value)) {
+ err.jspError(n, "jsp.error.tag.conflict.errorOnELNotFound",
+ pageInfo.getErrorOnELNotFound(), value);
+ }
} else if ("pageEncoding".equals(attr)) {
if (pageEncodingSeen) {
err.jspError(n, "jsp.error.tag.multi.pageencoding");
diff --git a/java/org/apache/jasper/resources/LocalStrings.properties b/java/org/apache/jasper/resources/LocalStrings.properties
index 898e173..3a0f990 100644
--- a/java/org/apache/jasper/resources/LocalStrings.properties
+++ b/java/org/apache/jasper/resources/LocalStrings.properties
@@ -143,6 +143,7 @@ jsp.error.page.conflict.autoflush=Page directive: illegal to have multiple occur
jsp.error.page.conflict.buffer=Page directive: illegal to have multiple occurrences of ''buffer'' with different values (old: [{0}], new: [{1}])
jsp.error.page.conflict.contenttype=Page directive: illegal to have multiple occurrences of ''contentType'' with different values (old: [{0}], new: [{1}])
jsp.error.page.conflict.deferredsyntaxallowedasliteral=Page directive: illegal to have multiple occurrences of ''deferredSyntaxAllowedAsLiteral'' with different values (old: [{0}], new: [{1}])
+jsp.error.page.conflict.errorOnELNotFound=Page directive: illegal to have multiple occurrences of ''errorOnELNotFound'' with different values (old: [{0}], new: [{1}])
jsp.error.page.conflict.errorpage=Page directive: illegal to have multiple occurrences of ''errorPage'' with different values (old: [{0}], new: [{1}])
jsp.error.page.conflict.extends=Page directive: illegal to have multiple occurrences of ''extends'' with different values (old: [{0}], new: [{1}])
jsp.error.page.conflict.info=Page directive: illegal to have multiple occurrences of ''info'' with different values (old: [{0}], new: [{1}])
@@ -154,6 +155,7 @@ jsp.error.page.conflict.session=Page directive: illegal to have multiple occurre
jsp.error.page.conflict.trimdirectivewhitespaces=Page directive: illegal to have multiple occurrences of ''trimDirectiveWhitespaces'' with different values (old: [{0}], new: [{1}])
jsp.error.page.invalid.buffer=Page directive: invalid value for buffer
jsp.error.page.invalid.deferredsyntaxallowedasliteral=Page directive: invalid value for deferredSyntaxAllowedAsLiteral
+jsp.error.page.invalid.errorOnELNotFound=Page directive: invalid value for errorOnELNotFound
jsp.error.page.invalid.import=Page directive: invalid value for import
jsp.error.page.invalid.iselignored=Page directive: invalid value for isELIgnored
jsp.error.page.invalid.iserrorpage=Page directive: invalid value for isErrorPage
@@ -200,10 +202,12 @@ jsp.error.stream.closed=Stream closed
jsp.error.string_interpreter_class.instantiation=Failed to load or instantiate StringInterpreter class [{0}]
jsp.error.tag.conflict.attr=Tag directive: illegal to have multiple occurrences of the attribute [{0}] with different values (old: [{1}], new: [{2}])
jsp.error.tag.conflict.deferredsyntaxallowedasliteral=Tag directive: illegal to have multiple occurrences of ''deferredSyntaxAllowedAsLiteral'' with different values (old: [{0}], new: [{1}])
+jsp.error.tag.conflict.errorOnELNotFound=Tag directive: illegal to have multiple occurrences of ''errorOnELNotFound'' with different values (old: [{0}], new: [{1}])
jsp.error.tag.conflict.iselignored=Tag directive: illegal to have multiple occurrences of ''isELIgnored'' with different values (old: [{0}], new: [{1}])
jsp.error.tag.conflict.language=Tag directive: illegal to have multiple occurrences of ''language'' with different values (old: [{0}], new: [{1}])
jsp.error.tag.conflict.trimdirectivewhitespaces=Tag directive: illegal to have multiple occurrences of ''trimDirectiveWhitespaces'' with different values (old: [{0}], new: [{1}])
jsp.error.tag.invalid.deferredsyntaxallowedasliteral=Tag directive: invalid value for deferredSyntaxAllowedAsLiteral
+jsp.error.tag.invalid.errorOnELNotFound=Tag directive: invalid value for errorOnELNotFound
jsp.error.tag.invalid.iselignored=Tag directive: invalid value for isELIgnored
jsp.error.tag.invalid.trimdirectivewhitespaces=Tag directive: invalid value for trimDirectiveWhitespaces
jsp.error.tag.language.nonjava=Tag directive: invalid language attribute
diff --git a/java/org/apache/jasper/runtime/JspContextWrapper.java b/java/org/apache/jasper/runtime/JspContextWrapper.java
index 718c803..a7820a7 100644
--- a/java/org/apache/jasper/runtime/JspContextWrapper.java
+++ b/java/org/apache/jasper/runtime/JspContextWrapper.java
@@ -48,6 +48,7 @@ import jakarta.servlet.jsp.JspWriter;
import jakarta.servlet.jsp.PageContext;
import jakarta.servlet.jsp.el.ELException;
import jakarta.servlet.jsp.el.ExpressionEvaluator;
+import jakarta.servlet.jsp.el.NotFoundELResolver;
import jakarta.servlet.jsp.el.VariableResolver;
import jakarta.servlet.jsp.tagext.BodyContent;
import jakarta.servlet.jsp.tagext.JspTag;
@@ -563,6 +564,14 @@ public class JspContextWrapper extends PageContext implements VariableResolver {
if (key == JspContext.class) {
return pageContext;
}
+ if (key == NotFoundELResolver.class) {
+ if (jspTag instanceof JspSourceDirectives) {
+ return Boolean.valueOf(((JspSourceDirectives) jspTag).getErrorOnELNotFound());
+ } else {
+ // returning Boolean.FALSE would have the same effect
+ return null;
+ }
+ }
return wrapped.getContext(key);
}
diff --git a/java/org/apache/jasper/runtime/JspSourceDirectives.java b/java/org/apache/jasper/runtime/JspSourceDirectives.java
new file mode 100644
index 0000000..cb531ac
--- /dev/null
+++ b/java/org/apache/jasper/runtime/JspSourceDirectives.java
@@ -0,0 +1,27 @@
+/*
+ * 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.jasper.runtime;
+
+/**
+ * Provides runtime access to selected compile time directives. Page directives
+ * are not added to this interface until there is a requirement to access them
+ * at runtime.
+ */
+public interface JspSourceDirectives {
+
+ boolean getErrorOnELNotFound();
+}
diff --git a/java/org/apache/jasper/runtime/PageContextImpl.java b/java/org/apache/jasper/runtime/PageContextImpl.java
index 1477013..3000439 100644
--- a/java/org/apache/jasper/runtime/PageContextImpl.java
+++ b/java/org/apache/jasper/runtime/PageContextImpl.java
@@ -43,6 +43,7 @@ import jakarta.servlet.jsp.JspException;
import jakarta.servlet.jsp.JspFactory;
import jakarta.servlet.jsp.JspWriter;
import jakarta.servlet.jsp.PageContext;
+import jakarta.servlet.jsp.el.NotFoundELResolver;
import jakarta.servlet.jsp.tagext.BodyContent;
import org.apache.jasper.Constants;
@@ -721,6 +722,11 @@ public class PageContextImpl extends PageContext {
}
}
}
+ if (servlet instanceof JspSourceDirectives) {
+ if (((JspSourceDirectives) servlet).getErrorOnELNotFound()) {
+ elContext.putContext(NotFoundELResolver.class, Boolean.TRUE);
+ }
+ }
}
return this.elContext;
}
diff --git a/java/org/apache/tomcat/util/descriptor/web/JspPropertyGroup.java b/java/org/apache/tomcat/util/descriptor/web/JspPropertyGroup.java
index 9246c60..07f3dd3 100644
--- a/java/org/apache/tomcat/util/descriptor/web/JspPropertyGroup.java
+++ b/java/org/apache/tomcat/util/descriptor/web/JspPropertyGroup.java
@@ -34,6 +34,12 @@ public class JspPropertyGroup extends XmlEncodingBase {
}
public Boolean getDeferredSyntax() { return deferredSyntax; }
+ private Boolean errorOnELNotFound = null;
+ public void setErrorOnELNotFound(String errorOnELNotFound) {
+ this.errorOnELNotFound = Boolean.valueOf(errorOnELNotFound);
+ }
+ public Boolean getErrorOnELNotFound() { return errorOnELNotFound; }
+
private Boolean elIgnored = null;
public void setElIgnored(String elIgnored) {
this.elIgnored = Boolean.valueOf(elIgnored);
diff --git a/java/org/apache/tomcat/util/descriptor/web/JspPropertyGroupDescriptorImpl.java b/java/org/apache/tomcat/util/descriptor/web/JspPropertyGroupDescriptorImpl.java
index 4785ee2..0f67f61 100644
--- a/java/org/apache/tomcat/util/descriptor/web/JspPropertyGroupDescriptorImpl.java
+++ b/java/org/apache/tomcat/util/descriptor/web/JspPropertyGroupDescriptorImpl.java
@@ -72,6 +72,18 @@ public class JspPropertyGroupDescriptorImpl
@Override
+ public String getErrorOnELNotFound() {
+ String result = null;
+
+ if (jspPropertyGroup.getErrorOnELNotFound() != null) {
+ result = jspPropertyGroup.getErrorOnELNotFound().toString();
+ }
+
+ return result;
+ }
+
+
+ @Override
public String getErrorOnUndeclaredNamespace() {
String result = null;
diff --git a/java/org/apache/tomcat/util/descriptor/web/WebRuleSet.java b/java/org/apache/tomcat/util/descriptor/web/WebRuleSet.java
index 2472aae..ba3bd53 100644
--- a/java/org/apache/tomcat/util/descriptor/web/WebRuleSet.java
+++ b/java/org/apache/tomcat/util/descriptor/web/WebRuleSet.java
@@ -283,6 +283,8 @@ public class WebRuleSet implements RuleSet {
"setDeferredSyntax", 0);
digester.addCallMethod(fullPrefix + "/jsp-config/jsp-property-group/el-ignored",
"setElIgnored", 0);
+ digester.addCallMethod(fullPrefix + "/jsp-config/jsp-property-group/error-on-el-not-found",
+ "setErrorOnELNotFound", 0);
digester.addCallMethod(fullPrefix + "/jsp-config/jsp-property-group/include-coda",
"addIncludeCoda", 0);
digester.addCallMethod(fullPrefix + "/jsp-config/jsp-property-group/include-prelude",
diff --git a/test/org/apache/jasper/compiler/TestJspConfig.java b/test/org/apache/jasper/compiler/TestJspConfig.java
index 9389c2c..64f6d0c 100644
--- a/test/org/apache/jasper/compiler/TestJspConfig.java
+++ b/test/org/apache/jasper/compiler/TestJspConfig.java
@@ -18,6 +18,8 @@ package org.apache.jasper.compiler;
import java.io.File;
+import jakarta.servlet.http.HttpServletResponse;
+
import org.junit.Assert;
import org.junit.Test;
@@ -192,4 +194,147 @@ public class TestJspConfig extends TomcatBaseTest {
Assert.assertTrue(result.indexOf("<p>00-hello world</p>") > 0);
}
+
+ @Test
+ public void testErrorOnELNotFound01() throws Exception {
+ // Defaults
+
+ Tomcat tomcat = getTomcatInstance();
+
+ File appDir = new File("test/webapp");
+ tomcat.addWebapp(null, "/test", appDir.getAbsolutePath());
+
+ tomcat.start();
+
+ ByteChunk res = new ByteChunk();
+ int rc = getUrl("http://localhost:" + getPort() + "/test/jsp/errorOnELNotFound/default.jsp", res, null);
+
+ Assert.assertEquals(HttpServletResponse.SC_OK, rc);
+
+ String result = res.toString();
+ Assert.assertTrue(result, result.indexOf("<p>00-OK</p>") > 0);
+ }
+
+ @Test
+ public void testErrorOnELNotFound02() throws Exception {
+ // Page directive true
+
+ Tomcat tomcat = getTomcatInstance();
+
+ File appDir = new File("test/webapp");
+ tomcat.addWebapp(null, "/test", appDir.getAbsolutePath());
+
+ tomcat.start();
+
+ ByteChunk res = new ByteChunk();
+ int rc = getUrl("http://localhost:" + getPort() + "/test/jsp/errorOnELNotFound/page-directive-true.jsp", res, null);
+
+ Assert.assertEquals(HttpServletResponse.SC_INTERNAL_SERVER_ERROR, rc);
+
+ // Look for the non-i18n part of the Exception message
+ String result = res.toString();
+ Assert.assertTrue(result, result.indexOf("[unknown]") > 0);
+ }
+
+ @Test
+ public void testErrorOnELNotFound03() throws Exception {
+ // Page directive false
+
+ Tomcat tomcat = getTomcatInstance();
+
+ File appDir = new File("test/webapp");
+ tomcat.addWebapp(null, "/test", appDir.getAbsolutePath());
+
+ tomcat.start();
+
+ ByteChunk res = new ByteChunk();
+ int rc = getUrl("http://localhost:" + getPort() + "/test/jsp/errorOnELNotFound/page-directive-false.jsp", res, null);
+
+ Assert.assertEquals(HttpServletResponse.SC_OK, rc);
+
+ String result = res.toString();
+ Assert.assertTrue(result, result.indexOf("<p>00-OK</p>") > 0);
+ }
+
+ @Test
+ public void testErrorOnELNotFound04() throws Exception {
+ // web.xml true
+
+ Tomcat tomcat = getTomcatInstance();
+
+ File appDir = new File("test/webapp");
+ tomcat.addWebapp(null, "/test", appDir.getAbsolutePath());
+
+ tomcat.start();
+
+ ByteChunk res = new ByteChunk();
+ int rc = getUrl("http://localhost:" + getPort() + "/test/jsp/errorOnELNotFound/web-xml-true.jsp", res, null);
+
+ Assert.assertEquals(HttpServletResponse.SC_INTERNAL_SERVER_ERROR, rc);
+
+ // Look for the non-i18n part of the Exception message
+ String result = res.toString();
+ Assert.assertTrue(result, result.indexOf("[unknown]") > 0);
+ }
+
+ @Test
+ public void testErrorOnELNotFound05() throws Exception {
+ // web.xml false
+
+ Tomcat tomcat = getTomcatInstance();
+
+ File appDir = new File("test/webapp");
+ tomcat.addWebapp(null, "/test", appDir.getAbsolutePath());
+
+ tomcat.start();
+
+ ByteChunk res = new ByteChunk();
+ int rc = getUrl("http://localhost:" + getPort() + "/test/jsp/errorOnELNotFound/web-xml-false.jsp", res, null);
+
+ Assert.assertEquals(HttpServletResponse.SC_OK, rc);
+
+ String result = res.toString();
+ Assert.assertTrue(result, result.indexOf("<p>00-OK</p>") > 0);
+ }
+
+ @Test
+ public void testErrorOnELNotFound06() throws Exception {
+ // tag file true
+
+ Tomcat tomcat = getTomcatInstance();
+
+ File appDir = new File("test/webapp");
+ tomcat.addWebapp(null, "/test", appDir.getAbsolutePath());
+
+ tomcat.start();
+
+ ByteChunk res = new ByteChunk();
+ int rc = getUrl("http://localhost:" + getPort() + "/test/jsp/errorOnELNotFound/tag-file-true.jsp", res, null);
+
+ Assert.assertEquals(HttpServletResponse.SC_INTERNAL_SERVER_ERROR, rc);
+
+ // Look for the non-i18n part of the Exception message
+ String result = res.toString();
+ Assert.assertTrue(result, result.indexOf("[unknown]") > 0);
+ }
+
+ @Test
+ public void testErrorOnELNotFound07() throws Exception {
+ // tag file false
+
+ Tomcat tomcat = getTomcatInstance();
+
+ File appDir = new File("test/webapp");
+ tomcat.addWebapp(null, "/test", appDir.getAbsolutePath());
+
+ tomcat.start();
+
+ ByteChunk res = new ByteChunk();
+ int rc = getUrl("http://localhost:" + getPort() + "/test/jsp/errorOnELNotFound/tag-file-false.jsp", res, null);
+
+ Assert.assertEquals(HttpServletResponse.SC_OK, rc);
+
+ String result = res.toString();
+ Assert.assertTrue(result, result.indexOf("<p>00-OK</p>") > 0);
+ }
}
diff --git a/test/org/apache/jasper/servlet/TestJspCServletContext.java b/test/org/apache/jasper/servlet/TestJspCServletContext.java
index f8d0adb..cc0032e 100644
--- a/test/org/apache/jasper/servlet/TestJspCServletContext.java
+++ b/test/org/apache/jasper/servlet/TestJspCServletContext.java
@@ -41,7 +41,7 @@ public class TestJspCServletContext {
Assert.assertTrue(jspConfigDescriptor.getTaglibs().isEmpty());
Collection<JspPropertyGroupDescriptor> propertyGroups =
jspConfigDescriptor.getJspPropertyGroups();
- Assert.assertEquals(4, propertyGroups.size());
+ Assert.assertEquals(6, propertyGroups.size());
Iterator<JspPropertyGroupDescriptor> groupIterator =
propertyGroups.iterator();
JspPropertyGroupDescriptor groupDescriptor;
diff --git a/test/webapp/WEB-INF/tags/error-on-el-not-found-false.tag b/test/webapp/WEB-INF/tags/error-on-el-not-found-false.tag
new file mode 100644
index 0000000..8466d0e
--- /dev/null
+++ b/test/webapp/WEB-INF/tags/error-on-el-not-found-false.tag
@@ -0,0 +1,18 @@
+<%--
+ 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.
+--%>
+<%@ tag errorOnELNotFound="false" %>
+<p>00-O${unknown}K</p>
\ No newline at end of file
diff --git a/test/webapp/WEB-INF/tags/error-on-el-not-found-true.tag b/test/webapp/WEB-INF/tags/error-on-el-not-found-true.tag
new file mode 100644
index 0000000..ba23cac
--- /dev/null
+++ b/test/webapp/WEB-INF/tags/error-on-el-not-found-true.tag
@@ -0,0 +1,18 @@
+<%--
+ 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.
+--%>
+<%@ tag errorOnELNotFound="true" %>
+<p>00-O${unknown}K</p>
\ No newline at end of file
diff --git a/test/webapp/WEB-INF/web.xml b/test/webapp/WEB-INF/web.xml
index 0a28fc1..b1f30f0 100644
--- a/test/webapp/WEB-INF/web.xml
+++ b/test/webapp/WEB-INF/web.xml
@@ -152,6 +152,14 @@
<page-encoding>ISO-8859-1</page-encoding>
<is-xml>true</is-xml>
</jsp-property-group>
+ <jsp-property-group>
+ <url-pattern>/jsp/errorOnELNotFound/web-xml-true.jsp</url-pattern>
+ <error-on-el-not-found>true</error-on-el-not-found>
+ </jsp-property-group>
+ <jsp-property-group>
+ <url-pattern>/jsp/errorOnELNotFound/web-xml-false.jsp</url-pattern>
+ <error-on-el-not-found>false</error-on-el-not-found>
+ </jsp-property-group>
</jsp-config>
<servlet>
diff --git a/test/webapp/jsp/errorOnELNotFound/default.jsp b/test/webapp/jsp/errorOnELNotFound/default.jsp
new file mode 100644
index 0000000..a3e66c9
--- /dev/null
+++ b/test/webapp/jsp/errorOnELNotFound/default.jsp
@@ -0,0 +1,21 @@
+<%--
+ 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.
+--%>
+<html>
+ <body>
+ <p>00-O${unknown}K</p>
+ </body>
+</html>
\ No newline at end of file
diff --git a/test/webapp/jsp/errorOnELNotFound/page-directive-false.jsp b/test/webapp/jsp/errorOnELNotFound/page-directive-false.jsp
new file mode 100644
index 0000000..26ba5de
--- /dev/null
+++ b/test/webapp/jsp/errorOnELNotFound/page-directive-false.jsp
@@ -0,0 +1,22 @@
+<%--
+ 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.
+--%>
+<%@ page errorOnELNotFound="false" %>
+<html>
+ <body>
+ <p>00-O${unknown}K</p>
+ </body>
+</html>
\ No newline at end of file
diff --git a/test/webapp/jsp/errorOnELNotFound/page-directive-true.jsp b/test/webapp/jsp/errorOnELNotFound/page-directive-true.jsp
new file mode 100644
index 0000000..fe241b0
--- /dev/null
+++ b/test/webapp/jsp/errorOnELNotFound/page-directive-true.jsp
@@ -0,0 +1,22 @@
+<%--
+ 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.
+--%>
+<%@ page errorOnELNotFound="true" %>
+<html>
+ <body>
+ <p>00-O${unknown}K</p>
+ </body>
+</html>
\ No newline at end of file
diff --git a/test/webapp/jsp/errorOnELNotFound/tag-file-false.jsp b/test/webapp/jsp/errorOnELNotFound/tag-file-false.jsp
new file mode 100644
index 0000000..df20a0b
--- /dev/null
+++ b/test/webapp/jsp/errorOnELNotFound/tag-file-false.jsp
@@ -0,0 +1,23 @@
+<%--
+ 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.
+--%>
+<%@ page errorOnELNotFound="true" %>
+<%@ taglib prefix="tags" tagdir="/WEB-INF/tags" %>
+<html>
+ <body>
+ <tags:error-on-el-not-found-false />
+ </body>
+</html>
\ No newline at end of file
diff --git a/test/webapp/jsp/errorOnELNotFound/tag-file-true.jsp b/test/webapp/jsp/errorOnELNotFound/tag-file-true.jsp
new file mode 100644
index 0000000..84c9021
--- /dev/null
+++ b/test/webapp/jsp/errorOnELNotFound/tag-file-true.jsp
@@ -0,0 +1,23 @@
+<%--
+ 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.
+--%>
+<%@ page errorOnELNotFound="false" %>
+<%@ taglib prefix="tags" tagdir="/WEB-INF/tags" %>
+<html>
+ <body>
+ <tags:error-on-el-not-found-true />
+ </body>
+</html>
\ No newline at end of file
diff --git a/test/webapp/jsp/errorOnELNotFound/web-xml-false.jsp b/test/webapp/jsp/errorOnELNotFound/web-xml-false.jsp
new file mode 100644
index 0000000..a3e66c9
--- /dev/null
+++ b/test/webapp/jsp/errorOnELNotFound/web-xml-false.jsp
@@ -0,0 +1,21 @@
+<%--
+ 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.
+--%>
+<html>
+ <body>
+ <p>00-O${unknown}K</p>
+ </body>
+</html>
\ No newline at end of file
diff --git a/test/webapp/jsp/errorOnELNotFound/web-xml-true.jsp b/test/webapp/jsp/errorOnELNotFound/web-xml-true.jsp
new file mode 100644
index 0000000..a3e66c9
--- /dev/null
+++ b/test/webapp/jsp/errorOnELNotFound/web-xml-true.jsp
@@ -0,0 +1,21 @@
+<%--
+ 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.
+--%>
+<html>
+ <body>
+ <p>00-O${unknown}K</p>
+ </body>
+</html>
\ No newline at end of file
diff --git a/webapps/docs/changelog.xml b/webapps/docs/changelog.xml
index 5aba0a1..efe4093 100644
--- a/webapps/docs/changelog.xml
+++ b/webapps/docs/changelog.xml
@@ -179,6 +179,11 @@
rather than the types being passed explicitly to
<code>ExpressionFactory.createMethodExpression()</code>. (markt)
</fix>
+ <add>
+ Add support for a new page/tag directive <code>errorOnELNotFound</code>
+ that can be used to trigger an identifier if an EL expression in a
+ page/tag contains an identifier that cannot be resolved. (markt)
+ </add>
</changelog>
</subsection>
<subsection name="Web applications">
---------------------------------------------------------------------
To unsubscribe, e-mail: dev-unsubscribe@tomcat.apache.org
For additional commands, e-mail: dev-help@tomcat.apache.org