# opencode Spring Boot: a practical developer guide

URL: https://agentvera.dev/en/blog/opencode-for-spring-boot/ · Published: 2026-11-01

Use the opencode coding agent on a Spring Boot project. Set up AGENTS.md, drive controllers, services, JPA, tests, and Testcontainers, and verify the work.

**In short:**

- opencode works well inside an existing Spring Boot project when you encode Maven or Gradle commands and package conventions in AGENTS.md.
- Drive the agent in small steps: add DTO, service, controller, slice test, then integration test, running tests after each change.
- Review diffs closely for dependency changes, transaction boundaries, and Testcontainers lifecycle issues.

opencode is a terminal coding agent that can work directly inside an existing Spring Boot project. This guide shows how to configure it with Maven or Gradle, write an AGENTS.md that reflects your stack, and drive it through real controller, service, JPA, and Testcontainers work. It assumes you already know Spring Boot and want predictable output from the agent.

## Spring Boot’s conventions make opencode useful

Spring Boot projects are convention-heavy: package structure, annotation wiring, dependency versions, and test slicing all matter. opencode reads the project tree, Maven or Gradle build files, and AGENTS.md, so once you encode those conventions the agent can generate controllers, services, and repositories that match your existing Java style. It can also run your test command and read stack traces, which makes the feedback loop concrete. For a closer look at the agent itself, see [opencode](/en/agents/opencode/). Unlike a generic chat model, opencode operates as a CLI agent in the repository, so it can apply multi-file edits across controller, service, and repository layers without leaving the terminal.

## Give the agent the build and package rules up front

Create an AGENTS.md in the project root before asking opencode to change code. The file should be short but specific: exact build and test commands, package layout, and Spring Boot rules you never want it to break. Do not copy a generic Java AGENTS.md; include your dependency manager, test slice preferences, and any conventions around records, Lombok, or transaction boundaries.

```
# AGENTS.md

## Build and test
- Maven: ./mvnw clean verify
- Gradle: ./gradlew clean test
- Run a single test: ./mvnw -Dtest=OrderControllerTest test
- No lint command; use ./mvnw checkstyle:check if configured.

## Project layout
- src/main/java/com/acme/orderapp
  - controller/ -> REST controllers, thin, delegate to services
  - service/ -> business logic, @Service, @Transactional on write operations
  - repository/ -> Spring Data JPA interfaces only, no implementation classes
  - dto/ -> request/response records or immutable classes
  - entity/ -> JPA entities, avoid Lombok unless already in pom
- src/test/java/com/acme/orderapp
  - unit tests in service/, slice tests with @WebMvcTest, integration tests with @SpringBootTest and Testcontainers PostgreSQL

## Spring Boot rules
- Controllers return ResponseEntity<T>, use constructor injection only.
- Validate request DTOs with jakarta.validation annotations, add @Valid in controller method argument.
- Services throw custom exceptions; controllers map them with @RestControllerAdvice.
- Do not add new dependencies without asking. Use existing pom.xml or build.gradle.
- For tests, prefer JUnit 5 and AssertJ. Use Testcontainers only for integration tests that need PostgreSQL/RabbitMQ.
```

If you use Maven, replace Gradle commands accordingly. The key is that opencode will follow these rules when generating tests or refactoring, so avoid listing every file.

## Plan small, run tests, review the diff

Use a plan-first loop. When you open opencode, ask it to summarize the relevant files before editing: the controller, service, repository, and any DTOs. Then give one small task, run the tests, and review git diff before accepting. For larger changes, split into: add DTO and entity validation, add service method, add controller endpoint, add slice test, then integration test. For step-by-step usage, [How to use opencode: a step-by-step guide](/en/blog/how-to-use-opencode/) covers the CLI workflow.

Example prompts for typical Spring Boot work:

- "Add a GET /orders/{id} endpoint that returns an OrderResponse from OrderService; use constructor injection and return 404 when the service throws OrderNotFoundException."
- "Create OrderService.placeOrder that saves Order and OrderItem in one transaction with @Transactional and validates that the customer exists."
- "Write a @WebMvcTest for OrderController with @MockBean OrderService; cover 200 with a valid id and 404 with an unknown id."
- "Add a Testcontainers PostgreSQL integration test for OrderRepository that saves and finds an order with order items."
- "Refactor the exception handler in OrderControllerAdvice to return RFC 7807 problem details and update any affected tests."

After each prompt, run ./mvnw test or ./gradlew test, and inspect git diff. If the change touches Spring configuration or dependencies, review those files manually.

## Where opencode excels and where to double-check it

opencode handles the repetitive parts well: REST endpoints, JPA query methods, DTO mapping, validation, and test scaffolding. The table below shows tasks, good prompts, and pitfalls.

| Task | Good prompt | Watch closely |
|------|-------------|---------------|
| Add endpoint | "Add POST /orders with @Valid request body and return 201 with location header." | It may add a service method but forget transaction or DTO validation. |
| Spring Data JPA | "Add a repository method to find all orders by customer id and status, sorted by created date." | It may create a derived method that generates an inefficient query or ignores fetch size. |
| Service logic | "Create OrderService.cancelOrder with business rules: only pending orders can be cancelled, and update status." | It may put business rules in the controller or skip @Transactional on read-write operations. |
| Testcontainers | "Write an integration test for inventory reduction using PostgreSQL Testcontainers." | It may start a container for every test class instead of reusing a singleton, slowing builds. |

Other pitfalls: it may suggest changing pom.xml or build.gradle for features already available in Spring Boot; ask it first or set a rule in AGENTS.md. It may also generate tests that assert only HTTP status and not the response body, so add assertion requirements in the prompt.

## Keep tests green with slice tests and Testcontainers

Make opencode run tests after each change. Tell it to run the specific test class first, then the full suite. For Maven, ./mvnw -Dtest=OrderControllerTest test; for Gradle, ./gradlew test --tests com.acme.orderapp.controller.OrderControllerTest. Verify Testcontainers tests clean up after themselves; opencode sometimes leaves containers running if it does not use singleton containers or @Testcontainers(disabledWithoutDocker = true). Check that integration tests do not rely on a shared embedded database when production uses PostgreSQL; prefer Testcontainers and the same RDBMS. Review application-test.yml or test properties for hard-coded ports and credentials. If you use JUnit 5, ask the agent to extend your base integration test class instead of re-implementing container config.

## Run parallel Spring Boot agents with AgentVera

Spring Boot features often span multiple layers, so parallel agents can help when the change is large enough. AgentVera runs opencode and other CLI agents in real terminal panels, and each can work in its own git worktree, which prevents controller, service, and test changes from overwriting each other. Automatic code review with file:line links catches cross-layer mistakes such as a controller returning an entity instead of a DTO or a service missing a transaction. Token budgets keep experiments bounded, and when an agent hits a cap it stops but keeps its conversation for later handoff. This matches the way Spring Boot teams split work; see [Best tools to run AI coding agents in parallel (2026)](/en/blog/best-tools-parallel-ai-coding-agents/) for the parallel approach.

## Closing thoughts

Set up an AGENTS.md with exact Maven or Gradle commands, package conventions, and Spring Boot rules, then drive opencode in small, test-verified steps. Review every diff for dependency changes, transaction boundaries, and Testcontainers lifecycle. With that discipline, opencode becomes a reliable pair on real Spring Boot feature work.

## Frequently asked questions

**How do I start opencode in a Spring Boot project?** Open a terminal in the Spring Boot project folder and run opencode. Before editing, add an AGENTS.md with your Maven or Gradle commands and package conventions so the agent follows your project structure.

**What should I include in AGENTS.md for Spring Boot?** Include the exact build and test commands, Java package layout, rules for controllers, services, repositories, and tests, plus any dependency or Lombok restrictions. A short file is better than a long generic one.

**Can opencode write integration tests with Testcontainers for Spring Boot?** Yes. Specify JUnit 5, Testcontainers, and the target database such as PostgreSQL. Ask it to reuse a singleton container and extend a base test class to avoid slow build times and leftover containers.

**How do I keep opencode from adding unnecessary dependencies to pom.xml or build.gradle?** State in AGENTS.md that dependencies must not be added without approval. Review the dependency diff after each session, and ask the agent to use existing libraries or Spring Boot starters already in the build.

---

**About AgentVera.** AgentVera is a desktop app for macOS, Windows and Linux, built by Solviera Teknoloji. It runs 18 AI coding agents (Claude Code, Codex, Gemini CLI, Copilot, Cursor, Antigravity, opencode, Hermes, Qwen Code, Kimi Code, Kiro, Amp, Droid, Goose, Vibe, Crush, Aider, Cline) side by side, per project, in real terminals with the user's own CLI installs and logins. The free plan has unlimited agents. Download: https://agentvera.dev/en/download/ · Pricing: https://agentvera.dev/en/pricing/
