/// <summary> /// Unregisters a previous registration with the <see cref="ServiceBusService"/> to produce or consume <see cref="Message"/>s /// </summary> /// <param name="request">The <see cref="RegistrationRequest"/> used when registering.</param> public virtual void Unregister(RegistrationRequest request) { // Retrieve registration information. RegistrationInfo registration; if (request.MessageType == MessageType.Queue) { // Queue m_queuesLock.EnterReadLock(); try { m_queues.TryGetValue(request.MessageName, out registration); } finally { m_queuesLock.ExitReadLock(); } } else if (request.MessageType == MessageType.Topic) { // Topic m_topicsLock.EnterReadLock(); try { m_topics.TryGetValue(request.MessageName, out registration); } finally { m_topicsLock.ExitReadLock(); } } else { // Unsupported throw new NotSupportedException(string.Format("Message type '{0}' is not supported by this operation", request.MessageType)); } // Update registration information. if (registration != null) { List<ClientInfo> clients = (request.RegistrationType == RegistrationType.Produce ? registration.Producers : registration.Consumers); lock (clients) { clients.RemoveAt(clients.FindIndex(client => client.SessionId == OperationContext.Current.SessionId)); } } }
/// <summary> /// Gets the latest <see cref="Message"/> distributed to the subscribers of the specified <paramref name="topic"/>. /// </summary> /// <param name="topic">The topic <see cref="RegistrationRequest"/> used when registering.</param> /// <returns>The latest <see cref="Message"/> distributed to the <paramref name="topic"/> subscribers.</returns> public virtual Message GetLatestMessage(RegistrationRequest topic) { // Retrieve registration information. RegistrationInfo registration; m_topicsLock.EnterReadLock(); try { m_topics.TryGetValue(topic.MessageName, out registration); } finally { m_topicsLock.ExitReadLock(); } // Retrieve the latest message. if (registration != null) { lock (registration.Consumers) { if (registration.Consumers.Exists(consumer => consumer.SessionId == OperationContext.Current.SessionId)) // Requestor has subscribed to the topic. return registration.LatestMessage; else // Requestor didn't subscribe to the topic. return null; } } else { return null; } }
/// <summary> /// Registers with the <see cref="ServiceBusService"/> to produce or consume <see cref="Message"/>s. /// </summary> /// <param name="request">An <see cref="RegistrationRequest"/> containing registration data.</param> public virtual void Register(RegistrationRequest request) { // Initialize if uninitialized. Initialize(); // Save client information if not already present. ClientInfo client; m_clientsLock.EnterUpgradeableReadLock(); try { if (!m_clients.TryGetValue(OperationContext.Current.SessionId, out client)) { m_clientsLock.EnterWriteLock(); try { client = new ClientInfo(OperationContext.Current); m_clients.Add(client.SessionId, client); client.OperationContext.Channel.Faulted += OnChannelFaulted; client.OperationContext.Channel.Closing += OnChannelClosing; } finally { m_clientsLock.ExitWriteLock(); } } } finally { m_clientsLock.ExitUpgradeableReadLock(); } // Retrieve registration information. RegistrationInfo registration; if (request.MessageType == MessageType.Queue) { // Queue m_queuesLock.EnterUpgradeableReadLock(); try { if (!m_queues.TryGetValue(request.MessageName, out registration)) { m_queuesLock.EnterWriteLock(); try { registration = new RegistrationInfo(request); m_queues.Add(request.MessageName, registration); } finally { m_queuesLock.ExitWriteLock(); } } } finally { m_queuesLock.ExitUpgradeableReadLock(); } } else if (request.MessageType == MessageType.Topic) { // Topic m_topicsLock.EnterUpgradeableReadLock(); try { if (!m_topics.TryGetValue(request.MessageName, out registration)) { m_topicsLock.EnterWriteLock(); try { registration = new RegistrationInfo(request); m_topics.Add(request.MessageName, registration); } finally { m_topicsLock.ExitWriteLock(); } } } finally { m_topicsLock.ExitUpgradeableReadLock(); } } else { // Unsupported throw new NotSupportedException(string.Format("Message type '{0}' is not supported by this operation", request.MessageType)); } // Update registration information. if (registration != null) { List<ClientInfo> clients = (request.RegistrationType == RegistrationType.Produce ? registration.Producers : registration.Consumers); lock (clients) { if (!clients.Contains(client)) clients.Add(client); } } }
/// <summary> /// Initializes a new instance of the <see cref="RegistrationInfo"/> class. /// </summary> /// <param name="request">An <see cref="RegistrationRequest"/> object.</param> internal RegistrationInfo(RegistrationRequest request) { MessageType = request.MessageType; MessageName = request.MessageName; Producers = new List<ClientInfo>(); Consumers = new List<ClientInfo>(); ProducersLock = new ReaderWriterLockSlim(); ConsumersLock = new ReaderWriterLockSlim(); }