Skip to main content

Introduction

The TelegrmBot API is built using Hexagonal Architecture (also known as Ports and Adapters), a design pattern that promotes separation of concerns, testability, and maintainability. This architecture ensures the business logic remains independent of external frameworks, databases, and APIs.

Three-Layer Structure

The application is organized into three distinct layers:
src/main/java/com/acamus/telegrm/
├── core/               # The Hexagon (Domain)
├── application/        # Use Cases
└── infrastructure/     # Adapters & Framework Code

Core

Pure business logic with no external dependencies

Application

Use case orchestration and business workflows

Infrastructure

External integrations and framework-specific code

Core Layer (The Hexagon)

The core layer is the heart of the application and contains:
Entities that encapsulate business rules and state:
  • User: Represents authenticated users of the system
  • Conversation: Telegram chat sessions with metadata
  • Message: Individual messages with direction (incoming/outgoing)
Immutable objects that ensure data validity:
  • Email: Validates email format
  • Password: Ensures non-empty passwords
  • TelegramChatId: Wraps Telegram chat identifiers
  • MessageContent: Validates message length (Telegram’s 4096 char limit)
  • Input Ports: Define how external actors interact with the application
  • Output Ports: Define what the application needs from the outside world
The core layer has zero dependencies on Spring, JPA, or any external libraries (except Jakarta validation annotations).

Application Layer

This layer contains Use Cases that implement the input ports. Each use case has a single responsibility:
  • RegisterUserUseCase - User registration
  • AuthenticateUserUseCase - User authentication
  • ProcessTelegramUpdateUseCase - Handle incoming Telegram messages
  • SendMessageUseCase - Send proactive messages to Telegram
  • ListConversationsUseCase - Retrieve all conversations
  • GetMessagesByConversationUseCase - Retrieve conversation history
Use cases orchestrate business logic by coordinating domain models and output ports, but contain no framework-specific code.

Infrastructure Layer

The infrastructure layer connects the application to the outside world:

Input Adapters (Driving)

Web Controllers

REST endpoints that receive HTTP requests and invoke use cases
  • AuthController - /api/auth/*
  • ConversationController - /api/conversations/*

Schedulers

Background tasks that trigger use cases
  • TelegramPollingService - Polls Telegram API every 5 seconds

Output Adapters (Driven)

These implement the output ports defined in the core:
  • Persistence Adapters: JPA repositories for PostgreSQL
  • Telegram Adapter: REST client for Telegram Bot API
  • AI Adapter: REST client for OpenRouter API
  • Security Adapters: JWT token generation and password hashing

Key Benefits

Testability

Business logic can be tested without frameworks or databases

Independence

Core domain is isolated from technology choices

Flexibility

Easy to swap implementations (e.g., change from PostgreSQL to MongoDB)

Maintainability

Clear separation of concerns makes code easier to understand

Request Flow Example

The controller knows about the use case, but the use case doesn’t know about the controller. Dependencies always point inward toward the core.

Directory Structure

com.acamus.telegrm

├── core
│   ├── domain
│   │   ├── model/          # Entities (User, Conversation, Message)
│   │   ├── valueobjects/   # Value objects (Email, Password, etc.)
│   │   └── exception/      # Business exceptions
│   └── ports
│       ├── in/             # Input ports (interfaces)
│       │   ├── user/
│       │   ├── conversation/
│       │   └── telegram/
│       └── out/            # Output ports (interfaces)
│           ├── user/
│           ├── conversation/
│           ├── ai/
│           ├── telegram/
│           └── security/

├── application
│   └── usecases/           # Use case implementations
│       ├── user/
│       ├── conversation/
│       └── telegram/

└── infrastructure
    ├── adapters
    │   ├── in/             # Driving adapters
    │   │   ├── web/        # REST controllers
    │   │   └── scheduler/  # Scheduled tasks
    │   └── out/            # Driven adapters
    │       ├── persistence/
    │       ├── telegram/
    │       ├── ai/
    │       └── security/
    ├── config/             # Spring configuration
    ├── decorators/         # Transactional decorators
    └── exceptions/         # Global exception handling

Next Steps

Hexagonal Architecture Deep Dive

Learn about the hexagonal architecture pattern and implementation

Domain Model

Explore the domain entities and value objects

Ports and Adapters

Understand the port interfaces and adapter implementations

Build docs developers (and LLMs) love