Convert Figma logo to code with AI

microservices-patterns logoftgo-application

Example code for the book Microservice patterns

3,471
1,328
3,471
97

Top Related Projects

Cross-platform .NET sample microservices and container based application that runs on Linux Windows and macOS. Powered by .NET 7, Docker Containers and Azure Kubernetes Services. Supports Visual Studio, VS for Mac and CLI based environments with Docker CLI, dotnet CLI, VS Code or any other code editor. Moved to https://github.com/dotnet/eShop.

Quick Overview

The ftgo-application repository is a sample implementation of a food delivery application using a microservices architecture. It demonstrates the use of various design patterns and best practices for building scalable and maintainable microservices-based systems.

Pros

  • Microservices Architecture: The application is designed using a microservices architecture, which promotes modularity, scalability, and independent deployment of individual services.
  • Design Patterns: The project showcases the implementation of several microservices design patterns, such as the Saga pattern, the API Gateway pattern, and the Circuit Breaker pattern.
  • Polyglot Persistence: The application utilizes different data storage technologies (e.g., MongoDB, PostgreSQL) for different microservices, demonstrating the flexibility of a polyglot persistence approach.
  • Comprehensive Documentation: The project's documentation provides detailed explanations of the architecture, design decisions, and implementation details, making it a valuable learning resource.

Cons

  • Complexity: The microservices architecture and the use of various design patterns can make the codebase and deployment more complex, especially for newcomers to the domain.
  • Learning Curve: Developers may need to invest time in understanding the different components, technologies, and patterns used in the project, which can be a barrier to entry.
  • Overhead: The microservices approach introduces additional overhead, such as network latency, service discovery, and coordination, which need to be carefully managed.
  • Operational Challenges: Running and maintaining a microservices-based application can be more challenging compared to a monolithic application, requiring additional tooling and infrastructure.

Getting Started

To get started with the ftgo-application project, follow these steps:

  1. Clone the repository:
git clone https://github.com/microservices-patterns/ftgo-application.git
  1. Navigate to the project directory:
cd ftgo-application
  1. Set up the required infrastructure (e.g., MongoDB, PostgreSQL) using the provided Docker Compose configuration:
docker-compose up -d
  1. Build and run the individual microservices using the provided Gradle commands:
./gradlew :ftgo-order-service:bootRun
./gradlew :ftgo-restaurant-service:bootRun
# Run other services as needed
  1. Access the application through the API Gateway, which is typically available at http://localhost:8080.

  2. Explore the project's documentation to understand the architecture, design patterns, and implementation details.

Competitor Comparisons

Cross-platform .NET sample microservices and container based application that runs on Linux Windows and macOS. Powered by .NET 7, Docker Containers and Azure Kubernetes Services. Supports Visual Studio, VS for Mac and CLI based environments with Docker CLI, dotnet CLI, VS Code or any other code editor. Moved to https://github.com/dotnet/eShop.

Pros of eShopOnContainers

  • More comprehensive and production-ready, with a full-fledged e-commerce application
  • Extensive documentation and learning resources, including eBooks and video courses
  • Broader technology stack, showcasing various Azure services and .NET technologies

Cons of eShopOnContainers

  • Larger and more complex, potentially overwhelming for beginners
  • Heavily focused on Microsoft technologies, which may limit its applicability for non-.NET developers
  • Requires more resources to run and deploy due to its comprehensive nature

Code Comparison

eShopOnContainers (C#):

public class CatalogItem
{
    public int Id { get; set; }
    public string Name { get; set; }
    public string Description { get; set; }
    public decimal Price { get; set; }
    public string PictureFileName { get; set; }
}

ftgo-application (Java):

public class MenuItem {
    private String id;
    private String name;
    private Money price;

    // Constructor, getters, and setters
}

Both repositories demonstrate microservices architecture, but eShopOnContainers provides a more extensive implementation with additional features and services. The ftgo-application focuses on core microservices patterns and is more lightweight, making it easier to understand for those new to microservices. eShopOnContainers offers a broader learning experience but requires more time and resources to explore fully.

Convert Figma logo designs to code with AI

Visual Copilot

Introducing Visual Copilot: A new AI model to turn Figma designs to high quality code using your components.

Try Visual Copilot

README

= FTGO example application

This is the example code for my book https://microservices.io/book[Microservice patterns].

image::http://microservices.io/i/Microservices-Patterns-Cover.png[width=50%]

== Please note

  • The code is still work in progress
  • It primarily illustrates the technical aspects of the microservice architecture and so the business logic is minimal
  • The documentation is sparse/non-existent and you will need to look in the book
  • The application consists of many services and so requires a lot of memory. It runs well, for example, on a 16GB Macbook pro.
  • The application's services and the infrastructure services, such as MySQL and Apache Kafka, are deployed using Docker containers using either Docker Compose or Kubernetes.

== Got questions?

Please create a https://github.com/microservices-patterns/ftgo-application/issues[github issue] and I'll do my best to help you.

== Application architecture

Not surprisingly, this application has a microservice architecture. There are the following services:

  • link:./ftgo-consumer-service[ftgo-consumer-service] - the Consumer Service
  • link:./ftgo-restaurant-service[ftgo-restaurant-service] - the Restaurant Service
  • link:./ftgo-order-service[ftgo-order-service] - the Order Service
  • link:./ftgo-kitchen-service[ftgo-kitchen-service] - the Kitchen Service
  • link:./ftgo-accounting-service[ftgo-accounting-service] - the Accounting Service
  • link:./ftgo-order-history-service[ftgo-order-history-service] - a Order History Service, which is a CQRS view
  • link:./ftgo-api-gateway[ftgo-api-gateway] - the API gateway

== Service design

Key points:

  • A service consists of a single Gradle module. For example, ftgo-order-service implements the Order Service
  • A service is a Spring Boot application
  • A service has a Swagger UI http://.../swagger-ui.html. See open-swagger-uis.sh
  • A service typically consists of the following packages: ** domain - domain logic including aggregates ** messaging - messaging adapters ** web - Spring MVC controllers (HTTP adapters) ** main - the main application
  • The services use the following other frameworks ** https://github.com/eventuate-tram/eventuate-tram-core[`Eventuate Tram framework] - implements transactional messaging ** https://github.com/eventuate-tram/eventuate-tram-sagas[Eventuate Tram Saga framework] - implements sagas ** https://github.com/eventuate-clients/eventuate-client-java[Eventuate Client framework`] - implements event sourcing

== Chapter by chapter

This section maps the chapters to the code.

=== Chapter 3 Inter-process communication in a microservice architecture

  • The services have a REST API
  • The services also communicate using the Apache Kafka message broker via the Eventuate Tram framework

=== Chapter 4 Managing transactions with sagas

The link:./ftgo-order-service[ftgo-order-service] uses sagas to maintain data consistency:

  • link:./ftgo-order-service/src/main/java/net/chrisrichardson/ftgo/orderservice/sagas/createorder/CreateOrderSaga.java[CreateOrderSaga]
  • link:./ftgo-order-service/src/main/java/net/chrisrichardson/ftgo/orderservice/sagas/cancelorder/CancelOrderSaga.java[CancelOrderSaga]
  • link:./ftgo-order-service/src/main/java/net/chrisrichardson/ftgo/orderservice/sagas/reviseorder/ReviseOrderSaga.java[ReviseOrderSaga]

The services that participate in these sagas define the following command handlers:

  • Accounting Service link:./ftgo-accounting-service/src/main/java/net/chrisrichardson/ftgo/accountingservice/messaging/AccountingServiceCommandHandler.java[AccountingServiceCommandHandler]
  • Consumer Service link:./ftgo-consumer-service/src/main/java/net/chrisrichardson/ftgo/consumerservice/domain/ConsumerServiceCommandHandlers.java[ConsumerServiceCommandHandlers]
  • Kitchen Service link:./ftgo-kitchen-service/src/main/java/net/chrisrichardson/ftgo/kitchenservice/messagehandlers/KitchenServiceCommandHandler.java[KitchenServiceCommandHandler]
  • Order Service link:./ftgo-order-service/src/main/java/net/chrisrichardson/ftgo/orderservice/service/OrderCommandHandlers.java[OrderCommandHandlers]

=== Chapter 5 Designing business logic in a microservice architecture

All the services' business logic is implemented using Domain-Driven design aggregates.

  • Accounting Service ** link:./ftgo-accounting-service/src/main/java/net/chrisrichardson/ftgo/accountingservice/domain/Account.java[Account] aggregate in the link:./ftgo-accounting-service[ftgo-accounting-service]
  • Consumer Service ** link:./ftgo-consumer-service/src/main/java/net/chrisrichardson/ftgo/consumerservice/domain/Consumer.java[Consumer]
  • Order Service ** link:./ftgo-order-service/src/main/java/net/chrisrichardson/ftgo/orderservice/domain/Order.java[Order] ** link:./ftgo-order-service/src/main/java/net/chrisrichardson/ftgo/orderservice/domain/Restaurant.java[Restaurant]
  • Kitchen Service ** link:./ftgo-kitchen-service/src/main/java/net/chrisrichardson/ftgo/kitchenservice/domain/Restaurant.java[Restaurant] ** link:./ftgo-kitchen-service/src/main/java/net/chrisrichardson/ftgo/kitchenservice/domain/Ticket.java[Ticket]
  • Restaurant Service ** link:./ftgo-restaurant-service/src/main/java/net/chrisrichardson/ftgo/restaurantservice/domain/Restaurant.java[Restaurant]

=== Chapter 6 Developing business logic with event sourcing

  • The link:./ftgo-accounting-service/src/main/java/net/chrisrichardson/ftgo/accountingservice/domain/Account.java[Account] aggregate in the link:./ftgo-accounting-service[ftgo-accounting-service] is implemented using event sourcing

=== Chapter 7 Implementing queries in a microservice architecture

  • link:./ftgo-order-history-service[ftgo-order-history-service] is an example of a CQRS view
  • link:./ftgo-api-gateway[ftgo-api-gateway] uses API composition to implement the REST endpoint for retrieving the order history

=== Chapter 8 External API patterns

  • link:./ftgo-api-gateway[ftgo-api-gateway] is the API gateway

== Building and running the application

=== Pre-requisites

  • Java 8+
  • Docker and Docker Compose
  • Internet access so that Gradle and Docker can download dependencies and container images

=== Building

Temporary: Build the Spring Cloud Contracts using this command:

./gradlew buildContracts

Build the services using this command:

./gradlew assemble

=== Running the application

Run the application using this command:

./gradlew :composeUp

Note: the ':'

This can take a while.

=== Using the application

Use the services Swagger UIs to invoke the services.

  • Create consumer - http://localhost:8081/swagger-ui/index.html
  • Create a restaurant - http://localhost:8084/swagger-ui/index.html
  • Create an order - http://localhost:8082/swagger-ui/index.html
  • View the order - http://localhost:8082/swagger-ui/index.html
  • View the order history - http://localhost:8086/swagger-ui/index.html

You can also access the application via the API Gateway at http://localhost:8087. However, currently it doesn't have a Swagger UI so you will have to use curl, for example.

Note: if the containers aren't accessible via localhost - e.g. you are using Docker Toolbox, you will have to use ${DOCKER_HOST_IP} as described below.

=== Stopping the application

Stop the application using this command:

./gradlew :composeDown

== Deploying the application on Kubernetes

You can find Kubernetes YAML files in the following directories: deployment/kubernetes and */src/deployment/kubernetes. There are also some helpful shell scripts.

=== Deploying services

You can run this command

./deployment/kubernetes/scripts/kubernetes-deploy-all.sh

=== Undeploying the services

You can run the script to undeploy the services:

./deployment/kubernetes/scripts/kubernetes-delete-all.sh

If you want to delete the persistent volumes for Apache Kafka, Zookeeper and MySQL please run the command:

./deployment/kubernetes/scripts/kubernetes-delete-volumes.sh

== Setting environment variables to do development

You should not need to set any environment variables. To run the application, you certainly do not. Similarly, to do development (e.g. run tests), you typically do not need to set any environment variables. That's because Docker containers are generally accessible (e.g. Docker for Windows/Mac) on the host via localhost. However, if Docker is running elsewhere (e.g. you are using Docker Toolbox) you will need to set DOCKER_HOST_IP.

=== Quick way

A quick way to set the environment variables is to run the script ./set-env.sh.

=== Long way

The value of DOCKER_HOST_IP must be meaningful to both Java services/tests running on your desktop/laptop and to Docker containers. Please do NOT set it to the unresolvable hostname of your machine, localhost or 127.0.0.1 since the Docker containers will probably not work correctly.

=== Verifying that DOCKER_HOST_IP is set correctly

You can verify that DOCKER_HOST_IP is set correctly by running this command:


docker run -p 8889:8888 -e DOCKER_DIAGNOSTICS_PORT=8889 -e DOCKER_HOST_IP
--rm eventuateio/eventuateio-docker-networking-diagnostics:0.2.0.RELEASE

=== Setting the environment variable in your IDE

If you want to run Java services/tests within your IDE on your desktop/laptop AND the Docker containers are not accessible via localhost THEN you will need to set DOCKER_HOST_IP within your IDE. How to do this depends on your operating system and IDE. For example, I find it convenient to launch my IDE from the command line and after setting this environment variable.