Canonical URL: Republished from munonye.com. Full code on GitHub.
This Spring AI tutorial step by step walks you through your first LLM-powered REST endpoint on Spring Boot 3. You will call OpenAI from Java using ChatClient, keep API keys out of source code, and verify with curl — the backend foundation for our AI Developer Tutorials series.
If you have built REST APIs with our Angular CRUD + Spring Boot series, you already know the architecture; we are adding an AI layer on top.
Prerequisites: Java 17+, Maven, OpenAI API key, basic Spring Boot REST knowledge.
Time: ~45 minutes.
Architecture
Client (curl / Angular)
POST /api/chat { "message": "Hello" }
▼
ChatController → ChatClient → OpenAI API
▼
{ "reply": "..." }
Step 1 — Create the project
curl https://start.spring.io/starter.zip \
-d dependencies=web \
-d javaVersion=17 \
-d name=ai-chat-api \
-o ai-chat-api.zip
unzip ai-chat-api.zip && cd ai-chat-api
Add Spring AI BOM and OpenAI starter in pom.xml:
<dependencyManagement>
<dependencies>
<dependency>
<groupId>org.springframework.ai</groupId>
<artifactId>spring-ai-bom</artifactId>
<version>1.0.0</version>
<type>pom</type>
<scope>import</scope>
</dependency>
</dependencies>
</dependencyManagement>
<dependencies>
<dependency>
<groupId>org.springframework.ai</groupId>
<artifactId>spring-ai-openai-spring-boot-starter</artifactId>
</dependency>
</dependencies>
Step 2 — Configure OpenAI
# application.properties
server.port=8080
spring.ai.openai.api-key=${OPENAI_API_KEY}
spring.ai.openai.chat.options.model=gpt-4o-mini
spring.ai.openai.chat.options.temperature=0.7
Run with:
export OPENAI_API_KEY=sk-...
./mvnw spring-boot:run
Never commit API keys. Use environment variables or a secrets manager in production (see M11-A secure AI tutorial).
Step 3 — Chat REST endpoint
@RestController
@RequestMapping("/api/chat")
@CrossOrigin(origins = "http://localhost:4200")
public class ChatController {
private final ChatClient chatClient;
public ChatController(ChatClient.Builder builder) {
this.chatClient = builder
.defaultSystem("You are a helpful Java and Spring Boot assistant.")
.build();
}
@PostMapping
public ChatResponse chat(@RequestBody ChatRequest request) {
String reply = chatClient.prompt()
.user(request.message())
.call()
.content();
return new ChatResponse(reply);
}
}
public record ChatRequest(String message) {}
public record ChatResponse(String reply) {}
Step 4 — Test with curl
curl -s -X POST http://localhost:8080/api/chat \
-H "Content-Type: application/json" \
-d '{"message":"Explain Spring Boot in one sentence"}' | jq
Expected: JSON with a reply field containing the model response.
Troubleshooting
| Error | Fix |
|---|---|
| 401 from OpenAI | Check OPENAI_API_KEY is set and valid |
| Bean ChatClient missing | Ensure spring-ai-openai-spring-boot-starter is on classpath |
| CORS blocked from Angular | Add @CrossOrigin or configure WebMvcConfigurer
|
Next steps
- M7-B: [Build a streaming chat UI in Angular 19](https://www.munonye.com/angular-19-streaming-c
Read the full tutorial with all code on munonye.com →
Full tutorial: Spring AI Tutorial — Your First REST Endpoint with OpenAI (2026)
Top comments (0)