使用 Spring Security 3.1 对 Active Directory 进行身份验证时处理角色
我正在尝试使用 Spring Security 3.1 对 Active Directory 进行身份验证。 我得到了身份验证,一切都很好。
<sec:ldap-server id="ldapServer" url="ldap://ldap/dc=sub,dc=domain,dc=com" port="389" />
<sec:authentication-manager erase-credentials="true" >
<sec:authentication-provider ref="ldapActiveDirectoryAuthProvider" />
</sec:authentication-manager>
<bean id="ldapActiveDirectoryAuthProvider"
class="org.springframework.security.ldap.authentication.ad.ActiveDirectoryLdapAuthenticationProvider">
<constructor-arg value="domain" />
<constructor-arg value="ldap://server:389/"/>
</bean>
现在回答问题。如何处理用户的角色以便我可以设置过滤器?
例如。
<sec:intercept-url pattern="/**" access="ROLE_USER"/>
解决方案
我找到了如何使用 UserDetailContextMapper 并将我的 AD 组映射到 ROLE_USER、ROLE_ADMIN 等
<bean id="ldapActiveDirectoryAuthProvider"
class="org.springframework.security.ldap.authentication.ad.ActiveDirectoryLdapAuthenticationProvider">
<constructor-arg value="domain" />
<constructor-arg value="ldap://host:389/"/>
<property name="userDetailsContextMapper" ref="tdrUserDetailsContextMapper"/>
<property name="useAuthenticationRequestCredentials" value="true"/>
</bean>
<bean id="tdrUserDetailsContextMapper" class="com.bla.bla.UserDetailsContextMapperImpl"/>
Mapper 类:
public class UserDetailsContextMapperImpl implements UserDetailsContextMapper, Serializable{
private static final long serialVersionUID = 3962976258168853954L;
@Override
public UserDetails mapUserFromContext(DirContextOperations ctx, String username, Collection<? extends GrantedAuthority> authority) {
List<GrantedAuthority> mappedAuthorities = new ArrayList<GrantedAuthority>();
for (GrantedAuthority granted : authority) {
if (granted.getAuthority().equalsIgnoreCase("MY USER GROUP")) {
mappedAuthorities.add(new GrantedAuthority(){
private static final long serialVersionUID = 4356967414267942910L;
@Override
public String getAuthority() {
return "ROLE_USER";
}
});
} else if(granted.getAuthority().equalsIgnoreCase("MY ADMIN GROUP")) {
mappedAuthorities.add(new GrantedAuthority() {
private static final long serialVersionUID = -5167156646226168080L;
@Override
public String getAuthority() {
return "ROLE_ADMIN";
}
});
}
}
return new User(username, "", true, true, true, true, mappedAuthorities);
}
@Override
public void mapUserToContext(UserDetails arg0, DirContextAdapter arg1) {
}
}
I'm trying to use a authenticate with an Active directory using Spring Security 3.1.
I get authenticated and all is well.
<sec:ldap-server id="ldapServer" url="ldap://ldap/dc=sub,dc=domain,dc=com" port="389" />
<sec:authentication-manager erase-credentials="true" >
<sec:authentication-provider ref="ldapActiveDirectoryAuthProvider" />
</sec:authentication-manager>
<bean id="ldapActiveDirectoryAuthProvider"
class="org.springframework.security.ldap.authentication.ad.ActiveDirectoryLdapAuthenticationProvider">
<constructor-arg value="domain" />
<constructor-arg value="ldap://server:389/"/>
</bean>
Now to the question. How do I handle roles for the user so that I can setup my filters?
eg.
<sec:intercept-url pattern="/**" access="ROLE_USER"/>
Solution
I found out how to do this by using the UserDetailContextMapper and map my AD groups to ROLE_USER,ROLE_ADMIN etc.
<bean id="ldapActiveDirectoryAuthProvider"
class="org.springframework.security.ldap.authentication.ad.ActiveDirectoryLdapAuthenticationProvider">
<constructor-arg value="domain" />
<constructor-arg value="ldap://host:389/"/>
<property name="userDetailsContextMapper" ref="tdrUserDetailsContextMapper"/>
<property name="useAuthenticationRequestCredentials" value="true"/>
</bean>
<bean id="tdrUserDetailsContextMapper" class="com.bla.bla.UserDetailsContextMapperImpl"/>
Mapper class:
public class UserDetailsContextMapperImpl implements UserDetailsContextMapper, Serializable{
private static final long serialVersionUID = 3962976258168853954L;
@Override
public UserDetails mapUserFromContext(DirContextOperations ctx, String username, Collection<? extends GrantedAuthority> authority) {
List<GrantedAuthority> mappedAuthorities = new ArrayList<GrantedAuthority>();
for (GrantedAuthority granted : authority) {
if (granted.getAuthority().equalsIgnoreCase("MY USER GROUP")) {
mappedAuthorities.add(new GrantedAuthority(){
private static final long serialVersionUID = 4356967414267942910L;
@Override
public String getAuthority() {
return "ROLE_USER";
}
});
} else if(granted.getAuthority().equalsIgnoreCase("MY ADMIN GROUP")) {
mappedAuthorities.add(new GrantedAuthority() {
private static final long serialVersionUID = -5167156646226168080L;
@Override
public String getAuthority() {
return "ROLE_ADMIN";
}
});
}
}
return new User(username, "", true, true, true, true, mappedAuthorities);
}
@Override
public void mapUserToContext(UserDetails arg0, DirContextAdapter arg1) {
}
}
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(2)
您还可以注入
GrantedAuthoritiesMapper
,它是在 3.1 中引入的,作为修改权限的通用策略。另外,您可能希望使用SimpleGrantedAuthority
来实现GrantedAuthority
。或者,您可以使用枚举,因为您有一组固定的值:You can also inject a
GrantedAuthoritiesMapper
which was introduced in 3.1 as a general strategy for modifying the authorites. Plus you might want to useSimpleGrantedAuthority
for theGrantedAuthority
implementation. Alternatively, you could use an enum since you have a fixed set of values:beans.xml 中的角色必须与memberOf 值属性的CN(通用名称)完全匹配。您应该阅读有关目录基础知识的教程。
假设有这个用户:
CN=Michael-O,OU=用户,OU=部门,DC=子,DC=公司,DC=net
在他的上下文中存在这个memberOf值
CN=Group Name,OU=Permissions,OU=Groups,OU=department,DC=sub,DC=company,DC=net
Bean将找到这个memberOf值并提取
组名称
。 beans.xml 必须具有这个值。The roles in the beans.xml must be an exact match of the CN (common name) of the memberOf value attribute. You should read a tutorial about directory basics.
Say have this user:
CN=Michael-O,OU=Users,OU=department,DC=sub,DC=company,DC=net
In his context exists this memberOf value
CN=Group Name,OU=Permissions,OU=Groups,OU=department,DC=sub,DC=company,DC=net
The Bean will locate this memberOf value and extract
Group Name
. You beans.xml has to have exactly this value.