September 3, 2026

InventoryMS – SpringBoot Roles and Privileges 3 (Implementing Granted Authorities)

Learn how to implement SpringBoot roles and privileges with Granted Authorities, design secure REST API routes, and restrict access using hasAuthority().

TL;DR

  • Granted Authorities represent the privileges or permissions a user has in Spring Security.

  • hasRole() and hasAuthority() are similar, but roles use the ROLE_ prefix while authorities do not.

  • A clear REST API route hierarchy makes it easier to apply authorization at a granular level.

  • UserPrincipal can return a user’s privileges as SimpleGrantedAuthority objects through getAuthorities().

  • hasAuthority() can then protect specific API endpoints based on privileges such as VIEW_PRODUCT and CREATE_PRODUCT.

This is Part 3 of our implementation of SpringBoot roles and Privileges for our Inventory Management System (InventoryMS). In this part we would discuss and implement granted authorities in Spring Boot.

Parts 1 and 2 can be gotten from the links:

 

1. What are Granted Authorities?

In Spring Security, we have the concept of Granted Authority. This represents a privilege or a permission granted to a user to perform a certain action.

What is difference between Role and Authority?

This two represent the same concept and are basically the same. The difference is how Spring Boot handle the prefixing. A role is expected to be prefixed with “ROLE_” but an authority is not.

For example, the authority “ADMIN” is the same as the role “ROLE_ADMIN”.

hasRole() vs hasAuthority()

This is also the same in concept. When you use hasRole(“ADMIN”), Spring Boot would expect that your role is named “ROLE_ADMIN”. However, if you use hasAuthority(“ADMIN”), Spring Boot would check if you have to role “ADMIN”

In our InventoryMS project, we would be using hasAuthority().

 

2. Design the REST API Endpoint Pattern

To be able to achieve and efficient way to protect your API, you will have to design the routing pattern. What does this mean? It means you need some hierarchy for the API route. For example:

  • top level: version number would (/v1)
  • next level: modules for example, /orders, /products and /suppliers
  • from here you can have methods GET, POST, PUT and DELETE

With this we would be able provide authorization at a granular level

 

3. Retrieving the User’s GrantedAuthorities

To be able to protect our REST API based on user roles, we would have to do the following:

return the users authorities (privileges) from UserPrincipal

Here, we would need to update the getAuthorities method of the UserPrincipal class so that it returns a lit of SimpleGrantedAuthorities.

@Override
public Collection<? extends GrantedAuthority> getAuthorities() {
    return userPrivilegeAssignmentService.getUserPrivileges(user.getId())
            .stream()
            .map(privilege -> new SimpleGrantedAuthority(privilege.getDescription())) // Use SimpleGrantedAuthority
            .collect(Collectors.toList());
}

 

4. Configure Authorization Rules

At this point we would have to configure the permission on the routes. So we would have to check if the user has the required authority before the request is permitted.

The following changes would need to be made:

...
...
.authorizeHttpRequests(auth -> auth
                .requestMatchers("/register").permitAll()
                .requestMatchers("/login").permitAll()
                
                //Configuration for the product module
                .requestMatchers(HttpMethod.GET, "/api/v1/products").hasAuthority("VIEW_PRODUCT")
                .requestMatchers(HttpMethod.POST, "/api/v1/products").hasAuthority("CREATE_PRODUCT")
                .requestMatchers(HttpMethod.DELETE, "api/vi/product").hasAuthority("DELETE_PRODUCT")
                
                //Configuration for the order module
                .requestMatchers(HttpMethod.GET, "/api/v1/products").hasAuthority("VIEW_PRODUCT")
                .requestMatchers(HttpMethod.POST, "/api/v1/products").hasAuthority("CREATE_PRODUCT")                                
                .anyRequest().authenticated()
        )
...
...

Then we would have to repeat this for all other roles we identified.

You could also create an enum type to hold these roles instead of using just strings. But I see no added benefits for taking this extra step.

Note that in our application, we use Roles only as grouping for privileges.

Frequently Asked Questions

What is a Granted Authority in Spring Security?

A Granted Authority represents a permission or privilege that allows a user to perform a specific action within an application.

What is the difference between a role and an authority?

They represent similar concepts, but Spring Security handles their naming differently. Roles are typically prefixed with ROLE_, while authorities do not require that prefix.

What is the difference between hasRole() and hasAuthority()?

hasRole("ADMIN") checks for ROLE_ADMIN, while hasAuthority("ADMIN") checks for the authority named ADMIN.

Why does InventoryMS use hasAuthority()?

InventoryMS uses privileges as the actual permissions for API access, with roles serving primarily as groups for those privileges. hasAuthority() therefore fits the application’s fine-grained authorization model.

How does UserPrincipal provide authorities?

The getAuthorities() method retrieves the user’s privileges and converts each one into a SimpleGrantedAuthority, which Spring Security can use when evaluating authorization rules.

Why is API route design important for authorization?

A consistent hierarchy such as version → module → HTTP method makes it easier to apply specific permissions to individual API operations.

Final Thoughts

Granted Authorities provide the connection between the privileges defined in InventoryMS and the actual security rules protecting its API. Once a user’s privileges are exposed through UserPrincipal, Spring Security can use those authorities to decide which operations the user is allowed to perform.

Using hasAuthority() also supports the fine-grained approach established in the earlier parts of this series. Instead of treating roles as the final permission, InventoryMS uses roles to group privileges while individual authorities control access to specific API operations.

With a consistent REST API structure and clearly defined privileges such as VIEW_PRODUCT, CREATE_PRODUCT, and DELETE_PRODUCT, you have a flexible foundation for controlling access across the application’s modules.

 

Kindson Munonye

Kindson Munonye is a software engineer and technical author covering machine learning, statistics, REST APIs, Python, and software engineering. He publishes free tutorials on The Genius Blog and live classes on Alkademy. GitHub · LinkedIn · About · Alkademy

View all posts by Kindson Munonye →
0 0 votes
Article Rating
Subscribe
Notify of
guest

0 Comments
Oldest
Newest Most Voted