/// <summary> /// Notifies the connected digital shelf/shelves when a shopping cart has been manipulated in the It-System. /// </summary> /// <param name="shoppingCart">The shopping cart that has been manipulated.</param> /// <returns><c>true</c> if the shopping cart update message was sent successfully, <c>false</c> otherwise.</returns> public bool UpdateShoppingCart(IShoppingCart shoppingCart) { if (shoppingCart == null) { throw new ArgumentException("No shopping cart specified."); } if (!this.Connected) { throw new InvalidOperationException("The digital shelf is currently not connected."); } var message = new ShoppingCartUpdateMessageEnvelope() { ShoppingCartUpdateMessage = new ShoppingCartUpdateMessage() { Id = MessageId.Next, Destination = _destinationId, Source = SubscriberID, ShoppingCart = (ShoppingCart)shoppingCart } }; if (!_messageObjectStream.Write(message)) { throw new ApplicationException("Sending 'ShoppingCartUpdateMessage' to digital shelf failed."); } return(true); }
/// <summary> /// Sends the specified message envelope and waits for the response in form of the specified message type. /// </summary> /// <param name="messageEnvelope">The message envelope to send.</param> /// <param name="messageId">The message identifier to use while waiting for the response.</param> /// <param name="responseType">The type of the response message to wait for.</param> /// <param name="waitTimeoutMilliseconds">The wait timeout milliseconds.</param> /// <returns> /// Requested response message if it was received; null otherwise. /// </returns> public MessageBase SendAndWaitForResponse(object messageEnvelope, string messageId, Type responseType, int waitTimeoutMilliseconds = 0) { if (messageEnvelope == null) { throw new ArgumentException("Invalid messageEnvelope specified."); } if (responseType == null) { throw new ArgumentException("Invalid responseType specified."); } MessageInterceptor interceptor = null; try { lock (_syncLock) { if (_messageObjectStream == null) { return(null); } interceptor = new MessageInterceptor(messageId, responseType); AddInterceptor(interceptor); if (_messageObjectStream.Write(messageEnvelope) == false) { throw new ApplicationException(string.Format("Sending '{0}' to storage system failed.", messageEnvelope.GetType().Name)); } } if (waitTimeoutMilliseconds == 0) { interceptor.Wait(); return(interceptor.Message); } else { if (interceptor.Wait(waitTimeoutMilliseconds)) { return(interceptor.Message); } return(null); } } finally { if (interceptor != null) { RemoveInterceptor(interceptor); interceptor.Dispose(); } } }
/// <summary> /// Sends the specified message envelope and waits for the response in form of the specified message type. /// </summary> /// <param name="messageEnvelope">The message envelope to send.</param> /// <param name="messageId">The message identifier to use while waiting for the response.</param> /// <param name="responseType">The type of the response message to wait for.</param> /// <param name="waitTimeoutMilliseconds">The wait timeout milliseconds.</param> /// <returns> /// Requested response message if it was received; null otherwise. /// </returns> public MessageBase SendAndWaitForResponse(object messageEnvelope, string messageId, Type responseType, int waitTimeoutMilliseconds = 0) { if (messageEnvelope == null) { throw new ArgumentException("Invalid messageEnvelope specified."); } if (responseType == null) { throw new ArgumentException("Invalid responseType specified."); } MessageInterceptor interceptor = null; try { lock (_syncLock) { if (_messageObjectStream == null) { return(null); } this.Trace("Initialize a new Message Interceptor and add it to the internal interceptor list."); interceptor = new MessageInterceptor(messageId, responseType); AddInterceptor(interceptor); this.Trace($"Start sending {messageEnvelope.GetType().Name} to Storage System."); if (_messageObjectStream.Write(messageEnvelope) == false) { throw new ApplicationException(string.Format("Sending '{0}' to storage system failed.", messageEnvelope.GetType().Name)); } } this.Trace("Waiting for the message interception notification and return the intercepted message."); if (waitTimeoutMilliseconds == 0) { interceptor.Wait(); return(interceptor.Message); } else { if (interceptor.Wait(waitTimeoutMilliseconds)) { return(interceptor.Message); } return(null); } } finally { if (interceptor != null) { RemoveInterceptor(interceptor); interceptor.Dispose(); } } }
/// <summary> /// Reads the next Mosaic message from the underlying connection and returns it. This method will block until a new Mosaic message /// has been read, the converter stream has been cancelled or an error occurred. /// </summary> /// <returns> /// Read Mosaic message if successful; <c>null</c> otherwise. /// </returns> public MosaicMessage Read() { while (true) { IMessageConversion message = null; while (message == null) { object readMessage = _objectStream.Read(); if (readMessage == null) { return(null); } if (readMessage.GetType() == typeof(KeepAliveRequestEnvelope)) { var request = (KeepAliveRequestEnvelope)readMessage; var response = new KeepAliveResponseEnvelope() { KeepAliveResponse = new KeepAliveResponse() { Id = request.KeepAliveRequest.Id, Source = _configuration.SubscriberID, Destination = request.KeepAliveRequest.Source } }; if (_objectStream.Write(response) == false) { this.Error("Sending keep alive response with ID '{0}' failed.", request.KeepAliveRequest.Id); return(null); } continue; } if (readMessage.GetType() == typeof(KeepAliveResponseEnvelope)) { var response = (KeepAliveResponseEnvelope)readMessage; if (TypeConverter.ConvertInt(response.KeepAliveResponse.Id) == _keepAliveID) { System.Threading.Interlocked.Exchange(ref _lastKeepAlive, 0); continue; } this.Error("Received orphan keep alive response with ID '{0}' but expected ID '{1}'.", response.KeepAliveResponse.Id, _keepAliveID); return(null); } message = readMessage as IMessageConversion; if (message == null) { this.Error("Ignored unsupported message of type '{0}'.", readMessage.GetType().FullName); continue; } } var mosaicMessage = message.ToMosaicMessage(this); if (mosaicMessage != null) { mosaicMessage.TenantID = _tenantID; } return(mosaicMessage); } }