api-standard-spring-boot-starter

πŸš€ api-standard-spring-boot-starter

Bring organization-wide API consistency to every Spring Boot service.

Turn Spring Boot into a governed API platform with one dependency. Standardize responses, errors, tracing, and OpenAPI documentation automatically.

[![Spring Boot 4.0.6](https://img.shields.io/badge/Spring%20Boot-4.0.6-brightgreen.svg)](https://spring.io/projects/spring-boot) [![Java 21](https://img.shields.io/badge/Java-21-orange.svg)](https://www.oracle.com/java/technologies/downloads/#java21) [![Version](https://img.shields.io/badge/version-2.0.0-blue.svg)](https://github.com/saul789/api-standard-spring-boot-starter/releases) [![License: MIT](https://img.shields.io/badge/License-MIT-yellow.svg)](https://opensource.org/licenses/MIT) [![Docs](https://img.shields.io/badge/docs-Redoc-blue.svg)](https://saul789.github.io/api-standard-spring-boot-starter/)

A plug-and-play Spring Boot starter that standardizes API responses, implements RFC 9457 (Problem Details for HTTP APIs), and provides distributed tracing via Trace Context propagation.

</div>


🚫 Stop Copy-Pasting API Infrastructure

Most organizations eventually create:

This starter centralizes those cross-cutting concerns into a single reusable standard. Stop reinventing the wheel and eliminate boilerplate technical debt.

🏒 Ideal For


⚑ Zero-Configuration Philosophy

Add the dependency and keep building your API. We handle the rest.


πŸ—οΈ Architecture Flow

graph TD
    A[Client Request] --> B[TraceContextFilter]
    B --> C[Spring Controller]
    C -- "Throws Exception" --> D[GlobalExceptionHandler]
    D --> E[ProblemDetailService]
    E -- "1. Map ErrorCode" --> F[i18n Messages]
    E -- "2. Enrich metadata" --> G[Enricher SPI]
    F --> H[ProblemDetail JSON]
    G --> H
    H --> I[Client Response RFC 9457]
    
    subgraph "api-standard-starter"
    D
    E
    F
    G
    end

πŸš€ Quick Start

1. Add the dependency

<dependency>
    <groupId>io.github.saul789</groupId>
    <artifactId>api-standard-spring-boot-starter</artifactId>
    <version>2.0.0</version>
</dependency>

2. Create a normal controller

@RestController
@RequestMapping("/api/users")
public class UserController {

    @GetMapping("/{id}")
    public User get(@PathVariable String id) {
        throw new BusinessException(ErrorCode.NOT_FOUND, "User not found", HttpStatus.NOT_FOUND);
    }
}

3. Automatic API Governance Enabled

Without writing any boilerplate, your API now automatically returns standardized responses, RFC 9457 errors, traceIds, auto-generated OpenAPI schemas, and translated messages.


πŸ“¦ The Standard Contract

By simply returning objects or throwing exceptions, the starter enforces a rigorous contract globally:

βœ… Success Response (200 OK)

{
  "success": true,
  "timestamp": "2026-05-10T18:34:45Z",
  "data": { 
      "id": "123", 
      "name": "Jane Doe" 
  }
}

❌ Error Response (RFC 9457 Compliant)

{
  "type": "https://api.yourdomain.com/errors/not-found",
  "title": "User Not Found",
  "status": 404,
  "detail": "User with ID 123 does not exist",
  "instance": "/api/users/123",
  "code": "NOT_FOUND",
  "timestamp": "2026-05-10T18:34:46Z",
  "traceId": "5f9b3b8c-1234-4a56-b789-abcdef123456"
}

πŸ’‘ Bonus: Transparent MDC Logging Every request gets a traceId injected into SLF4J MDC instantly. Watch your logs become 10x easier to debug: INFO [traceId: 5f9b3b8c-1234...] c.s.UserController: Fetching user 123


✨ The Organizational Savings

Capability Traditional Setup This Starter
RFC 9457 Compliance Manual construction βœ… Automatic
OpenAPI Response Wrapping Manual annotations on every method βœ… Automatic
TraceId Propagation Custom Servlet filters βœ… Built-in
Error Translation (i18n) Custom boilerplate βœ… Built-in
Organization-wide Consistency Hard to enforce βœ… Automatic

πŸ” Before vs After

Before (Manual & Boilerplate):

- @RestControllerAdvice
- public class GlobalExceptionHandler { ... }
-
- public class ApiResponse<T> { ... }
-
- @Component
- public class TraceFilter extends OncePerRequestFilter { ... }
-
- @PostMapping
- @ApiResponses({
-     @ApiResponse(responseCode = "200", description = "Success"),
-     @ApiResponse(responseCode = "400", description = "Bad Request")
- })
- public ResponseEntity<ApiResponse<User>> createUser(@RequestBody UserRequest request) { ... }

After (Using this Starter):

+ @PostMapping
+ @ResponseStatus(HttpStatus.CREATED)
+ public User createUser(@Valid @RequestBody UserRequest request) {
+     return userService.create(request);
+ }

πŸ›‘οΈ Enterprise-Grade Foundations

Built for large-scale microservice platforms from day one:

βš™οΈ How It Works (For the Skeptics)

The starter integrates deeply with Spring Boot auto-configuration:

No annotations required.


πŸ—ΊοΈ Platform Vision (V2 Roadmap)

Building the ultimate API governance platform for Spring Boot:


πŸ› οΈ Architecture Overview

Click to view architecture diagram ```mermaid sequenceDiagram participant Client participant TraceFilter participant Controller participant ExceptionHandler Client->>TraceFilter: GET /api/users activate TraceFilter TraceFilter->>TraceFilter: Generate UUID (traceId) TraceFilter->>Controller: MDC Injected Request activate Controller Controller-->>ExceptionHandler: throw BusinessException deactivate Controller activate ExceptionHandler ExceptionHandler->>ExceptionHandler: Map to RFC 9457 & i18n ExceptionHandler-->>TraceFilter: ProblemDetail JSON deactivate ExceptionHandler TraceFilter-->>Client: HTTP 400 + JSON deactivate TraceFilter ```

🀝 Contributing & Testing

πŸ“„ License

This project is licensed under the Apache License 2.0 - see the LICENSE file for details.


Do you find this useful? Give us a ⭐ on GitHub to support the project!