Java 迁移到Spring Security 4获得访问权限指定页面

Java 迁移到Spring Security 4获得访问权限指定页面,java,spring,spring-mvc,spring-security,Java,Spring,Spring Mvc,Spring Security,我目前正在迁移到spring sec 4,但遇到了麻烦。 下面是我的背景 我的security.xml文件 <?xml version="1.0" encoding="UTF-8"?> <beans xmlns="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:security="htt

我目前正在迁移到spring sec 4,但遇到了麻烦。 下面是我的背景

我的security.xml文件

    <?xml version="1.0" encoding="UTF-8"?>  
<beans xmlns="http://www.springframework.org/schema/beans"
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"  
    xmlns:security="http://www.springframework.org/schema/security"  
    xmlns:p="http://www.springframework.org/schema/p"   
    xsi:schemaLocation="
        http://www.springframework.org/schema/beans  
        http://www.springframework.org/schema/beans/spring-beans.xsd  
        http://www.springframework.org/schema/security  
        http://www.springframework.org/schema/security/spring-security.xsd">

    <!-- Exclude all files and folders under resources for security -->
    <security:http pattern="/resources/**" security="none" />

    <security:http  auto-config="true" disable-url-rewriting="false">
        <security:headers disabled="true"/>
        <security:csrf disabled="true"/>
        <security:intercept-url pattern="/login" access="permitAll"/>
        <security:intercept-url pattern="/**" access="hasAnyRole('RS001', 'RS002', 'RS003')"/>      
        <security:form-login login-page="/login"/>
        <security:logout logout-success-url="/login"/> 
    </security:http>

    <bean id="userDetailService" class="vm.security.UserDetailServiceImpl" />

    <!-- For hashing and salting the password -->
    <bean id="encoder" class="org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder"/>

    <security:authentication-manager>
        <security:authentication-provider ref="authProvider"></security:authentication-provider>        
    </security:authentication-manager> 

    <bean id="authProvider" class="org.springframework.security.authentication.dao.DaoAuthenticationProvider">
        <property name="userDetailsService" ref="userDetailService" />
        <property name="passwordEncoder" ref="encoder" />
    </bean>

    <!-- To load the message properties for overwrite default spring security error message -->
    <bean id="messageSource" class="org.springframework.context.support.ReloadableResourceBundleMessageSource">
        <property name="basename" value="classpath:message"/>
    </bean>

</beans>

自定义用户详细信息服务

        package vm.security;

    import java.util.ArrayList;
    import java.util.Date;
    import java.util.List;

    import org.apache.log4j.Logger;
    import org.springframework.beans.factory.annotation.Autowired;
    import org.springframework.security.core.GrantedAuthority;
    import org.springframework.security.core.authority.SimpleGrantedAuthority;
    import org.springframework.security.core.userdetails.User;
    import org.springframework.security.core.userdetails.UserDetails;
    import org.springframework.security.core.userdetails.UserDetailsService;
    import org.springframework.security.core.userdetails.UsernameNotFoundException;

    import vm.data.dto.VmAccount;
    import vm.data.dto.VmSystemResource;
    import vm.exception.VmException;
    import vm.service.AuditLogService;
    import vm.service.UserAccountService;
    import vm.util.PropertiesConstants;

    public class UserDetailServiceImpl implements UserDetailsService {

        private static final Logger logger= Logger.getLogger(UserDetailServiceImpl.class);

        @Autowired
        private AuditLogService auditLogService;

        @Autowired
        private PropertiesConstants propertiesConstants;

        @Autowired
        private UserAccountService userAccountService;

        @Override
        public UserDetails loadUserByUsername(String userid) throws UsernameNotFoundException{
            try{
                VmAccount account = userAccountService.getVmAccountById(userid);
                if(account != null){
                    List<VmSystemResource> systemResourceList = userAccountService.getUserSystemResources(userid);
                    List<GrantedAuthority> roles= new ArrayList<GrantedAuthority>();
                    for(VmSystemResource resource : systemResourceList)
                        roles.add(new SimpleGrantedAuthority(resource.getResourceId()));
                    UserDetails user = new User(account.getUserid(), account.getPwd(), (account.getStatus().equals(propertiesConstants.getCoreStatusActive()) ? true : false), true, true, true, roles);

                    logger.info(roles);
                    auditLogService.addAuditDetails(userid, new Date(), propertiesConstants.getAuthentication(), propertiesConstants.getLoginSucceed());
                    return user;
                }
                throw new UsernameNotFoundException(userid + " not found."); 
            }catch (VmException ce){
                logger.error(ce.getErrorCode(),ce);
                throw new UsernameNotFoundException(ce.getErrorCode() + ":userid object is null");
            }

        }
    }
包vm.security;
导入java.util.ArrayList;
导入java.util.Date;
导入java.util.List;
导入org.apache.log4j.Logger;
导入org.springframework.beans.factory.annotation.Autowired;
导入org.springframework.security.core.GrantedAuthority;
导入org.springframework.security.core.authority.SimpleGrantedAuthority;
导入org.springframework.security.core.userdetails.User;
导入org.springframework.security.core.userdetails.userdetails;
导入org.springframework.security.core.userdetails.userdetails服务;
导入org.springframework.security.core.userdetails.UsernameNotFoundException;
导入vm.data.dto.VmAccount;
导入vm.data.dto.VmSystemResource;
导入vm.exception.VmException;
导入vm.service.AuditLogService;
导入vm.service.UserAccountService;
导入vm.util.PropertiesConstants;
公共类UserDetailServiceImpl实现UserDetailsService{
私有静态最终记录器Logger=Logger.getLogger(UserDetailServiceImpl.class);
@自动连线
私有AuditLogService AuditLogService;
@自动连线
私人财产;私人财产;
@自动连线
私人用户帐户服务用户帐户服务;
@凌驾
public UserDetails loadUserByUsername(字符串userid)引发UsernameNotFoundException{
试一试{
VmAccount=userAccountService.getVmAccountById(userid);
如果(帐户!=null){
List systemResourceList=userAccountService.getUserSystemResources(用户ID);
列表角色=新的ArrayList();
用于(VmSystemResource资源:systemResourceList)
添加(新的SimpleGrantedAuthority(resource.getResourceId());
UserDetails user=新用户(account.getUserid(),account.getPwd(),(account.getStatus().equals(propertiesConstants.getCoreStatusActive())?true:false),true,true,true,roles);
logger.info(角色);
auditLogService.addAuditDetails(userid,new Date(),propertiesConstants.getAuthentication(),propertiesConstants.getLoginsAcceed());
返回用户;
}
抛出新的UsernameNotFoundException(userid+“未找到”);
}捕获(VMCE异常){
logger.error(ce.getErrorCode(),ce);
抛出新的UsernameNotFoundException(ce.getErrorCode()+“:userid对象为null”);
}
}
}
Login.jsp

<!DOCTYPE html>
<html lang="en">
    <head>      
        <link href="${pageContext.request.contextPath}/resources/css/bootstrap-3.3.4.min.css" rel="stylesheet">
        <style type="text/css">
            /* For nav header not to overlap*/
            body {
                padding-top:150px;  
                background-color: #eee;                 
            }                                   
        </style>                            
    </head>
    <body>              
        <div class="container"> 
            <div class="row">
                <div class="col-xs-6 col-xs-offset-3">
                    <div class="panel panel-primary">

                        <div class="panel-body">
                            <form id="creForm" class="form-horizontal" method="post" action="${pageContext.request.contextPath}/login">
                                <div id="errPanel" class="form-group">
                                    <div class="col-xs-8 col-xs-offset-3">
                                        <span style="color: red;">${sessionScope["SPRING_SECURITY_LAST_EXCEPTION"].message}</span>
                                    </div>
                                </div>
                                <div class="form-group">
                                    <label class="col-xs-4 control-label" for="userid">USERID:</label>
                                    <div class="col-xs-6">
                                        <input name="username" type="text" class="form-control" placeholder="USERID" />
                                    </div>
                                </div>                      
                                <div class="form-group">
                                    <label class="col-xs-4 control-label" for="name">PASSWORD:</label>
                                    <div class="col-xs-6">
                                         <input name="password" type="password" class="form-control" placeholder="PASSWORD" />
                                    </div>
                                </div>
                                <div class="form-group">
                                    <div class="col-xs-6 col-xs-offset-4">                                          
                                        <button type="submit" class="btn btn-primary">SIGN IN</button>
                                    </div>
                                </div>                                                                      
                            </form>
                        </div>
                        <div class="panel-footer"> 
                        </div>
                    </div>
                </div>
            </div>
        </div>              
    </body>
</html>

/*导航标头不重叠*/
身体{
填充顶部:150px;
背景色:#eee;
}                                   
${sessionScope[“SPRING\u SECURITY\u LAST\u EXCEPTION”].message}
用户标识:
密码:
登录
我的问题是,当我用旧版本SpringSecurity3.2.7替换时,它工作正常。 但SpringSecurity4总是让我进入拒绝访问页面。
希望有人能帮助我。

Spring Security 4对默认设置进行了几处更改,同时也进行了一些更改,以使行为更加一致。您正在运行对一致性()所做的更改,这意味着所有的
hasRole
(及其派生)现在都在使用默认的
role
角色前缀作为传入参数的前缀,而Spring3.2之前的情况并非如此(但在其他地方也是如此)

要修复此问题,您有3个选项

  • 按照迁移指南中的说明执行,或
  • 转换角色时,只需在角色前面加上
    角色
  • 使用而不是
    hasAnyRole

  • 检查您添加的依赖项。可能是JAR与spring security 3.2.7不兼容。您有自定义登录页面吗?如果是这样,请确保相应地更改了URL和输入字段。。。(默认设置已更改)。@VigNesh我使用的是SpringMVC4.1.6和SpringSecurity 4.0.2。另外,我只是把我需要的每一个依赖项都放进去。@M.Deinum。我已根据迁移指南更改了登录页面,但仍然无法工作。问题是我无法获取访问的角色:(使用
    hasRole
    (或相关)时,传入的值得到p