Skip to content

Commit 6c65c97

Browse files
authored
Merge pull request #218244 from spelluru/ehubalance1114
review & update
2 parents 92745ba + a27689a commit 6c65c97

File tree

2 files changed

+26
-25
lines changed

2 files changed

+26
-25
lines changed

articles/event-hubs/event-hubs-federation-patterns.md

Lines changed: 11 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -32,7 +32,7 @@ samples and the [Use Apache Kafka MirrorMaker with Event Hubs](event-hubs-kafka-
3232

3333
### Streams and order preservation
3434

35-
Replication, either through Azure Functions or Azure Stream Analytics, does not
35+
Replication, either through Azure Functions or Azure Stream Analytics, doesn't
3636
aim to assure the creation of exact 1:1 clones of a source Event Hub into a
3737
target Event Hub, but focuses on preserving the relative order of events where
3838
the application requires it. The application communicates this by grouping
@@ -89,13 +89,13 @@ existing properties, with values separated by semicolons.
8989

9090
### Failover
9191

92-
If you are using replication for disaster recovery purposes, to protect against
92+
If you're using replication for disaster recovery purposes, to protect against
9393
regional availability events in the Event Hubs service, or against network
9494
interruptions, any such failure scenario will require performing a failover from
9595
one Event Hub to the next, telling producers and/or consumers to use the
9696
secondary endpoint.
9797

98-
For all failover scenarios, it is assumed that the required elements of the
98+
For all failover scenarios, it's assumed that the required elements of the
9999
namespaces are structurally identical, meaning that Event Hubs and Consumer
100100
Groups are identically named and that shared access signature rules and/or
101101
role-based access control rules are set up in the same way. You can create (and
@@ -116,13 +116,13 @@ One candidate approach is to hold the information in DNS SRV records in a DNS
116116
you control and point to the respective Event Hub endpoints.
117117

118118
> [!IMPORTANT]
119-
> Mind that Event Hubs does not allow for its endpoints to be
120-
> directly aliased with CNAME records, which means you will use DNS as a
119+
> Mind that Event Hubs doesn't allow for its endpoints to be
120+
> directly aliased with CNAME records, which means you'll use DNS as a
121121
> resilient lookup mechanism for endpoint addresses and not to directly resolve
122122
> IP address information.
123123
124124
Assume you own the domain `example.com` and, for your application, a zone
125-
`test.example.com`. For two alternate Event Hubs, you will now create two
125+
`test.example.com`. For two alternate Event Hubs, you'll now create two
126126
further nested zones, and an SRV record in each.
127127

128128
The SRV records are, following common convention, prefixed with
@@ -204,7 +204,7 @@ from about the same position where processing was interrupted.
204204

205205
To realize either scenario and using the event processor of your respective
206206
Azure SDK,
207-
[you will create a new checkpoint store](event-processor-balance-partition-load.md#checkpointing)
207+
[you will create a new checkpoint store](event-processor-balance-partition-load.md#checkpoint)
208208
and provide an initial partition position, based on the _timestamp_ that you
209209
want to resume processing from.
210210

@@ -229,7 +229,7 @@ Variations of these patters are:
229229
those Event Hubs containing the same streams, no matter where events are
230230
produced.
231231

232-
The first two pattern variations are trivial and do not differ from plain
232+
The first two pattern variations are trivial and don't differ from plain
233233
replication tasks.
234234

235235
The last scenario requires excluding already replicated events from being
@@ -262,7 +262,7 @@ Examples for such modifications are:
262262
input event transfer or aggregate a set of events that are then transferred
263263
together.
264264
- **_Validation_** - Event data from external sources often need to be checked
265-
for whether they are in compliance with a set of rules before they may be
265+
for whether they're in compliance with a set of rules before they may be
266266
forwarded. The rules may be expressed using schemas or code. Events that are
267267
found not to be in compliance may be dropped, with the issue noted in logs, or
268268
may be forwarded to a special target destination to handle them further.
@@ -273,7 +273,7 @@ Examples for such modifications are:
273273
contained in the events.
274274
- **_Filtering_** - Some events arriving from a source might have to be withheld
275275
from the target based on some rule. A filter tests the event against a rule
276-
and drops the event if the event does not match the rule. Filtering out
276+
and drops the event if the event doesn't match the rule. Filtering out
277277
duplicate events by observing certain criteria and dropping subsequent events
278278
with the same values is a form of filtering.
279279
- **_Cryptography_** - A replication task may have to decrypt content arriving
@@ -341,7 +341,7 @@ select * into dest2Output from inputSource where Info = 2
341341
The log projection pattern flattens the event stream onto an indexed database,
342342
with events becoming records in the database. Typically, events are added to the
343343
same collection or table, and the Event Hub partition key becomes part of the
344-
the primary key looking for making the record unique.
344+
primary key looking for making the record unique.
345345

346346
Log projection can produce a time-series historian of your event data or a
347347
compacted view, whereby only the latest event is retained for each partition

articles/event-hubs/event-processor-balance-partition-load.md

Lines changed: 15 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -2,13 +2,14 @@
22
title: Balance partition load across multiple instances - Azure Event Hubs | Microsoft Docs
33
description: Describes how to balance partition load across multiple instances of your application using an event processor and the Azure Event Hubs SDK.
44
ms.topic: conceptual
5-
ms.date: 09/15/2021
5+
ms.date: 11/14/2022
66
---
77

88
# Balance partition load across multiple instances of your application
9-
To scale your event processing application, you can run multiple instances of the application and have it balance the load among themselves. In the older versions, [EventProcessorHost](event-hubs-event-processor-host.md) allowed you to balance the load between multiple instances of your program and checkpoint events when receiving. In the newer versions (5.0 onwards), **EventProcessorClient** (.NET and Java), or **EventHubConsumerClient** (Python and JavaScript) allows you to do the same. The development model is made simpler by using events. You subscribe to the events that you're interested in by registering an event handler. If you're using the old version of the client library, see the following migration guides: [.NET](https://github.com/Azure/azure-sdk-for-net/blob/master/sdk/eventhub/Azure.Messaging.EventHubs/MigrationGuide.md), [Java](https://github.com/Azure/azure-sdk-for-java/blob/master/sdk/servicebus/azure-messaging-servicebus/migration-guide.md), [Python](https://github.com/Azure/azure-sdk-for-python/blob/master/sdk/servicebus/azure-servicebus/migration_guide.md), and [JavaScript](https://github.com/Azure/azure-sdk-for-js/blob/master/sdk/servicebus/service-bus/migrationguide.md).
109

11-
This article describes a sample scenario for using multiple instances to read events from an event hub and then give you details about features of event processor client, which allows you to receive events from multiple partitions at once and load balance with other consumers that use the same event hub and consumer group.
10+
To scale your event processing application, you can run multiple instances of the application and have the load balanced among themselves. In the older versions, [EventProcessorHost](event-hubs-event-processor-host.md) allowed you to balance the load between multiple instances of your program and checkpoint events when receiving the events. In the newer versions (5.0 onwards), **EventProcessorClient** (.NET and Java), or **EventHubConsumerClient** (Python and JavaScript) allows you to do the same. The development model is made simpler by using events. You subscribe to the events that you're interested in by registering an event handler. If you're using the old version of the client library, see the following migration guides: [.NET](https://github.com/Azure/azure-sdk-for-net/blob/master/sdk/eventhub/Azure.Messaging.EventHubs/MigrationGuide.md), [Java](https://github.com/Azure/azure-sdk-for-java/blob/master/sdk/servicebus/azure-messaging-servicebus/migration-guide.md), [Python](https://github.com/Azure/azure-sdk-for-python/blob/master/sdk/servicebus/azure-servicebus/migration_guide.md), and [JavaScript](https://github.com/Azure/azure-sdk-for-js/blob/master/sdk/servicebus/service-bus/migrationguide.md).
11+
12+
This article describes a sample scenario for using multiple instances of client `applications to read events from an event hub. It also gives you details about features of event processor client, which allows you to receive events from multiple partitions at once and load balance with other consumers that use the same event hub and consumer group.
1213

1314
> [!NOTE]
1415
> The key to scale for Event Hubs is the idea of partitioned consumers. In contrast to the [competing consumers](/previous-versions/msp-n-p/dn568101(v=pandp.10)) pattern, the partitioned consumer pattern enables high scale by removing the contention bottleneck and facilitating end to end parallelism.
@@ -19,32 +20,32 @@ As an example scenario, consider a home security company that monitors 100,000 h
1920

2021
Each sensor pushes data to an event hub. The event hub is configured with 16 partitions. On the consuming end, you need a mechanism that can read these events, consolidate them (filter, aggregate, and so on) and dump the aggregate to a storage blob, which is then projected to a user-friendly web page.
2122

22-
## Write the consumer application
23+
## Consumer application
2324

2425
When designing the consumer in a distributed environment, the scenario must handle the following requirements:
2526

2627
1. **Scale:** Create multiple consumers, with each consumer taking ownership of reading from a few Event Hubs partitions.
2728
2. **Load balance:** Increase or reduce the consumers dynamically. For example, when a new sensor type (for example, a carbon monoxide detector) is added to each home, the number of events increases. In that case, the operator (a human) increases the number of consumer instances. Then, the pool of consumers can rebalance the number of partitions they own, to share the load with the newly added consumers.
2829
3. **Seamless resume on failures:** If a consumer (**consumer A**) fails (for example, the virtual machine hosting the consumer suddenly crashes), then other consumers can pick up the partitions owned by **consumer A** and continue. Also, the continuation point, called a *checkpoint* or *offset*, should be at the exact point at which **consumer A** failed, or slightly before that.
29-
4. **Consume events:** While the previous three points deal with the management of the consumer, there must be code to consume the events and do something useful with it. For example, aggregate it and upload it to blob storage.
30+
4. **Consume events:** While the previous three points deal with the management of the consumer, there must be code to consume events and do something useful with it. For example, aggregate it and upload it to blob storage.
3031

3132
## Event processor or consumer client
3233

33-
You don't need to build your own solution to meet these requirements. The Azure Event Hubs SDKs provide this functionality. In .NET or Java SDKs, you use an event processor client (EventProcessorClient), and in Python and JavaScript SDKs, you use EventHubConsumerClient. In the old version of SDK, it was the event processor host (EventProcessorHost) that supported these features.
34+
You don't need to build your own solution to meet these requirements. The Azure Event Hubs SDKs provide this functionality. In .NET or Java SDKs, you use an event processor client (`EventProcessorClient`), and in Python and JavaScript SDKs, you use `EventHubConsumerClient`. In the old version of SDK, it was the event processor host (`EventProcessorHost`) that supported these features.
3435

35-
For the majority of production scenarios, we recommend that you use the event processor client for reading and processing events. The processor client is intended to provide a robust experience for processing events across all partitions of an event hub in a performant and fault tolerant manner while providing a means to checkpoint its progress. Event processor clients can work cooperatively within the context of a consumer group for a given event hub. Clients will automatically manage distribution and balancing of work as instances become available or unavailable for the group.
36+
For most production scenarios, we recommend that you use the event processor client for reading and processing events. The processor client is intended to provide a robust experience for processing events across all partitions of an event hub in a performant and fault tolerant manner while providing a means to checkpoint its progress. Event processor clients can work cooperatively within the context of a consumer group for a given event hub. Clients will automatically manage distribution and balancing of work as instances become available or unavailable for the group.
3637

37-
## Partition ownership tracking
38+
## Partition ownership
3839

3940
An event processor instance typically owns and processes events from one or more partitions. Ownership of partitions is evenly distributed among all the active event processor instances associated with an event hub and consumer group combination.
4041

41-
Each event processor is given a unique identifier and claims ownership of partitions by adding or updating an entry in a checkpoint store. All event processor instances communicate with this store periodically to update its own processing state as well as to learn about other active instances. This data is then used to balance the load among the active processors. New instances can join the processing pool to scale up. When instances go down, either because of failures or to scale down, partition ownership is gracefully transferred to other active processors.
42+
Each event processor is given a unique identifier and claims ownership of partitions by adding or updating an entry in a checkpoint store. All event processor instances communicate with this store periodically to update its own processing state and to learn about other active instances. This data is then used to balance the load among the active processors. New instances can join the processing pool to scale up. When instances go down, either because of failures or to scale down, partition ownership is gracefully transferred to other active processors.
4243

4344
Partition ownership records in the checkpoint store keep track of Event Hubs namespace, event hub name, consumer group, event processor identifier (also known as owner), partition ID, and the last modified time.
4445

4546

4647

47-
| Event Hubs namespace | Event Hub name | **Consumer group** | Owner | Partition ID | Last modified time |
48+
| Event Hubs namespace | Event hub name | **Consumer group** | Owner | Partition ID | Last modified time |
4849
| ---------------------------------- | -------------- | :----------------- | :----------------------------------- | :----------- | :------------------ |
4950
| mynamespace.servicebus.windows.net | myeventhub | myconsumergroup | 3be3f9d3-9d9e-4c50-9491-85ece8334ff6 | 0 | 2020-01-15T01:22:15 |
5051
| mynamespace.servicebus.windows.net | myeventhub | myconsumergroup | f5cc5176-ce96-4bb4-bbaa-a0e3a9054ecf | 1 | 2020-01-15T01:22:17 |
@@ -53,15 +54,15 @@ Partition ownership records in the checkpoint store keep track of Event Hubs nam
5354
| | | : | | | |
5455
| mynamespace.servicebus.windows.net | myeventhub | myconsumergroup | 844bd8fb-1f3a-4580-984d-6324f9e208af | 15 | 2020-01-15T01:22:00 |
5556

56-
Each event processor instance acquires ownership of a partition and starts processing the partition from last known [checkpoint](#checkpointing). If a processor fails (VM shuts down), then other instances detect it by looking at the last modified time. Other instances try to get ownership of the partitions previously owned by the inactive instance, and the checkpoint store guarantees that only one of the instances succeeds in claiming ownership of a partition. So, at any given point of time, there is at most one processor that receives events from a partition.
57+
Each event processor instance acquires ownership of a partition and starts processing the partition from last known [checkpoint](#checkpoint). If a processor fails (VM shuts down), then other instances detect it by looking at the last modified time. Other instances try to get ownership of the partitions previously owned by the inactive instance. The checkpoint store guarantees that only one of the instances succeeds in claiming ownership of a partition. So, at any given point of time, there is at most one processor that receives events from a partition.
5758

5859
## Receive messages
5960

60-
When you create an event processor, you specify the functions that will process events and errors. Each call to the function that processes events delivers a single event from a specific partition. It's your responsibility to handle this event. If you want to make sure the consumer processes every message at least once, you need to write your own code with retry logic. But be cautious about poisoned messages.
61+
When you create an event processor, you specify functions that will process events and errors. Each call to the function that processes events delivers a single event from a specific partition. It's your responsibility to handle this event. If you want to make sure the consumer processes every message at least once, you need to write your own code with retry logic. But be cautious about poisoned messages.
6162

6263
We recommend that you do things relatively fast. That is, do as little processing as possible. If you need to write to storage and do some routing, it's better to use two consumer groups and have two event processors.
6364

64-
## Checkpointing
65+
## Checkpoint
6566

6667
*Checkpointing* is a process by which an event processor marks or commits the position of the last successfully processed event within a partition. Marking a checkpoint is typically done within the function that processes the events and occurs on a per-partition basis within a consumer group.
6768

@@ -78,7 +79,7 @@ When the checkpoint is performed to mark an event as processed, an entry in chec
7879
7980
## Thread safety and processor instances
8081

81-
By default, the function that processes the events is called sequentially for a given partition. Subsequent events and calls to this function from the same partition queue up behind the scenes as the event pump continues to run in the background on other threads. Events from different partitions can be processed concurrently and any shared state that is accessed across partitions have to be synchronized.
82+
By default, the function that processes events is called sequentially for a given partition. Subsequent events and calls to this function from the same partition queue up behind the scenes as the event pump continues to run in the background on other threads. Events from different partitions can be processed concurrently and any shared state that is accessed across partitions have to be synchronized.
8283

8384
## Next steps
8485
See the following quick starts:

0 commit comments

Comments
 (0)