public AmqpServiceClient(AmqpEventHubClient eventHubClient, string address) : base("AmqpServiceClient-" + StringUtility.GetRandomString()) { this.eventHubClient = eventHubClient; Address = address; link = new FaultTolerantAmqpObject <RequestResponseAmqpLink>(OpenLinkAsync, rrlink => rrlink.CloseAsync(TimeSpan.FromSeconds(10))); }
internal static async Task <AmqpResponseMessage> ExecuteRequestResponseAsync( AmqpConnectionScope connectionScope, FaultTolerantAmqpObject <RequestResponseAmqpLink> managementLink, AmqpRequestMessage amqpRequestMessage, string transactionGroup, TimeSpan timeout) { AmqpMessage amqpMessage = amqpRequestMessage.AmqpMessage; ArraySegment <byte> transactionId = AmqpConstants.NullBinary; var ambientTransaction = Transaction.Current; if (ambientTransaction != null) { transactionId = await AmqpTransactionManager.Instance.EnlistAsync( ambientTransaction, connectionScope, transactionGroup, timeout) .ConfigureAwait(false); } if (!managementLink.TryGetOpenedObject(out var requestResponseAmqpLink)) { // MessagingEventSource.Log.CreatingNewLink(this.ClientId, this.isSessionReceiver, this.SessionIdInternal, true, this.LinkException); requestResponseAmqpLink = await managementLink.GetOrCreateAsync(timeout).ConfigureAwait(false); } var responseAmqpMessage = await Task.Factory.FromAsync( (c, s) => requestResponseAmqpLink.BeginRequest(amqpMessage, transactionId, timeout, c, s), (a) => requestResponseAmqpLink.EndRequest(a), null).ConfigureAwait(false); return(AmqpResponseMessage.CreateResponse(responseAmqpMessage)); }
/// <summary> /// Initializes a new instance of the <see cref="AmqpProducer"/> class. /// </summary> /// /// <param name="eventHubName">The name of the Event Hub to which events will be published.</param> /// <param name="partitionId">The identifier of the Event Hub partition to which it is bound; if unbound, <c>null</c>.</param> /// <param name="connectionScope">The AMQP connection context for operations.</param> /// <param name="messageConverter">The converter to use for translating between AMQP messages and client types.</param> /// <param name="retryPolicy">The retry policy to consider when an operation fails.</param> /// <param name="requestedFeatures">The flags specifying the set of special transport features that should be opted-into.</param> /// <param name="partitionOptions">The set of options, if any, that should be considered when initializing the producer.</param> /// /// <remarks> /// As an internal type, this class performs only basic sanity checks against its arguments. It /// is assumed that callers are trusted and have performed deep validation. /// /// Any parameters passed are assumed to be owned by this instance and safe to mutate or dispose; /// creation of clones or otherwise protecting the parameters is assumed to be the purview of the /// caller. /// </remarks> /// public AmqpProducer(string eventHubName, string partitionId, AmqpConnectionScope connectionScope, AmqpMessageConverter messageConverter, EventHubsRetryPolicy retryPolicy, TransportProducerFeatures requestedFeatures = TransportProducerFeatures.None, PartitionPublishingOptions partitionOptions = null) { Argument.AssertNotNullOrEmpty(eventHubName, nameof(eventHubName)); Argument.AssertNotNull(connectionScope, nameof(connectionScope)); Argument.AssertNotNull(messageConverter, nameof(messageConverter)); Argument.AssertNotNull(retryPolicy, nameof(retryPolicy)); EventHubName = eventHubName; PartitionId = partitionId; RetryPolicy = retryPolicy; ConnectionScope = connectionScope; MessageConverter = messageConverter; ActiveFeatures = requestedFeatures; ActiveOptions = partitionOptions?.Clone() ?? new PartitionPublishingOptions(); SendLink = new FaultTolerantAmqpObject <SendingAmqpLink>( timeout => CreateLinkAndEnsureProducerStateAsync(partitionId, ActiveOptions, timeout, CancellationToken.None), link => { link.Session?.SafeClose(); link.SafeClose(); }); }
public IotHubConnection(IotHubConnectionString connectionString, AccessRights accessRights) { this.connectionString = connectionString; this.accessRights = accessRights; this.faultTolerantSession = new FaultTolerantAmqpObject <AmqpSession>(this.CreateSessionAsync, this.CloseConnection); this.refreshTokenTimer = new IOThreadTimer(s => ((IotHubConnection)s).OnRefreshToken(), this, false); }
internal static async Task DisposeMessageAsync(FaultTolerantAmqpObject <ReceivingAmqpLink> faultTolerantReceivingLink, string lockToken, Outcome outcome, bool batchable) { var deliveryTag = IotHubConnection.ConvertToDeliveryTag(lockToken); Outcome disposeOutcome; try { ReceivingAmqpLink deviceBoundReceivingLink = await faultTolerantReceivingLink.GetReceivingLinkAsync().ConfigureAwait(false); disposeOutcome = await deviceBoundReceivingLink.DisposeMessageAsync(deliveryTag, outcome, batchable, IotHubConnection.DefaultOperationTimeout).ConfigureAwait(false); } catch (Exception exception) { if (exception.IsFatal()) { throw; } throw AmqpClientHelper.ToIotHubClientContract(exception); } if (disposeOutcome.DescriptorCode != Accepted.Code) { throw AmqpErrorMapper.GetExceptionFromOutcome(disposeOutcome); } }
/// <summary> /// Initializes a new instance of the <see cref="AmqpProducer"/> class. /// </summary> /// /// <param name="eventHubName">The name of the Event Hub to which events will be published.</param> /// <param name="partitionId">The identifier of the Event Hub partition to which it is bound; if unbound, <c>null</c>.</param> /// <param name="connectionScope">The AMQP connection context for operations.</param> /// <param name="messageConverter">The converter to use for translating between AMQP messages and client types.</param> /// <param name="retryPolicy">The retry policy to consider when an operation fails.</param> /// /// <remarks> /// As an internal type, this class performs only basic sanity checks against its arguments. It /// is assumed that callers are trusted and have performed deep validation. /// /// Any parameters passed are assumed to be owned by this instance and safe to mutate or dispose; /// creation of clones or otherwise protecting the parameters is assumed to be the purview of the /// caller. /// </remarks> /// public AmqpProducer(string eventHubName, string partitionId, AmqpConnectionScope connectionScope, AmqpMessageConverter messageConverter, EventHubsRetryPolicy retryPolicy) { Argument.AssertNotNullOrEmpty(eventHubName, nameof(eventHubName)); Argument.AssertNotNull(connectionScope, nameof(connectionScope)); Argument.AssertNotNull(messageConverter, nameof(messageConverter)); Argument.AssertNotNull(retryPolicy, nameof(retryPolicy)); EventHubName = eventHubName; PartitionId = partitionId; RetryPolicy = retryPolicy; ConnectionScope = connectionScope; MessageConverter = messageConverter; SendLink = new FaultTolerantAmqpObject <SendingAmqpLink>( timeout => CreateLinkAndEnsureProducerStateAsync(partitionId, timeout, CancellationToken.None), link => { link.Session?.SafeClose(); link.SafeClose(); }); }
///// <summary> ///// The converter to use for translating between AMQP messages and client library ///// types. ///// </summary> //private AmqpMessageConverter MessageConverter { get; } ///// <summary> ///// The AMQP connection scope responsible for managing transport constructs for this instance. ///// </summary> ///// //internal AmqpConnectionScope ConnectionScope { get; } ///// <summary> ///// The AMQP link intended for use with receiving operations. ///// </summary> ///// //internal FaultTolerantAmqpObject<ReceivingAmqpLink> ReceiveLink { get; } /// <summary> /// Initializes a new instance of the <see cref="AmqpConsumer"/> class. /// </summary> /// /// <param name="entityName">The name of the Service Bus entity from which events will be consumed.</param> /// <param name="prefetchCount">Controls the number of events received and queued locally without regard to whether an operation was requested. If <c>null</c> a default will be used.</param> /// <param name="ownerLevel">The relative priority to associate with the link; for a non-exclusive link, this value should be <c>null</c>.</param> /// <param name="connectionScope">The AMQP connection context for operations .</param> /// <param name="retryPolicy">The retry policy to consider when an operation fails.</param> /// <param name="sessionId"></param> /// /// <remarks> /// As an internal type, this class performs only basic sanity checks against its arguments. It /// is assumed that callers are trusted and have performed deep validation. /// /// Any parameters passed are assumed to be owned by this instance and safe to mutate or dispose; /// creation of clones or otherwise protecting the parameters is assumed to be the purview of the /// caller. /// </remarks> /// public AmqpConsumer( string entityName, long?ownerLevel, uint?prefetchCount, AmqpConnectionScope connectionScope, ServiceBusRetryPolicy retryPolicy, string sessionId) { Argument.AssertNotNullOrEmpty(entityName, nameof(entityName)); Argument.AssertNotNull(connectionScope, nameof(connectionScope)); Argument.AssertNotNull(retryPolicy, nameof(retryPolicy)); EntityName = entityName; ConnectionScope = connectionScope; RetryPolicy = retryPolicy; ReceiveLink = new FaultTolerantAmqpObject <ReceivingAmqpLink>( timeout => ConnectionScope.OpenConsumerLinkAsync( //consumerGroup, //partitionId, timeout, prefetchCount ?? DefaultPrefetchCount, ownerLevel, sessionId, CancellationToken.None), link => { CloseLink(link); }); }
private async Task <Controller> GetController(TimeSpan timeout) { FaultTolerantAmqpObject <Controller> faultTolerantController = _connectionScope.TransactionController; Controller controller = await faultTolerantController.GetOrCreateAsync(timeout).ConfigureAwait(false); return(controller); }
/// <summary> /// Initializes a new instance of the <see cref="AmqpConnectionScope"/> class. /// </summary> /// /// <param name="serviceEndpoint">Endpoint for the Service Bus service to which the scope is associated.</param> /// <param name="credential">The credential to use for authorization with the Service Bus service.</param> /// <param name="transport">The transport to use for communication.</param> /// <param name="proxy">The proxy, if any, to use for communication.</param> /// <param name="identifier">The identifier to assign this scope; if not provided, one will be generated.</param> /// public AmqpConnectionScope(Uri serviceEndpoint, ServiceBusTokenCredential credential, ServiceBusTransportType transport, IWebProxy proxy, string identifier = default) { Argument.AssertNotNull(serviceEndpoint, nameof(serviceEndpoint)); Argument.AssertNotNull(credential, nameof(credential)); ValidateTransport(transport); ServiceEndpoint = serviceEndpoint; Transport = transport; Proxy = proxy; TokenProvider = new CbsTokenProvider(new ServiceBusTokenCredential(credential, serviceEndpoint.ToString()), OperationCancellationSource.Token); Id = identifier ?? $"{ ServiceEndpoint }-{ Guid.NewGuid().ToString("D").Substring(0, 8) }"; Task <AmqpConnection> connectionFactory(TimeSpan timeout) => CreateAndOpenConnectionAsync(AmqpVersion, ServiceEndpoint, Transport, Proxy, Id, timeout); ActiveConnection = new FaultTolerantAmqpObject <AmqpConnection>( connectionFactory, CloseConnection); TransactionController = new FaultTolerantAmqpObject <Controller>( CreateControllerAsync, CloseController); }
public IotHubConnection(IotHubConnectionString connectionString, AccessRights accessRights) { this.connectionString = connectionString; this.accessRights = accessRights; this.faultTolerantSession = new FaultTolerantAmqpObject<AmqpSession>(this.CreateSessionAsync, this.CloseConnection); this.refreshTokenTimer = new IOThreadTimer(s => ((IotHubConnection)s).OnRefreshToken(), this, false); }
/// <summary> /// Initializes a new instance of the <see cref="AmqpConnectionScope"/> class. /// </summary> /// /// <param name="serviceEndpoint">Endpoint for the Service Bus service to which the scope is associated.</param> /// <param name="credential">The credential to use for authorization with the Service Bus service.</param> /// <param name="transport">The transport to use for communication.</param> /// <param name="proxy">The proxy, if any, to use for communication.</param> /// <param name="identifier">The identifier to assign this scope; if not provided, one will be generated.</param> /// public AmqpConnectionScope(Uri serviceEndpoint, ServiceBusTokenCredential credential, ServiceBusTransportType transport, IWebProxy proxy, string identifier = default) { Argument.AssertNotNull(serviceEndpoint, nameof(serviceEndpoint)); Argument.AssertNotNull(credential, nameof(credential)); ValidateTransport(transport); ServiceEndpoint = serviceEndpoint; Transport = transport; Proxy = proxy; TokenProvider = new CbsTokenProvider(new ServiceBusTokenCredential(credential, serviceEndpoint.ToString()), OperationCancellationSource.Token); Id = identifier ?? $"{ ServiceEndpoint }-{ Guid.NewGuid().ToString("D", CultureInfo.InvariantCulture).Substring(0, 8) }"; #pragma warning disable CA2214 // Do not call overridable methods in constructors. This internal method is virtual for testing purposes. Task <AmqpConnection> connectionFactory(TimeSpan timeout) => CreateAndOpenConnectionAsync(AmqpVersion, ServiceEndpoint, Transport, Proxy, Id, timeout); #pragma warning restore CA2214 // Do not call overridable methods in constructors ActiveConnection = new FaultTolerantAmqpObject <AmqpConnection>( connectionFactory, CloseConnection); TransactionController = new FaultTolerantAmqpObject <Controller>( CreateControllerAsync, CloseController); }
protected void InitializeConnection(ServiceBusConnectionStringBuilder builder) { this.Endpoint = new Uri(builder.Endpoint); this.NetCredential = new System.Net.NetworkCredential(builder.Username, builder.Password); this.TransportType = builder.TransportType; this.ConnectionManager = new FaultTolerantAmqpObject <AmqpConnection>(this.CreateConnectionAsync, CloseConnection); }
/// <summary> /// Initializes a new instance of the <see cref="AmqpSender"/> class. /// </summary> /// /// <param name="entityPath">The name of the entity to which messages will be sent.</param> /// <param name="connectionScope">The AMQP connection context for operations.</param> /// <param name="retryPolicy">The retry policy to consider when an operation fails.</param> /// /// <remarks> /// As an internal type, this class performs only basic sanity checks against its arguments. It /// is assumed that callers are trusted and have performed deep validation. /// /// Any parameters passed are assumed to be owned by this instance and safe to mutate or dispose; /// creation of clones or otherwise protecting the parameters is assumed to be the purview of the /// caller. /// </remarks> /// public AmqpSender( string entityPath, AmqpConnectionScope connectionScope, ServiceBusRetryPolicy retryPolicy) { Argument.AssertNotNullOrEmpty(entityPath, nameof(entityPath)); Argument.AssertNotNull(connectionScope, nameof(connectionScope)); Argument.AssertNotNull(retryPolicy, nameof(retryPolicy)); _entityPath = entityPath; _retryPolicy = retryPolicy; _connectionScope = connectionScope; _sendLink = new FaultTolerantAmqpObject <SendingAmqpLink>( timeout => CreateLinkAndEnsureSenderStateAsync(timeout, CancellationToken.None), link => { link.Session?.SafeClose(); link.SafeClose(); }); _managementLink = new FaultTolerantAmqpObject <RequestResponseAmqpLink>( timeout => _connectionScope.OpenManagementLinkAsync( _entityPath, timeout, CancellationToken.None), link => { link.Session?.SafeClose(); link.SafeClose(); }); }
private async Task SinglePhaseCommitAsync(SinglePhaseEnlistment singlePhaseEnlistment) { try { FaultTolerantAmqpObject <Controller> faultTolerantController = _connectionScope.TransactionController; Controller controller = await faultTolerantController.GetOrCreateAsync(_timeout) .ConfigureAwait(false); await controller.DischargeAsync(AmqpTransactionId, fail : false).ConfigureAwait(false); singlePhaseEnlistment.Committed(); ServiceBusEventSource.Log.TransactionDischarged( _transactionId, AmqpTransactionId, false); await CloseAsync().ConfigureAwait(false); } catch (Exception e) { Exception exception = AmqpExceptionHelper.TranslateException(e, null); ServiceBusEventSource.Log.TransactionDischargeException( _transactionId, AmqpTransactionId, exception); singlePhaseEnlistment.InDoubt(exception); } }
public AmqpServiceClient( IotHubConnectionProperties connectionProperties, bool useWebSocketOnly, ServiceClientTransportSettings transportSettings, ServiceClientOptions options) { var iotHubConnection = new IotHubConnection(connectionProperties, useWebSocketOnly, transportSettings); Connection = iotHubConnection; OpenTimeout = IotHubConnection.DefaultOpenTimeout; OperationTimeout = IotHubConnection.DefaultOperationTimeout; _faultTolerantSendingLink = new FaultTolerantAmqpObject <SendingAmqpLink>(CreateSendingLinkAsync, Connection.CloseLink); _feedbackReceiver = new AmqpFeedbackReceiver(Connection); _fileNotificationReceiver = new AmqpFileNotificationReceiver(Connection); _iotHubName = connectionProperties.IotHubName; _clientOptions = options; _httpClientHelper = new HttpClientHelper( connectionProperties.HttpsEndpoint, connectionProperties, ExceptionHandlingHelper.GetDefaultErrorMapping(), s_defaultOperationTimeout, transportSettings.HttpProxy, transportSettings.ConnectionLeaseTimeoutMilliseconds); // Set the trace provider for the AMQP library. AmqpTrace.Provider = new AmqpTransportLog(); }
protected void InitializeConnection(ServiceBusConnectionStringBuilder builder) { this.Endpoint = new Uri(builder.Endpoint); this.SasKeyName = builder.SasKeyName; this.SasKey = builder.SasKey; this.ConnectionManager = new FaultTolerantAmqpObject <AmqpConnection>(this.CreateConnectionAsync, CloseConnection); }
/// <summary> /// Initializes a new instance of the <see cref="AmqpRuleManager"/> class. /// </summary> /// /// <param name="subscriptionPath">The path of the Service Bus subscription to which the rule manager is bound.</param> /// <param name="connectionScope">The AMQP connection context for operations.</param> /// <param name="retryPolicy">The retry policy to consider when an operation fails.</param> /// <param name="identifier">The identifier for the rule manager.</param> /// /// <remarks> /// As an internal type, this class performs only basic sanity checks against its arguments. It /// is assumed that callers are trusted and have performed deep validation. /// /// Any parameters passed are assumed to be owned by this instance and safe to mutate or dispose; /// creation of clones or otherwise protecting the parameters is assumed to be the purview of the /// caller. /// </remarks> public AmqpRuleManager( string subscriptionPath, AmqpConnectionScope connectionScope, ServiceBusRetryPolicy retryPolicy, string identifier) { Argument.AssertNotNullOrEmpty(subscriptionPath, nameof(subscriptionPath)); Argument.AssertNotNull(connectionScope, nameof(connectionScope)); Argument.AssertNotNull(retryPolicy, nameof(retryPolicy)); _subscriptionPath = subscriptionPath; _connectionScope = connectionScope; _retryPolicy = retryPolicy; _identifier = identifier; _managementLink = new FaultTolerantAmqpObject <RequestResponseAmqpLink>( timeout => _connectionScope.OpenManagementLinkAsync( _subscriptionPath, _identifier, timeout, CancellationToken.None), link => { link.Session?.SafeClose(); link.SafeClose(); }); }
/// <summary> /// Initializes a new instance of the <see cref="AmqpClient"/> class. /// </summary> /// /// <param name="host">The fully qualified host name for the Event Hubs namespace. This is likely to be similar to <c>{yournamespace}.servicebus.windows.net</c>.</param> /// <param name="eventHubName">The name of the specific Event Hub to connect the client to.</param> /// <param name="credential">The Azure managed identity credential to use for authorization. Access controls may be specified by the Event Hubs namespace or the requested Event Hub, depending on Azure configuration.</param> /// <param name="clientOptions">A set of options to apply when configuring the client.</param> /// <param name="connectionScope">The optional scope to use for AMQP connection management. If <c>null</c>, a new scope will be created.</param> /// <param name="messageConverter">The optional converter to use for transforming AMQP message-related types. If <c>null</c>, a new converter will be created.</param> /// /// <remarks> /// As an internal type, this class performs only basic sanity checks against its arguments. It /// is assumed that callers are trusted and have performed deep validation. /// /// Any parameters passed are assumed to be owned by this instance and safe to mutate or dispose; /// creation of clones or otherwise protecting the parameters is assumed to be the purview of the /// caller. /// </remarks> /// protected AmqpClient(string host, string eventHubName, TokenCredential credential, EventHubConnectionOptions clientOptions, AmqpConnectionScope connectionScope, AmqpMessageConverter messageConverter) { Argument.AssertNotNullOrEmpty(host, nameof(host)); Argument.AssertNotNullOrEmpty(eventHubName, nameof(eventHubName)); Argument.AssertNotNull(credential, nameof(credential)); Argument.AssertNotNull(clientOptions, nameof(clientOptions)); try { EventHubsEventSource.Log.EventHubClientCreateStart(host, eventHubName); ServiceEndpoint = new UriBuilder { Scheme = clientOptions.TransportType.GetUriScheme(), Host = host }.Uri; EventHubName = eventHubName; Credential = credential; MessageConverter = messageConverter ?? new AmqpMessageConverter(); ConnectionScope = connectionScope ?? new AmqpConnectionScope(ServiceEndpoint, eventHubName, credential, clientOptions.TransportType, clientOptions.Proxy); ManagementLink = new FaultTolerantAmqpObject <RequestResponseAmqpLink>(timeout => ConnectionScope.OpenManagementLinkAsync(timeout, CancellationToken.None), link => link.SafeClose()); } finally { EventHubsEventSource.Log.EventHubClientCreateComplete(host, eventHubName); } }
/// <summary> /// Initializes a new instance of the <see cref="AmqpConsumer"/> class. /// </summary> /// /// <param name="entityName">The name of the Service Bus entity from which events will be consumed.</param> /// <param name="prefetchCount">Controls the number of events received and queued locally without regard to whether an operation was requested. If <c>null</c> a default will be used.</param> /// <param name="receiveMode">The <see cref="ReceiveMode"/> used to specify how messages are received. Defaults to PeekLock mode.</param> /// <param name="connectionScope">The AMQP connection context for operations .</param> /// <param name="retryPolicy">The retry policy to consider when an operation fails.</param> /// <param name="sessionId"></param> /// <param name="isSessionReceiver"></param> /// /// <remarks> /// As an internal type, this class performs only basic sanity checks against its arguments. It /// is assumed that callers are trusted and have performed deep validation. /// /// Any parameters passed are assumed to be owned by this instance and safe to mutate or dispose; /// creation of clones or otherwise protecting the parameters is assumed to be the purview of the /// caller. /// </remarks> /// public AmqpConsumer( string entityName, ReceiveMode receiveMode, uint?prefetchCount, AmqpConnectionScope connectionScope, ServiceBusRetryPolicy retryPolicy, string sessionId, bool isSessionReceiver) { Argument.AssertNotNullOrEmpty(entityName, nameof(entityName)); Argument.AssertNotNull(connectionScope, nameof(connectionScope)); Argument.AssertNotNull(retryPolicy, nameof(retryPolicy)); EntityName = entityName; _connectionScope = connectionScope; _retryPolicy = retryPolicy; _isSessionReceiver = isSessionReceiver; _receiveMode = receiveMode; ReceiveLink = new FaultTolerantAmqpObject <ReceivingAmqpLink>( timeout => _connectionScope.OpenConsumerLinkAsync( timeout: timeout, prefetchCount: prefetchCount ?? DefaultPrefetchCount, receiveMode: receiveMode, sessionId: sessionId, isSessionReceiver: isSessionReceiver, cancellationToken: CancellationToken.None), link => { CloseLink(link); }); }
/// <summary> /// Initializes a new instance of the <see cref="AmqpEventHubConsumer"/> class. /// </summary> /// /// <param name="eventHubName">The name of the Event Hub from which events will be consumed.</param> /// <param name="consumerGroup">The name of the consumer group this consumer is associated with. Events are read in the context of this group.</param> /// <param name="partitionId">The identifier of the Event Hub partition from which events will be received.</param> /// <param name="consumerOptions">The set of active options for the consumer that will make use of the link.</param> /// <param name="eventPosition">The position of the event in the partition where the consumer should begin reading.</param> /// <param name="connectionScope">The AMQP connection context for operations .</param> /// <param name="messageConverter">The converter to use for translating between AMQP messages and client types.</param> /// <param name="retryPolicy">The retry policy to consider when an operation fails.</param> /// /// <remarks> /// As an internal type, this class performs only basic sanity checks against its arguments. It /// is assumed that callers are trusted and have performed deep validation. /// /// Any parameters passed are assumed to be owned by this instance and safe to mutate or dispose; /// creation of clones or otherwise protecting the parameters is assumed to be the purview of the /// caller. /// </remarks> /// public AmqpEventHubConsumer(string eventHubName, string consumerGroup, string partitionId, EventPosition eventPosition, EventHubConsumerOptions consumerOptions, AmqpConnectionScope connectionScope, AmqpMessageConverter messageConverter, EventHubRetryPolicy retryPolicy) { Argument.AssertNotNullOrEmpty(eventHubName, nameof(eventHubName)); Argument.AssertNotNullOrEmpty(consumerGroup, nameof(consumerGroup)); Argument.AssertNotNullOrEmpty(partitionId, nameof(partitionId)); Argument.AssertNotNull(eventPosition, nameof(EventPosition)); Argument.AssertNotNull(consumerOptions, nameof(EventHubConsumerOptions)); Argument.AssertNotNull(connectionScope, nameof(connectionScope)); Argument.AssertNotNull(messageConverter, nameof(messageConverter)); Argument.AssertNotNull(retryPolicy, nameof(retryPolicy)); EventHubName = eventHubName; ConsumerGroup = consumerGroup; PartitionId = partitionId; Options = consumerOptions; ConnectionScope = connectionScope; MessageConverter = messageConverter; ReceiveLink = new FaultTolerantAmqpObject <ReceivingAmqpLink>(timeout => ConnectionScope.OpenConsumerLinkAsync(consumerGroup, partitionId, eventPosition, consumerOptions, timeout, CancellationToken.None), link => link.SafeClose()); _retryPolicy = retryPolicy; _tryTimeout = retryPolicy.CalculateTryTimeout(0); }
public AmqpFeedbackReceiver(IotHubConnection iotHubConnection) { this.iotHubConnection = iotHubConnection; this.openTimeout = IotHubConnection.DefaultOpenTimeout; this.operationTimeout = IotHubConnection.DefaultOperationTimeout; this.receivingPath = GetReceivingPath(EndpointKind.Feedback); this.faultTolerantReceivingLink = new FaultTolerantAmqpObject <ReceivingAmqpLink>(this.CreateReceivingLinkAsync, this.iotHubConnection.CloseLink); }
public AmqpFileNotificationReceiver(IotHubConnection iotHubConnection) { this.Connection = iotHubConnection; this.OpenTimeout = IotHubConnection.DefaultOpenTimeout; this.OperationTimeout = IotHubConnection.DefaultOperationTimeout; this.receivingPath = AmqpClientHelper.GetReceivingPath(EndpointKind.FileNotification); this.faultTolerantReceivingLink = new FaultTolerantAmqpObject <ReceivingAmqpLink>(this.CreateReceivingLinkAsync, this.Connection.CloseLink); }
public AmqpServiceClient(AmqpEventHubClient eventHubClient, string address) : base("AmqpServiceClient-" + StringUtility.GetRandomString()) { this.eventHubClient = eventHubClient; this.Address = address; this.link = new FaultTolerantAmqpObject <RequestResponseAmqpLink>(t => this.OpenLinkAsync(t), rrlink => rrlink.CloseAsync(TimeSpan.FromSeconds(10))); this.clientLinkManager = new ActiveClientLinkManager(this.eventHubClient); }
internal AmqpServiceClient(IotHubConnection iotHubConnection, IHttpClientHelper httpClientHelper) { this.iotHubConnection = iotHubConnection; this.faultTolerantSendingLink = new FaultTolerantAmqpObject <SendingAmqpLink>(this.CreateSendingLinkAsync, iotHubConnection.CloseLink); this.feedbackReceiver = new AmqpFeedbackReceiver(iotHubConnection); this.fileNotificationReceiver = new AmqpFileNotificationReceiver(iotHubConnection); this.httpClientHelper = httpClientHelper; }
public AmqpFeedbackReceiver(IotHubConnection iotHubConnection) { Connection = iotHubConnection; OpenTimeout = IotHubConnection.DefaultOpenTimeout; OperationTimeout = IotHubConnection.DefaultOperationTimeout; _receivingPath = AmqpClientHelper.GetReceivingPath(EndpointKind.Feedback); _faultTolerantReceivingLink = new FaultTolerantAmqpObject <ReceivingAmqpLink>(CreateReceivingLinkAsync, Connection.CloseLink); }
// internal test helper internal ServiceClient(IotHubConnection connection, IHttpClientHelper httpClientHelper) { Connection = connection; _httpClientHelper = httpClientHelper; _feedbackReceiver = new AmqpFeedbackReceiver(Connection); _fileNotificationReceiver = new AmqpFileNotificationReceiver(Connection); _faultTolerantSendingLink = new FaultTolerantAmqpObject <SendingAmqpLink>(CreateSendingLinkAsync, Connection.CloseLink); }
internal static async Task DisposeMessageAsync( FaultTolerantAmqpObject <ReceivingAmqpLink> faultTolerantReceivingLink, string lockToken, Outcome outcome, bool batchable) { using var cts = new CancellationTokenSource(IotHubConnection.DefaultOperationTimeout); await DisposeMessageAsync(faultTolerantReceivingLink, lockToken, outcome, batchable, cts.Token).ConfigureAwait(false); }
internal static async Task <ReceivingAmqpLink> GetReceivingLinkAsync(this FaultTolerantAmqpObject <ReceivingAmqpLink> faultTolerantReceivingLink) { if (!faultTolerantReceivingLink.TryGetOpenedObject(out ReceivingAmqpLink receivingLink)) { receivingLink = await faultTolerantReceivingLink.GetOrCreateAsync(IotHubConnection.DefaultOpenTimeout).ConfigureAwait(false); } return(receivingLink); }
public AmqpDeviceClient(IotHubConnectionString connectionString, bool useWebSocketOnly) { this.IotHubConnection = connectionCache.GetConnection(connectionString, useWebSocketOnly); this.deviceId = connectionString.DeviceId; this.openTimeout = IotHubConnection.DefaultOpenTimeout; this.operationTimeout = IotHubConnection.DefaultOperationTimeout; this.DefaultReceiveTimeout = IotHubConnection.DefaultOperationTimeout; this.faultTolerantEventSendingLink = new FaultTolerantAmqpObject<SendingAmqpLink>(this.CreateEventSendingLinkAsync, this.IotHubConnection.CloseLink); this.faultTolerantDeviceBoundReceivingLink = new FaultTolerantAmqpObject<ReceivingAmqpLink>(this.CreateDeviceBoundReceivingLinkAsync, this.IotHubConnection.CloseLink); }
/// <inheritdoc/> public void Dispose() { _faultTolerantSession?.Dispose(); _faultTolerantSession = null; _refreshTokenTimer?.Dispose(); _refreshTokenTimer = null; _clientWebSocketTransport?.Dispose(); _clientWebSocketTransport = null; }
public AmqpDeviceClient(IotHubConnectionString connectionString, AmqpTransportSettings transportSettings) { this.IotHubConnection = connectionCache.GetConnection(connectionString, transportSettings); this.deviceId = connectionString.DeviceId; this.openTimeout = IotHubConnection.DefaultOpenTimeout; this.operationTimeout = IotHubConnection.DefaultOperationTimeout; this.DefaultReceiveTimeout = IotHubConnection.DefaultOperationTimeout; this.faultTolerantEventSendingLink = new FaultTolerantAmqpObject<SendingAmqpLink>(this.CreateEventSendingLinkAsync, this.IotHubConnection.CloseLink); this.faultTolerantDeviceBoundReceivingLink = new FaultTolerantAmqpObject<ReceivingAmqpLink>(this.CreateDeviceBoundReceivingLinkAsync, this.IotHubConnection.CloseLink); this.prefetchCount = transportSettings.PrefetchCount; }
internal AmqpEventDataSender(AmqpEventHubClient eventHubClient, string partitionId) : base(eventHubClient, partitionId) { Path = !string.IsNullOrEmpty(partitionId) ? $"{eventHubClient.EventHubName}/Partitions/{partitionId}" : eventHubClient.EventHubName; SendLinkManager = new FaultTolerantAmqpObject <SendingAmqpLink>(CreateLinkAsync, CloseSession); _clientLinkManager = new ActiveClientLinkManager((AmqpEventHubClient)EventHubClient); MaxMessageSize = 256 * 1024; // Default. Updated when link is opened }
public void FaultTolerantAmqpObjectShouldInvokeCloseMethodOnClose() { bool isCloseHandlerInvoked = false; var faultTolerantObject = new FaultTolerantAmqpObject <TestAmqpObject>( span => Task.FromResult(new TestAmqpObject("string")), amqpObject => { isCloseHandlerInvoked = true; }); var testAmqpObject = faultTolerantObject.GetOrCreateAsync(TimeSpan.FromSeconds(3)).Result; testAmqpObject.Close(); Assert.True(isCloseHandlerInvoked); }
public AmqpServiceClient(IotHubConnectionString iotHubConnectionString, bool useWebSocketOnly) { var iotHubConnection = new IotHubConnection(iotHubConnectionString, AccessRights.ServiceConnect, useWebSocketOnly); this.iotHubConnection = iotHubConnection; this.openTimeout = IotHubConnection.DefaultOpenTimeout; this.operationTimeout = IotHubConnection.DefaultOperationTimeout; this.sendingPath = "/messages/deviceBound"; this.faultTolerantSendingLink = new FaultTolerantAmqpObject<SendingAmqpLink>(this.CreateSendingLinkAsync, this.iotHubConnection.CloseLink); this.feedbackReceiver = new AmqpFeedbackReceiver(this.iotHubConnection); this.iotHubName = iotHubConnectionString.IotHubName; this.httpClientHelper = new HttpClientHelper( iotHubConnectionString.HttpsEndpoint, iotHubConnectionString, ExceptionHandlingHelper.GetDefaultErrorMapping(), DefaultOperationTimeout, client => {}); }