Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Spring-Boot: Web-Filter for Redirection

I am having a filter. It should redirect to /b if /a is requested.

public class WebFilter extends GenericFilterBean
{ 
 @Override
 public void doFilter (ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException
 {
    HttpServletRequest req = (HttpServletRequest) request;
    HttpServletResponse res = (HttpServletResponse) response;

    String path = req.getRequestURI ().toString ();

    if (path.equals ("/a") == true)
    {
        System.out.println ("FILTER: a -> b");
        res.reset ();
        res.resetBuffer();
        res.sendRedirect ("b");
    }

    chain.doFilter (req, res);
  }
}

Here is the handler for the content.

@Component
@Controller
@RequestMapping ("/")
public class WebHandler
{

 @RequestMapping ("/a")
 public String a ()
 {
    System.out.println ("a");
    return "a"; // point to a.jsp
 }

 @RequestMapping ("/b")
 public String b (HttpSession ses)
 {
     System.out.println ("b");
     return "b"; // point to b.jsp
 }
}

If I request /a in a browser, then that is the output.

FILTER: a -> b
IN a
IN b

Why is method a called? I would expect only b because I redirect in doFilter from a to b. How can I make that happen?

like image 845
chris01 Avatar asked Apr 14 '20 18:04

chris01


1 Answers

So you are actually doing a redirect although it seems you just want to direct the request to a different controller mapping.

    res.sendRedirect ("b");

Just changes the response code to 302 and adds a location field, you will still hit the first controller, which is why you still see a in the logs. The browser then acknowledges this redirect directive and will send a second request for /b.

One way to achieve what you appear to want would be to create a new Request from the submitted one, and simply override the getRequestUri() method.

    @Override
    public void doFilter (ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException
    {
        HttpServletRequest req = (HttpServletRequest) request;
        HttpServletResponse res = (HttpServletResponse) response;

        String path = req.getRequestURI();


        if (path.equals("/a")) {
            req = new HttpServletRequestWrapper((HttpServletRequest) request) {
                @Override
                public String getRequestURI() {
                    return "/b";
                }
            };
        }

        chain.doFilter (req, res);
    }

This is then passed to the filter chain and everything continues as though that were the original request

like image 83
123 Avatar answered Nov 17 '22 14:11

123