I have a generic jsp which is in charge of printing some values, the values depends on a parameter.
For example, I have an object car with and attribute color and a object house with the same attribute, I want to use the same jsp receiveng the name of the object as a parameter.
<jsp:include page="/jsp/prv/generic/PaintColor.jsp" >
<jsp:param name="element" value="car" />
</jsp:include>
So, I want to print the value of car color. I try to do it like this:
<s:set var="propertyName">${param.element}.color<s:set/>
<s:property value="%{#attr.propertyName}" />
It doesnt work, but if I do
<s:textfield name="%{#attr.propertyName}"/>
it works perfect.
How can I use the parametrized name in avalue?
I finally solve it accesing the value from a java scriptlet
Related
How do I convert a JSP variable to a Struts2 variable?
I've tried the following:
<%=scoredDocument%>
<s:push value="scoredDocument"/>
<s:push value="#scoredDocument"/>
<s:push value="%{scoredDocument}"/>
<s:push value="${scoredDocument}"/>
<s:push value="#page.scoredDocument"/>
<s:push value="%{#page.scoredDocument}"/>
<display:column title="Study Code" sortable="true">
<s:property value="id"/>
The most frequent error is
Caused by: tag 'push', field 'value': You must specify a value to push on the stack. Example: person - [unknown location]
<s:push> must enclose the <s:property> tag. Also
<s:push value="#attr.scoredDocument">
<display:column title="Study Code" sortable="true">
<s:property value="id"/>
</display:column>
</s:push>
#attr? WTF Struts? It's not even documented! https://struts.apache.org/release/2.0.x/docs/jsp.html
The push tag requires the value attribute and it has to be initialized, otherwise it shows the JSP error. Unlike other tags where the value could be preinitialized with empty string, the JSP doesn't complain.
The OGNL expression is evaluated in this attribute, like in many other attributes of Struts tags, and if can't resolve the value it returns null. This value is unacceptable for the push tag and it throws exception. The error mislead to make a different tries to access the scriptlet variable value via the OGNL expression, unfortunately none of that methods worked.
Scriptlet expressions has a one pitfall when used with the Struts tags that you can use only in the body of the tag and it's converted to string. Like in this example
<s:set var="scoredDocument"><%=scoredDocument%></s:set>
you can't do the same with the push tag. After that you can use the stringified version of #scoredDocument in OGNL expressions.
I am appending the parameters with action but I am getting an exception of on my Struts 2 page.
PWC6212: equal symbol expected
Below is my action with appended parameters code which is to be submitted.
action="MyAction.action?id=<%=request.getParameter("id")%>&name=<%=request.getParameter("name")%>&age=<%=request.getParameter("age")%>&num=<%=request.getParameter("num")%>"
Is the above is the syntax problem? If not then how can we set the parameters as a query string with action?
You should not use Scriptlets (<%= %>)
And, if action is an attribute of a Struts tag (like <s:form>), you can't use scriptlets, you should use OGNL.
Please refer to this question: Struts 2 s:select tag dynamic id for more details
Assumed the action attribute is used with the <form tag. Then the construction
<form name="MyAction.action" action="upload?id=<%=request.getParameter("id")%>&name=<%=request.getParameter("name")%>&age=<%=request.getParameter("age")%>&num=<%=request.getParameter("num")%>" method="POST">
should work with the current context. But in your case given error message (Exception Name: org.apache.jasper.JasperException: equal symbol expected is occurred when <s:form tag is used. So, you cannot use this url in the action attribute. This attribute should contain the plain action name that would be used to find your action.
"How we set parameters as a querystring?"
Actually we do it with <s:param tag. For example, when using hyperlinks
<s:a action="MyAction">
<s:param name="id" value="%{id}"/>
<s:param name="name" value="%{name}"/>
</s:a>
But this construction doesn't work with <s:form tag, unless you applying a special syntax as described in this answer and you definitely want to get these parameters if you do in the action
String quesyString = request.getQueryString();
and this string should not be empty.
However, this usecase is rarely applied, If you don't have a reason to get parameters in such way then as alternative you always can use <s:hidden fields to contain the values of the parameters. For example
<s:form action="MyAction" method="POST">
<s:hidden name="id" value="%{id}"/>
<s:hidden name="name" value="%{name}"/>
</s:form>
These values are passed as a parameters and initialize the action attributes after params interceptor worked. You could also get this parameters directly from the request as
Map<String, String[]> params = (Map<String, String[]>)request.getParameterMap();
However, the more convenient way to do this in your action is to implement ParameterAware.
Just like #AndreaLigios mentioned, you should use Struts2 specified EL, check out the Document here.
If you are using <s:url/>, check out Document please for more information.
Your code should look something like this:
<s:url value="MyAction.action">
<s:param name="id" value="%{#parameters.id}" />
<s:param name="name" value="%{#parameters.name}" />
<s:param name="age" value="%{#parameters.age}" />
<s:param name="num" value="%{#parameters.num}" />
</s:url>
I have following code:
<s:iterator value="reviews">
<img src="<s:property value="#request.restaurant.portalImage.url" />" />
<s:property value="user.firstName" />
<s:property value="user.lastName" />
<s:property value="rating" />
<s:property value="review" />
</s:iterator>
reviews is a list of review objects which contain details of a review, such as rating and name of user.
My problem is that I'm not able to access any of the objects present on the ValueStack within the loop.
Outside the loop <s:property value="#request.restaurant.portalImage.url" /> works correctly. But within the loop it prints null.
AFAIK an iterator pushes it's collection on the ValueStack so that all OGNL expressions resolve against it. But I've used # which means I'm explicitly specifying the root object for resolution.
Why is it still not working?
I just spent my whole afternoon fighting against a similar issue.
In my case, the issue was that my iterator variable (In your case reviews) had a field with the same name as the outer variable.
No matter how hard I tried to break out of the local stack of the iterator, it would not access the outer variable.
If your reviews iterator has a field called restaurant its going to override the outer restaurant variable, no matter how hard you try :(
The solution I found was to simply rename the outer variable. (eg: theRestaurant)
Once I renamed it, it was no longer clashing with the inner variable, and I was able to access it from within the iterator.
I am not sure what object is contained in the collection you are using in the Iterator.As per the iterator when you iterate the collection using the S2 iterator tag it will push the object on the top of value stack, which means, say you have collection of user object on which you are iterating like
<s:iterator value="userCollection">
</s:iterator>
so when this will iterate, S2 iterator will push the user object on top of value stack and if we want to refer to the name property of user object, all we need to refer to the name property
<s:property name="userName"/>
since OGNL will try to resolve userName in the value stack and we already have user object as top level object in value stack.I suggest to go through the Iterator tag documentation and how it push values
S2 Iterator tag
You should change it like below:
<s:iterator value="reviews" var="varrequest">
<img src="<s:property value="#varrequest.restaurant.portalImage.url" />" />
<s:property value="#varrequest.user.firstName" />
<s:property value="#varrequest.user.lastName" />
<s:property value="#varrequest.rating" />
<s:property value="#varrequest.review" />
</s:iterator>
Using a iterator reference variable to fetch the unique index object.
I think it resolves your issue
s:iterator value="reviews" status="position">
<img src="<s:property value="#request.restaurant.portalImage.url"/>"/>
<s:property value="#position.user.firstName"/>
<s:property value="#position.user.lastName"/>
<s:property value="#position.rating"/>
<s:property value="#position.review"/>
</s:iterator>
your requirement is little confusing
Inside a POST in a .jsp file, I'd like to do something like this:
<input type="text" name="...">
And inside the servlet I'd like to do:
request.getParameter(...)
Now where should and how should I declare "..." so that I can avoid duplication and reuse the same String.
Should this go in an interface like this:
public interface SO {
String POST_PARAM = "userinput";
}
Or in a property file? Or ...?
In any case, how do I then access this from the .jsp and from the .java file?
You can define constants like final String POST_PARAM = "userinput"; and then use them in markup: <input type="text" name="<%=POST_PARAM%>">.
Moving fields names to properties file does not sound as a beneficial unless you have reasons to do this.
To get parameter value from HTTP request caused by form submit say request.getParameter(POST_PARAM).
I hope this helps.
You might get the ... from a bean using EL. However, it is not usual for me.
You can use standard actions: jsp:useBean, jsp:setProperty and JavaBean technology:
Example:
A.jsp should call HTTP POST to B.jsp. B.jsp should automatically map all fields and redirect to your servlet.
// model.MyBean.java
class MyBean {
private int age;
// getters&setters
}
// A.jsp:
<form method="POST" action="B.jsp">
<input type="text" name="age">
</form>
// B.jsp
<jsp:useBean id="form" class="model.MyBean" scope="request" />
<jsp:setProperty name="form" property="*" />
<jsp:include page="/servletURL" />
Small description:
MyBean class will be created. This bean should has exactly the same
fields name like name in your form: for <input type="text"
name="age"> in bean should exists int age field and getter/setter.
jsp:setProperty with wildcard map all values from form A.jsp into your bean automatically.
if you want to call your servlet you can simple include appropriate url. Then in the servlet you will have access to request attribute "form" which will has MyBean with entered values.
My web server - tomcat sets two attributes in the session. In the jsp page, am retrieving them as
<% String age = (String) session.getAttribute("age"); %>
Am setting this value to a hidden field in the form in the same jsp file.
<input type="hidden" name="age" id="age" value="<%=age%>" />
And am trying to use this value in javascript file as below
document.cForm.age.value
But this value is null for most of the times. Sometimes, the variable to set to proper value? Is there any reason for this inconsistency? Please explain
Try to get the value on DOM load not inline. i mean inside a $(document).ready(function() {})