• Stars
    star
    243
  • Rank 160,917 (Top 4 %)
  • Language
    Go
  • Created about 1 year ago
  • Updated about 1 year ago

Reviews

There are no reviews yet. Be the first to send feedback to the community and the maintainers!

Repository Details

A demo microservice with Clean Architecture in practice

Clean Architecture in Microservices Demo

Introduction

If you're very new to Clean Architecture, I recommend you check more simple demo.

This repo was built up with three services: Task, User and Auth. Each of them conforms Clean Architecture.

Clean Architecture Overview Clean Architecture Flow

Folder structure

Let's focus on directories in /services:

services
β”œβ”€β”€ auth
β”‚Β Β  β”œβ”€β”€ business
β”‚Β Β  β”œβ”€β”€ entity
β”‚Β Β  β”œβ”€β”€ repository
β”‚Β Β  β”‚Β Β  β”œβ”€β”€ mysql
β”‚Β Β  β”‚Β Β  └── rpc
β”‚Β Β  └── transport
β”‚Β Β      β”œβ”€β”€ api
β”‚Β Β      └── rpc
β”œβ”€β”€ task
β”‚Β Β  β”œβ”€β”€ business
β”‚Β Β  β”œβ”€β”€ entity
β”‚Β Β  β”œβ”€β”€ repository
β”‚Β Β  β”‚Β Β  β”œβ”€β”€ mysql
β”‚Β Β  β”‚Β Β  └── rpc
β”‚Β Β  └── transport
β”‚Β Β      └── api
└── user
    β”œβ”€β”€ business
    β”œβ”€β”€ entity
    β”œβ”€β”€ repository
    β”‚Β Β  └── mysql
    └── transport
        β”œβ”€β”€ api
        └── rpc

Protobuf and generated files at proto folder:

β”œβ”€β”€ auth.proto
β”œβ”€β”€ pb
β”‚Β Β  β”œβ”€β”€ auth.pb.go
β”‚Β Β  β”œβ”€β”€ auth_grpc.pb.go
β”‚Β Β  β”œβ”€β”€ user.pb.go
β”‚Β Β  └── user_grpc.pb.go
└── user.proto

Microservices in this demo

Instead of separating to 3 repos on GitHub, I merged them to a single repo to give more transparent and convenience to build up the demo. But the services are isolated with each others.

Service stacks:

  • GIN (for HTTP service)
  • gRPC (internal rpc)
  • MySQL (with GORM)
  • JWT

Task Service

  • REST API: CRUD Task (require authorization for all apis)
  • gRPC: None

User Service

  • REST API:
    • Get user profile (require authorization)
  • gRPC:
    • Get public user info by ID
    • Get many public user infos by IDs

Auth Service

  • REST API:
    • Register new user account
    • Login (issue JWT)
  • gRPC:
    • Introspect Access Token

The Diagrams

Some of main diagrams to demonstration how they work together:

Create Task

Create Task Diagram

Fetch Tasks

Fetch Task Diagram

How to run this demo

1. Clone and start the service with Docker-Compose

Open your terminal/console:

git clone https://github.com/viettranx/microservices-clean-architecture-demo
cd microservices-clean-architecture-demo

docker compose up --force-recreate --detach --build app

If everything is ok, the service will be running at on localhost:3000

Print all ENV variables:

docker compose exec app ./demo_app outenv

2. Make some requests

  • Register new account
curl --location 'http://localhost:3000/v1/register' \
--header 'Content-Type: application/json' \
--data-raw '{
    "email": "[email protected]",
    "password": "12345678",
    "last_name": "Microservices",
    "first_name": "Demo "
}'
{"data": true}
  • Login
curl --location 'http://localhost:3000/v1/authenticate' \
--header 'Content-Type: application/json' \
--data-raw '{
    "email": "[email protected]",
    "password": "12345678"
}'

The access token will return like this

{
  "data": {
    "access_token": {
      "token": "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiJlNTMycW9zOGpqTTIiLCJleHAiOjE2ODAyNTI0MDgsIm5iZiI6MTY3OTY0NzYwOCwiaWF0IjoxNjc5NjQ3NjA4LCJqdGkiOiI3OTEzYzhjYy05NmI0LTQ3ZmUtOWIzZi01MTUwZTk5NTM3MGUifQ.51d6zVuGtcAbw2poEWV4TffhEqJG8uxMOcGq7Mt8sZA",
      "expire_in": 604800
    }
  }
}
  • Create a new task
curl --location 'http://localhost:3000/v1/tasks' \
--header 'Authorization: Bearer eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiJlNTMycW9zOGpqTTIiLCJleHAiOjE2ODAyNTI0MDgsIm5iZiI6MTY3OTY0NzYwOCwiaWF0IjoxNjc5NjQ3NjA4LCJqdGkiOiI3OTEzYzhjYy05NmI0LTQ3ZmUtOWIzZi01MTUwZTk5NTM3MGUifQ.51d6zVuGtcAbw2poEWV4TffhEqJG8uxMOcGq7Mt8sZA' \
--header 'Content-Type: application/json' \
--data '{
    "title": "This is a new task",
    "description": "Build a simple demo clean architecture"
}'

New Task id will be returned

{"data":"e532sJ4XpCi8"}
  • Fetch list tasks
curl --location 'http://localhost:3000/v1/tasks' \
--header 'Authorization: Bearer eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiJnR3pUQlVScWhhakciLCJleHAiOjE2ODAwNjQzNzcsIm5iZiI6MTY3OTQ1OTU3NywiaWF0IjoxNjc5NDU5NTc3LCJqdGkiOiI5Y2U4ZjUwMC1hYTczLTQ1MTYtYmJhYy04OTBiNDBjNDVkMDAifQ.VsqU8_Gn_EMwKAYW-En3BG58nWTREG6s3zCVXu7sZgQ'
{
  "data": [
    {
      "id": "e532sJ4XpCi8",
      "created_at": "2023-03-24T08:50:07Z",
      "updated_at": "2023-03-24T08:50:07Z",
      "title": "This is a new task",
      "description": "Build a simple demo clean architecture",
      "status": "doing",
      "user": {
        "id": "e532qos8jjM2",
        "last_name": "Microservices",
        "first_name": "Demo",
        "avatar": null
      }
    }
  ],
  "paging": {
    "page": 1,
    "limit": 10,
    "total": 1,
    "cursor": "",
    "next_cursor": ""
  },
  "extra": {}
}

Conclusion

Building services with Clean Architecture is difficult, especially in Microservices. I hope this repo help you. Enjoy it and feel free to create PRs or Issues.