realtech2000 / falconTest

Chat room app for tech assignment (microservices, Java 8, Spring Boot, WebSocket, REST, Kafka, Zookeeper)

Geek Repo:Geek Repo

Github PK Tool:Github PK Tool

Falcon Test - Chat room
by Gergő Pásztor

INSTALL & UNINSTALL

See the 'INSTALL' file!


FEATURES

Chat room app:
- Separated rooms
- Send messages with WebSocket (WS /ws/chat)
- Send messages with REST API (PUT /api/message)
- Receiver messages with WebSocket (WS /ws/chat)
- See all archive messages with REST API (GET /api/messages)
- See archive messages in one room with REST API (GET /api/messages/<roomName>)

Technology stack:
- Language: Java 8
- Build system: Gradle
- Framework: Spring Boot with MVC, Spring Data, Spring Integration, Spring Cloud Stream, Spring Cloud Service Discovery
- Messaging: Kafka, WebSocket with STOMP
- Database: Postgresql 9.4 with Hibernate (JPA)
- Service discovery: Zookeeper
- OS: Ubuntu (Docker image)
- Running environment: Docker and Docker Composer


DISCLAIMER
I'm not a Spring master and I'm also not familiar with the Kafka before that, so almost all of
my code is built with new technology from my point of view. That was fun, but maybe you know
some tricks in the frameworks that I should use, but I don't know about it.


CODE STYLE
This app is very-very over-engineered, but hey, this is a tech assessment!
I completely separated the DB layer from the domain layer and the endpoints (controller) from
the domain layer. Messaging also separated from the other parts of the app. This is not
necessary in this project, but important in a bigger one.

One of the microservice architecture's disadvantages that you need to make some code
duplications. This is a standard practice, because you need to completely separate the services.
If your services have a common dependency and this dependency was changed somehow you will
not know about that changes and your services will fail. To preventing this everybody needs to
maintain the connection with the common dependency (like db schemas). This is why this code
contains some duplications.


ARCHITECTURE

I used microservice architecture for this app. We will have 7 separated service, 4 from my code.
You can also use this app as one. For example if you are a startup you can start with one app on
one server and later separate the services to different servers. Also good for debugging.

Create message:
User ---HTTP--> REST API --|--Kafka--> Process ---JDBC--> DB
                           |--Kafka--> Ws ---WebSocket--> Users in the room
Get archive messages:
User ---HTTP--> REST API ---JDBC--> DB


Api
This is the REST API service:
- get archive messages: read (only) the db
- create message: send message to the Kafka
I used the CQRS pattern so later you can divide this service to two parts easily.
This service only reads from the db so only one service writes the db. This is important in a
microservice architecture to prevent a lot of possible mistakes.


Frontend
This is a normal MVC and/or static app for the app's frontend. This is separated from the APIs
so you can change this code in a different speed and you can also specialize the environment
for this type of task. For example you can use something more convenient and faster solution
than Java for the static files.

This app also contains a load balancer: it's using the Zookeeper to get the port of a REST
API and a WebSocket endpoint. If you have more than one of this service it can handle the load
balancing for you.


Process
This is a background process to process the incoming data and save them. Currently is very
lightweight but in the real life this type of tasks are very heavy. The messages came from
the Kafka and this app save them to the db.


Ws
This is the WebSocket endpoint service:
- receive incoming messages: messages coming from the Kafka
- create message: send message to the Kafka
This is a gateway between the websocket and the Kafka. WebSockets need a special care from the
DevOps side, because it's using a lot of port and I/O and the response time is matter. Usually
you need special softwares (better tcp stack) for this type of servers.


CommonDb
This is not a real service, just a module in the project. Hibernate not tolerate different
entity classes for the same table so I need to create this common db implementation and later
use it in the Process and the Api service. This is a trade-off between the two type of usage.
If you want to use this app as separated services you can easily copy this code to this
two project. Or you can create a REST API for this module and create another real service
on the top of the DB.



About

Chat room app for tech assignment (microservices, Java 8, Spring Boot, WebSocket, REST, Kafka, Zookeeper)


Languages

Language:Java 76.9%Language:HTML 23.1%