Request Attributes not available in jsp page when using sendRedirect from a servlet
Asked Answered
S

2

7

I am new to jsp and servlet. My scenario is as follows

I have a jsp page which have a form in it. with two fields. The code snipet of the jsp page is as follows.

MyFirstJSP.jsp file

<body>
<h1> This is my first jsp and servlet project</h1>
<%
//System.out.println(request.getAttribute("fname"));

if(request.getAttribute("fname")!=null){
    System.out.println(request.getAttribute("fname"));
}else{
    System.out.println("No request ");
}
%>
<form action="MyFirstServlet" method="get">
First Name<input type="text" name="fname" value= ${fname}><br>
Last Name<input type="text" name="lname" value= ${lname}>
<input type="submit" value="Send">
</form>
</body>

When I submit this form the MyFirstServlet is called which checks the first name entered by user. If the first name is equals to "abc" then servlet sets the attribute to request object and send redirect it to the callsing jsp page i.e. above page. Which will get the value from request object and fill it in to respective field of form. I have Java Expression language too for same effect.

Here is my code snipet of the MyFirstServlet.java servlet file

/**
 * Servlet implementation class MyFirstServlet
 */
public class MyFirstServlet extends HttpServlet {
    private static final long serialVersionUID = 1L;

/**
 * @see HttpServlet#HttpServlet()
 */
public MyFirstServlet() {
    super();
    // TODO Auto-generated constructor stub
}

/**
 * @see HttpServlet#doGet(HttpServletRequest request, HttpServletResponse response)
 */
protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {       // TODO Auto-generated method stub
    String firstname=request.getParameter("fname");
    if(firstname.equalsIgnoreCase("abc")){
        System.out.println("Setting attributes");
        request.setAttribute("fname",firstname);
        request.setAttribute("lname",request.getParameter("lname"));
        response.sendRedirect("MyFirstJSP.jsp");
    }else{
        System.out.Println("No problem");
    }
}
/**
 * @see HttpServlet#doPost(HttpServletRequest request, HttpServletResponse response)
 */
protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
    // TODO Auto-generated method stub
    PrintWriter p=response.getWriter();
    p.println("Success!");
    doGet(request,response);
}
}

But when I execute the code the servlet redirects to the jsp page but not fills the form fields with the respective values. As to find the cause I have added the if-else-block to know the cause and I get to know that the request objects attribute is not available here.

If I use the request dispatcher in this case then the values are gets available and the form is gets filled with the values but the url in the address bar does not chage and always shows the url to the servlet.

So My query is

**1)Why the request object is not available to jsp page using sendRedirect.

2)Is thre any other way to show my form in jsp page prefilled with the values entered by user if the servlet sendredirects to the calling jsp so that user need not to reenter the data in to form.**

Please guide me friends in this problem Thank You!

Scamper answered 10/9, 2012 at 11:51 Comment(1)
Read BalusC's answer: #2047622Insomuch
P
19

You need to forward to the jsp page on server side, as a redirect is a client side action (check out the location header 1) the request attributes get lost.

replace

response.sendRedirect("MyFirstJSP.jsp");

with

request.getRequestDispatcher("MyFirstJSP.jsp").forward(request, response);

Edit: sorry, I skipped this part

If I use the request dispatcher in this case then the values are gets available and the form is gets filled with the values but the url in the address bar does not chage and always shows the url to the servlet.

nevertheless, you cannot pass request attributes to your jsp when redirecting (as i've already mentioned above it's a clientside action)

I'd suggest doing the following:

  • Implement doGet for only rendering the page that contains the form
  • Implement doPost for handling the submitted form data
  • use POST instead of GET in the HTML-Form to submit the form

In both, doGet and doPost, use forward to render the *.jsp page.

GET /MyFirstServlet -> forward to MyFirstJSP.jsp

POST /MyFirstServlet -> forward to MyFirstJSP.jsp

this is the most commonly used and clean approach.

EDIT 2: Simple Example

SimpleFormServlet.java

public class SimpleFormServlet extends HttpServlet {
private static final long serialVersionUID = 1L;

private static final String VIEW_NAME = "/WEB-INF/jsp/simpleForm.jsp";
private static final String MODEL_NAME = "form";

public SimpleFormServlet() {
    super();
}

protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
    request.setAttribute(MODEL_NAME, new SimpleForm());
    request.getRequestDispatcher(VIEW_NAME).forward(request, response);
}

protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {

    final SimpleForm form = map(request);

    if(form.getfName().equalsIgnoreCase("abc")){
        request.setAttribute(MODEL_NAME, form);
        // put additional attributes on the request
        // e.g. validation errors,...
        request.getRequestDispatcher(VIEW_NAME).forward(request, response);
    }else{
        System.out.println("No problem");
        response.sendRedirect("/SuccessServlet");
    }
}

private SimpleForm map(final HttpServletRequest request) {
    SimpleForm form = new SimpleForm();
    form.setfName(request.getParameter("fName"));
    form.setlName(request.getParameter("lName"));
    return form;
}

public static class SimpleForm implements Serializable {
    private static final long serialVersionUID = -2756917543012439177L;

    private String fName;
    private String lName;

    public String getfName() {
        return fName;
    }
    public void setfName(String fName) {
        this.fName = fName;
    }
    public String getlName() {
        return lName;
    }
    public void setlName(String lName) {
        this.lName = lName;
    }

}

}

/WEB-INF/jsp/simpleForm.jsp

<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=ISO-8859-1">
</head>
<body>

<form method="POST">
    First Name<input type="text" name="fName" value="${form.fName}"><br>
    Last Name<input type="text" name="lName" value="${form.lName}">
    <input type="submit" value="Send">
</form>

</body>
</html> 
  1. GET /SimpleFormServlet
  2. doGet() prepares the form model (SimpleForm) and adds it as a request attribute named 'form'
  3. forward to the simpleForm.jsp
  4. access the model values and prefill the form: ${form.fName} and ${form.lName}
  5. the browser still shows /SimpleFormServlet (and we like it ;-))
  6. POST the form relatively to /SimpleFormSerlvet (you don't have to set the action attribute of the form element explicitly)
  7. doPost() maps the request parameters to the SimpleForm.
  8. process the request and do whatever you want to do (validation)
  9. then you can either forward to the simpleForm.jsp (like when validation fails) or redirect to another servlet (/SuccessServlet for example)
Parliamentarianism answered 10/9, 2012 at 12:23 Comment(7)
Thank You! friend for your reply but one of my concern is the url in the address bar of the browser which is not get change if I use the request dispatcher. My requirement is that the value should be get available to jsp page for refilling the form as well as the url in the address bar of the browser should change to jsp page url.Scamper
@Param-Ganak: Then use Session scopeInsomuch
@Param-Ganak: sorry, I've just edited my post (and pls, dont' ever use the Session scope for such things like form attributs and params)Parliamentarianism
@reagten Thank You friend for your guidance! I checked your edited reply but as I am a beginner in jsp and servlet I dont understand your suggestion completely. Do you have any demo code to demonstrate what exactly you want to suggest.Scamper
i'm preparing a simple example for you. just wait a minute ;-)Parliamentarianism
@reagten Thank You Very much! I am waiting for your example!Scamper
Another full example can also be found here: community.oracle.com/thread/2063481?start=0&tstart=0Benzyl
A
6

I know it's too late to answer but this would be helpful to someone. redirect is a client side action so that we can't getAttribute values but we can solve it by using URL Rewriting concept.

protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {       // TODO Auto-generated method stub
String firstname=request.getParameter("fname");
if(firstname.equalsIgnoreCase("abc")){
    //System.out.println("Setting attributes");

    response.sendRedirect("MyFirstJSP.jsp?fname="+firstname+"&lname="+request.getParameter("lname")+"");
}
else{
    System.out.Println("No problem");
  }
}

then use request.getParameter() to extract values as string in MyFirstJSP.jsp.

Algorithm answered 27/4, 2015 at 8:45 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.