If loop variable is named 'param', tag 'out' evaluates it to EMPTY string. If loop variable has any other name, it is processed correctly. Example 1. Incorrect processing. <c:forEach items="${cols}" var="param"> <c:out value="${param.name}"/><br> </c:forEach> Example 2. Correct processing. <c:forEach items="${cols}" var="col"> <c:out value="${col.name}"/><br> </c:forEach> Example 3. Correct processing. This is modified Example 1. <c:forEach items="${cols}" var="param"> <c:out value="${pageScope.param.name}"/><br> </c:forEach> I checked the code in debugger. In all cases 'pageContext' contains attribute with correct name. E.g. in Example 1, 'pageContext' contains an attribute 'param' with correct value. The same problem exists if <c:forEach> is replaced by <logic:iterate>. Other tags work correctly in this case. E.g. following code works correctly: <c:forEach items="${cols}" var="param"> <html:text name="param" property="name"/><br> </c:forEach> So, the problem is somewhere inside 'out'.
Created attachment 19069 [details] test.jsp For simplicity, this JSP contains definition of bean class used in the described examples.
Is this with the JSTL 1.1.2 release? Looking at the source, I don't see the word 'param' mentioned, which is odd as you'd expect either the Out of the ForEach code to mention 'param' somewhere for this bug to be happening.
'param' is an implicit JSP variable (map of HTTP request parameters), and IMO, its best to not step over implicit variables by re-defining them in any scope (choose a different variable name)
Thanks Rahul - I'm very rusty :)
(In reply to comment #3) > 'param' is an implicit JSP variable (map of HTTP request parameters), and IMO, > its best to not step over implicit variables by re-defining them in any scope > (choose a different variable name) > You are right, 'param' is am implicit EL variable. But despite this, tags 'forEach' and 'iterate' correctly create the loop variable 'param' and correctly place it to the page context. While looping, this variable is correctly changed. Besides, the tag 'html:text' correctly retrieves variable 'param' from the page context and correctly processes it. So why these three tags correctly process 'param' variable, but 'out' doesn't? This seems to be an inconsistency. Why some tags process 'param' in one way, some - in another way? Either NONE of tags should process 'param' as local variable, or ALL of them should process it in the same way.
The loop isn't necessary, the following confirms the bug: <c:set var="param" value="52"/> <c:out value="${pageScope.param}"/><br/> <c:out value="${param}"/><br/>
Digging into it, my gut feel is that it's due to line 70 of org/apache/taglibs/standard/lang/jstl/JSTLVariableResolver.java. It also suggests that the same problem will exist for: pageContext pageScope requestScope sessionScope applicationScope param paramValues header headerValues initParam cookie Testing 'header', it's got the same problem. I think it's not worth the time to try and rewrite this so that things can work for some of them in certain contexts and not for other ones. So we should FAQ this and point out the pageScope workaround.
Added to the FAQ: http://wiki.apache.org/jakarta-taglibs/Standard1%2e1%2e3FAQ Resoling WONTFIX.