Forwarding a request from one servlet to another using Request dispatcher - java

I was trying to create a cookie in one servlet , add it to response() and forwarded it to another servlet using DisaptcherServlet and tried to retrive the cookie using request.getCookies(). But this always coming out to be null.
//Servlet one
protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
String userName = request.getParameter("username");
String password = request.getParameter("password");
Cookie cookie = new Cookie("name", "value");
cookie.setMaxAge(30);
response.addCookie(cookie);
if(userName.equals("username") && password.equals("*****")){
RequestDispatcher requestDispatcher = request.getRequestDispatcher("/Welcome");
requestDispatcher.forward(request, response);
}
else{
System.out.println("invalid credentials");
}
}
//welcome servlet
protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
Cookie [] cookie = request.getCookies();
if(cookie != null){
System.out.println("sucess");
}
else{
System.out.println("cookieis null");
}
}

When you forward a request you are basically saying "no I don't want to process this request give it to this other resource instead". This means the forwarded request uses the same request and response as the original request.
In your example servlet one sets a cookie on the response, which welcome servlet cannot access because there is no API on the response object to get cookies. If you want this pattern servlet one should set a parameter on the request object which welcome servlet can then get from the request object.

Related

back button goes to confirm form resubmission

I made a logout servlet for logout button, when clicking on logout servlet it successfully going to login page as coded. But when clicking on back button, it asks for form resubmission and after confirming it again going to previous user session.
protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
// TODO Auto-generated method stub
/* PrintWriter out = response.getWriter(); */
HttpSession session = request.getSession();
response.setHeader("Cache-Control", "no-store, no-cache, must-revalidate, max-age=0, post-check=0, pre-check=0");
response.setHeader("Cache-control", "no-cache");
response.setHeader("Pragma", "no-cache");
response.setHeader("Expire","0");
response.setDateHeader("Expires",-1);
session.invalidate();
String userr = (String)request.getAttribute("k");
if (userr == null)
response.sendRedirect("Login.html");
}
To anyone, who has a similar issue, here is the solution that worked for me.
Create your login.jsp page with the user input form (method should be POST)
<form action="${pageContext.request.contextPath}/userAuth" method="POST">
...
</form>
Create a filter class and map it to login.jsp. Inside the filter class make a check for null, retrieve session and check if it contains an attribute, which will signal that the user has already logged in (I used User object and mapped it as "user")
#WebFilter("/login.jsp")
public class AuthFilter implements Filter {
public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException {
HttpSession session = ((HttpServletRequest) request).getSession();
if (session.getAttribute("user") != null) {
response.setContentType("text/html;charset=UTF-8");
request.getRequestDispatcher("homepage.jsp").forward(request, response);
}
chain.doFilter(request, response);
}
}
Create servlet class and map it to the form action inside login.jsp. Override doPost and doGet methods: former will contain user credentials processing logic, latter will contain log out logic.
#WebServlet("/userAuth")
public class AuthServlet extends HttpServlet {
/**
* Log in
*/
#Override
protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
HttpSession session = request.getSession();
String email = request.getParameter("email");
String password = request.getParameter("password");
try {
User user = UserDAO.getUser(email, password);
session.setAttribute("user", user);
response.sendRedirect(request.getContextPath() + "/login.jsp");
} catch (DAOException e) {
e.printStackTrace();
}
}
/**
* Log out
*/
#Override
protected void doGet(HttpServletRequest request, HttpServletResponse response) throws IOException {
request.getSession().invalidate();
response.setContentType("text/html;charset=UTF-8");
response.sendRedirect("login.jsp");
}
}
Create your homepage.jsp and add the logout button which will send GET to the servlet
Logout
Now the logic behind this is as follows:
The servlet doesn't actually redirect to user homepage. All it does is adding that one attribute, that the filter is looking for, and redirecting request back to login.jsp. And login.jsp always gets intercepted by the filter, who redirects to the homepage if that attribute is present.
This way you will solve the problem of keeping the user logged in until the session is on, as well as the problem of user being able to return or refresh page (which will cause form resubmission) after logging out. No additional headers like "no-cache" are needed.

forward request from servlet to jsp after login using tomcat

I'm trying to forward request to a jsp file after login using tomacat. But it (servlet) does not forwarding the request. Can anyone figure it out the error here ?
Servlet :
public class AuthenticationServer extends HttpServlet {
public void doPost (HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
doService(request, response);
}
public void doGet (HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
doService (request, response);
}
public void doService (HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
String user = request.getRemoteUser();
request.setAttribute("user", user);
RequestDispatcher dispatcher = request.getRequestDispatcher("/" + request.getParameter("direct"));
dispatcher.forward(request, response);
}
}
When I printed the "/" + request.getParameter("direct"), it prints out /welcome.jsp. But it just don't forwards it.
request.getRequestDispatcher(String path);
The path specified may be relative, although it cannot extend outside the current servlet context. If the path begins with a "/" it is interpreted as relative to the current context root. If the servlet container cannot return a RequestDispatcher also this method returns null.Try this:RequestDispatcher dispatcher = request.getRequestDispatcher(request.getParameter("direct"));
If you could specify the error it will make it easier to solve your problem...
The problem could be because it cannot find the jsp view.
When you put a "/" in getRequestDispatcher() the path is relative to the root of your application. if http://localhost:8080 is your root then your url will be http://localhost:8080/YourApp/welcome.jsp
you can get a more explanation here

get same session object in jsp and Servlet Filter?

I am setting an attribute to the session object in jsp page as shown below:
String remoteAddr = request.getRemoteAddr();
session.setAttribute("remoteAddr",remoteAddr);
Then, I am trying to retrieve that session attribute in the servlet filter:
public void doFilter(ServletRequest request, ServletResponse response,
FilterChain chain) throws IOException, ServletException {
HttpServletRequest httpServletRequest = (HttpServletRequest) request;
String remoteIP = httpServletRequest.getSession(false).getAttribute("remoteAddr");
}
But I am getting a null value for the session object here. What is the correct way to get same session object here?
The method HttpServletRequest.html#getSession(boolean) may return null
If create is false and the request has no valid HttpSession, this method returns null.
A Filter may be invoked before a resource is requested or after it is requested depending on when you perform chain.doFilter(request, response);
In your case it seem that you query the session before the jsp is executed, i.e. doing something like this:
HttpServletRequest httpServletRequest = (HttpServletRequest) request;
String remoteIP = (String) httpServletRequest.getSession(false).getAttribute("remoteAddr");
// pass the request along the filter chain
chain.doFilter(request, response);
Changing it to
// pass the request along the filter chain
chain.doFilter(request, response);
HttpServletRequest httpServletRequest = (HttpServletRequest) request;
String remoteIP = (String) httpServletRequest.getSession(false).getAttribute("remoteAddr");
Will get it to work, but I doubt this is what you intend to do, since you probably want to check the remote IP and decide whether to allow access or deny it to the requested resource, in which case you may want to do something like this:
String remoteIP= request.getRemoteAddr();
if(remoteIP.matches("some pattern")) {
((HttpServletResponse)response).setStatus(HttpServletResponse.SC_FORBIDDEN);
} else {
// pass the request along the filter chain
chain.doFilter(request, response);
}

Create http session in filter

My xhtml web pages are called from an external system using a simple request, I suppose to check if the user name - given from the request - is valid or not, if valid he suppose to get to the home page, other than that he is redirected to the external system. I created a filter to get the request:
#Override
public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException {
HttpServletRequest req = (HttpServletRequest) request;
HttpServletResponse res = (HttpServletResponse) response;
// skip the resources library
if (!req.getRequestURI().startsWith(req.getContextPath() + ResourceHandler.RESOURCE_IDENTIFIER)) {
res.setHeader("Cache-Control", "no-cache, no-store, must-revalidate"); // HTTP
// 1.1.
res.setHeader("Pragma", "no-cache"); // HTTP 1.0.
res.setDateHeader("Expires", 0); // Proxies.
}
Object attr = req.getParameter("user");
String language = (String) req.getParameter("language");
if (attr != null && language != null) {
// check user in db
String userAdmin = (String) attr;
ResultStatus result = myDao.findUser(userAdmin);
if (result.getStatus().equals(ResponseStatus.SUCCESS)) {
// User is logged in, so just continue request.
User user = new User();
user.setAccountId(result.getAccount().getAccountId());
chain.doFilter(req, res);
} else {
// User is not logged in, so redirect to index.
res.sendRedirect(req.getContextPath() + "/test.xhtml");
}
} else {
// User is not logged in, so redirect to index.
res.sendRedirect(req.getContextPath() + "/test.xhtml");
}
}
I need to create session for the user in the filter if he is a valid user, so I can get the user object at any back bean.
To set it just do this :
req.getSession().getServletContext().setAttribute(LoginFilter.USER_KEY, user);
chain.doFilter(req, res);
To get it :
FacesContext facesContext = FacesContext.getCurrentInstance();
HttpServletRequest request = (HttpServletRequest) facesContext.getExternalContext().getRequest();
User user = (User) request.getSession().getServletContext().getAttribute(LoginFilter.USER_KEY);

Filter is not retrieving request.getAttribute()

public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException {
try {
String logged = (String) ((HttpServletRequest) request).getAttribute("loginstatus");
if(logged != null) {
out.print("ok");
} else {
out.print("not ok");
}
Why is the value of logged always null?
A filter is by default the very first thing which get executed on a HTTP request. The request attribtues are usually managed by server side code. Who/what should have set the request attribute before this filter does its job?
Aren't you confusing how HTTP requests/responses work? A request get finished/garbaged, including all attributes, when the associated response is finished. Every subsequent request is a brand new one which doesn't contain at all the same attributes as the previous one.
Don't you actually want to use the session scope? Do the following on login:
request.getSession().setAttribute("user", user);
And then the following in authentication filter:
if (((HttpServletRequest).getSession().getAttribute("user") != null) {
chain.doFilter(request, response); // Continue.
} else {
((HttpServletResponse) response).sendRedirect("login"); // Redirect to login.
}
See also:
How does a servlet environment work? ServletContext, HttpSession, HttpServletRequest/Response.
Servlet filters wiki page

Categories

Resources