Note: This project is for my own testing and a reference for Docker scripts
Server for a chat application.
- ChatServer
- .NET Core Web API
- ChatBroker
- .NET Core Web API
- Handles new messages from RabbitMQ
- Client
- React application
- Send and receive messages
- RabbitMQ
- Queue for new messages
- Redis
- Client register
- Has information on which server user is logged on
- TODO Postgres
- Messages that are not delivered to offline users
- TODO Authentication
- TODO User Service
- Node.js Express
- Search users
- Uses status
- Share message history between clients
# Developemnt
$ docker-compose build
$ docker-compose up
# Production
$ docker-compose -f docker-compose-prod.yml build
$ docker-compose -f docker-compose-prod.yml up
Install required containers:
# Create network
$ docker network create --attachable chat
# Redis
$ docker run -d --name chat-redis --network=chat -p 6379:6379 redis
# RabbitMQ
$ docker run -d --name chat-rabbit --network=chat -p 5672:5672 -p 15672:15672 rabbitmq:3-management
# Quick start/stop
$ docker start chat-redis && docker start chat-rabbit
$ docker stop chat-redis && docker stop chat-rabbit
Start project from Visual Studio.
Start debuggable projects in containers.
# Build image
$ docker build -t chatserver:dev .
# Start container
$ docker run --rm -it -e "Connections__Redis=chat-redis" -e "Connections__RabbitMQ=chat-rabbit" -e "DOTNET_RUNNING_IN_CONTAINER=true" -p 5000:5000 -p 10222:22 --name chat-server --network=chat -v C:\src\GitHub\chat-server\src\ChatServer:/app/ -w /app chatserver:dev
# Login to container
$ docker exec -it chat-server /bin/bash
# Start SSH server (TODO: should be always on)
$ service ssh start
# Debug -> Attach to process -> SSH (localhost:10222 root:Docker!)
# Attach to dotnet exec process
# Select Managed Managed (.NET Core for Unix)
If you don't care about debugging from container, just start clean image with dotnet watch
$ docker run --rm -it -e "Connections__Redis=chat-redis" -e "Connections__RabbitMQ=chat-rabbit" -e "DOTNET_RUNNING_IN_CONTAINER=true" -p 5000:5000 --name chat-server --network=chat -v C:\src\GitHub\chat-server\src\ChatServer:/app/ -w /app microsoft/dotnet:2.1-sdk dotnet watch run
$ docker run --rm -it -e "Connections__Redis=chat-redis" -e "Connections__RabbitMQ=chat-rabbit" -e "DOTNET_RUNNING_IN_CONTAINER=true" -p 5000:5000 --name chat-server --network=chat -v C:\src\GitHub\chat-server\src\ChatBroker:/app/ -w /app microsoft/dotnet:2.1-sdk dotnet watch run
sourceMapPathOverrides
in launch.json
must override folder structure in Docker container.
{
"version": "0.2.0",
"configurations": [
{
"type": "chrome",
"request": "attach",
"name": "Attach to Chrome",
"port": 9222,
"webRoot": "${workspaceFolder}/src",
"sourceMapPathOverrides": {
"/app/src/*": "${webRoot}/*"
}
}
]
}
# Build image
$ docker build -f Dockerfile-prod -t chatapp:prod .
# Start prod React app
$ docker run -it -p 800:80 --rm --name chat-app-prod chatapp:prod
- Docker doesn't set ASPNETCORE_ENVIRONMENT correctly on development compose
- Authorization
- Save messages temporarily to DB
- When user logs in send not sent messages to him immediately
- Handle same user with multiple clients on multiple servers
https://www.npmjs.com/package/redis-commander
$ npm install -g redis-commander
$ redis-commander
Open: http://localhost:8081/
...
...
...
...
# Client logs in
ChatServer: Login
Authenticate
Send update to client register
Check if there is waiting messages for the client in the sent_queue
# Client sends a new message
ChatServer: New message /api/send
Validate
Send update to client register
Send message to RabbitMQ
ChatBroker: New message from RabbitMQ
Get receiver server from client register
Save message to sent_queue
Send to correct server /api/receive
Success
Remove message from sent_queue
Fail
Update message status to sent_queue_
ChatServer: New message /api/receive
Send to receiver with WebSocket
Send status to broker (success/fail)
- Routes: https://docs.microsoft.com/en-us/aspnet/core/fundamentals/routing?view=aspnetcore-2.1#id7
- Route constraints: https://docs.microsoft.com/en-us/aspnet/core/fundamentals/routing?view=aspnetcore-2.1#route-constraint-reference
- https://runnable.com/docker/docker-compose-networking
- https://docs.microsoft.com/en-us/dotnet/standard/microservices-architecture/multi-container-microservice-net-applications/multi-container-applications-docker-compose