该应用程序不适用于弹簧安全性

时间:2013-05-24 09:04:42

标签: spring spring-mvc spring-security

我正在乞求框架弹簧和弹簧安全性。要学习,我正在开发一个应用程序。 到目前为止,我已经开发了没有spring-security的app,用于通过登录表单对用户进行验证。当用户介绍您的用户名和密码时,我的应用程序将转到控制器,方法“发布”,并且我在那里验证您的ID(用户名和密码),我使用Validator类

现在我已经介绍了spring-security以获得更高的安全性,但是当用户引入你的id(用户名和密码)时,如果没有重定向到方法得到整个时间,应用程序永远不会重定向到控制器的方法帖子

接下来是源代码

表单的jsp文件是:

...
<form:form name="f" commandName="usuario" action="j_spring_security_check" method="POST" >
    <table align="center">
        <tr>
                <td><form:errors path="errorUsuario" cssClass="error"/></td>
            </tr>
    </table>
    <table border="0" cellpadding="2" cellspacing="3">
    <tbody>
             <tr>
                    <td><span id="letra">Usuario</span></td>
                    <td><form:input path="nombreUsuario" name='j_username' id="fondo-gris"/></td>
                 <td><form:errors path="nombreUsuario" cssClass="error"/></td>
        </tr>
        <tr>
                  <td><span id="letra">Password</span></td>
                  <td><form:password path="clave" name='j_password' id="fondo-gris"/></td>
               <td><form:errors path="clave" cssClass="error"/></td>
        </tr>
        <tr>   
                   <td colspan="3"><center><input id="botonInciar" type="submit" name="guardar" value="Iniciar Sesión"/></center></td>
        </tr>
    </tbody>
    </table>
</form:form>
...

此页面的控制器是:

...
@RequestMapping(value = "/index", method = RequestMethod.GET)
    public String login(Model modelo) throws Exception {

        logger.info("LogginController --> login: ha entrado en el método GET");

        Usuario usuario = new Usuario();

        modelo.addAttribute("usuario", usuario);

        logger.info("LogginController --> login: los resultados del usuario son, userName: " + usuario.getNombreUsuario());

        return "index";
    }

    /**
     * Recoge los parámetros y redireccionamos donde necesitamos
     * @param usuario El usuario que intenta acceder al sistema
     * @param result Resultado del acceso
     * @param status Estado de lasesión
     * @return Retornamos la redirección a la página donde debe de ir tras la validación
     */
   @RequestMapping(value = "/index", method = RequestMethod.POST)
   public String processSubmitLogin(@ModelAttribute("usuario") Usuario usuario, BindingResult result, SessionStatus status) {

    logger.info("LogginController --> processSubmitLogin: ha entrado en el método POST");

    UsuarioLoggin ul = new UsuarioLoggin(usuario, usuarioService);
    new LogginValidator().validate(ul, result);

        if (result.hasErrors()) {
            return "index";
        } else {
            status.setComplete();
            return "redirect:/ok.htm";
        }
    }
...

spring-security的配置文件是:securityApplicationContext.xml:

...
<security:http auto-config="true" use-expressions="true">
        <security:intercept-url pattern="/index" access="permitAll"/>
        <security:intercept-url pattern="/*" access="hasAnyRole('ROLE_USER','ROLE_ADMIN')"/>
        <security:form-login login-page="/index"/>
    </security:http>

    <security:authentication-manager alias="authenticationManager">
        <security:authentication-provider>
            <security:jdbc-user-service data-source-ref="dataSource"/>
        </security:authentication-provider>
    </security:authentication-manager>
...
PS:测试和测试..我看到如果删除标签:jsp文件的“j_spring_security_check”,应用程序发现直到现在,但如果我在用户推送时发送数据,应用程序是控制器“get”方法的全部时间

感谢。

2 个答案:

答案 0 :(得分:0)

Spring Security引入了一组拦截器来拦截某些请求。默认情况下,Spring Security将拦截j_spring_security_check的请求并为您处理身份验证。

因此,您永远不会看到Spring MVC处理您期望的POST请求,原因有两个:

  1. 您永远不会POST /index - 从我上面看到的情况来看,用户将GET /index并将表单提交给j_spring_security_check。永远不会有POST/index
  2. 您永远不会希望Spring MVC处理身份验证请求 - 这是使用安全框架的好处;您的MVC代码不必处理身份验证或授权。
  3. 您需要执行以下操作,而不是上述代码:

    1. 从MVC代码中删除processSubmitLogin()方法,因为它不再需要。
    2. processSubmitLogin()中的所有自定义处理添加到Spring Security配置中,以获得相同的用户体验。
    3. processSubmitLogin()执行以下操作:实际验证用户身份(现在通过Spring Security完成),如果出现错误则转发到index,并在成功时重定向到ok.htm。最后两个在Spring Security中配置如下:

      <security:http auto-config="true" use-expressions="true">
          ...
          <security:form-login 
              login-page="/index"
              authentication-failure-url="index"
              default-target-url="/ok.htm"
              always-use-default-target="true"/>
      </security:http>
      

      使用Spring Security时,上述配置应与您的自定义登录页面匹配。有关上述内容的详情,请参阅form-login namespace

答案 1 :(得分:0)

谢谢你的回答。 我不明白你写的一切,也就是说,当你说: 1.从MVC代码中删除processSubmitLogin()方法,因为不再需要它。你提到什么?有点类似的东西:

新的jsp文件

 ... 
   <form name="f" action="j_spring_security_check" method="post" >
       <table border="0" cellpadding="2" cellspacing="3">
          <tbody>
             <tr>
            <td><span id="letra">Usuario</span></td>
            <td><input type="text" name="j_username" id="fondo-gris"/></td>
             </tr>
             <tr>
            <td><span id="letra">Password</span></td>
            <td><input type="password" name="j_password" id="fondo-gris"/></td>
             </tr>
             <tr>   
            <td colspan="3"><center><input id="botonInciar" type="submit" name="guardar" value="Iniciar Sesión"/></center></td>
         </tr>
          </tbody>
        </table>
     </form>
...

新控制器.java

/**
     * Método que sirve para visualizar la página principal de la aplicación
     * @param modelo
     * @return Un String con el nombre de la página
     * @throws Exception
     */
    @RequestMapping(value = "/index", method = RequestMethod.GET)
    //@RequestMapping(method = RequestMethod.GET)
    public String login(Model modelo) throws Exception {
        //modelo.addAttribute("tituloUsuario", "Listado de Usuarios");

        logger.info("LogginController --> login: ha entrado en el método GET");

        Usuario usuario = new Usuario();

        modelo.addAttribute("usuario", usuario);

        logger.info("LogginController --> login: los resultados del usuario son, userName: " + usuario.getNombreUsuario());

        //return "/principal/loguear";
        return "index";
    }

新的spring-security:securityApplicationContext.xml:

<security:http auto-config="true" use-expressions="true">
        <security:intercept-url pattern="/index" access="permitAll"/>
        <security:intercept-url pattern="/*" access="hasAnyRole('ROLE_USER','ROLE_ADMIN')"/>
        <security:form-login login-page="/index"
                             default-target-url="/principal/usuarios/form.htm"
                             always-use-default-target="true"
                             authentication-failure-url="/index"/>

    </security:http>

    <security:authentication-manager alias="authenticationManager">
        <security:authentication-provider>
            <security:jdbc-user-service data-source-ref="dataSource"/>
        </security:authentication-provider>
    </security:authentication-manager>

如果我这样做,当用户介绍错误的数据时,浏览器不会显示信息,即不正确的用户名/密码组合

如何在浏览器中显示数据?

由于