< Summary

Class:Azure.Messaging.EventHubs.Primitives.PartitionReceiver
Assembly:Azure.Messaging.EventHubs
File(s):C:\Git\azure-sdk-for-net\sdk\eventhub\Azure.Messaging.EventHubs\src\Primitives\PartitionReceiver.cs
Covered lines:106
Uncovered lines:11
Coverable lines:117
Total lines:495
Line coverage:90.5% (106 of 117)
Covered branches:21
Total branches:22
Branch coverage:95.4% (21 of 22)

Metrics

MethodCyclomatic complexity Line coverage Branch coverage
get_FullyQualifiedNamespace()-100%100%
get_EventHubName()-100%100%
get_ConsumerGroup()-100%100%
get_PartitionId()-100%100%
get_InitialPosition()-100%100%
get_IsClosed()-100%100%
set_IsClosed(...)-100%100%
get_Logger()-0%100%
get_OwnsConnection()-0%100%
get_DefaultMaximumWaitTime()-100%100%
get_RetryPolicy()-100%100%
get_Connection()-100%100%
get_InnerConsumer()-100%100%
.ctor(...)-100%100%
.ctor(...)-100%100%
.ctor(...)-100%100%
.ctor(...)-100%100%
.ctor()-0%100%
GetPartitionPropertiesAsync()-100%100%
ReadLastEnqueuedEventProperties()-100%100%
ReceiveBatchAsync()-100%100%
ReceiveBatchAsync()-100%100%
CloseAsync()-82.61%83.33%
DisposeAsync()-100%100%
Equals(...)-0%100%
GetHashCode()-100%100%
ToString()-0%100%
CreateTransportConsumer(...)-100%100%
ReceiveBatchInternalAsync(...)-100%100%

File(s)

C:\Git\azure-sdk-for-net\sdk\eventhub\Azure.Messaging.EventHubs\src\Primitives\PartitionReceiver.cs

#LineLine coverage
 1// Copyright (c) Microsoft Corporation. All rights reserved.
 2// Licensed under the MIT License.
 3
 4using System;
 5using System.Collections.Generic;
 6using System.ComponentModel;
 7using System.Globalization;
 8using System.Runtime.ExceptionServices;
 9using System.Threading;
 10using System.Threading.Tasks;
 11using Azure.Core;
 12using Azure.Messaging.EventHubs.Consumer;
 13using Azure.Messaging.EventHubs.Core;
 14using Azure.Messaging.EventHubs.Diagnostics;
 15
 16namespace Azure.Messaging.EventHubs.Primitives
 17{
 18    /// <summary>
 19    ///   Allows reading events from a specific partition of an Event Hub, and in the context
 20    ///   of a specific consumer group, to be read with a greater level of control over
 21    ///   communication with the Event Hubs service than is offered by other event consumers.
 22    /// </summary>
 23    ///
 24    /// <remarks>
 25    ///   It is recommended that the <c>EventProcessorClient</c> or <see cref="EventHubConsumerClient" />
 26    ///   be used for reading and processing events for the majority of scenarios.  The partition receiver is
 27    ///   intended to enable scenarios with special needs which require more direct control.
 28    /// </remarks>
 29    ///
 30    /// <seealso href="https://www.nuget.org/packages/Azure.Messaging.EventHubs.Processor" />
 31    /// <seealso cref="EventHubConsumerClient.ReadEventsFromPartitionAsync(string, EventPosition, CancellationToken)"/>
 32    /// <seealso cref="EventHubConsumerClient.ReadEventsFromPartitionAsync(string, EventPosition, ReadEventOptions, Canc
 33    ///
 34    public class PartitionReceiver : IAsyncDisposable
 35    {
 36        /// <summary>Indicates whether or not this instance has been closed.</summary>
 37        private volatile bool _closed = false;
 38
 39        /// <summary>
 40        ///   The fully qualified Event Hubs namespace that the client is associated with.  This is likely
 41        ///   to be similar to <c>{yournamespace}.servicebus.windows.net</c>.
 42        /// </summary>
 43        ///
 244        public string FullyQualifiedNamespace => Connection.FullyQualifiedNamespace;
 45
 46        /// <summary>
 47        ///   The name of the Event Hub that the client is connected to, specific to the
 48        ///   Event Hubs namespace that contains it.
 49        /// </summary>
 50        ///
 5851        public string EventHubName => Connection.EventHubName;
 52
 53        /// <summary>
 54        ///   The name of the consumer group that this client is associated with.  Events will be read
 55        ///   only in the context of this group.
 56        /// </summary>
 57        ///
 1258        public string ConsumerGroup { get; }
 59
 60        /// <summary>
 61        ///   The identifier of the Event Hub partition that this client is associated with.  Events will be read
 62        ///   only from this partition.
 63        /// </summary>
 64        ///
 2265        public string PartitionId { get; }
 66
 67        /// <summary>
 68        ///   The position within the partition where the client begins reading events.
 69        /// </summary>
 70        ///
 1271        public EventPosition InitialPosition { get; }
 72
 73        /// <summary>
 74        ///   Indicates whether or not this <see cref="PartitionReceiver"/> has been closed.
 75        /// </summary>
 76        ///
 77        /// <value>
 78        ///   <c>true</c> if the client is closed; otherwise, <c>false</c>.
 79        /// </value>
 80        ///
 81        public bool IsClosed
 82        {
 6483            get => _closed;
 2684            protected set => _closed = value;
 85        }
 86
 87        /// <summary>
 88        ///   The instance of <see cref="EventHubsEventSource" /> which can be mocked for testing.
 89        /// </summary>
 90        ///
 091        internal EventHubsEventSource Logger { get; set; } = EventHubsEventSource.Log;
 92
 93        /// <summary>
 94        ///   Indicates whether the client has ownership of the associated <see cref="EventHubConnection" />
 95        ///   and should take responsibility for managing its lifespan.
 96        /// </summary>
 97        ///
 098        private bool OwnsConnection { get; } = true;
 99
 100        /// <summary>
 101        ///   The default maximum amount of time to wait to build up the requested message count for the batch.
 102        /// </summary>
 103        ///
 10104        private TimeSpan? DefaultMaximumWaitTime { get; }
 105
 106        /// <summary>
 107        ///   The policy to use for determining retry behavior for when an operation fails.
 108        /// </summary>
 109        ///
 114110        private EventHubsRetryPolicy RetryPolicy { get; }
 111
 112        /// <summary>
 113        ///   The active connection to the Azure Event Hubs service, enabling client communications for metadata
 114        ///   about the associated Event Hub and access to transport-aware consumers.
 115        /// </summary>
 116        ///
 182117        private EventHubConnection Connection { get; }
 118
 119        /// <summary>
 120        ///   The transport consumer that is used for operations performed against
 121        ///   the Event Hubs service.
 122        /// </summary>
 123        ///
 40124        private TransportConsumer InnerConsumer { get; }
 125
 126        /// <summary>
 127        ///   Initializes a new instance of the <see cref="PartitionReceiver"/> class.
 128        /// </summary>
 129        ///
 130        /// <param name="consumerGroup">The name of the consumer group this client is associated with.  Events are read 
 131        /// <param name="partitionId">The identifier of the Event Hub partition from which events will be received.</par
 132        /// <param name="eventPosition">The position within the partition where the client should begin reading events.<
 133        /// <param name="connectionString">The connection string to use for connecting to the Event Hubs namespace; it i
 134        /// <param name="options">A set of options to apply when configuring the client.</param>
 135        ///
 136        /// <remarks>
 137        ///   If the connection string is copied from the Event Hubs namespace, it will likely not contain the name of t
 138        ///   which is needed.  In this case, the name can be added manually by adding ";EntityPath=[[ EVENT HUB NAME ]]
 139        ///   connection string.  For example, ";EntityPath=telemetry-hub".
 140        ///
 141        ///   If you have defined a shared access policy directly on the Event Hub itself, then copying the connection s
 142        ///   Event Hub will result in a connection string that contains the name.
 143        /// </remarks>
 144        ///
 145        /// <seealso href="https://docs.microsoft.com/en-us/azure/event-hubs/event-hubs-get-connection-string"/>
 146        ///
 147        public PartitionReceiver(string consumerGroup,
 148                                 string partitionId,
 149                                 EventPosition eventPosition,
 150                                 string connectionString,
 54151                                 PartitionReceiverOptions options = default) : this(consumerGroup, partitionId, eventPos
 152        {
 42153        }
 154
 155        /// <summary>
 156        ///   Initializes a new instance of the <see cref="PartitionReceiver"/> class.
 157        /// </summary>
 158        ///
 159        /// <param name="consumerGroup">The name of the consumer group this client is associated with.  Events are read 
 160        /// <param name="partitionId">The identifier of the Event Hub partition from which events will be received.</par
 161        /// <param name="eventPosition">The position within the partition where the client should begin reading events.<
 162        /// <param name="connectionString">The connection string to use for connecting to the Event Hubs namespace; it i
 163        /// <param name="eventHubName">The name of the specific Event Hub to associate the client with.</param>
 164        /// <param name="options">A set of options to apply when configuring the client.</param>
 165        ///
 166        /// <remarks>
 167        ///   If the connection string is copied from the Event Hub itself, it will contain the name of the desired Even
 168        ///   and can be used directly without passing the <paramref name="eventHubName" />.  The name of the Event Hub 
 169        ///   passed only once, either as part of the connection string or separately.
 170        /// </remarks>
 171        ///
 172        /// <seealso href="https://docs.microsoft.com/en-us/azure/event-hubs/event-hubs-get-connection-string"/>
 173        ///
 66174        public PartitionReceiver(string consumerGroup,
 66175                                 string partitionId,
 66176                                 EventPosition eventPosition,
 66177                                 string connectionString,
 66178                                 string eventHubName,
 66179                                 PartitionReceiverOptions options = default)
 180        {
 66181            Argument.AssertNotNullOrEmpty(consumerGroup, nameof(consumerGroup));
 58182            Argument.AssertNotNullOrEmpty(partitionId, nameof(partitionId));
 50183            Argument.AssertNotNullOrEmpty(connectionString, nameof(connectionString));
 184
 42185            options = options?.Clone() ?? new PartitionReceiverOptions();
 186
 42187            Connection = new EventHubConnection(connectionString, eventHubName, options.ConnectionOptions);
 42188            ConsumerGroup = consumerGroup;
 42189            PartitionId = partitionId;
 42190            InitialPosition = eventPosition;
 42191            DefaultMaximumWaitTime = options.DefaultMaximumReceiveWaitTime;
 42192            RetryPolicy = options.RetryOptions.ToRetryPolicy();
 193
 194#pragma warning disable CA2214 // Do not call overridable methods in constructors. This internal method is virtual for t
 42195            InnerConsumer = CreateTransportConsumer(consumerGroup, partitionId, eventPosition, RetryPolicy, options);
 196#pragma warning restore CA2214 // Do not call overridable methods in constructors.
 197
 42198        }
 199
 200        /// <summary>
 201        ///   Initializes a new instance of the <see cref="PartitionReceiver"/> class.
 202        /// </summary>
 203        ///
 204        /// <param name="consumerGroup">The name of the consumer group this client is associated with.  Events are read 
 205        /// <param name="partitionId">The identifier of the Event Hub partition from which events will be received.</par
 206        /// <param name="eventPosition">The position within the partition where the client should begin reading events.<
 207        /// <param name="fullyQualifiedNamespace">The fully qualified Event Hubs namespace to connect to.  This is likel
 208        /// <param name="eventHubName">The name of the specific Event Hub to associate the client with.</param>
 209        /// <param name="credential">The Azure managed identity credential to use for authorization.  Access controls ma
 210        /// <param name="options">A set of options to apply when configuring the client.</param>
 211        ///
 34212        public PartitionReceiver(string consumerGroup,
 34213                                 string partitionId,
 34214                                 EventPosition eventPosition,
 34215                                 string fullyQualifiedNamespace,
 34216                                 string eventHubName,
 34217                                 TokenCredential credential,
 34218                                 PartitionReceiverOptions options = default)
 219        {
 34220            Argument.AssertNotNullOrEmpty(consumerGroup, nameof(consumerGroup));
 30221            Argument.AssertNotNullOrEmpty(partitionId, nameof(partitionId));
 26222            Argument.AssertWellFormedEventHubsNamespace(fullyQualifiedNamespace, nameof(fullyQualifiedNamespace));
 20223            Argument.AssertNotNullOrEmpty(eventHubName, nameof(eventHubName));
 16224            Argument.AssertNotNull(credential, nameof(credential));
 225
 14226            options = options?.Clone() ?? new PartitionReceiverOptions();
 227
 14228            Connection = new EventHubConnection(fullyQualifiedNamespace, eventHubName, credential, options.ConnectionOpt
 14229            ConsumerGroup = consumerGroup;
 14230            PartitionId = partitionId;
 14231            InitialPosition = eventPosition;
 14232            DefaultMaximumWaitTime = options.DefaultMaximumReceiveWaitTime;
 14233            RetryPolicy = options.RetryOptions.ToRetryPolicy();
 234
 235#pragma warning disable CA2214 // Do not call overridable methods in constructors. This internal method is virtual for t
 14236            InnerConsumer = CreateTransportConsumer(consumerGroup, partitionId, eventPosition, RetryPolicy, options);
 237#pragma warning restore CA2214 // Do not call overridable methods in constructors.
 14238        }
 239
 240        /// <summary>
 241        ///   Initializes a new instance of the <see cref="PartitionReceiver"/> class.
 242        /// </summary>
 243        ///
 244        /// <param name="consumerGroup">The name of the consumer group this client is associated with.  Events are read 
 245        /// <param name="partitionId">The identifier of the Event Hub partition from which events will be received.</par
 246        /// <param name="eventPosition">The position within the partition where the client should begin reading events.<
 247        /// <param name="connection">The <see cref="EventHubConnection" /> connection to use for communication with the 
 248        /// <param name="options">A set of options to apply when configuring the client.</param>
 249        ///
 56250        public PartitionReceiver(string consumerGroup,
 56251                                 string partitionId,
 56252                                 EventPosition eventPosition,
 56253                                 EventHubConnection connection,
 56254                                 PartitionReceiverOptions options = default)
 255        {
 56256            Argument.AssertNotNullOrEmpty(consumerGroup, nameof(consumerGroup));
 52257            Argument.AssertNotNullOrEmpty(partitionId, nameof(partitionId));
 48258            Argument.AssertNotNull(connection, nameof(connection));
 259
 46260            options = options?.Clone() ?? new PartitionReceiverOptions();
 261
 46262            OwnsConnection = false;
 46263            Connection = connection;
 46264            ConsumerGroup = consumerGroup;
 46265            PartitionId = partitionId;
 46266            InitialPosition = eventPosition;
 46267            DefaultMaximumWaitTime = options.DefaultMaximumReceiveWaitTime;
 46268            RetryPolicy = options.RetryOptions.ToRetryPolicy();
 269
 270#pragma warning disable CA2214 // Do not call overridable methods in constructors. This internal method is virtual for t
 46271            InnerConsumer = CreateTransportConsumer(consumerGroup, partitionId, eventPosition, RetryPolicy, options);
 272#pragma warning restore CA2214 // Do not call overridable methods in constructors.
 46273        }
 274
 275        /// <summary>
 276        ///   Initializes a new instance of the <see cref="PartitionReceiver"/> class.
 277        /// </summary>
 278        ///
 0279        protected PartitionReceiver()
 280        {
 0281            OwnsConnection = false;
 0282        }
 283
 284        /// <summary>
 285        ///   Retrieves information about the partition this client is associated to, including elements that describe t
 286        ///   available events in the partition event stream.
 287        /// </summary>
 288        ///
 289        /// <param name="cancellationToken">An optional <see cref="CancellationToken"/> instance to signal the request t
 290        ///
 291        /// <returns>The set of information for the associated partition under the Event Hub this client is associated w
 292        ///
 293        public virtual async Task<PartitionProperties> GetPartitionPropertiesAsync(CancellationToken cancellationToken =
 294        {
 8295            cancellationToken.ThrowIfCancellationRequested<TaskCanceledException>();
 296
 8297            Argument.AssertNotClosed(IsClosed, nameof(PartitionReceiver));
 6298            return await Connection.GetPartitionPropertiesAsync(PartitionId, RetryPolicy, cancellationToken).ConfigureAw
 6299        }
 300
 301        /// <summary>
 302        ///   A set of information about the last enqueued event of the partition associated with this receiver, observe
 303        ///   are received from the Event Hubs service.  This is only available if the receiver was created with <see cr
 304        ///   set.  Otherwise, the properties will contain default values.
 305        /// </summary>
 306        ///
 307        /// <returns>The set of properties for the last event that was enqueued to the partition.  If no events were rea
 308        ///
 309        /// <remarks>
 310        ///   When information about the partition's last enqueued event is being tracked, each event received from the 
 311        ///   service will carry metadata about the partition that it otherwise would not. This results in a small amoun
 312        ///   additional network bandwidth consumption that is generally a favorable trade-off when considered
 313        ///   against periodically making requests for partition properties using an Event Hub client.
 314        /// </remarks>
 315        ///
 316        /// <exception cref="EventHubsException">Occurs when the Event Hubs client needed to read this information is no
 317        ///
 318        public virtual LastEnqueuedEventProperties ReadLastEnqueuedEventProperties()
 319        {
 4320            Argument.AssertNotClosed(InnerConsumer.IsClosed, Resources.ClientNeededForThisInformationNotAvailable);
 4321            return new LastEnqueuedEventProperties(InnerConsumer.LastReceivedEvent);
 322        }
 323
 324        /// <summary>
 325        ///   Receives a batch of <see cref="EventData" /> from the Event Hub partition this client is associated with.
 326        /// </summary>
 327        ///
 328        /// <param name="maximumEventCount">The maximum number of messages to receive in this batch.</param>
 329        /// <param name="cancellationToken">An optional <see cref="CancellationToken"/> instance to signal the request t
 330        ///
 331        /// <returns>The batch of <see cref="EventData" /> from the Event Hub partition this client is associated with. 
 332        ///
 333        public virtual async Task<IEnumerable<EventData>> ReceiveBatchAsync(int maximumEventCount,
 334                                                                            CancellationToken cancellationToken = defaul
 4335            await ReceiveBatchInternalAsync(maximumEventCount, null, cancellationToken).ConfigureAwait(false);
 336
 337        /// <summary>
 338        ///   Receives a batch of <see cref="EventData" /> from the Event Hub partition this client is associated with.
 339        /// </summary>
 340        ///
 341        /// <param name="maximumEventCount">The maximum number of messages to receive in this batch.</param>
 342        /// <param name="maximumWaitTime">The maximum amount of time to wait to build up the requested message count for
 343        /// <param name="cancellationToken">An optional <see cref="CancellationToken"/> instance to signal the request t
 344        ///
 345        /// <returns>The batch of <see cref="EventData" /> from the Event Hub partition this client is associated with. 
 346        ///
 347        public virtual async Task<IEnumerable<EventData>> ReceiveBatchAsync(int maximumEventCount,
 348                                                                            TimeSpan maximumWaitTime,
 349                                                                            CancellationToken cancellationToken = defaul
 20350            await ReceiveBatchInternalAsync(maximumEventCount, maximumWaitTime, cancellationToken).ConfigureAwait(false)
 351
 352        /// <summary>
 353        ///   Closes the client.
 354        /// </summary>
 355        ///
 356        /// <param name="cancellationToken">An optional <see cref="CancellationToken"/> instance to signal the request t
 357        ///
 358        public virtual async Task CloseAsync(CancellationToken cancellationToken = default)
 359        {
 28360            cancellationToken.ThrowIfCancellationRequested<TaskCanceledException>();
 361
 26362            if (IsClosed)
 363            {
 0364                return;
 365            }
 366
 26367            IsClosed = true;
 368
 26369            var clientHash = GetHashCode().ToString(CultureInfo.InvariantCulture);
 26370            Logger.ClientCloseStart(nameof(PartitionReceiver), EventHubName, clientHash);
 371
 372            // Attempt to close the transport consumer.  In the event that an exception is encountered,
 373            // it should not impact the attempt to close the connection, assuming ownership.
 374
 26375            var transportConsumerException = default(Exception);
 376
 377            try
 378            {
 26379                await InnerConsumer.CloseAsync(CancellationToken.None).ConfigureAwait(false);
 22380            }
 4381            catch (Exception ex)
 382            {
 4383                Logger.ClientCloseError(nameof(PartitionReceiver), EventHubName, clientHash, ex.Message);
 4384                transportConsumerException = ex;
 4385            }
 386
 387            // An exception when closing the connection supersedes one observed when closing the
 388            // transport consumer.
 389
 390            try
 391            {
 26392                if (OwnsConnection)
 393                {
 10394                    await Connection.CloseAsync().ConfigureAwait(false);
 395                }
 26396            }
 0397            catch (Exception ex)
 398            {
 0399                Logger.ClientCloseError(nameof(PartitionReceiver), EventHubName, clientHash, ex.Message);
 0400                throw;
 401            }
 402            finally
 403            {
 26404                Logger.ClientCloseComplete(nameof(PartitionReceiver), EventHubName, clientHash);
 405            }
 406
 407            // If there was an active exception pending from closing the transport
 408            // consumer, surface it now.
 409
 26410            if (transportConsumerException != default)
 411            {
 4412                ExceptionDispatchInfo.Capture(transportConsumerException).Throw();
 413            }
 22414        }
 415
 416        /// <summary>
 417        ///   Performs the task needed to clean up resources used by the <see cref="PartitionReceiver" />,
 418        ///   including ensuring that the client itself has been closed.
 419        /// </summary>
 420        ///
 8421        public virtual async ValueTask DisposeAsync() => await CloseAsync().ConfigureAwait(false);
 422
 423        /// <summary>
 424        ///   Determines whether the specified <see cref="System.Object" /> is equal to this instance.
 425        /// </summary>
 426        ///
 427        /// <param name="obj">The <see cref="System.Object" /> to compare with this instance.</param>
 428        ///
 429        /// <returns><c>true</c> if the specified <see cref="System.Object" /> is equal to this instance; otherwise, <c>
 430        ///
 431        [EditorBrowsable(EditorBrowsableState.Never)]
 0432        public override bool Equals(object obj) => base.Equals(obj);
 433
 434        /// <summary>
 435        ///   Returns a hash code for this instance.
 436        /// </summary>
 437        ///
 438        /// <returns>A hash code for this instance, suitable for use in hashing algorithms and data structures like a ha
 439        ///
 440        [EditorBrowsable(EditorBrowsableState.Never)]
 26441        public override int GetHashCode() => base.GetHashCode();
 442
 443        /// <summary>
 444        ///   Converts the instance to string representation.
 445        /// </summary>
 446        ///
 447        /// <returns>A <see cref="System.String" /> that represents this instance.</returns>
 448        ///
 449        [EditorBrowsable(EditorBrowsableState.Never)]
 0450        public override string ToString() => base.ToString();
 451
 452        /// <summary>
 453        ///   Creates an <see cref="TransportConsumer" /> to use for reading events.
 454        /// </summary>
 455        ///
 456        /// <param name="consumerGroup">The name of the consumer group the consumer will be associated with.  Events wil
 457        /// <param name="partitionId">The identifier of the Event Hub partition from which events will be received.</par
 458        /// <param name="eventPosition">The position within the partition where the consumer should begin reading events
 459        /// <param name="retryPolicy">The policy which governs retry behavior and try timeouts.</param>
 460        /// <param name="options">A set of options to apply when configuring the consumer.</param>
 461        ///
 462        /// <returns>A <see cref="TransportConsumer" /> configured in the requested manner.</returns>
 463        ///
 464        internal virtual TransportConsumer CreateTransportConsumer(string consumerGroup,
 465                                                                   string partitionId,
 466                                                                   EventPosition eventPosition,
 467                                                                   EventHubsRetryPolicy retryPolicy,
 468                                                                   PartitionReceiverOptions options) =>
 104469            Connection.CreateTransportConsumer(consumerGroup, partitionId, eventPosition, retryPolicy, options.TrackLast
 470
 471        /// <summary>
 472        ///   Receives a batch of <see cref="EventData" /> from the Event Hub partition this client is associated with.
 473        /// </summary>
 474        ///
 475        /// <param name="maximumEventCount">The maximum number of messages to receive in this batch.</param>
 476        /// <param name="maximumWaitTime">The maximum amount of time to wait to build up the requested message count for
 477        /// <param name="cancellationToken">An optional <see cref="CancellationToken"/> instance to signal the request t
 478        ///
 479        /// <returns>The batch of <see cref="EventData" /> from the Event Hub partition this client is associated with. 
 480        ///
 481        private Task<IReadOnlyList<EventData>> ReceiveBatchInternalAsync(int maximumEventCount,
 482                                                                         TimeSpan? maximumWaitTime,
 483                                                                         CancellationToken cancellationToken = default)
 484        {
 24485            cancellationToken.ThrowIfCancellationRequested<TaskCanceledException>();
 22486            maximumWaitTime ??= DefaultMaximumWaitTime;
 487
 22488            Argument.AssertNotClosed(IsClosed, nameof(PartitionReceiver));
 20489            Argument.AssertInRange(maximumEventCount, 1, int.MaxValue, nameof(maximumEventCount));
 12490            Argument.AssertNotNegative(maximumWaitTime ?? TimeSpan.Zero, nameof(maximumWaitTime));
 491
 6492            return InnerConsumer.ReceiveAsync(maximumEventCount, maximumWaitTime, cancellationToken);
 493        }
 494    }
 495}