JSP parent/child param manipulation - java

I have a parent jsp file that includes two child jsp's. I have a variable defined in the parent file like so:
<c:set var="test" value="N" />
which I then pass into two child jsp files:
<div id="div_data_1" style="display:none;">
<jsp:include page="page1.jsp">
<jsp:param name="controlFlag" value="${test}"/>
</jsp:include>
</div>
<div id="div_data_2" style="display:none;">
<jsp:include page="page2.jsp">
<jsp:param name="controlFlag" value="${test}"/>
</jsp:include>
</div>
In my page1.jsp file I then store the value in a hidden div:
<div id="cashAuditFlag" style="display: none;">${param.cashAuditFlag}</div>
I then have a button in page1.jsp that, when clicked, I want it to change the value of the parent variable ${test} to "Y". This in turn would then change the value of ${test} in page2.jsp which would cause a change in page2.jsp.
I basically want to have a child jsp communicate an update to another child jsp, both of which belong to the same parent.
A - Is this the best way of doing this process?
B - How can I have a child jsp update the parent jsp variable?
Thank you!

To understand this, you need to understand scopes. Think of a scope as a bucket that variables go into when they are defined. Some code only has access to some of those buckets.
Request scoped variables are available in any part of the code that knows about the http request. There is only one request scope per HTTP request to your webapp. In your example, the parent file, page1.jsp, and page2.jsp all have access to that request scope. For example, if you did this in your parent JSP page:
<c:set var="test" value="N" scope="request" />
...it would put the "test" variable into the request scope bucket with a value of N.
Then, if you want to view or modify this value in either page1.jsp or page2.jsp, you don't even need to have a jsp:param element in your jsp:include, so you can just do this:
<div id="div_data_1" style="display:none;">
<jsp:include page="page1.jsp"/>
</div>
<div id="div_data_2" style="display:none;">
<jsp:include page="page2.jsp"/>
</div>
So, if you want to display this in either child page, you can simply use Expression Language and tell it to look in the requestScope for the variable named "test" by using the requestScope object:
<p>The Test Variable is: ${requestScope.test}</p>
Similarly, if you wanted to modify this variable in either childPage, you can simply do another c:set statement:
<c:set var="test" value="Y" scope="request" />
Now, if you print out the value of ${requestScope.test} in any page, it will be Y.
In your example, when you used the c:set statement without scope="request", you created a variable in that jsp page's "page scope", meaning you could only access that variable in the jsp code you wrote in your parent jsp page.
Now, as to whether this is the best way to do this...
You say you have a button in page1.jsp that, when clicked, should change the test variable to Y and cause some display change in page2.jsp. Here's the flow of what would need to happen:
User vists your JSP page at some url, like "mywebapp/testPage.jsp"
The page renders. The initial c:set statement runs which sets the "test" var to a value of "N".
The user clicks the button, which causes the browser to send a new request but adds a request parameter, resulting in a request of something like "mywebapp/testPage.jsp?buttonClicked=1"
All your JSP pages render again (keep in mind JSP does not do things "dynamically" i.e. without a browser refresh - when you click a button, the browser sends a new HTTP request to the webserver and your JSP is rendered again).
At the top of your parent JSP, you need logic that checks whether the buttonClicked request parameter is present. If so, it sets the value of test to "Y" instead of "N".
So, to explain: in order to have the page render differently based on whether the button was just clicked, you would need to have your button pass a request parameter when it is clicked, and you would need to have your JSP look at the new request to find that request parameter (to see the value that was submitted when the button was clicked). If you don't have your code check that, then, every time your page loads, your parent JSP page will just keep re-setting the test variable to N because your initial c:set value="N" statement will always run when the JSP renders.
So, if you want something like the case you described, you'd have to do something like this in your parent JSP page:
<c:set var="test" value="N" scope="request"/>
<!-- Here's the check for whether the request parameter is present -->
<c:if test="${not empty param.buttonClicked}">
<c:set var="test" value="Y" scope="request"/>
</c:if>
<div id="div_data_1" style="display:none;">
<jsp:include page="page1.jsp"/>
</div>
<div id="div_data_2" style="display:none;">
<jsp:include page="page2.jsp"/>
</div>
...then in page1.jsp, where you have the button, you would do something like this:
<input type="submit" name="buttonClicked" value="1" />
That way, when the button is clicked, it will refresh the page and add a new request parameter called buttonClicked with a value of "1". In the parent JSP, it will see that this request parameter is present (with "not empty param.buttonClicked") and it will set the value of the test variable to "Y", overwriting the previous assignment of "N".
Then in your page2.jsp, you can access the value of test using ${requestScope.test} at any point on your page.

Related

Use value of a local variable as global in thymeleaf

I have a variable that is obtain inside each block in thymeleaf. I want to send that variable to a certain method in my controller. The limitation is that the variable is obtain inside a block which makes it local, not accessible global.Hence I get an error while trying to use it. How can I move inside the scope to get the variable so as I can use it global in thymeleaf.
<form th:action="#{/masomo/somo(date=${dateMpya.date})}" method="POST">
<select id="date" name="date" required="true">
<option value="none" selected disabled hidden >
Select a Date
</option>
<th:block th:each="somoChagua : ${masomoChagua}">
<option th:each="dateMpya: ${somoChagua}" th:value="${dateMpya}" th:text="${dateMpya.date}" ></option>
</th:block>
</select>
<button type="submit"><i class="fa fa-search"></i> </button>
</form>
There can be many different "dateMpya" objects for each "somoChagua".
But there is only one submit button.
So which "dateMpya" should be used for the submit button value?
I think what you are actually trying to do here is get the value of the "dateMpya" which the user selected in the drop-down. Is that right?
If that's the case there is no need to add any attributes to the submit button. You would access that value by using the name of the select element, which is "date".
EDIT: For the same reason you also need to remove the (date=${dateMpya.date}) part of the form action as well. The value selected in the drop-down will automatically be submitted under the name of the select element "date", it does not need to be specified.

How to force a java bean to be updated after using back button?

Suppose I have a jsp page called index1.jsp. On this page I have a checkbox,
as follows.
<form name="form1" method="post" action="index2.jsp">
<input type="checkbox" name="check">
On my server I have a java bean say mybean that has setCheck and getCheck
functions.
I also have the following at the end.
<input type="submit" value="Submit" >
</form>
I check the check box, click on submit button, I go to the next page,
and the function setCheck of mybean is called.
then I click the back button of my browser, go back to index1.jsp
uncheck the checkbox, and click submit button.
I again go to index2.jsp, but this time, mybean is not updated, setCheck is not called, when I check the value, the "check" variable of mybean is still "on", even though I just turned it off.
Can anyone tell me how I can go back to the jsp page, uncheck the check button and have it reflected in my bean, that has a member variable of the same name as the check box name in my jsp ?
when you press "Back button" on the browser, it go back to cached version of the previous JSP (responsed).
Try this:
Adding this code to your jsp will cause most browsers to not cache the response:
<%
response.setHeader("Pragma","no-cache"); // HTTP 1.0
response.setHeader("Cache-Control","no-store"); // HTTP 1.1
response.setDateHeader("Expires", 0);
%>

calling Java method from jsp page

I have jsp page that imports Testing.java
<jsp:useBean id="test" scope="session" class="Testing" />
<jsp:useBean id="sb" scope="session" class="SessionBean" />
<jsp:useBean id="eb" scope="session" class="ErrorBean" />
I need to call public method that is in Testing class after user confirms changes.
this is what I have so far:
<tr>
<td align="left">
<a href="<%=test.persistPrintingInfo(eb,sb) %>" >
<img src="../images/update.gif" OnClick="if( !confirm('Update printing information?')) return false"></a>
</td>
</tr>
Does anyone know how to do this?
Can I maybe call javascript method and call persistPrintingInfo() through javascript?
the page has been sent by the server to your browser. while javascript can modify the content of your page , in order to call a bean's method you must make a call to the server(a request to the servlet) beacause the bean lives on the server side. and this call can be made by creating an url mapped to the servlet, or a form whose action is the servlet
`<FORM ACTION="${pageContext.request.contextPath}/sampleServlet">`
if the form's method is GET, then on the doGet() method of the servlet you call your bean's method.
this form does not need to contain any kind of field. it is created just to make a request to the servlet. while you would normally click the submit button to proceed to the action, this time we will submit the form through javascript. with some javascript tricks, i think this form can also be hidden, because you don't actually need it to be displayed in your page
so you simply create this form in your jsp, and submit it through javascript , like this:
on your link, you will have onClick=myJavascriptMethod(); in your jsp, you create a javascript block
<script type="text/javascript">
function myJavascriptMethod)=()
{
document.forms["myform"].submit();
}
</script>
You can use this way, although there is better approaches using servlets.
<%com.example.Testing.yourMethod()%>
a second approach which i found while googling is this one:
How do I pass current item to Java method by clicking a hyperlink or button in JSP page?
in your case, the code will be
<img.. >
the newPage.jsp will contain just
<%yourPackage.YourClass.yourMethod()%>

accessing information inside a jsp:include from the parent jsp

I'm trying to access form data that is filled out inside a jsp:included page from outside the page. I am using jquery and am open to using ajax. My code looks a little like this:
<form name=form1>
<jsp:include page="someFormData.jsp" />
//Other inputs out here in <% include %> files
<input type=button value=Submit onClick="return commonSubmit()"
</form>
I need to use the jsp:include style include because having everything on one page using
<%include...%> was causing an exception due to my jsp being too large. Alls I need to do is be able to submit the form and include the data inside "someFormData.jsp"

JSP Form page goes into infinite loop when action URL is initialized from a variable

I have a simple JSP as follows:
<form name="myform" id="myform"
action="${pageContext.request.contextPath}/validateLoginID.do" method="POST">
<input type="text" name = "loginID" id="loginID" value="${loginID}"/>
</form>
<script>
window.alert("Submitting form!");
document.myform.submit();
</script>
The above JSP code works. But when I try to initialize the action from a variable instead, using something like:
action="${myLink}" method="POST">
It goes into an infinite loop, printing "Submitting form!" each time. Why is this happening?
Well, probably because the action it submits the form to returns the above page, which submits the form, which displays the page, which submits the form, etc.
"myLink" was actually a dummy name for the variable "name" that I was actually using. I tried to mimic ${pageContext.request.contextPath} and have a name like that, but unfortunately, the dot in the variable name was causing the problem. With the dot removed, it works.
I think the struts validation framework implied underneath the code above. A far as it returns the input the same page involve the javascript to submit the page with errors again and it's repeating. Remove document.myform.submit(); or make function
<script type="text/javascript">
function doSubmit(){
window.alert("Submitting form!");
document.myform.submit();
}
</script>
that will stop submitting on load.

Categories