Skip to content

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

14 Commits
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 

Repository files navigation

OpenAI Chat Service with Spring AI

A Spring Boot service that integrates the OpenAI API via Spring AI to provide chat with persistent memory and retrieval-augmented generation (RAG) backed by PostgreSQL + pgvector.

The service supports stateless single-turn chat, stateful multi-turn conversations whose history is persisted in PostgreSQL, and document ingestion that embeds PDFs into a pgvector store so answers can be grounded in your own documents.

Features

  • Stateless chat — single-turn requests with no retained history
  • Stateful chat — multi-turn conversations keyed by a conversationId, with history persisted to PostgreSQL via a custom ChatMemory implementation
  • Retrieval-augmented generation — a QuestionAnswerAdvisor retrieves relevant context from a pgvector store on every request
  • PDF ingestion — read a PDF from a file path, split it into chunks, and embed it into the vector store
  • OpenAI embeddingstext-embedding-3-small (1536-dim) stored in pgvector with HNSW indexing and cosine distance

Tech Stack

  • Java 21
  • Spring Boot 3.5.10 (Web, Data JPA)
  • Spring AI 1.1.2 — OpenAI model starter, pgvector vector store, vector-store advisors, PDF & Tika document readers
  • PostgreSQL with the pgvector extension
  • Lombok
  • Maven (wrapper included)

Getting Started

Prerequisites

  • Java 21+
  • Maven 3.9+ (or use the bundled ./mvnw wrapper)
  • An OpenAI API key
  • PostgreSQL with the pgvector extension installed

Database setup

Apply the provided schema (creates the conversations table for chat history and the vector_store table for embeddings, and enables the vector extension):

psql -U <username> -d <database> -f src/main/resources/queries/create_tables.sql

Build & Run

./mvnw clean install
./mvnw spring-boot:run

Or run the packaged JAR:

java -jar target/openai-0.0.1-SNAPSHOT.jar

The application starts on port 8080.

Configuration

All sensitive values are read from environment variables (src/main/resources/application.yaml). Provide your own values:

Environment variable Description
OPENAI_API_KEY OpenAI API key
DB_URL PostgreSQL JDBC URL, e.g. jdbc:postgresql://localhost:5432/<database>
DB_USERNAME Database username
DB_PASSWORD Database password

Model and vector-store defaults (also in application.yaml):

Key Value
spring.ai.openai.chat.options.model gpt-4.1-nano
spring.ai.openai.chat.options.temperature 0.7
spring.ai.openai.embedding.model text-embedding-3-small
spring.ai.vectorstore.pgvector.index-type HNSW
spring.ai.vectorstore.pgvector.distance-type COSINE_DISTANCE
spring.ai.vectorstore.pgvector.dimension 1536

API

Stateless chat

POST /v1/chat/stateless — body is the raw message text.

curl -X POST http://localhost:8080/v1/chat/stateless \
  -H 'Content-Type: text/plain' \
  -d 'What is machine learning?'

Response:

{ "response": "...", "timeTaken": 2450 }

Stateful chat

POST /v1/chat/stateful — body is the raw message text. Pass ?conversationId=<id> to continue an existing conversation; omit it to start a new one (the response returns the generated id).

curl -X POST 'http://localhost:8080/v1/chat/stateful?conversationId=<id>' \
  -H 'Content-Type: text/plain' \
  -d 'And tell me more about its history'

Response:

{ "conversationId": "<id>", "response": "...", "timeTaken": 1823 }

Document ingestion

GET /v1/ingest/filepath?filepath=<path> — ingest a PDF at the given file path into the vector store.

curl 'http://localhost:8080/v1/ingest/filepath?filepath=/path/to/document.pdf'

Database Schema

Table Purpose
conversations Persisted chat history (conversation_id, content, role, metadata, created_at)
vector_store Document embeddings (id, content, metadata, embedding vector(1536))

Project Structure

src/main/java/com/navneet/openai/
├── OpenaiApplication.java                  # Spring Boot entry point
├── controller/
│   ├── ChatController.java                 # /v1/chat endpoints
│   └── IngestionController.java            # /v1/ingest endpoint
├── service/
│   ├── ChatService.java / impl             # Chat logic (RAG + memory advisors)
│   ├── IngestionService.java / impl        # PDF read, split, embed
│   └── helper/ChatServiceHelper.java       # Conversation-entity helpers
├── memory/
│   ├── PersistedChatMemory.java            # Custom ChatMemory backed by JPA
│   ├── entity/Conversations.java           # JPA entity
│   └── repo/ConversationRepo.java          # Spring Data repository
├── models/                                 # Chat request/response DTOs
└── constants/AgentConstants.java           # System prompt and role constants

License

Licensed under the MIT License — see LICENSE.

About

Spring AI chat service with OpenAI: stateful memory in PostgreSQL and RAG over a pgvector store

Topics

Resources

Stars

0 stars

Watchers

1 watching

Forks

Releases

Packages

Used by

Contributors

Languages