Question

In my applications I usually create three tables for access management. Roles, Rights and an association table that maps between Roles and Rights.

I am trying to translate this approach to Spring security and after reading [this article][1] I thought I was on the right track. I created a custom AuthenticationProvider and implemented the authenticate() method like so:

@Override
public Authentication authenticate(Authentication authentication) throws AuthenticationException {
    UserProfile profile = userProfileService.findByEmail(authentication.getPrincipal().toString());

    if(profile == null){
        throw new UsernameNotFoundException(String.format("Invalid credentials", authentication.getPrincipal()));
    }

    String suppliedPasswordHash = DigestUtils.shaHex(authentication.getCredentials().toString());

    if(!profile.getPasswordHash().equals(suppliedPasswordHash)){
        throw new BadCredentialsException("Invalid credentials");
    }

    UsernamePasswordAuthenticationToken token = new UsernamePasswordAuthenticationToken(profile, null, profile.getAuthorities());

    return token;
}

The profile.getAuthorities() method creates a list of Rights (rights are wrapped in my own implementation of GrantedAuthority). So, the UsernamePasswordAuthenticationToken object is created with this list. This is the UserProfile.getGrantedAuthorities() method that takes care of this:

public Collection<? extends GrantedAuthority> getAuthorities() {
    Set<ProduxAuthority> authorities = new HashSet<ProduxAuthority>();
    for (Role role : roles) {
        for (Right right : role.getRights()) {
            ProduxAuthority produxAuthority = new ProduxAuthority(right.getName());
            authorities.add(produxAuthority);
        }
    }
    return authorities;
}

My question is whether this is a correct approach. I am getting the impression that I should stuff roles into GrantedAuthorities instead of rights, but I would like to use rights to secure methods and urls, because it gives me more fine grained control over authorization. How would I accomplish this? And what is the difference between a ROLE and a PERMISSION in Spring? Do permissions map to rights and could I use hasPermission() to secure stuff bases on rights instead of roles?

Was it helpful?

Solution

I am going to answer my own question again:

Spring doesn't know rights and permissions that are used by the hasPermission method apply only to the relatively complex Domain Object Security/ACL in Spring security. Spring's simple security knows just roles and roles or more generic "permissions" (in the general sense of the word, not to be confused with permissions in Domain Object Security/ACL) like IS_AUTHENTICATED_ANONYMOUSLY are handed to Spring in the third constructor parameter of the Authentication object's.

I summerized everything on my own website and created an example implementation that stuffs rights into roles and in that way still manages to be pretty flexible.

http://en.tekstenuitleg.net/blog/spring-security-with-roles-and-rights

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top