title: Spring Security custom filter
body: <p>I would like to customize Spring security 3.0.5 and change login URL to be /login instead of /j_spring_security_check. </p>
  
  <p>What I need to do, is to to allow login to "/" directory and to secure "/admin/report.html" page.</p>
  
  <p>First of All I create my own filter using tutorial and Spring Security source code:</p>
  
  <pre><code>public class MyFilter extends AbstractAuthenticationProcessingFilter {
      private static final String DEFAULT_FILTER_PROCESSES_URL = "/login";
      private static final String POST = "POST";
      public static final String SPRING_SECURITY_FORM_USERNAME_KEY = "j_username";
      public static final String SPRING_SECURITY_FORM_PASSWORD_KEY = "j_password";
      public static final String SPRING_SECURITY_LAST_USERNAME_KEY = "SPRING_SECURITY_LAST_USERNAME";
  
      private String usernameParameter = SPRING_SECURITY_FORM_USERNAME_KEY;
      private String passwordParameter = SPRING_SECURITY_FORM_PASSWORD_KEY;
  
      protected MyFilter() {
          super(DEFAULT_FILTER_PROCESSES_URL);
      }
  
      @Override
      public Authentication attemptAuthentication(HttpServletRequest request,
                                                  HttpServletResponse response) 
                            throws AuthenticationException, IOException, ServletException {
          String username = obtainUsername(request);
          String password = obtainPassword(request);
  
          if (username == null) {
              username = "";
          }
  
          if (password == null) {
              password = "";
          }
  
          username = username.trim();
          UsernamePasswordAuthenticationToken authRequest = new UsernamePasswordAuthenticationToken(username, password);
          HttpSession session = request.getSession(false);
          if (session != null || getAllowSessionCreation()) {
              request.getSession().setAttribute(SPRING_SECURITY_LAST_USERNAME_KEY, TextEscapeUtils.escapeEntities(username));
          }
          setDetails(request, authRequest);
  
          return this.getAuthenticationManager().authenticate(authRequest);
      }
  
      protected void setDetails(HttpServletRequest request, UsernamePasswordAuthenticationToken authRequest) {
          authRequest.setDetails(authenticationDetailsSource.buildDetails(request));
      }
  
      @Override
      public void doFilter(ServletRequest req, ServletResponse res,
                           FilterChain chain) throws IOException, ServletException {
          final HttpServletRequest request = (HttpServletRequest) req;
          final HttpServletResponse response = (HttpServletResponse) res;
          if (request.getMethod().equals(POST)) {
              // If the incoming request is a POST, then we send it up
              // to the AbstractAuthenticationProcessingFilter.
              super.doFilter(request, response, chain);
          } else {
              // If it's a GET, we ignore this request and send it
              // to the next filter in the chain.  In this case, that
              // pretty much means the request will hit the /login
              // controller which will process the request to show the
              // login page.
              chain.doFilter(request, response);
          }
      }
  
      protected String obtainUsername(HttpServletRequest request) {
          return request.getParameter(usernameParameter);
      }
  
      protected String obtainPassword(HttpServletRequest request) {
          return request.getParameter(passwordParameter);
      }
  }
  </code></pre>
  
  <p>after It I'm making the following changes in xml</p>
  
  <pre><code> &lt;security:http auto-config="true"&gt;
          &lt;!--&lt;session-management session-fixation-protection="none"/&gt;--&gt;
          &lt;security:custom-filter ref="myFilter" before="FORM_LOGIN_FILTER"/&gt;
          &lt;security:intercept-url pattern="/admin/login.jsp*" filters="none"/&gt;
          &lt;security:intercept-url pattern="/admin/report.html" access="ROLE_ADMIN"/&gt;
          &lt;security:form-login login-page="/admin/login.jsp" login-processing-url="/login" always-use-default-target="true"/&gt;
          &lt;security:logout logout-url="/logout" logout-success-url="/login.jsp" invalidate-session="true"/&gt;
      &lt;/security:http&gt;   
  &lt;security:authentication-manager alias="authenticationManager"&gt;
    &lt;security:authentication-provider&gt;
      &lt;security:password-encoder hash="md5" /&gt;
      &lt;security:user-service&gt;
      &lt;!-- peter/opal --&gt;
        &lt;security:user name="peter" password="22b5c9accc6e1ba628cedc63a72d57f8" authorities="ROLE_ADMIN" /&gt;
       &lt;/security:user-service&gt;
    &lt;/security:authentication-provider&gt;
  &lt;/security:authentication-manager&gt;
  &lt;bean id="myFilter" class="com.vanilla.springMVC.controllers.MyFilter"&gt;
  &lt;property name="authenticationManager" ref="authenticationManager"/&gt;
  &lt;/bean&gt;
  </code></pre>
  
  <p>and then I have JSP with my code.</p>
  
  <pre><code>&lt;form action="../login" method="post"&gt;
      &lt;label for="j_username"&gt;Username&lt;/label&gt;
      &lt;input type="text" name="j_username" id="j_username" /&gt;
      &lt;br/&gt;
      &lt;label for="j_password"&gt;Password&lt;/label&gt;
      &lt;input type="password" name="j_password" id="j_password"/&gt;
      &lt;br/&gt;
      &lt;input type='checkbox' name='_spring_security_remember_me'/&gt; Remember me on this computer.
      &lt;br/&gt;
      &lt;input type="submit" value="Login"/&gt;
  &lt;/form&gt;
  </code></pre>
  
  <p>when trying to navigate to /admin/report.html I'm redirected to login page.
  but after submitting credentials I'm getting:</p>
  
  <pre><code>HTTP Status 404 - /SpringMVC/login/
  
  type Status report
  
  message /SpringMVC/login/
  
  description The requested resource (/SpringMVC/login/) is not available.
  </code></pre>
  
  <p>It looks like I have problem in configuration, but I can't figure it out what causing this.
  Can you help?</p>