Пример #1
0
 public override object Manage(CommandMessage commandMessage)
 {
     object result = base.Manage(commandMessage);
     switch (commandMessage.operation)
     {
         case CommandMessage.SubscribeOperation:
             lock (SyncRoot)
             {
                 bool enableReceive = _consumers.Count == 0;
                 _consumers[commandMessage.clientId] = null;
                 if (enableReceive)
                     EnableReceiving(true);
             }
             break;
         case CommandMessage.UnsubscribeOperation:
             lock (SyncRoot)
             {
                 if (_consumers.Contains(commandMessage.clientId))
                 {
                     _consumers.Remove(commandMessage.clientId);
                     if (_consumers.Count == 0)
                         EnableReceiving(false);
                 }
             }
             break;
     }
     return result;
 }
Пример #2
0
        private IDictionary Invoke(IDictionary request)
        {
            ValidationUtils.ArgumentNotNull(request, "request");
            object error = null;
            object result = null;

            ISession session = this.MessageBroker.SessionManager.GetHttpSession(HttpContext.Current);
            FluorineContext.Current.SetSession(session);
            //Context initialized, notify listeners.
            if (session != null && session.IsNew)
                session.NotifyCreated();

            // Get the ID of the request.
            object id = request["id"];
            string credentials = request["credentials"] as string;
            if (!StringUtils.IsNullOrEmpty(credentials))
            {
                try
                {
                    CommandMessage commandMessage = new CommandMessage(CommandMessage.LoginOperation);
                    commandMessage.body = credentials;
                    IMessage message = this.MessageBroker.RouteMessage(commandMessage);
                    if (message is ErrorMessage)
                    {
                        error = FromException(message as ErrorMessage);
                        return CreateResponse(id, result, error);
                    }
                }
                catch (Exception ex)
                {
                    error = FromException(ex);
                    return CreateResponse(id, result, error);
                }
            }

            // If the ID is not there or was not set then this is a notification
            // request from the client that does not expect any response. Right
            // now, we don't support this.
            bool isNotification = JavaScriptConvert.IsNull(id);

            if (isNotification)
                throw new NotSupportedException("Notification are not yet supported.");

            log.Debug(string.Format("Received request with the ID {0}.", id.ToString()));

            // Get the method name and arguments.
            string methodName = StringUtils.MaskNullString((string)request["method"]);

            if (methodName.Length == 0)
                throw new JsonRpcException("No method name supplied for this request.");

            if (methodName == "clearCredentials")
            {
                try
                {
                    CommandMessage commandMessage = new CommandMessage(CommandMessage.LogoutOperation);
                    IMessage message = this.MessageBroker.RouteMessage(commandMessage);
                    if (message is ErrorMessage)
                    {
                        error = FromException(message as ErrorMessage);
                        return CreateResponse(id, result, error);
                    }
                    else
                        return CreateResponse(id, message.body, null);
                }
                catch (Exception ex)
                {
                    error = FromException(ex);
                    return CreateResponse(id, result, error);
                }
            }

            //Info("Invoking method {1} on service {0}.", ServiceName, methodName);

            // Invoke the method on the service and handle errors.
            try
            {
                RemotingMessage message = new RemotingMessage();
                message.destination = this.Request.QueryString["destination"] as string;
                message.source = this.Request.QueryString["source"] as string;
                message.operation = methodName;
                object argsObject = request["params"];
                object[] args = (argsObject as JavaScriptArray).ToArray();
                message.body = args;
                IMessage response = this.MessageBroker.RouteMessage(message);
                if (response is ErrorMessage)
                    error = FromException(response as ErrorMessage);
                else
                    result = response.body;

                /*
                Method method = serviceClass.GetMethodByName(methodName);

                object[] args;
                string[] names = null;

                object argsObject = request["params"];
                IDictionary argByName = argsObject as IDictionary;

                if (argByName != null)
                {
                    names = new string[argByName.Count];
                    argByName.Keys.CopyTo(names, 0);
                    args = new object[argByName.Count];
                    argByName.Values.CopyTo(args, 0);
                }
                else
                {
                    args = (argsObject as JavaScriptArray).ToArray();
                }

                result = method.Invoke(instance, names, args);
                 */
            }
            catch (Exception ex)
            {
                log.Error(ex.Message, ex);
                throw;
            }

            // Setup and return the response object.
            return CreateResponse(id, result, error);
        }
Пример #3
0
        /// <summary>
        /// Closes the handler.
        /// </summary>
        public void Close()
        {
            lock (this.SyncRoot)
            {
                if (IsClosed || IsClosing)
                    return;
                SetIsClosing(true);
            }
            if (_session != null)
                _session.RemoveSessionDestroyedListener(this);
            _flexClient.UnregisterEndpointPushHandler(this, _endpoint.Id);

#if !(NET_1_1)
            List<IMessage> list = new List<IMessage>(1);
#else
            ArrayList list = new ArrayList(1);
#endif
            CommandMessage disconnect = new CommandMessage(CommandMessage.DisconnectOperation);
            PushMessage(disconnect);

            // Invalidate associated subscriptions. This doesn't attempt to notify the client.
            foreach (MessageClient messageClient in _messageClients)
                messageClient.Invalidate();

            lock (this.SyncRoot)
            {
                SetIsClosed(true);
                SetIsClosing(false);
            }
            lock (this.SyncRoot)
            {
                Monitor.PulseAll(this.SyncRoot);
            }
        }
Пример #4
0
 protected override MessageBase CopyImpl(MessageBase clone)
 {
     // Instantiate the clone, if a derived type hasn't already.
     if (clone == null) clone = new CommandMessage();
     // Allow base type(s) to copy their state into the new clone.
     base.CopyImpl(clone);
     // Copy our state into the clone.
     ((CommandMessage)clone)._messageRefType = _messageRefType;
     ((CommandMessage)clone)._operation = _operation;
     return clone;
 }
Пример #5
0
        public override IMessage ServiceMessage(IMessage message)
        {
            if (FluorineContext.Current.Client != null)
                FluorineContext.Current.Client.Renew();

            if (message is CommandMessage)
            {
                CommandMessage commandMessage = message as CommandMessage;
                switch (commandMessage.operation)
                {
                    case CommandMessage.PollOperation:
                        {
                            if (log.IsDebugEnabled)
                                log.Debug(__Res.GetString(__Res.Endpoint_HandleMessage, this.Id, message.ToString()));

                            if (FluorineContext.Current.Client != null)
                                FluorineContext.Current.Client.Renew();

                            //IMessage[] messages = null;
                            IList messages = null;
                            _waitingPollRequests.Increment();
                            int waitIntervalMillis = this.ChannelDefinition.Properties.WaitIntervalMillis != -1 ? this.ChannelDefinition.Properties.WaitIntervalMillis : 60000;// int.MaxValue;

                            if (commandMessage.HeaderExists(CommandMessage.FluorineSuppressPollWaitHeader))
                                waitIntervalMillis = 0;
                            //If async handling was not set long polling is not supported
                            if (!FluorineConfiguration.Instance.FluorineSettings.Runtime.AsyncHandler)
                                waitIntervalMillis = 0;
                            if (this.ChannelDefinition.Properties.MaxWaitingPollRequests <= 0 || _waitingPollRequests.Value >= this.ChannelDefinition.Properties.MaxWaitingPollRequests)
                                waitIntervalMillis = 0;

                            if (message.destination != null && message.destination != string.Empty)
                            {
                                string clientId = commandMessage.clientId as string;
                                MessageDestination messageDestination = this.GetMessageBroker().GetDestination(message.destination) as MessageDestination;
                                MessageClient client = messageDestination.SubscriptionManager.GetSubscriber(clientId);
                                client.Renew();
                                //messages = client.GetPendingMessages();
                            }
                            else
                            {
                                //if (FluorineContext.Current.Client != null)
                                //    messages = FluorineContext.Current.Client.GetPendingMessages(waitIntervalMillis);
                            }

                            if (FluorineContext.Current.Client != null)
                            {
                                IEndpointPushHandler handler = FluorineContext.Current.Client.GetEndpointPushHandler(this.Id);
                                if (handler != null)
                                    messages = handler.GetPendingMessages();
                                if (messages == null)
                                {
                                    lock (handler.SyncRoot)
                                    {
                                        Monitor.Wait(handler.SyncRoot, waitIntervalMillis);
                                    }
                                    messages = handler.GetPendingMessages();
                                }
                            }

                            _waitingPollRequests.Decrement();
                            IMessage response = null;
                            if (messages == null || messages.Count == 0)
                                response = new AcknowledgeMessage();
                            else
                            {
                                CommandMessage resultMessage = new CommandMessage();
                                resultMessage.operation = CommandMessage.ClientSyncOperation;
                                resultMessage.body = messages;
                                response = resultMessage;
                            }
                            if (log.IsDebugEnabled)
                                log.Debug(__Res.GetString(__Res.Endpoint_Response, this.Id, response.ToString()));
                            return response;

                        }
                    case CommandMessage.SubscribeOperation:
                        {
                            /*
                            if (FluorineContext.Current.Client == null)
                                FluorineContext.Current.SetCurrentClient(this.GetMessageBroker().ClientRegistry.GetClient(message));
                            RemotingConnection remotingConnection = null;
                            foreach (IConnection connection in FluorineContext.Current.Client.Connections)
                            {
                                if (connection is RemotingConnection)
                                {
                                    remotingConnection = connection as RemotingConnection;
                                    break;
                                }
                            }
                            if (remotingConnection == null)
                            {
                                remotingConnection = new RemotingConnection(this, null, FluorineContext.Current.Client.Id, null);
                                FluorineContext.Current.Client.Renew(this.ClientLeaseTime);
                                remotingConnection.Initialize(FluorineContext.Current.Client);
                            }
                            FluorineWebContext webContext = FluorineContext.Current as FluorineWebContext;
                            webContext.SetConnection(remotingConnection);
                            */

                            if (this.ChannelDefinition.Properties.IsPollingEnabled)
                            {
                                //Create and forget, client will close the notifier
                                IEndpointPushHandler handler = FluorineContext.Current.Client.GetEndpointPushHandler(this.Id);
                                if( handler == null )
                                    handler = new EndpointPushNotifier(this, FluorineContext.Current.Client);
                                /*
                                lock (_endpointPushHandlers.SyncRoot)
                                {
                                    _endpointPushHandlers.Add(notifier.Id, notifier);
                                }
                                */
                            }
                        }
                        break;
                    case CommandMessage.DisconnectOperation:
                        {
                            if (log.IsDebugEnabled)
                                log.Debug(__Res.GetString(__Res.Endpoint_HandleMessage, this.Id, message.ToString()));

                            if (FluorineContext.Current.Client != null && FluorineContext.Current.Client.IsValid)
                            {
                                IList messageClients = FluorineContext.Current.Client.MessageClients;
                                if (messageClients != null)
                                {
                                    foreach (MessageClient messageClient in messageClients)
                                    {
                                        messageClient.Invalidate();
                                    }
                                }
                                FluorineContext.Current.Client.Invalidate();
                            }
                            if (FluorineContext.Current.Session != null)
                            {
                                FluorineContext.Current.Session.Invalidate();
                            }
                            //Disconnect command is received from a client channel.
                            //The response returned by this method is not guaranteed to get to the client, which is free to terminate its physical connection at any point.
                            IMessage response = new AcknowledgeMessage();

                            if (log.IsDebugEnabled)
                                log.Debug(__Res.GetString(__Res.Endpoint_Response, this.Id, response.ToString()));
                            return response;
                        }
                }
            }
            return base.ServiceMessage(message);
        }
Пример #6
0
        /// <summary>
        /// Invalidates the MessageClient.
        /// </summary>
        /// <param name="notifyClient">Push a subscription invalidation message to the client.</param>
        public void Invalidate(bool notifyClient)
        {
            lock (this.SyncRoot)
            {
                if (!IsValid || IsInvalidating)
                    return; // Already shutting down.

                SetIsInvalidating(true);
                _messageDestination.SubscriptionManager.CancelTimeout(this);
            }

            // Build a subscription invalidation message and push to the client if it is still valid.
            if (notifyClient && _client != null && _client.IsValid)
            {
                CommandMessage commandMessage = new CommandMessage();
                commandMessage.destination= _messageDestination.Id;
                commandMessage.clientId = _clientId;
                commandMessage.operation = CommandMessage.SessionInvalidateOperation;

                MessageService messageService = _messageDestination.Service as MessageService;
                object[] subscribers = new object[] { commandMessage.clientId };
                try
                {
                    messageService.PushMessageToClients(subscribers, commandMessage);
                }
                catch (MessageException) 
                { }
            }

            // Notify listeners that we're being invalidated.
            if (_messageClientDestroyedListeners != null && _messageClientDestroyedListeners.Count != 0)
            {
                foreach (IMessageClientListener listener in _messageClientDestroyedListeners.Keys )
                {
                    listener.MessageClientDestroyed(this);
                }
                _messageClientDestroyedListeners.Clear();
            }

            // Generate unsubscribe messages for all of the MessageClient's subscriptions and 
            // route them to the destination this MessageClient is subscribed to.
            // Some adapters manage their own subscription state.
            ArrayList unsubscribeMessages = new ArrayList();
            lock (this.SyncRoot)
            {
                foreach(SubscriptionInfo subscription in _subscriptions)
                {
                    CommandMessage unsubscribeMessage = new CommandMessage();
                    unsubscribeMessage.destination = _messageDestination.Id;
                    unsubscribeMessage.clientId = _clientId;
                    unsubscribeMessage.operation = CommandMessage.UnsubscribeOperation;
                    unsubscribeMessage.SetHeader(CommandMessage.SessionInvalidatedHeader, true);
                    unsubscribeMessage.SetHeader(CommandMessage.SelectorHeader, subscription.Selector);
                    unsubscribeMessage.SetHeader(AsyncMessage.SubtopicHeader, subscription.Subtopic);
                    unsubscribeMessages.Add(unsubscribeMessage);
                }
            }
            // Release the lock and send the unsub messages.
            foreach (CommandMessage commandMessage in unsubscribeMessages)
            {
                try
                {
                    _messageDestination.Service.ServiceMessage(commandMessage);
                }
                catch (MessageException me)
                {
                    if (log.IsDebugEnabled)
                        log.Debug("MessageClient: " + _clientId + " issued an unsubscribe message during invalidation that was not processed but will continue with invalidation.", me);
                }
            }

            //TODO
            RemoveSubscription(this.Selector, this.Subtopic);

            lock (this.SyncRoot)
            {
                // If we didn't clean up all subscriptions log an error and continue with shutdown.
                int remainingSubscriptionCount = _subscriptions.Count;
                if (remainingSubscriptionCount > 0 && log.IsErrorEnabled)
                    log.Error("MessageClient: " + _clientId + " failed to remove " + remainingSubscriptionCount + " subscription(s) during invalidation");
            }

            _messageDestination.SubscriptionManager.RemoveSubscriber(this);

            lock (this.SyncRoot)
            {
                SetIsValid(false);
                SetIsInvalidating(false);
            }
        }  
Пример #7
0
 /// <summary>
 /// Accept a command from the adapter's service (subscribe, unsubscribe and ping operations).
 /// </summary>
 /// <param name="commandMessage"></param>
 /// <returns></returns>
 public virtual object Manage(CommandMessage commandMessage)
 {
     return new AcknowledgeMessage();
 }
Пример #8
0
		public override object ServiceMessage(IMessage message)
		{
			CommandMessage commandMessage = message as CommandMessage;
			if( commandMessage != null )
			{
                //Sub/unsub handled by base class
				return base.ServiceMessage(commandMessage);
			}
			else
			{
				AsyncMessage responseMessage = null;
				DataMessage dataMessage = message as DataMessage;

				DataDestination dataDestination = this.GetDestination(dataMessage) as DataDestination;
				if( dataDestination.SubscriptionManager.GetSubscriber(dataMessage.clientId as string) == null )
				{
					//Subscribe here as DS doesn't send a separate subscribe command
                    CommandMessage commandMessageSubscribe = new CommandMessage();
                    commandMessageSubscribe.destination = dataDestination.Id;
                    commandMessageSubscribe.operation = CommandMessage.SubscribeOperation;
                    commandMessageSubscribe.clientId = dataMessage.clientId as string;
                    string endpointId = dataMessage.GetHeader(MessageBase.EndpointHeader) as string;
                    commandMessageSubscribe.headers[MessageBase.EndpointHeader] = endpointId;
                    string flexClientIdHeader = dataMessage.GetHeader(MessageBase.FlexClientIdHeader) as string;
                    if( flexClientIdHeader != null )
                        commandMessageSubscribe.headers[MessageBase.FlexClientIdHeader] = flexClientIdHeader;
                    IEndpoint endpoint = GetMessageBroker().GetEndpoint(endpointId);
                    endpoint.ServiceMessage(commandMessageSubscribe);//route through the endpoint again
                    //base.ServiceMessage(commandMessageSubscribe);
				}

				switch(dataMessage.operation)
				{
					case DataMessage.FillOperation:
						responseMessage = ExecuteFillOperation(message);
						break;
					case DataMessage.GetOperation:
						responseMessage = ExecuteGetOperation(message);
						break;
					case DataMessage.BatchedOperation:
					case DataMessage.MultiBatchOperation:
					case DataMessage.TransactedOperation:
						responseMessage = ExecuteMultiBatchOperation(message);
						break;
					case DataMessage.PageItemsOperation:
						responseMessage = ExecutePageItemsOperation(message);
						break;
					case DataMessage.PageOperation:
						responseMessage = ExecutePageOperation(message);
						break;
					case DataMessage.ReleaseCollectionOperation:
						responseMessage = ExecuteReleaseCollectionOperation(message);
						break;
					case DataMessage.GetSequenceIdOperation:
						responseMessage = ExecuteGetSequenceIdOperation(message);
						break;
					case DataMessage.ReleaseItemOperation:
						responseMessage = ExecuteReleaseItemOperation(message);
						break;
					default:
						if(log.IsErrorEnabled)
							log.Error(__Res.GetString(__Res.DataService_Unknown, dataMessage.operation));

						responseMessage = new AcknowledgeMessage();
						break;
				}
				responseMessage.clientId = message.clientId;
				responseMessage.correlationId = message.messageId;
				//Dump();
				return responseMessage;
			}
		}