Katkat

Build Spring Boot POST, PUT, and GET Endpoints

Wells FargoSoftware Engineer · Technical Screen

Last updated

Design and implement RESTful endpoints in Spring Boot for an account resource, covering controller annotations, validation, HTTP status codes, error handling, and MockMvc tests.

Overview

In a retail banking system, you need to expose a RESTful API for managing customer bank accounts using Spring Boot. Implement the controller, request/response DTOs, and exception handling for creating, retrieving, and updating bank accounts.

Requirements

1. Data Contract

Define a BankAccount representation with the following fields:

  • id (Long, auto-generated)
  • accountNumber (String, 10 digits, unique, immutable)
  • accountHolderName (String, required, 2–100 characters)
  • accountType (Enum: CHECKING, SAVINGS)
  • balance (BigDecimal, must be non-negative)
  • status (Enum: ACTIVE, FROZEN, CLOSED)

2. Endpoints

Implement an AccountController mapped to /api/v1/accounts:

  • POST /api/v1/accounts
    • Accepts a valid creation payload.
    • Returns HTTP 201 Created with the created resource and a Location header pointing to the new resource URI.
    • Rejects invalid payloads with HTTP 400 Bad Request.
  • GET /api/v1/accounts/{id}
    • Returns HTTP 200 OK with the account details.
    • Returns HTTP 404 Not Found if the account does not exist.
  • GET /api/v1/accounts
    • Supports an optional query parameter status (e.g., ?status=ACTIVE).
    • Returns HTTP 200 OK with a list of matching accounts.
  • PUT /api/v1/accounts/{id}
    • Performs a full replacement/update of the mutable fields (accountHolderName, status). Note that accountNumber and balance cannot be updated through this endpoint.
    • Returns HTTP 200 OK on success, or HTTP 404 Not Found if the ID does not exist.

3. Error Handling & Testing

  • Provide a global exception handler (@RestControllerAdvice) returning a consistent error payload with timestamp, status, error, and message.
  • Write a unit/slice test using @WebMvcTest(AccountController.class) and MockMvc verifying the POST endpoint validation failure and success response.

Hints

Hint 1

Use standard Jakarta Bean Validation annotations like `@NotBlank`, `@Size`, and `@PositiveOrZero` on your request DTOs combined with `@Valid` in the controller method signature.

Hint 2

Ensure the PUT endpoint adheres strictly to idempotent semantics and explicitly rejects attempts to mutate immutable fields such as the account number or balance.

Hint 3

For the 201 Created response, use `ServletUriComponentsBuilder.fromCurrentRequest().path("/{id}").buildAndExpand(createdId).toUri()` to construct the Location header.

Follow-up questions

  • How would you handle optimistic locking on the PUT endpoint to prevent lost updates under high concurrency?
  • How does Spring Boot 3 utilize RFC 7807 (ProblemDetail) for standardizing API error responses compared to custom error bodies?
  • How would you extend the `GET /api/v1/accounts` endpoint to support database-level pagination and sorting using Spring Data `Pageable`?