Search icon CANCEL
Subscription
0
Cart icon
Your Cart (0 item)
Close icon
You have no products in your basket yet
Arrow left icon
Explore Products
Best Sellers
New Releases
Books
Videos
Audiobooks
Learning Hub
Newsletter Hub
Free Learning
Arrow right icon
timer SALE ENDS IN
0 Days
:
00 Hours
:
00 Minutes
:
00 Seconds
Arrow up icon
GO TO TOP
Implementing Event-Driven Microservices Architecture in .NET 7

You're reading from   Implementing Event-Driven Microservices Architecture in .NET 7 Develop event-based distributed apps that can scale with ever-changing business demands using C# 11 and .NET 7

Arrow left icon
Product type Paperback
Published in Mar 2023
Publisher Packt
ISBN-13 9781803232782
Length 326 pages
Edition 1st Edition
Languages
Tools
Arrow right icon
Authors (2):
Arrow left icon
Joshua Garverick Joshua Garverick
Author Profile Icon Joshua Garverick
Joshua Garverick
Omar Dean McIver Omar Dean McIver
Author Profile Icon Omar Dean McIver
Omar Dean McIver
Arrow right icon
View More author details
Toc

Table of Contents (21) Chapters Close

Preface 1. Part 1:Event-Driven Architecture and .NET 7
2. Chapter 1: The Sample Application FREE CHAPTER 3. Chapter 2: The Producer-Consumer Pattern 4. Chapter 3: Message Brokers 5. Chapter 4: Domain Model and Asynchronous Events 6. Part 2:Testing and Deploying Microservices
7. Chapter 5: Containerization and Local Environment Setup 8. Chapter 6: Localized Testing and Debugging of Microservices 9. Chapter 7: Microservice Observability 10. Chapter 8: CI/CD Pipelines and Integrated Testing 11. Chapter 9: Fault Injection and Chaos Testing 12. Part 3:Testing and Deploying Microservices
13. Chapter 10: Modern Design Patterns for Scalability 14. Chapter 11: Minimizing Data Loss 15. Chapter 12: Service and Application Resiliency 16. Chapter 13: Telemetry Capture and Integration 17. Chapter 14: Observability Revisited 18. Assessments 19. Index 20. Other Books You May Enjoy

Reviewing domain structures and components

In Chapter 1, The Sample Application, we took a quick look at the outlined domains for the application, as well as a few (but not all) of the commands, events, entities, and other domain objects. Now that we are armed with some knowledge of how the consumer-producer pattern works and how the message broker facilitates that pattern, we will dive into each domain at length to review the pertinent objects within them.

Equipment

The equipment domain is of critical importance. Without a means to manage events that are related to the turnstile units, as well as the cameras in each unit, the application itself does not serve much of a purpose. The following diagram shows the domain architecture for the equipment domain:

Figure 4.2 – The domain architecture for the equipment domain

Figure 4.2 – The domain architecture for the equipment domain

The equipment domain is central to the application. Many events are triggered by events that originate from this domain.

Aggregates

The equipment domain leverages two aggregate root objects to manage all interactions within the domain:

  • Camera: This is used to track basic device information related to the camera and associated maintenance events. It includes the camera ID, the equipment model information, and the station ID.
  • Turnstile: This is used to track basic device information related to the turnstile and associated maintenance events. It includes the turnstile ID, the equipment model information, the maximum number of turns before maintenance is required, the install date, and the station ID.

You will notice that the camera and turnstile aggregates appear in other domains as well. In some cases, they have different information associated with them. Since these are objects that are relevant across several domains, it is common to see this level of duplication. The events and entities they interact with, however, will be relegated to that particular domain.

Entities

The equipment domain interacts with the station domain entity to help track equipment. This is a domain entity that contains minimal station information (ID and address), as well as a full inventory of equipment at that location.

Events

There are nine core events within the equipment domain. All but one of these events is related to actions that can occur with a turnstile. The only event associated with a camera is CameraInstalled, which is triggered after TurnstileCameraInstalled is handled. CameraInstalled intends to pass the model information of the camera back to the domain and associate it with the turnstile and the station.

Event handlers

There are three specific event handlers, two of which are related to the turnstiles located within a station (installation and decommissioning). There is also an event handler for closing stations, which would lead to decommissioning all the equipment objects related to that station.

Value objects

For value objects, we have the following entities:

  • Address: A standard address format that's used to locate the station.
  • Model: Equipment model information related to a turnstile, camera, or another type of station equipment.

Now that we have a better understanding of the workings of the equipment domain, let's move on to the station domain.

Station

The station domain deals with domain objects directly related to physical mass transit stations. This is more of a supportive domain in the context of the application as the primary interactions are with the equipment at each station. There is a need to identify where each piece of equipment is, and some core data around that, which is where the station domain comes in. The following diagram shows the domain architecture for the station domain:

Figure 4.3 – The domain architecture for the station domain

Figure 4.3 – The domain architecture for the station domain

While it may seem that this domain is rather small, it does serve a greater purpose, giving a location to equipment, maintenance records, scheduling, and identifying potentially dangerous fugitives at large.

Aggregates

The primary aggregate for this domain is the station. This aggregate tracks basic information about the station, including whether it is still open (operational) or closed. It also allows the history of work orders associated with the station to be pulled.

Entities

There is only one domain entity associated with the station, and that is WorkOrder. This is a domain entity that contains information about a specific work order related to a maintenance schedule. It can apply to any type of equipment and captures when the work order was created, when it was assigned, and when it was completed.

Events

There are six domain events related to stations:

  • Two are related to a change in station information (name or address).
  • Two events indicate a change in the station's status.
  • Two events deal with installing or decommissioning a turnstile in a station.

These events relate directly to the event handlers for the domain, listed in the next paragraph.

Event handlers

The station domain has three event handlers to manage events related to the station, namely a change in name, address, or status. Status indicators for a station include active, closed, and offline.

Maintenance

The maintenance domain deals with events related to any maintenance that's needed on turnstiles and cameras at any mass transit station. While not responsible for scheduling maintenance, it is responsible for raising events that state that maintenance is needed, which, in turn, will raise events in the scheduling domain to initiate the creation of a work order. This is shown in the following diagram:

Figure 4.4 – The domain architecture for the maintenance domain

Figure 4.4 – The domain architecture for the maintenance domain

The maintenance domain is managed by several different domain objects. Let's take a look.

Aggregates

The maintenance domain leverages the camera and the turnstile aggregates, as shown in the equipment domain, though the events that each control are different. In the case of this domain, the events that are leveraged only reference the events that can be triggered to invoke maintenance requests.

Entities

The sole domain entity for the maintenance domain is the station, a minimalist domain entity that tracks the equipment for a particular station. This only contains the station ID, the address, and a list of equipment that's been registered to the station.

Events

Two events indicate when a maintenance request is triggered, one for a camera and one for a turnstile. There is also an event that can be raised when a turnstile exceeds its maximum number of turns.

Event handlers

There are two event handlers for managing an incoming maintenance request (one for turnstiles and one for cameras) and one for managing an incoming event that's triggered by the turnstile exceeding its maximum turn count.

With that, we have seen how the maintenance domain handles requests for maintenance activities to be performed. Next, we will look into the scheduling domain and its relationship with the maintenance domain.

Scheduling

The scheduling domain deals with adding, updating, or removing scheduled maintenance events. These changes in schedule status are triggered primarily from the maintenance domain but can be triggered from the equipment domain as well in the case of a jammed turnstile:

Figure 4.5 – The domain architecture for the scheduling domain

Figure 4.5 – The domain architecture for the scheduling domain

The scheduling domain is split into the object types shown in the preceding diagram, which are responsible for scheduling maintenance activities. Let's take a closer look.

Aggregates

The scheduling domain has two aggregate roots that manage scheduling maintenance activities. One is CameraMaintenceSchedule, which deals with any maintenance schedule records related to camera equipment. The other is TurnstileMaintenanceSchedule, which deals with any maintenance schedule records related to turnstiles.

Entities

There is only one domain entity that the scheduling domain deals directly with, and that is the WorkOrder entity. WorkOrder is a domain entity that contains information about a specific work order related to a maintenance schedule. It can apply to any type of equipment and captures when the work order was created, when it was assigned, and when it was completed.

Events

There are a total of six events in the domain, split across the two aggregates evenly. There are create, change, and remove events for turnstiles as well as cameras.

Event handlers

Three event handlers exist within the domain, one for each action type that can be performed on a schedule: creation, modification, or removal.

As we've seen, the scheduling domain manages how work orders are created to facilitate maintenance activities taking place on equipment located within a station. Next, we'll look at the notifications domain, which is a crucial part of the application.

Notifications

The notifications domain deals with sending notifications to various consumers as a direct result of an event being handled. Configurations are stored in the domain to help classify the type of notification, where it should go, and what template to use when deriving the output. The following diagram shows the domain architecture of the notifications domain:

Figure 4.6 – The domain architecture for the notifications domain

Figure 4.6 – The domain architecture for the notifications domain

Notifications are a critical part of the application since many domains need to send notifications out once certain events have been handled. Let's take a look at the notifications domain in a bit more detail.

Aggregates

There is only one aggregate root within the notifications domain, and that is NotificationConfiguration. This aggregate contains information about a specific notification configuration setup. It houses the configuration identifier, the address to deliver the notification to, the type of notification, and a template identifier that can optionally be used to pull in a template to format the body of the notification itself.

Events

This domain has three events related to NotificationConfiguration – one for creating a configuration, one for updating it, and one for removing it from use.

Event handlers

There are three event handlers:

  • MaintenanceRequested: This will handle a maintenance request being raised and create a WorkOrder to initiate the process.
  • WorkOrderCreated: This will handle the initial processing of WorkOrder once the maintenance request event has been handled.
  • OffenderIdentified: This will send a notification to the appropriate recipients when an event is raised by the identification domain stating that a match has been found in the offender list.

Now that we've covered the notifications domain, we can move on to the passenger domain.

Passenger

The passenger domain is reserved for future use, where payment information and other program membership information may be stored. The overall structure of this domain has been planned out, but the code for any implementations has not been written. The following diagram shows the domain architecture of the passenger domain:

Figure 4.7 – The domain architecture for the passenger domain

Figure 4.7 – The domain architecture for the passenger domain

While this domain is not widely used across the application at this point, it does have a tie-in to the identification domain and allows for future expansion into more customer-facing interactions.

Aggregates

The passenger domain has only one aggregate root, which happens to be the passenger. This aggregate contains the identifier for the passenger along with a reference to the LoyaltyProgram entity. A separate structure for passenger information (PassengerInfo) is also used to update basic information for the passenger.

Events

There are three events related to the loyalty program itself: one for requesting a new program for the passenger, one for updating the information, and one for retiring or closing out the program. There is also an event for updating the passenger's information by way of the PassengerInfo object.

Event handlers

A total of four event handlers are a part of this domain. Three of those handlers are related to the loyalty program events mentioned in the events section, while the other is related to the passenger information being updated. Each will fire a notification on completion to inform the passenger of changes.

Identification

The identification domain is solely responsible for taking images that have been captured by station cameras and validating them against a known list of fugitives wanted by law enforcement. The following diagram shows the domain architecture for the identification domain:

Figure 4.8 – The domain architecture for the identification domain

Figure 4.8 – The domain architecture for the identification domain

The identification domain serves a very focused purpose – allowing potentially dangerous fugitives to be recognized and alerting the appropriate personnel for additional investigation.

Aggregates

There are three aggregates:

  • Camera: This is used to track basic device information related to the camera that has made the identification. It will only store the camera identifier, station identifier, and turnstile identifier.
  • Offender: This is used to track the offender identifier, any station interactions (ingress and egress), and the offender's image.
  • Passenger: This is used to track the passenger identifier, any station interactions (ingress and egress), and the passenger's image.

While there are three aggregates within the domain, there is only one entity explicitly defined, as we will see next.

Entities

The only domain entity the identification domain has is the CustomerStationInteraction entity. This records information about specific interactions at a station, such as the turnstile the passenger used, as well as the ingress (entry) or egress (exit) timestamp. While both timestamps may have values for a single station, it is more common that one or the other will have a value based on the passenger's travel.

Events

The passenger domain only produces two events. One is for passenger identification, while the other is for offender identification. The offender identification event is raised when the camera interacts with facial recognition services to identify a fugitive on a selected list.

Event handlers

Just as the passenger domain only has two events, it also only has two event handlers. Each event handler matches up with either the passenger or offender identification. Each event handler will create a record of the identification using the CustomerStationInteraction entity, and in the case of an offender, a notification will also be sent.

Important note

Please take some time to review the source code for each domain solution, as well as the shared code library (MTAEDA.sln), in the src folder of the main repository.

With that, we've looked through the details of each domain, understanding how they operate as well as how they interact with each other's events. As we have learned throughout this book, these events do not require immediate responses. Now, let's look at asynchronous actions.

lock icon The rest of the chapter is locked
Register for a free Packt account to unlock a world of extra content!
A free Packt account unlocks extra newsletters, articles, discounted offers, and much more. Start advancing your knowledge today.
Unlock this book and the full library FREE for 7 days
Get unlimited access to 7000+ expert-authored eBooks and videos courses covering every tech area you can think of
Renews at $19.99/month. Cancel anytime