Skip to main content

Back to Projects

Project Detail

Kasina Backend API (ChatAPP)

A single-service backend that provides real-time chat and channel features for a web client. It exposes REST endpoints for authentication, user and channel management, file uploads, and message retrieval; it also accepts STOMP-over-WebSock...

Backend EngineerDuration: 3 monthsType: distributed-system

Key Achievement Metrics

P95_message_delivery_latency_ms

50-250

estimated_throughput_msgs_per_sec_single_instance

200-1000

Architecture View

Processing state: architecture signal graph is initializing...

Decision Log

Use of Spring SimpleBroker (in-memory STOMP broker)

Minimal infrastructure to get real-time updates to the browser quickly.

Trade-off: SimpleBroker provides low-latency messaging on a single instance but is not horizontally scalable; replacing it with a broker relay (RabbitMQ/ActiveMQ) would be required for multi-instance scaling.

JWT stored in HttpOnly cookie with SameSite=None

Simplifies authentication from the browser (no manual Authorization header management) and supports cookies across origins for cross-origin frontends.

Trade-off: With CSRF protection disabled (csrf.disable()), this increases CSRF exposure; Authorization header approach reduces CSRF risk but requires client code to manage token storage and attach headers.

MongoDB with @DBRef relationships

Easier to model relational references and reuse User/Message documents.

Trade-off: DBRef causes additional lookups (client/application-managed dereferencing) and can complicate sharding or performance at scale; embedding message docs in channels would reduce lookups but increase duplication.

Architecture Narrative

Challenge

Provides authenticated, low-latency messaging (direct and channel), persistent message storage, and basic user and channel management for a browser-based chat frontend.

Solution

Monolithic Spring Boot application with layered architecture (Controller → Service → Repository), augmented by an event-driven real-time messaging path (STOMP over SockJS WebSockets using Spring’s SimpleBroker).

Result

Key measurable signals: P95_message_delivery_latency_ms (50-250), estimated_throughput_msgs_per_sec_single_instance (200-1000).

Trade-off Matrix

DimensionSelected OptionImpactCompromise
Real-time brokerSpring SimpleBroker (in-memory)Very low operational overhead and low latency on single node.No cross-instance delivery; not suited for multi-node horizontal scaling.
Auth token placementJWT in HttpOnly cookie (SameSite=None)Simplifies browser integration and automatic cookie sending for WebSocket handshake.Increased CSRF risk and cross-origin cookie complexities; requires strict cookie security and CSRF mitigations.

What I'd Do Differently

+

Replace the in-memory STOMP broker and on-instance session registry with a broker relay (RabbitMQ/Redis pub/sub) and a centralized session store (Redis) so message delivery and session lookup work across multiple service instances; add sticky-less scaling.

+

Harden security: remove fallback JWT secret, re-enable CSRF or migrate JWT to Authorization: Bearer header for API requests, add input validation for uploads, sanitize filenames, and add rate limiting/Throttling (API gateway).

Estifanos Kebede

System Engineer & Full Stack Developer

Social

SYSTEM: ESTIFANOS.PORTFOLIO

STATUS: OPERATIONAL

LAST_UPDATED: 2026

© 2026 Estifanos Kebede. Built with precision and intent.