import HeaderLink from './HeaderLink.astro';

Complete Guide to Spring Framework

A comprehensive guide to Spring Framework, covering everything from core concepts to advanced topics like MVC, REST, persistence, and testing.

Complete Guide to Spring Framework

The Spring Framework is a mature, powerful, and highly flexible framework focused on building web applications in Java. It takes care of most low-level aspects of building applications, allowing developers to focus on features and business logic. With its active maintenance and thriving community, Spring remains at the forefront of Java development.

Table of Contents

  1. Introduction to Spring
  2. Spring Core Basics
  3. Spring MVC
  4. Spring REST
  5. Spring Persistence
  6. Spring Data
  7. Testing with Spring
  8. Spring Security
  9. Spring Cloud

Introduction

Spring Framework is an open-source application framework and inversion of control container for the Java platform. It provides a comprehensive programming and configuration model for modern Java-based enterprise applications.

Key Features

  • Dependency Injection (DI)
  • Aspect-Oriented Programming (AOP)
  • Transaction Management
  • MVC Framework
  • Data Access Framework
  • Security Framework

Spring Core Basics

Inversion of Control (IoC) and Dependency Injection (DI)

Spring’s core feature is its IoC container, which manages the lifecycle and configuration of application objects. Here’s a basic example:

@Service
public class UserService {
    private final UserRepository userRepository;
    
    @Autowired
    public UserService(UserRepository userRepository) {
        this.userRepository = userRepository;
    }
}

Spring Beans

Beans are the objects that form the backbone of your application and are managed by the Spring IoC container.

@Component
public class UserBean {
    private String name;
    private String email;
    
    // Getters and setters
}

Bean Scopes

Spring supports several bean scopes:

  • Singleton (default)
  • Prototype
  • Request
  • Session
  • Application
  • WebSocket
@Component
@Scope("prototype")
public class PrototypeBean {
    // Bean implementation
}

Spring Annotations

Common Spring annotations include:

  • @Component
  • @Service
  • @Repository
  • @Controller
  • @Autowired
  • @Qualifier
  • @Value
  • @Configuration
  • @Bean

Spring MVC

Spring MVC is a web framework built on the Servlet API that follows the Model-View-Controller design pattern.

Basic Controller

@Controller
@RequestMapping("/users")
public class UserController {
    
    @GetMapping("/{id}")
    public String getUser(@PathVariable Long id, Model model) {
        User user = userService.findById(id);
        model.addAttribute("user", user);
        return "user";
    }
    
    @PostMapping
    public String createUser(@ModelAttribute User user) {
        userService.save(user);
        return "redirect:/users";
    }
}

View Resolution

Spring MVC supports various view technologies:

  • JSP
  • Thymeleaf
  • FreeMarker
  • Velocity

Example with Thymeleaf:

<!DOCTYPE html>
<html xmlns:th="http://www.thymeleaf.org">
<head>
    <title>User Details</title>
</head>
<body>
    <h1 th:text="${user.name}">User Name</h1>
    <p th:text="${user.email}">User Email</p>
</body>
</html>

Spring REST

Spring provides excellent support for building RESTful web services.

REST Controller

@RestController
@RequestMapping("/api/users")
public class UserRestController {
    
    @GetMapping("/{id}")
    public ResponseEntity<User> getUser(@PathVariable Long id) {
        User user = userService.findById(id);
        return ResponseEntity.ok(user);
    }
    
    @PostMapping
    public ResponseEntity<User> createUser(@RequestBody User user) {
        User savedUser = userService.save(user);
        return ResponseEntity.created(URI.create("/api/users/" + savedUser.getId()))
                           .body(savedUser);
    }
}

Error Handling

@ControllerAdvice
public class GlobalExceptionHandler {
    
    @ExceptionHandler(UserNotFoundException.class)
    public ResponseEntity<ErrorResponse> handleUserNotFound(UserNotFoundException ex) {
        ErrorResponse error = new ErrorResponse("USER_NOT_FOUND", ex.getMessage());
        return ResponseEntity.status(HttpStatus.NOT_FOUND).body(error);
    }
}

Spring Persistence

Spring provides comprehensive support for data access.

JPA Configuration

@Configuration
@EnableJpaRepositories(basePackages = "com.example.repository")
public class JpaConfig {
    
    @Bean
    public DataSource dataSource() {
        return new EmbeddedDatabaseBuilder()
            .setType(EmbeddedDatabaseType.H2)
            .build();
    }
    
    @Bean
    public LocalContainerEntityManagerFactoryBean entityManagerFactory() {
        LocalContainerEntityManagerFactoryBean em = new LocalContainerEntityManagerFactoryBean();
        em.setDataSource(dataSource());
        em.setPackagesToScan("com.example.entity");
        return em;
    }
}

Transaction Management

@Service
@Transactional
public class UserService {
    
    @Autowired
    private UserRepository userRepository;
    
    public User createUser(User user) {
        return userRepository.save(user);
    }
}

Spring Data

Spring Data makes it easy to work with various data access technologies.

JPA Repository

@Repository
public interface UserRepository extends JpaRepository<User, Long> {
    List<User> findByEmail(String email);
    Optional<User> findByUsername(String username);
}

Custom Queries

@Repository
public interface UserRepository extends JpaRepository<User, Long> {
    @Query("SELECT u FROM User u WHERE u.age > :age")
    List<User> findUsersOlderThan(@Param("age") int age);
}

Testing with Spring

Spring provides comprehensive testing support.

Unit Testing

@SpringBootTest
class UserServiceTest {
    
    @Autowired
    private UserService userService;
    
    @MockBean
    private UserRepository userRepository;
    
    @Test
    void testCreateUser() {
        User user = new User("John", "john@example.com");
        when(userRepository.save(any(User.class))).thenReturn(user);
        
        User savedUser = userService.createUser(user);
        assertNotNull(savedUser);
        assertEquals("John", savedUser.getName());
    }
}

Integration Testing

@SpringBootTest(webEnvironment = WebEnvironment.RANDOM_PORT)
class UserControllerIntegrationTest {
    
    @Autowired
    private TestRestTemplate restTemplate;
    
    @Test
    void testGetUser() {
        ResponseEntity<User> response = restTemplate.getForEntity("/api/users/1", User.class);
        assertEquals(HttpStatus.OK, response.getStatusCode());
        assertNotNull(response.getBody());
    }
}

Spring Security

Spring Security provides comprehensive security services for Java applications.

Basic Security Configuration

@Configuration
@EnableWebSecurity
public class SecurityConfig extends WebSecurityConfigurerAdapter {
    
    @Override
    protected void configure(HttpSecurity http) throws Exception {
        http
            .authorizeRequests()
                .antMatchers("/public/**").permitAll()
                .anyRequest().authenticated()
            .and()
            .formLogin()
                .loginPage("/login")
                .permitAll();
    }
}

OAuth2 Configuration

@Configuration
@EnableOAuth2Client
public class OAuth2Config {
    
    @Bean
    public OAuth2RestTemplate oauth2RestTemplate(OAuth2ClientContext oauth2ClientContext,
                                               OAuth2ProtectedResourceDetails details) {
        return new OAuth2RestTemplate(details, oauth2ClientContext);
    }
}

Spring Cloud

Spring Cloud provides tools for common distributed system patterns.

Service Discovery

@SpringBootApplication
@EnableDiscoveryClient
public class UserServiceApplication {
    public static void main(String[] args) {
        SpringApplication.run(UserServiceApplication.class, args);
    }
}

Circuit Breaker

@Service
public class UserService {
    
    @CircuitBreaker(name = "userService")
    public User getUser(Long id) {
        return userRepository.findById(id)
            .orElseThrow(() -> new UserNotFoundException(id));
    }
}

Best Practices

  1. Use constructor injection over field injection
  2. Follow the single responsibility principle
  3. Use appropriate annotations
  4. Implement proper exception handling
  5. Write comprehensive tests
  6. Use Spring profiles for different environments
  7. Implement proper logging
  8. Follow security best practices

Conclusion

Spring Framework provides a robust foundation for building enterprise applications. Its modular architecture, comprehensive features, and active community make it an excellent choice for Java development.

Resources

Remember that Spring is constantly evolving, so always check the latest documentation for updates and new features. Happy coding!