Top 22 Spring Boot Interview Questions for 2–5 Years Experience (2026 Edition)
When interviewing for a mid-level Java backend role (2–5 years of experience), hiring managers assume you already know how to build a basic CRUD API. The interview will focus heavily on production troubleshooting, architectural decisions, and modern Spring Boot 3.x capabilities.
- Familiarity with Spring Boot 3.x updates (Java 21 Virtual Threads, AOT Compilation, RestClient).
- Deep understanding of the Spring Data JPA N+1 problem, Proxies, and Transaction Management.
- Ability to design clean, stateless, and idempotent REST APIs.
- Enterprise awareness (Testing with Testcontainers, securing Actuator endpoints).
1️⃣ Core Spring Boot & Spring Boot 3.x Features
1. How does Spring Boot Auto-Configuration work under the hood?
Spring Boot utilizes the @EnableAutoConfiguration annotation. At startup, it scans the classpath for specific jars and automatically registers beans based on dynamic conditions.
In modern Spring Boot 3.x, the framework looks for the META-INF/spring/org.springframework.boot.autoconfigure.AutoConfiguration.imports file to find these classes. They use conditional annotations such as @ConditionalOnClass, @ConditionalOnMissingBean, and @ConditionalOnProperty to decide if a bean should actually be created.
spring.factories. Spring Boot 2.7 deprecated it, and Spring Boot 3 entirely removed it in favor of the .imports file. Pointing this out proves your knowledge is up-to-date!
2. How do you enable Virtual Threads (Project Loom) in Spring Boot, and why?
Virtual Threads (introduced natively in Java 21 and Spring Boot 3.2) solve the traditional "thread-per-request" bottleneck. Traditional OS threads are heavy and block the CPU during database or network calls. Virtual threads are lightweight, allowing a standard Tomcat server to handle hundreds of thousands of concurrent connections without the steep learning curve of Reactive Programming (WebFlux).
To enable them, add this single property to application.properties:
spring.threads.virtual.enabled=true
3. What is AOT Compilation and GraalVM Native Image support?
Spring Boot 3 introduced native support for GraalVM using Ahead-of-Time (AOT) compilation. Instead of running on a traditional JVM, AOT translates the Java application into a standalone native executable at build time. This provides near-instant startup times (milliseconds) and drastically reduced memory footprints, making it perfect for serverless environments and Kubernetes scaling.
4. RestTemplate vs WebClient vs RestClient?
RestTemplate: The legacy, synchronous HTTP client. It is currently in maintenance mode.
WebClient: The reactive, non-blocking client introduced in Spring WebFlux. Great for high concurrency but requires learning Project Reactor.
RestClient: Introduced in Spring Boot 3.2, it is a modern, fluent, synchronous HTTP client designed to replace RestTemplate. It offers a builder-style API similar to WebClient but without the reactive complexity.
5. What is the exact difference between @Component and @Bean?
@Component is a class-level annotation. Spring automatically detects it during classpath scanning and registers it as a bean.
@Bean is a method-level annotation used within a @Configuration class. You must use @Bean when you need to register third-party classes (like ObjectMapper or a custom DataSource) because you cannot place a @Component annotation on library source code you don't own.
6. How do you optimize the startup time of a Spring Boot application?
Aside from AOT compilation, you can enable lazy initialization so beans are not instantiated until they are actually requested by the application:
spring.main.lazy-initialization=true
Other strategies include limiting the scope of @ComponentScan, avoiding heavy database migrations on application startup, and excluding unnecessary auto-configurations.
2️⃣ Spring Data JPA & Transaction Management
7. What is the N+1 Query Problem, and how do you solve it?
The N+1 problem occurs when JPA executes one query to fetch a list of entities (the "1"), and then executes an additional query for every single entity in that list to fetch lazy-loaded child relations (the "N"). This destroys database performance.
Solutions:
- JOIN FETCH: Write a custom JPQL query using
JOIN FETCHto pull parents and children in a single SQL statement. - @EntityGraph: Use Spring Data JPA's
@EntityGraphto override the default lazy-loading behavior for a specific repository method.
@Repository
public interface OrderRepository extends JpaRepository<Order, Long> {
// Solves N+1 by fetching the 'items' collection in the same query
@EntityGraph(attributePaths = {"items"})
List<Order> findAll();
}
8. Explain @Transactional. What happens if you call a @Transactional method from another method inside the same class?
@Transactional relies on Spring AOP (Aspect-Oriented Programming) Proxies. When an external class calls a transactional method, it hits the proxy first, which opens the database transaction, runs the method, and then commits or rolls back.
@Transactional. The internal call bypasses the Spring Proxy entirely. Fix this by moving Method B to a different service class.
9. What is the difference between REQUIRED and REQUIRES_NEW propagation?
| Propagation.REQUIRED (Default) | Propagation.REQUIRES_NEW |
|---|---|
| If a transaction already exists, the method joins it. If one doesn't exist, it creates a new one. | Suspends the current transaction and always creates a brand new, independent physical transaction. |
| If the inner method throws an exception, the entire outer transaction rolls back. | If the inner method rolls back, the outer transaction can catch the exception and still commit successfully. |
10. What causes LazyInitializationException and how do you fix it?
This occurs when a lazily-loaded JPA association is accessed outside of an active Hibernate transaction (commonly happening in the Controller layer when Jackson tries to serialize an entity to JSON).
The Fix: Never return JPA Entities directly from the Controller. Map the Entity to a DTO inside the @Transactional Service layer while the Hibernate session is still open, or use JOIN FETCH to eagerly load the required data.
11. Explain Optimistic vs. Pessimistic Locking.
Optimistic Locking: Uses a @Version field. When updating, JPA checks if the version matches. If another transaction updated it first, it throws an OptimisticLockingFailureException. Best for high-read/low-write scenarios.
Pessimistic Locking: Uses actual database-level locks (e.g., SELECT ... FOR UPDATE), preventing other transactions from reading or writing until the lock is released. Best for high-contention financial transactions.
12. Why is spring.jpa.hibernate.ddl-auto=update dangerous in production?
It allows Hibernate to automatically modify production database schemas, which can easily lead to dropped columns, locked tables, or catastrophic data loss. In production, this should always be set to validate or none. Schema changes must be version-controlled using migration tools like Flyway or Liquibase.
3️⃣ REST API Design & Architecture
13. How do you handle exceptions globally in a standardized way in Spring Boot 3?
Instead of returning raw strings or messy stack traces, enterprise applications use @RestControllerAdvice. Spring Boot 3 introduced native support for RFC 7807 (ProblemDetail), which creates a globally standardized JSON error format.
import org.springframework.http.ProblemDetail;
import org.springframework.web.bind.annotation.ExceptionHandler;
import org.springframework.web.bind.annotation.RestControllerAdvice;
@RestControllerAdvice
public class GlobalExceptionHandler {
@ExceptionHandler(UserNotFoundException.class)
public ProblemDetail handleUserNotFound(UserNotFoundException ex) {
ProblemDetail problem = ProblemDetail.forStatusAndDetail(HttpStatus.NOT_FOUND, ex.getMessage());
problem.setTitle("User Not Found");
return problem;
}
}
14. What is Idempotency in REST APIs, and why is it important?
An idempotent API means that making multiple identical requests has the same effect as making a single request.
GET,PUT, andDELETEare idempotent. Calling them 10 times results in the same resource state.POSTis not idempotent. Calling a POST API 10 times will create 10 distinct resources.
Understanding this is crucial for preventing duplicate payments or record creation when a client's network connection drops and they retry a request.
15. Filter vs. Interceptor vs. AOP: When do you use which?
| Filter (Servlet API) | Interceptor (Spring MVC) | AOP (Spring Aspect) |
|---|---|---|
| Executes before the request hits Spring. Good for CORS, raw request logging, and Security. | Executes inside the Spring context. Has access to the Handler (Controller method). Good for custom authorization or setting headers. | Executes at the method level. Good for business logic cross-cutting concerns like Transaction management or Audit logging. |
16. How do you implement a Custom Validation Annotation?
You create a custom annotation interface and annotate it with @Constraint(validatedBy = MyValidator.class). Then, you create the MyValidator class that implements ConstraintValidator<MyAnnotation, String>. This allows you to apply reusable, domain-specific validation (e.g., @ValidEmployeeId) directly onto your DTO fields.
4️⃣ Security & Production Readiness
17. How has Spring Security configuration changed in recent versions?
Extending WebSecurityConfigurerAdapter is completely obsolete—it was removed in Spring Boot 3. Today, security is configured via a component-based approach by declaring a SecurityFilterChain Bean using a modern lambda DSL:
@Configuration
@EnableWebSecurity
public class SecurityConfig {
@Bean
public SecurityFilterChain filterChain(HttpSecurity http) throws Exception {
http
.csrf(csrf -> csrf.disable())
.authorizeHttpRequests(auth -> auth
.requestMatchers("/api/public/**").permitAll()
.anyRequest().authenticated()
)
.sessionManagement(sess -> sess.sessionCreationPolicy(SessionCreationPolicy.STATELESS));
return http.build();
}
}
18. How does Stateless Authentication using JWT work?
In modern microservices, we do not store session IDs in server memory (which breaks horizontal scaling). Instead, we use JSON Web Tokens (JWT):
- The client logs in; the server validates credentials and generates a signed JWT containing user claims.
- The client attaches the JWT to the
Authorization: Bearer <token>header on subsequent requests. - A custom Spring Security Filter intercepts the request, mathematically validates the token's signature, and sets the SecurityContext without hitting the database.
19. How do you secure method-level execution?
You can enable @EnableMethodSecurity on your configuration class. This allows you to use annotations like @PreAuthorize("hasRole('ADMIN')") directly on your service or controller methods to enforce fine-grained access control before the method executes.
20. What is Spring Boot Actuator, and how do you secure it?
Actuator provides production-ready REST endpoints (e.g., /actuator/health, /actuator/metrics, /actuator/env) to monitor application health. Because these endpoints expose sensitive system configuration, they must be secured. You can restrict them to an ADMIN role using Spring Security, or expose them on an internal-only port using management.server.port=8081.
21. How do you manage sensitive secrets without storing them in properties files?
For sensitive credentials (like DB passwords or AWS Keys), we never commit them to source control. Instead, we use environment variables (e.g., ${DB_PASSWORD} in the yaml file), Kubernetes Secrets, or a secure remote vault like HashiCorp Vault. Spring Cloud Vault integrates seamlessly to inject these secrets at runtime.
22. What is Testcontainers, and why is it preferred over H2 for Integration Testing?
H2 is an in-memory database that behaves differently than production databases (lacking specific JSON operators or dialect features). Testcontainers uses Docker to spin up a real, lightweight instance of your actual production database (like PostgreSQL or Oracle) during integration tests. This eliminates "works on my machine" bugs and ensures your native queries and Flyway migrations work exactly as they will in production.
💼 Strengthen Your Spring Boot Interview Preparation
To clear mid-level and senior interviews, you must move beyond basic annotations. Master performance tuning, scalability, and system architecture with these deep-dive guides.
Learn how experienced developers design scalable and high-throughput systems using Java 21+ features.
Tackle common interview discussions around latency, connection pooling, and JVM memory tuning.
Interviewers frequently ask how to identify and resolve thread bottlenecks in production apps.
Learn how JPA caching, JDBC batching, and indexing impact performance in enterprise applications.
Master @RestControllerAdvice to handle API errors consistently—a mandatory skill for REST interviews.
Transition from Spring Boot coding questions to high-level architecture and system design discussions.