Example #1
0
        public Iq DequeueExpectedIqMessage()
        {
            Iq iq = null;

            //log.LogDebug("DequeueExpectedIqMessage - START");
            iq = iqMessagesReceived.Take();
            //log.LogDebug("DequeueExpectedIqMessage - END");
            return(iq);
        }
Example #2
0
		/// <summary>
		/// Sends an IQ response for the IQ request with the specified id.
		/// </summary>
		/// <param name="response">The IQ response to send.</param>
		/// <exception cref="ArgumentNullException">The response parameter is
		/// null.</exception>
		/// <exception cref="ArgumentException">The Type property of the response
		/// parameter is not IqType.Result or IqType.Error.</exception>
		/// <exception cref="ObjectDisposedException">The XmppCore object has been
		/// disposed.</exception>
		/// <exception cref="InvalidOperationException">The XmppCore instance is not
		/// connected to a remote host.</exception>
		/// <exception cref="IOException">There was a failure while writing to the
		/// network.</exception>
		public void IqResponse(Iq response) {
			AssertValid();
			response.ThrowIfNull("response");
			if (response.Type != IqType.Result && response.Type != IqType.Error)
				throw new ArgumentException("The IQ type must be either 'result' or 'error'.");
			Send(response);
		}
Example #3
0
		/// <summary>
		/// Performs an IQ set/get request asynchronously and optionally invokes a
		/// callback method when the IQ response comes in.
		/// </summary>
		/// <param name="request">The IQ request to send.</param>
		/// <param name="callback">A callback method which is invoked once the
		/// IQ response from the server comes in.</param>
		/// <returns>The ID value of the pending IQ stanza request.</returns>
		/// <exception cref="ArgumentNullException">The request parameter is null.</exception>
		/// <exception cref="ArgumentException">The type parameter is not IqType.Set
		/// or IqType.Get.</exception>
		/// <exception cref="ObjectDisposedException">The XmppCore object has been
		/// disposed.</exception>
		/// <exception cref="InvalidOperationException">The XmppCore instance is not
		/// connected to a remote host.</exception>
		/// <exception cref="IOException">There was a failure while writing to the
		/// network.</exception>
		public string IqRequestAsync(Iq request, Action<string, Iq> callback = null) {
			AssertValid();
			request.ThrowIfNull("request");
			if (request.Type != IqType.Set && request.Type != IqType.Get)
				throw new ArgumentException("The IQ type must be either 'set' or 'get'.");
			request.Id = GetId();
			// Register the callback.
			if (callback != null)
				iqCallbacks[request.Id] = callback;
			Send(request);
			return request.Id;
		}
Example #4
0
		/// <summary>
		/// Performs an IQ set/get request and blocks until the response IQ comes in.
		/// </summary>
		/// <param name="request">The IQ request to send.</param>
		/// <param name="millisecondsTimeout">The number of milliseconds to wait
		/// for the arrival of the IQ response or -1 to wait indefinitely.</param>
		/// <returns>The IQ response sent by the server.</returns>
		/// <exception cref="ArgumentNullException">The request parameter is null.</exception>
		/// <exception cref="ArgumentException">The type parameter is not IqType.Set
		/// or IqType.Get.</exception>
		/// <exception cref="ArgumentOutOfRangeException">The value of millisecondsTimeout
		/// is a negative number other than -1, which represents an indefinite
		/// timeout.</exception>
		/// <exception cref="ObjectDisposedException">The XmppCore object has been
		/// disposed.</exception>
		/// <exception cref="InvalidOperationException">The XmppCore instance is not
		/// connected to a remote host.</exception>
		/// <exception cref="IOException">There was a failure while writing to the
		/// network, or there was a failure reading from the network.</exception>
		/// <exception cref="TimeoutException">A timeout was specified and it
		/// expired.</exception>
		public Iq IqRequest(Iq request, int millisecondsTimeout = -1) {
            int timeOut = -1;
            AssertValid();
			request.ThrowIfNull("request");
			if (request.Type != IqType.Set && request.Type != IqType.Get)
				throw new ArgumentException("The IQ type must be either 'set' or 'get'.");
            if (millisecondsTimeout == -1)
            {
                timeOut = millisecondsDefaultTimeout;
            }
            else timeOut = millisecondsTimeout;        
            // Generate a unique ID for the IQ request.
			request.Id = GetId();
			AutoResetEvent ev = new AutoResetEvent(false);
			Send(request);
			// Wait for event to be signaled by task that processes the incoming
			// XML stream.
			waitHandles[request.Id] = ev;
			int index = WaitHandle.WaitAny(new WaitHandle[] { ev, cancelIq.Token.WaitHandle },
                timeOut);
            if (index == WaitHandle.WaitTimeout)
            {
                //An entity that receives an IQ request of type "get" or "set" MUST reply with an IQ response of type 
                //"result" or "error" (the response MUST preserve the 'id' attribute of the request). 
                //http://xmpp.org/rfcs/rfc3920.html#stanzas
                //if (request.Type == IqType.Set || request.Type == IqType.Get)

                //Make sure that its a request towards the server and not towards any client
                var ping = request.Data["ping"];

                if (request.To.Domain == Jid.Domain && (request.To.Node == null || request.To.Node == "") && (ping != null && ping.NamespaceURI == "urn:xmpp:ping"))
                {
                    Connected = false;
                    var e=  new XmppDisconnectionException("Timeout Disconnection happened at IqRequest");
                    if (!disposed)
                        Error.Raise(this, new ErrorEventArgs(e));
                    //throw new TimeoutException();
                }

                //This check is somehow not really needed doue to the IQ must be either set or get
            }
			// Reader task errored out.
			if (index == 1)
				throw new IOException("The incoming XML stream could not read.");
			// Fetch response stanza.
			Iq response;
			if (iqResponses.TryRemove(request.Id, out response))
				return response;
			// Shouldn't happen.      
            	
            throw new InvalidOperationException();
		}
Example #5
0
		/// <summary>
		/// Handles incoming IQ responses for previously issued IQ requests.
		/// </summary>
		/// <param name="iq">The received IQ response stanza.</param>
		void HandleIqResponse(Iq iq) {
			string id = iq.Id;
			AutoResetEvent ev;
			Action<string, Iq> cb;
			iqResponses[id] = iq;
			// Signal the event if it's a blocking call.
			if (waitHandles.TryRemove(id, out ev))
				ev.Set();
			// Call the callback if it's an asynchronous call.
			else if (iqCallbacks.TryRemove(id, out cb))
				Task.Factory.StartNew(() => { cb(id, iq); });
		}
Example #6
0
		/// <summary>
		/// Listens for incoming XML stanzas and raises the appropriate events.
		/// </summary>
		/// <remarks>This runs in the context of a separate thread. In case of an
		/// exception, the Error event is raised and the thread is shutdown.</remarks>
		void ReadXmlStream() {
			try {
				while (true) {
                    XmlElement elem = parser.NextElement("iq", "message", "presence");
					// Parse element and dispatch.
					switch (elem.Name) {
						case "iq":
							Iq iq = new Iq(elem);
							if (iq.IsRequest)
								stanzaQueue.Add(iq);
							else
								HandleIqResponse(iq);
							break;
						case "message":
							stanzaQueue.Add(new Message(elem));
							break;
						case "presence":
							stanzaQueue.Add(new Presence(elem));
							break;
					}
				}
			} catch (Exception e) {
				// Shut down the dispatcher task.
				cancelDispatch.Cancel();
				cancelDispatch = new CancellationTokenSource();
				// Unblock any threads blocking on pending IQ requests.
				cancelIq.Cancel();
				cancelIq = new CancellationTokenSource();
                //Add the failed connection
                if ((e is IOException) || (e is XmppDisconnectionException))
                {
                    Connected = false;
                    var ex = new XmppDisconnectionException(e.ToString());
                    e = ex;
                }
				// Raise the error event.
				if(!disposed)
					Error.Raise(this, new ErrorEventArgs(e));
			}
		}
Example #7
0
 /// <summary>
 /// Initializes a new instance of the IqEventArgs class.
 /// </summary>
 /// <param name="stanza">The IQ stanza on whose behalf the event is
 /// raised.</param>
 /// <exception cref="ArgumentNullException">The stanza parameter is null.</exception>
 public IqEventArgs(Iq stanza)
 {
     stanza.ThrowIfNull("stanza");
     Stanza = stanza;
 }
Example #8
0
 public void QueueExpectedIqMessage(Iq iq)
 {
     //log.LogDebug("QueueExpectedIqMessage :{0}", iq.ToString());
     iqMessagesReceived.Add(iq);
 }