1.9.1Class VMSlot

VM Interface for message oriented programming operations.

Class VMSlot( [name] )
name The name of the mesasge managed by this VMSlot.

The VMSlot instance is a direct interface to the messaging facility of the VM creating it. It is implicitly created by the getSlot function, but it can be directly created by the user.

If a slot with the given name didn't previously exist, a new message slot is created in the virtual machine, otherwise the already existing slot is wrapped in the returned instance.


      // create a message slot
      x = VMSlot( "message" )
      x.subscribe( handler )
      ...
      y = VMSlot( "message" )
      y.broadcast( "value" )  // handler is called.

Same happens if the VMSlot is created via getSlot, or implicitly referenced via subscribe function. Slots are considered unique by name, so that comparisons on slots are performed on their names.

If the name parameter is not given, the slot will be created as "anonymous", and won't be registered with this virtual machine. It will be possible to use it only through its methods.

Anonymous slots

An anonymous slot can be created using an empty call to the VMSlot class constructor. This will make the slot private for the users that can access it; in other words, the slot won't be published to the VM and it won't be possible to broadcast on it using the standard functions broadcast or assert functions.

Automatic broadcast marshaling

If a listener subscribed to a slot is a callable item, then it's called in case of broadcasts. If it's a non-callable property provider (class instances, blessed dictionaries, non-callable arrays) then a callable property named like "on_" is searched; if found, it's called (as a method of the host entity), otherwise a catch all method named "on_event" is searched.

If the "on_event" method is found, it's called with the first parameter containing the broadcast name. Otherwise, an access error is raised.

Events

Events are "named broadcasts". They are issued on slots and excite all the listeners that are subscribed to that slot. The main difference is that automatic marshalling is directed to the name of the event rather to the name of the slot.

See the following code:


      object Receiver
         _count = 0

         function display(): > "Count is now ", self._count
         function on_add(): self._count++
         function on_sub(): self._count--
         function __on_event( evname ): > "Received an unknown event: ", evname
      end

      s = VMSlot()  // creates an anonymous slot

      s.subscribe( Receiver )

      s.send( "add" ) // Instead of sending a broadcast ...
      s.send( "add" ) // ... generate some events via send()

      s.send( "A strange event", "some param" )  // will complain
      Receiver.display()   // show the count

The VMSlot.send method works similarly to the VMSlot.broadcast method, but it allows to specify an arbitrary event name. Callbacks subscribed to this slot would be called for every event, be it generated through a broadcast or via a send call.

Registering to events and Sub-slots

While callbacks subscribed to the slot will be excited no matter what kind of event is generated, it is possible to register callbacks to respond only to particular events via the VMSlot.register method.

See the following example:


   slot = VMSlot()  // creates an anonymous slot
   slot.register( "first",
      { param => printl( "First called with ", param ) } )

   slot.register( "second",
      { param => printl( "Second called with ", param ) } )

   // send "first" and "second" events
   slot.send( "first", "A parameter" )
   slot.send( "second", "Another parameter" )

   // this will actually do nothing
   slot.broadcast( "A third parameter" )

As no callback is subscribed to the slot, but some are just register to some events, a generic broadcast will have no effect.

An interesting thing about registering to events is that a slot keeps tracks of callbacks and items registered to a specific event via a named slot. For example, to know who is currently subscribed to the "first" event, it's possible to call the VMSlot.getEvent method and inspect the returned slot. Any change in that returned slot will cause the event registration to change.

For example, continuing the above code...


      //...
      fevt = slot.getEvent( "first" )

      // display each subscribed item
      for elem in fevt: > elem.toString()

      // and broadcast on the event first
      fevt.broadcast( "The parameter" )

As seen, a broadcast on a sub-slot is equivalent to an event send on the parent slot.

Note: It is then possible to cache repeatedly broadcast slots, so that the virtual machine is not forced to search across the subscribed events.

This structure can be freely replicated at any level. In the above example, fevt may be subject of send() and register() method application, and its own events can be retrieved trough its VMSlot.getEvent method.

Methods
assertCreates a message assertion on this certain message slot.
broadcastPerforms broadcast on this slot.
firstGets an iterator to the first subscriber.
getAssertGets the item asserted for this slot.
getEventReturns an event (as a child VMSlot) handled by this slot.
lastGets an iterator to the last subscriber.
nameReturns the name of this slot
prependRegisters a callback handler that will be called before the others.
registerRegisters a listener for a specific event.
retractRemoves a previous assertion on a message.
sendPerforms an event generation on this slot.
subscribeRegisters a callback handler on this slot.
unsubscribeUnregisters a callback handler from this slot.

Methods

assert

Creates a message assertion on this certain message slot.

VMSlot.assert( data )
data The value of the assertion.

If there are already subscribed callbacks for this message a broadcast on them is performed now.

broadcast

Performs broadcast on this slot.

VMSlot.broadcast( ... )
... Extra parameters to be sent to listeners.

first

Gets an iterator to the first subscriber.

VMSlot.first()
ReturnAn iterator to the first subscriber of this message slot.

getAssert

Gets the item asserted for this slot.

VMSlot.getAssert( [default] )
default If given, instead of raising in case the essartion is not found, return this item.
Raise
MessageError if the item has not an assertion and a default is not given.

getEvent

Returns an event (as a child VMSlot) handled by this slot.

VMSlot.getEvent( event, [force] )
event A string representing the event name.
force Pass true to create the event if it is not existing.
Returna VMSlot representing the given event in this slot, or nil if not found.

This method returns a named VMSlot that will be excited by VMSlot.send applied on this slot with the same event name.

In other words, subscribing or unsubscribing items from the returned slot would add or remove listeners for a VMSlot.send call on this slot.

Also, a broadcast on the returned VMSlot has the same effect of a VMSlot.send with the same name as the event passed.

See also: VMSlot.

last

Gets an iterator to the last subscriber.

VMSlot.last()
ReturnAn iterator to the last subscriber of this message slot.

name

Returns the name of this slot

VMSlot.name()
ReturnThe name of the event bind to this slot (as a string).

prepend

Registers a callback handler that will be called before the others.

VMSlot.prepend( handler )
handler The callable that must be unregistered.

register

Registers a listener for a specific event.

VMSlot.register( event, handler )
event A string representing the event name.
handler Handler to associate to this event.

This function associates the given handler to a sub-slot named after the event parameter. This operation is equivalent to call VMSlot.getEvent() to create the desired sub-slot, and then call VMSlot.subscribe() on that named slot.

See also: VMSlot.

retract

Removes a previous assertion on a message.

VMSlot.retract()

send

Performs an event generation on this slot.

VMSlot.send( event, ... )
event Event name.
... Extra parameters to be sent to listeners.

The send method works as broadcast, with two major differences;

subscribe

Registers a callback handler on this slot.

VMSlot.subscribe( handler, [prio] )
handler A callable item or instance providing callback support.
prio Set to true to have this handler called before the previous ones.

unsubscribe

Unregisters a callback handler from this slot.

VMSlot.unsubscribe( handler )
handler The callable that must be unregistered.
Raise
CodeError if the handler is not registered with this slot.
Made with http://www.falconpl.org