RBAC Permission Analysis and Spring Security Implementation Guide (including JWT and JSON Login)
This article explains the fundamentals of Role‑Based Access Control (RBAC), its model variants, permission concepts, and user‑group usage, then demonstrates practical Spring Security setups ranging from simple in‑memory authentication to JWT integration, JSON‑based login, password encryption, and database‑backed authentication with full code examples.
This document provides a comprehensive overview of Role‑Based Access Control (RBAC), starting with a definition of RBAC and its purpose of linking users, roles, and permissions to simplify permission management.
RBAC Model Classification
The RBAC models are described as follows:
RBAC0 – the basic model, supporting many‑to‑one and many‑to‑many relationships between users and roles.
RBAC1 – adds role hierarchies (sub‑roles) and inheritance.
RBAC2 – extends RBAC0 with constraints such as role separation (mutual exclusion), cardinality limits, and prerequisite roles.
RBAC3 – combines all previous features into a unified model.
Examples illustrate how a user can hold multiple roles (e.g., an employee acting as both administrator and finance officer) and how constraints prevent conflicting role assignments.
Permission Definition
Permissions are defined as the set of resources a user can access or manipulate, such as page navigation, data CRUD operations, and specific functional modules in a system.
User Group Usage
User groups allow bulk assignment of roles to many users, reducing administrative effort and improving manageability.
Spring Security – Simple Usage
To start using Spring Security, add the dependency:
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-security</artifactId>
</dependency>Create a test controller:
package com.example.demo.web;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
@RestController
@RequestMapping("/test")
public class Test {
@RequestMapping("/test")
public String test(){
return "test";
}
}Configure an in‑memory user in application.yml:
spring:
security:
user:
name: ming
password: 123456
roles: adminRun the application and log in with the defined credentials.
In‑Memory Authentication Example
package com.example.demo.config;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.security.config.annotation.authentication.builders.AuthenticationManagerBuilder;
import org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter;
import org.springframework.security.crypto.password.NoOpPasswordEncoder;
import org.springframework.security.crypto.password.PasswordEncoder;
@Configuration
public class MyWebSecurityConfig extends WebSecurityConfigurerAdapter {
@Bean
PasswordEncoder passwordEncoder(){
return NoOpPasswordEncoder.getInstance();
}
@Override
protected void configure(AuthenticationManagerBuilder auth) throws Exception {
auth.inMemoryAuthentication()
.withUser("admin").password("123").roles("admin");
}
}Spring Security with JWT Integration
Add the following Maven dependencies:
<!-- JWT -->
<dependency>
<groupId>io.jsonwebtoken</groupId>
<artifactId>jjwt</artifactId>
<version>0.9.1</version>
</dependency>
<!-- Spring Security -->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-security</artifactId>
<version>2.3.1.RELEASE</version>
</dependency>Create a JwtUser class implementing UserDetails:
package com.example.demo;
import org.springframework.security.core.GrantedAuthority;
import org.springframework.security.core.userdetails.UserDetails;
import java.util.Collection;
public class JwtUser implements UserDetails {
private String username;
private String password;
private Integer state;
private Collection<? extends GrantedAuthority> authorities;
// constructors, getters, and overridden methods omitted for brevity
}Utility class for token generation and validation:
package com.example.demo;
import io.jsonwebtoken.*;
import org.springframework.security.core.userdetails.UserDetails;
import java.util.*;
public class JwtTokenUtil implements Serializable {
private String secret;
private Long expiration;
private String header;
// token creation, parsing, validation methods omitted for brevity
}JWT authentication filter:
package com.example.demo;
import org.springframework.security.web.authentication.OncePerRequestFilter;
import javax.servlet.*;
import java.io.IOException;
public class JwtAuthenticationTokenFilter extends OncePerRequestFilter {
// filter logic that extracts token, validates it, and sets authentication
}Configure Spring Security to use the JWT filter and stateless session management:
@EnableWebSecurity
public class WebSecurity extends WebSecurityConfigurerAdapter {
@Autowired private UserDetailsService userDetailsService;
@Autowired private JwtAuthenticationTokenFilter jwtAuthenticationTokenFilter;
@Override
protected void configure(HttpSecurity http) throws Exception {
http.csrf().disable()
.sessionManagement().sessionCreationPolicy(SessionCreationPolicy.STATELESS)
.and().authorizeRequests()
.antMatchers(HttpMethod.OPTIONS, "/**").permitAll()
.antMatchers("/auth/**").permitAll()
.anyRequest().authenticated()
.and().addFilterBefore(jwtAuthenticationTokenFilter, UsernamePasswordAuthenticationFilter.class);
}
}JSON‑Based Login
Override UsernamePasswordAuthenticationFilter to read JSON payloads:
public class CustomAuthenticationFilter extends UsernamePasswordAuthenticationFilter {
@Override
public Authentication attemptAuthentication(HttpServletRequest request, HttpServletResponse response) throws AuthenticationException {
if (MediaType.APPLICATION_JSON_VALUE.equals(request.getContentType())) {
ObjectMapper mapper = new ObjectMapper();
try (InputStream is = request.getInputStream()) {
AuthenticationBean bean = mapper.readValue(is, AuthenticationBean.class);
UsernamePasswordAuthenticationToken authRequest = new UsernamePasswordAuthenticationToken(bean.getUsername(), bean.getPassword());
setDetails(request, authRequest);
return this.getAuthenticationManager().authenticate(authRequest);
} catch (IOException e) {
return super.attemptAuthentication(request, response);
}
}
return super.attemptAuthentication(request, response);
}
}Register the custom filter in the security configuration and map it to /login/self:
@Bean
public CustomAuthenticationFilter customAuthenticationFilter() throws Exception {
CustomAuthenticationFilter filter = new CustomAuthenticationFilter();
filter.setAuthenticationSuccessHandler(new SuccessHandler());
filter.setAuthenticationFailureHandler(new FailureHandler());
filter.setFilterProcessesUrl("/login/self");
filter.setAuthenticationManager(authenticationManagerBean());
return filter;
}Password Encryption
Define a BCrypt password encoder bean:
@Bean
public BCryptPasswordEncoder passwordEncoder(){
return new BCryptPasswordEncoder();
}Use the encoder when storing or verifying passwords, e.g.:
user.setPassword(bCryptPasswordEncoder.encode(user.getPassword()));
if (!bCryptPasswordEncoder.matches(rawPassword, storedHash)) { /* authentication fails */ }Database‑Backed Authentication
Implement UserDetailsService to load users from a database and configure Spring Security to use it:
@Service
public class JwtUserDetailsServiceImpl implements UserDetailsService {
@Autowired private UserMapper userMapper;
@Override
public UserDetails loadUserByUsername(String username) throws UsernameNotFoundException {
User user = userMapper.selectByUserName(username);
if (user == null) throw new UsernameNotFoundException("User not found");
List<SimpleGrantedAuthority> authorities = user.getRoles().stream()
.map(Role::getRolename)
.map(SimpleGrantedAuthority::new)
.collect(Collectors.toList());
return new JwtUser(user.getUsername(), user.getPassword(), user.getState(), authorities);
}
}Configure the security adapter to use this service and define role‑based URL restrictions.
Conclusion
The article walks through RBAC theory, its model variants, permission and user‑group concepts, then provides step‑by‑step code for Spring Security basics, in‑memory authentication, JWT token handling, JSON login, password encryption with BCrypt, and database‑backed authentication, giving a full picture of implementing secure access control in Java applications.
Signed-in readers can open the original source through BestHub's protected redirect.
This article has been distilled and summarized from source material, then republished for learning and reference. If you believe it infringes your rights, please contactand we will review it promptly.
Architecture Digest
Focusing on Java backend development, covering application architecture from top-tier internet companies (high availability, high performance, high stability), big data, machine learning, Java architecture, and other popular fields.
How this landed with the community
Was this worth your time?
0 Comments
Thoughtful readers leave field notes, pushback, and hard-won operational detail here.
