The Python Observer/Observable pattern
*********************************************************

This is an implementation of the Observer/Observable pattern.

In software development literature, Observer/Observable is a software
pattern.  From an Observer/Observable perspective, there are two kinds
of objects:
	
	- objects which experience events or state changes (Observables)
	- objects which need to know about other objects' events (Observers)

If you have any experience with event-based programming, such as with
toolkits like GTK+ or Qt, you'll be familiar with the Observer/Observable
pattern.  Observer objects register themselves with the Observable object
of their interest, and when Observables experience events, these events
are relayed to the Observers.

Observer/Observable lets software developers build loosely coupled object
meshes.  What this means to you: your software will be more stable and
easier to refactor.

This module has a complete Observer/Observable implementation.  To take
advantage of this module, all you have to do is:
	
	- Make your Observable classes inherit from Observable
	  (don't forget to call Observable.__init__(self) in the constructor)
	- Make your Observer classes inherit from Observer
	  (don't forget to call Observer.__init__(self) in the constructor)
	- At runtime, for each object you want to observe, call
		self.observe(observable_object)
	  in a method of your Observer object.
	- In your Observable object, every time an event happens, call:
		...
		self.broadcastEvent("MyEventName",argument1,argument2...)
		...
	- In your Observer object, implement a method named:
		def processEvent(self,notifierObject,eventName,*args):
	  which will receive the notifier object, an event name, and a
	  variable number of arguments, every time broadcastEvent is
	  called in any of the Observable objects that have been observe'd()

That's it.  Keep in mind that processEvent() will be invoked in the
same thread context as the code which called broadcastEvent() in the
Observable object.  Thus, processEvent() methods should return quickly and
never do blocking operations (suggested technique for coping with blocking
operations: run them in a separate thread, which sleeps until a flag is
raised, and raise the flag in the processEvent() method as appropriate).

Cute example:

from Observable import Observable,Observed

class Cat(Observable):
	def __init__(self):
		Observable.__init__(self)
	...
	def doMyLife(self):
		street = self.searchForFood()
		self.broadcastEvent("inNeighborhood",street)
	...
	
class Dog(Observer):
	def __init__(self,neighborsCat):
		Observer.__init__(self)
		self.hatedCat = neighborsCat
		self.myStreet = "Fake Street"
		self.observe(neighborsCat)
	...
	def processEvent(self,notifierObject,eventName,*arguments):
		if notifierObject == self.hatedCat: # the cat I was observing
			if eventName == "inNeighborhood": # the event name
				if arguments[0] == self.myStreet: # my street
					self.chaseCat(self.hatedCat)
					# chaseCat should return quickly


PREREQUISITES

This software requires:
- Python 2.2 or later


INSTALLATION

To install, use:

   python setup.py install # to build and install directly
   python setup.py bdist_rpm # to prepare an RPM


HELP

The module is heavily documented


FEEDBACK: REPORTING BUGS, PATCHES, ETC.

dragonfear@gmail.com for the moment


LICENSE AND LEGAL NOTICE

This software is under the GPL.  See the file COPYING for licensing
information.  Contact me if you need us to license this software under
a different license.


AUTHORS

Manuel Amador (Rudd-O) <dragonfear@gmail.com>
