Spring Security is based on Authorities.
User is first Authenticated through combination of its Username and Password.
Then Spring creates User Object that contains list of Authorities that are assigned to that user (from DB for instance).
These Authorities can then be used inside the Controller to control access to the endpoints.
Roles are just Authorities whose name starts with prefix ROLE_.
Inside the Controller you check for Roles and Authorities by using Annotations and Methods.
Some of these Annotations and Methods are specialized to be used only to look for Roles
● @Secured("ADMIN") is specialized Annotations that looks for Authority named ROLE_ADMIN
● hasRole() in @PreAuthorize("hasRole('ADMIN')") is specialized Method that looks for Authority named ROLE_ADMIN
This Method has the same effect as using @PreAuthorize("hasAuthority('ROLE_ADMIN')").
Roles can be used on their own to control access to endpoints.
Alternatively Roles can be used as containers for Authorities.
Inside DB you assign Roles to Users and then you assign Authorities to these Roles (through @ManyToMany Relationship)
Then when creating User Object you load it with Authorities that are related to Roles of Authenticated User.
You can also add Roles to list of User Authorities.
This might be useful to detect from which Roles those Authorities came from.
For instance both ADMIN and USER Roles might have book.read Authority
● But if book.read Authority came from ADMIN Role then Admin can read any book (so no other checks are necessary).
● But if book.read Authority came from USER Role then User can only read his own books.
In that case an additional check is needed through Custom Authorization where we compare ID of current User with
User ID assigned to the Book, and allow access to endpoint only if these two IDs match (if User owns the Book).