Class: Jabber::Observable

Inherits:
Object
  • Object
show all
Includes:
ObservableThing
Defined in:
lib/xmpp4r-observable.rb

Overview

Jabber::Observable - Creates observable Jabber Clients

Defined Under Namespace

Classes: PubSub, Subscriptions

Instance Attribute Summary collapse

Instance Method Summary collapse

Methods included from ObservableThing

#add_observer, #changed, #changed?, #count_notifications, #count_observers, #delete_observer, #delete_observers, #notify_observers, #pending_notifications?, #wait_notifications

Constructor Details

#initialize(jid, password, status = nil, status_message = "Available", host = nil, port = 5222) ⇒ Observable

Create a new Jabber::Observable client. You will be automatically connected to the Jabber server and your status message will be set to the string passed in as the status_message argument.

jabber = Jabber::Observable.new(“[email protected]”, “password”, “Chat with me - Please!”)



320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
# File 'lib/xmpp4r-observable.rb', line 320

def initialize(jid, password, status = nil, status_message = "Available", host = nil, port=5222)
	# Basic stuff
	@jid = jid
	@password = password
	@host = host
	@port = port
	@disconnected = false

	# Message dealing
	@delivered_messages = 0
	@deferred_messages = Queue.new
	start_deferred_delivery_thread

	# Tell everybody I am here
	status(status, status_message)

	# Subscription Accessor
	@subs = Subscriptions.new(self)

	# PubSub Accessor
	@pubsub = PubSub.new(self)

	# Auto Observer placeholder
	@auto = nil
end

Instance Attribute Details

#autoObject (readonly)

Returns the value of attribute auto.



313
314
315
# File 'lib/xmpp4r-observable.rb', line 313

def auto
  @auto
end

#jidObject (readonly)

Returns the value of attribute jid.



313
314
315
# File 'lib/xmpp4r-observable.rb', line 313

def jid
  @jid
end

#pubsubObject (readonly)

Returns the value of attribute pubsub.



313
314
315
# File 'lib/xmpp4r-observable.rb', line 313

def pubsub
  @pubsub
end

#subsObject (readonly)

Returns the value of attribute subs.



313
314
315
# File 'lib/xmpp4r-observable.rb', line 313

def subs
  @subs
end

Instance Method Details

#attach_auto_observerObject

Attach an auto-observer based on QObserver

Raises:

  • (StandardError)


369
370
371
372
373
374
375
376
# File 'lib/xmpp4r-observable.rb', line 369

def attach_auto_observer
	raise StandardError, "Already attached." if ! @auto.nil?

	@auto = QObserver.new
	[ :message, :presence, :iq, :new_subscription, :subscription_request, :event ].each do |thing|
		self.add_observer(thing, @auto)
	end
end

#clientObject

Direct access to the underlying Jabber client.



477
478
479
480
# File 'lib/xmpp4r-observable.rb', line 477

def client
	connect!() unless connected?
	@client
end

#connected?Boolean

Returns true if the Jabber client is connected to the Jabber server, false otherwise.

Returns:

  • (Boolean)


464
465
466
467
468
# File 'lib/xmpp4r-observable.rb', line 464

def connected?
	@client ||= nil
	connected = @client.respond_to?(:is_connected?) && @client.is_connected?
	return connected
end

#contacts(*contacts, &block) ⇒ Object

If contacts is a single contact, returns a Jabber::Contact object representing that user; if contacts is an array, returns an array of Jabber::Contact objects.

When called with a block, contacts will yield each Jabber::Contact object in turn. This is mainly used internally, but exposed as an utility function.



448
449
450
451
452
453
454
455
456
457
458
459
460
# File 'lib/xmpp4r-observable.rb', line 448

def contacts(*contacts, &block)
	@contacts ||= {}
	contakts = []
	contacts.each do |contact|
		jid = contact.to_s
		unless @contacts[jid]
			@contacts[jid] = contact.respond_to?(:ask_for_authorization!) ? contact : Contact.new(self, contact)
		end
		yield @contacts[jid] if block_given?
		contakts << @contacts[jid]
	end
	contakts.size > 1 ? contakts : contakts.first
end

#deferred_max_waitObject

Get the maximum time to wait for a message to be delivered. Default: 600 seconds (10 minutes).



534
535
536
# File 'lib/xmpp4r-observable.rb', line 534

def deferred_max_wait
	@deferred_max_wait || 600
end

#deferred_max_wait=(seconds) ⇒ Object

Sets the maximum time to wait for a message to be delivered (in seconds). It will be removed of the queue afterwards.



528
529
530
# File 'lib/xmpp4r-observable.rb', line 528

def deferred_max_wait=(seconds)
	@deferred_max_wait = seconds
end

#deliver(jid, message, type = :chat) ⇒ Object

Send a message to jabber user jid.

Valid message types are:

* :normal (default): a normal message.
* :chat: a one-to-one chat message.
* :groupchat: a group-chat message.
* :headline: a "headline" message.
* :error: an error message.

If the recipient is not in your contacts list, the message will be queued for later delivery, and the Contact will be automatically asked for authorization (see Jabber::Observable#add).

message should be a string or a valid Jabber::Message object. In either case, the message recipient will be set to jid.



404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
# File 'lib/xmpp4r-observable.rb', line 404

def deliver(jid, message, type=:chat)
	contacts(jid) do |friend|
		unless @subs.subscribed_to? friend
			@subs.add(friend.jid)
			return deliver_deferred(friend.jid, message, type)
		end
		if message.kind_of?(Jabber::Message)
			msg = message
			msg.to = friend.jid
		else
			msg = Message.new(friend.jid)
			msg.type = type
			msg.body = message
		end
		@delivered_messages += 1
		send!(msg)
	end
end

#deliver_deferred(jid, message, type) ⇒ Object

Queue messages for delivery once a user has accepted our authorization request. Works in conjunction with the deferred delivery thread.

You can use this method if you want to manually add friends and still have the message queued for later delivery.



520
521
522
523
# File 'lib/xmpp4r-observable.rb', line 520

def deliver_deferred(jid, message, type)
	msg = {:to => jid, :message => message, :type => type, :time => Time.now}
	@deferred_messages.enq msg
end

#dettach_auto_observerObject

Dettach the auto-observer

Raises:

  • (StandardError)


379
380
381
382
383
384
385
386
# File 'lib/xmpp4r-observable.rb', line 379

def dettach_auto_observer
	raise StandardError, "Not attached." if @auto.nil?

	[ :message, :presence, :iq, :new_subscription, :subscription_request, :event ].each do |thing|
		self.delete_observer(thing, @auto)
	end
	@auto = nil
end

#disconnectObject

Use this to force the client to disconnect and not automatically reconnect.



511
512
513
# File 'lib/xmpp4r-observable.rb', line 511

def disconnect
	disconnect!
end

#inspectObject

:nodoc:



346
347
348
# File 'lib/xmpp4r-observable.rb', line 346

def inspect # :nodoc:
	sprintf("#<%s:0x%x @jid=%s, @delivered_messages=%d, @deferred_messages=%d, @observer_count=%s, @notification_count=%s, @pubsub=%s>", self.class.name, __id__, @jid, @delivered_messages, @deferred_messages.length, observer_count.inspect, notification_count.inspect, @pubsub.inspect)
end

#notification_countObject

Count the notifications really send for each thing



360
361
362
363
364
365
366
# File 'lib/xmpp4r-observable.rb', line 360

def notification_count
	h = {}
	[ :message, :presence, :iq, :new_subscription, :subscription_request, :event ].each do |thing|
		h[thing] = count_notifications(thing)
	end
	h
end

#observer_countObject

Count the registered observers in each thing



351
352
353
354
355
356
357
# File 'lib/xmpp4r-observable.rb', line 351

def observer_count
	h = {}
	[ :message, :presence, :iq, :new_subscription, :subscription_request, :event ].each do |thing|
		h[thing] = count_observers(thing)
	end
	h
end

#reconnectObject

Use this to force the client to reconnect after a force_disconnect.



504
505
506
507
# File 'lib/xmpp4r-observable.rb', line 504

def reconnect
	@disconnected = false
	connect!
end

#rosterObject

Direct access to the underlying Roster helper.



471
472
473
474
# File 'lib/xmpp4r-observable.rb', line 471

def roster
	return @roster if @roster
	self.roster = Roster::Helper.new(client)
end

#send!(msg) ⇒ Object

Send a Jabber stanza over-the-wire.



483
484
485
486
487
488
489
490
491
492
493
494
495
496
497
498
499
500
501
# File 'lib/xmpp4r-observable.rb', line 483

def send!(msg)
	attempts = 0
	begin
		attempts += 1
		client.send(msg)
	rescue Errno::EPIPE, IOError => e
		sleep 1
		disconnect
		reconnect
		retry unless attempts > 3
		raise e
	rescue Errno::ECONNRESET => e
		sleep (attempts^2) * 60 + 60
		disconnect
		reconnect
		retry unless attempts > 3
		raise e
	end
end

#status(presence, message) ⇒ Object

Set your presence, with a message.

Available values for presence are:

* nil: online.
* :chat: free for chat.
* :away: away from the computer.
* :dnd: do not disturb.
* :xa: extended away.

It’s not possible to set an offline status - to do that, disconnect! :-)



434
435
436
437
438
439
# File 'lib/xmpp4r-observable.rb', line 434

def status(presence, message)
	@presence = presence
	@status_message = message
	stat_msg = Jabber::Presence.new(@presence, @status_message)
	send!(stat_msg)
end