Python Bound API¶
-
class
karabo.bound.
PythonDevice
(configuration: <MagicMock name='mock.Hash.__or__()' id='140105519408128'>)¶ The PythonDevice class is the basis for all karabo.bound devices
Devices implemented in the karabo.bound API should derive from this class. It provides an interface to the distributed system and holds properties that represent the state of a device. Commands may be exposed through it using so-called slots.
Devices can optionally either use a full finite state machine, deriving from the FSM class, or use a simplified approach (NoFSM), where state updates are explicitly called from the device logic. The latter is the default if a device class just inherits from this PythonDevice. Otherwise the device class has to also inherit from a concrete FSM implementation that inherits from BaseFsm.
Devices run in a separate process, but internally use an event loop with multiple threads to serve requests from the distributed system.
-
KARABO_ON_DATA
(channelName, handlerPerData)¶ Registers a data handler function
This function will be called if data is received on an input channel identified by channelName. The handler function should have the signature:
- def onData(data, metaData):
- pass
where data and metaData are both Hashes.
-
KARABO_ON_EOS
(channelName, handler)¶ Registers an end-of-stream handler
Registers a handler to be called if input channel identified by channelName is signaled end-of-stream.
The handler function should have the signature
- def onEos(input):
- pass
where input is a reference to the input channel.
-
KARABO_ON_INPUT
(channelName, handlerPerInput)¶ Registers an input handler function
Registers a handler to be called if data is available on the input channel identified by channelName. It is up to the device developer to read data (in contrast to the KARABO_ON_DATA registration).
- def onInput(input):
- for i in range(input.size()):
- data, metaData = input.read(i)
Here input is a reference to the input channel.
-
KARABO_SLOT
(slot, slotName=None, numArgs=None)¶ Register a slot in the distributed system.
:param slot is the callable to register :param slotname is used to call the slot, ‘None’ means slot.__name__,
note that a ‘_’ can also be called as ‘.’ as needed for nested slots in the Schema like ‘node.slotInNode’- :param numArgs number of arguments that the slot has,
- ‘None’ means to (try to) deduce from ‘slot’
Note that a slot is only connected with a SLOT_ELEMENT if the key of the SLOT_ELEMENT matches the slot name provided to this function.
SLOT_ELEMENT(expected).key(“slotDoSomething”)
self.KARABO_SLOT(slotDoSomething)
- def slotDoSomething(self):
- pass
For slots under a node, the method name needs to replace ‘.’ by ‘_’.
SLOT_ELEMENT(expected).key(“node.slotOther”)
self.KARABO_SLOT(node_slotOther)
- def node_slotOther(self):
- pass
-
aliasHasKey
(alias)¶ Check if a key for a given alias exists
-
allowLock
()¶ Overwrite this function for service devices that cannot be locked :return:
-
appendSchema
(schema)¶ Append to the existing device schema
If a property is being reinjected, and of the same type, then it will keep its current value. If it does not fit within range, an error will be raised. Likewise, if the type changes, and the value cannot be cast, an error will be raised.
Input and output channels will be created if injected. An output channel is also recreated if its schema changes, to make the other end aware. Note that for newly created input channels there are no data, input and end-of-stream handlers registered. This has to be done via the corresponding self.KARABO_ON_[DATA|INPUT|EOS] methods. If an InputChannel is re-injected, its handlers are kept.
Parameters: schema – to append to current full schema
-
appendSchemaMaxSize
(path, value, emitFlag=True)¶ Append Schema to change/set maximum size information for path. If paths does not exist, raise KeyError.
This is similar to the more general appendSchema, but dedicated to a common use case.
- :param path indicates the parameter which should be a
- Vector- or TableElement
:param value is the new maximum size of the element :param emitFlag indicates if others should be informed about this
Schema update. If this method is called for a bunch of paths, it is recommended to set this to True only for the last call.
-
call
(instanceId, slotName, *args)¶ Call a remote slot with arguments
Parameters: - instanceId – instance of the remote device to call slot on
- slotName – name of the slot to call on instanceId
- args – list of arguments to call slot with, maximum length is 4
-
connect
(signalInstance, signalName, slotInstance, slotName)¶ Connect a signal with a slot
Parameters: - signalInstance – instance the signal is on, use “” for local
- signalName – name of the signal to connect
- slotInstance – instance the slot is on, use “” for local
- slotName – name of the slot to be executed upon signal reception
:return whether connection could be established
-
classmethod
create
(*args)¶ The factory classmethod to create the instance of class with “classId” using input “configuration”. Example:
- instance = Shape.create(“EditableCircle”,
- Hash(“radius”, 12.345))
The factory classmethod to create instance according input “configuration”. The configuration should have “classId” of class to be created as a root element. Example:
configuration = Hash(“EditableCircle.radius”, 12.345) instance = Shape.create(configuration)
-
classmethod
createChoice
(choice, config)¶ The helper classmethod to create the instance using “choiceName” and input “configuration”.
-
classmethod
createList
(listname, configuration)¶ The helper method to create the list of instances using “listName” as a key to the list of configs in input “configuration”. The configurations will be validated.
-
classmethod
createNode
(nodename, classid, configuration)¶ The helper classmethod to create instance of class specified by “classId” using sub-configuration specified by “nodeName” which has to be a part of input “configuration”.
-
emit
(signalName, *args)¶ Emit a signal to the remote system
Parameters: - signalName – name of the signal.
- args – list of arguments signal is emitted with. Maximum 4
-
filterByTags
(configuration, tags)¶ Filter a given configuration Hash by tags
Parameters: - configuration –
- tags – a string, with several entries separated by commas spaces or semicolons
Returns: the filtered configuration Hash
-
fullSchema
¶ DEPRECATED - use getFullSchema()
-
get
(key)¶ Return a property of this device
Parameters: key – as defined in the expected parameter section Returns: the value of the property
-
getActualTimestamp
()¶ Returns the actual timestamp.
The Trainstamp part of Timestamp is extrapolated from the last values received via slotTimeTick (or zero if no time ticks received, i.e. timeServerId is empty). To receive time ticks, the server of the device has to be connected to a time server.
Returns: the actual timestamp
-
getAliasFromKey
(key, aliasReferenceType)¶ Return the alias of a key :param key: to return the alias from :param aliasReferenceType: type the alias is of :return: an object of aliasReferenceType
-
getAvailableInstances
()¶ Return available instances in the distributed system
-
getCurrentConfiguration
(tags='')¶ Return the current configuration, optionally filtered by tags
Parameters: tags – a string, with several entries separated by commas spaces or semicolons. Set to an empty string if no filtering is to be applied. Returns: a configuration Hash
-
getCurrentConfigurationSlice
(paths)¶ Retrieves a slice of the current configuration.
Parameters: paths – of the configuration which should be returned (as declared in expectedParameters,
method throws if a non-existing path is given)Returns: Hash with the current values and attributes (e.g. timestamp) of the selected configuration
-
getFullSchema
()¶ Return the full schema describing this device
Returns: a karabo Schema object
-
getKeyFromAlias
(alias)¶ Return the key mapping to a given alias
-
classmethod
getSchema
(classid, rules=None)¶ Use this classmethod to get schema for class with “classid” using assembly “rules” Example:
schema = Shape.getSchema(“Rectangle”)- or
- schema = Shape.getSchema(“Rectangle”, AssemblyRules())
-
getServerId
()¶ Return the id of the server hosting this devices
-
getTimestamp
(epoch)¶ Returns the Timestamp for given Epochstamp.
The Trainstamp part of Timestamp is extrapolated forward or backward from the last values received via slotTimeTick (or zero if no time ticks received yet). To receive time ticks, the server of the device has to be connected to a time server.
Parameters: epoch – Epochstamp for that the time stamp is searched for Returns: the matching Timestamp, consisting of epoch and the corresponding Trainstamp
-
getValueType
(key)¶ Get the ValueType of a given key
Returns: The type in terms of karabo::util::ReferenceTypes
-
initChannels
(topLevel='', schema=None)¶ Initialise Input-/OutputChannels :param schema to recurse for channels - if None, use self._fullSchema :param topLevel is path in schema hierarchy where to start recursion
-
keyHasAlias
(key)¶ Check if a given key has an alias defined
-
loadLogger
()¶ Load the distributed logger
Uses config in self._parameters[“Logger”] and PythonDevice._loggerCfg
-
noStateTransition
(currentState, currentEvent)¶ This function is called if a requested state transition is not allowed in the current context. Usually, this means you have an error in your state machine.
-
onTimeUpdate
(id, sec, frac, period)¶ Called when an update from the time server is received
Parameters: - id – train id
- sec – seconds
- frac – fractional seconds
- period –
Returns:
-
parameters
¶ DEPRECATED * for full config use getCurrentConfiguration() * maybe what you want is just some key, then use get(some_key)
-
postReconfigure
()¶ Use this hook to react on configuration changes after they have been validated and applied to the device, and have been notified to the distributed system.
-
preDestruction
()¶ Use this hook if you need to perform clean-up actions before a device gets destroyed.
-
preReconfigure
(incomingReconfiguration)¶ Use this hook to alter a configuration Hash before it gets applied to the device and the distributed system is notified of the change. :param incomingReconfiguration:
-
registerSignal
(signalName, *args)¶ Register a signal to be handles in the remote system
:param signalName:name of the signal to be registered :param args: signature of the signal, e.g. str, Hash, str
-
remote
()¶ Return a DeviceClient instance.
The DeviceClient will use this device’s SignalSlotable to interact with the distributed system :return:
-
reply
(*args)¶ Place the reply of a slot being called
Reply content will not be sent immediately, but when the slot call ends. If called more than once, the last call defines the slot reply.
Parameters: args – list of arguments to reply, maximum length is 4
-
request
(instanceId, slotName, *args)¶ Request a reply from a remote slot
Parameters: - instanceId – instance of the remote device to request from
- slotName – name of the slot to request from on instanceId
- args – list of arguments to call slot with, maximum length is 4
Returns: a SignalSlotable.Requestor object handling the reply
-
requestNoWait
(instanceId, slotName, replyInstance, replySlotName, *args)¶ Request a reply from a remote slot
Parameters: - instanceId – instance of the remote device to request from
- slotName – name of the slot to request from on instanceId
- replyInstance – instance on which to handle reply, use “” for local device.
- replySlotName – slot to call with reply on replyInstance
- args – list of arguments to call slot with, maximum length is 4
Returns: a SignalSlotable.Requestor object handling the reply
-
set
(*args, **kwargs)¶ Updates device properties and notifies any observers. Note that an update of the device “state” property must be done using updateState(..).
args: can be of length
- one: expects a Hash, and uses current timestamp
- two: expects a key, value pair and uses current timestamp or a
- Hash, timestamp pair
- three: expects key, value and timestamp
- kwargs: validate: specifies if validation of args should be performed
- before notification. Skipping validation should not be used with State or AlarmCondition.
If a Hash is provided, its keys should be device properties and the values should have the proper types. A State or AlarmCondition inside a Hash should be given as a string.
-
setAlarmCondition
(condition, **deprecated)¶ Set the global alarm condition
Parameters: condition – condition to set Returns: None
-
setVectorUpdate
(key, updates, updateType, timestamp=None)¶ Concurrency safe update of vector property (not for tables)
Parameters: - key – key of the vector property to update
- updates – iterable of items to remove from property vector (starting at the front) or to add (at the end)
- updateType – indicates update type, applied individually to all items in ‘updates’, one of “add”, “addIfNotIn”, “removeOne”, “removeAll”
- timestamp – optional timestamp to assign to updated vector property, defaults to self.getActualTimestamp()
-
signalEndOfStream
(channelName)¶ Signal an end-of-stream event
The channel is identified by channnelName
Note: The methods ‘writeChannel(..)’ and ‘signalEndOfStream(..)’ must not be called concurrently.
-
signalSlotable
¶ Get SignalSlotable object embedded in PythonDevice instance.
-
slotClearLock
()¶ Clear the lock on this device
-
slotGetTime
(info)¶ Return the actual time information of this device
Parameters: info – An empty place holder hash This slot returns a Hash with:
- key
time
and the attributes provide an actual
timestamp with train Id information - key
timeServerId
to show the configured time server - keyreference
and the attributes provide the latest received timestamp information from the timeserver- key
-
slotLoggerContent
(info)¶ Slot call to receive logger content from the print logger
This slot is similar to slotLoggerContent for servers except that the serverId key is substituted with key deviceId.
look in the device_server module for detailed informations
-
updateSchema
(schema)¶ Updates the existing device schema It merges the schema in argument to the static schema defined in expectedParameters, removing any previous schema injections.
If a property is being reinjected, and of the same type, then it will keep its current value. If it does not fit within range, an error will be raised. Likewise, if the type changes, and the value cannot be cast, an error will be raised.
Input and output channels will be created if injected and removed again in case updateSchema is called again without them. An output channel is also recreated if its schema changes. Note that for newly created input channels there are no data, input and end-of-stream handlers registered. This has to be done via the corresponding self.KARABO_ON_[DATA|INPUT|EOS] methods. If an InputChannel is re-injected, its handlers are kept.
Parameters: schema – to be merged with the static schema
-
updateState
(newState, propertyUpdates=None, timestamp=None)¶ Update the state property of the device to a new state.
This should be used for NoFSM devices and should not be used if you have an underlying FSM. :param newState: the state to set the device to :propertyUpdates: a Hash with further properties to update (or None) :timestamp: timestamp to be assigned to the update,
if None, use self.getActualTimestamp()Returns:
-
writeChannel
(channelName, data, timestamp=None, safeNDArray=False)¶ Write data to an output channel.
Parameters: - channelName – name given to an OUTPUT_CHANNEL in expectedParameters
- data – a Hash with keys as described in the Schema of the channel
- timestamp – optional timestamp; if none is given, the current timestamp is used
- safeNDArray – Boolean that should be set to ‘True’ if ‘data’ contains any ‘NDArray’ and their data is not changed after this ‘writeChannel’. Otherwise, data will be copied if needed, i.e. when the output channel has to queue or serves inner-process receivers.
Example for an output channel sending an image (key: “image”) and a frame number (key: “frame”):
imgArray = numpy.array(…) self.writeChannel(“output”, Hash(“image”, ImageData(imgArray),
“frame”, frameNumber))Note: The methods ‘writeChannel(..)’ and ‘signalEndOfStream(..)’ must not be called concurrently.
-
-
class
karabo.bound.
DeviceServer
(config)¶ Device server serves as a launcher of python devices.
It scans ‘plugins’ directory for new plugins (python scripts) available and communicates its findings to master device server. It communicates XSD form of schema of user devices and starts such devices as separate process if user push “Initiate” button in GUI
-
classmethod
create
(*args)¶ The factory classmethod to create the instance of class with “classId” using input “configuration”. Example:
- instance = Shape.create(“EditableCircle”,
- Hash(“radius”, 12.345))
The factory classmethod to create instance according input “configuration”. The configuration should have “classId” of class to be created as a root element. Example:
configuration = Hash(“EditableCircle.radius”, 12.345) instance = Shape.create(configuration)
-
classmethod
createChoice
(choice, config)¶ The helper classmethod to create the instance using “choiceName” and input “configuration”.
-
classmethod
createList
(listname, configuration)¶ The helper method to create the list of instances using “listName” as a key to the list of configs in input “configuration”. The configurations will be validated.
-
classmethod
createNode
(nodename, classid, configuration)¶ The helper classmethod to create instance of class specified by “classId” using sub-configuration specified by “nodeName” which has to be a part of input “configuration”.
-
classmethod
getSchema
(classid, rules=None)¶ Use this classmethod to get schema for class with “classid” using assembly “rules” Example:
schema = Shape.getSchema(“Rectangle”)- or
- schema = Shape.getSchema(“Rectangle”, AssemblyRules())
-
onStateUpdate
(currentState)¶ This function is DEPRECATED and will be removed.
-
scanPlugins
(pluginNamespace)¶ Scan for available device classes
Returns Hash with keys “deviceClasses” and “visibilities” to be merged into instance info and a list of log messages to be send. Inside the list there are tuples of two string: log level (e.g. “INFO”) and message. Also fills self.availableDevices dictionary.
-
setupFsm
()¶ Description of DeviceServer state machine
-
slotDeviceUp
(instanceId, success, reason)¶ Slot for device to tell us whether it managed to get alive
-
slotLoggerContent
(info)¶ Slot call to receive logger content from the CacheLogger
replies with a Hash containing a key, serverId and a content containing a vector of hashes formatted in the same way the broker based logging uses. For details:
src/karabo/log/CacheLogger.cc
Parameters: info – input Hash containing an optional logs integer defining the maximum number of lines returned
-
classmethod
-
karabo.bound.
DeviceClient
¶
-
class
karabo.bound.worker.
QueueWorker
(callback)¶
-
class
karabo.bound.worker.
Worker
(callback=None, timeout=-1, repetition=-1, daemon=True)¶ -
run
()¶ Method representing the thread’s activity.
You may override this method in a subclass. The standard run() method invokes the callable object passed to the object’s constructor as the target argument, if any, with sequential and keyword arguments taken from the args and kwargs arguments, respectively.
-
start
()¶ Start the thread’s activity.
It must be called at most once per thread object. It arranges for the object’s run() method to be invoked in a separate thread of control.
This method will raise a RuntimeError if called more than once on the same thread object.
-
-
karabo.bound.decorators.
KARABO_CLASSINFO
(classid, version)¶ This decorator should be placed just before class definition. It adds some variables used in KARABO configuration infrastructure. It has two parameters: “classId” and “version” similar to corresponding C++ macro: Example:
@KARABO_CLASSINFO(“Shape”,”1.0”) class Shape(object):
…
-
karabo.bound.decorators.
KARABO_CONFIGURATION_BASE_CLASS
(theClass)¶ This decorator should be placed just before “KARABO_CLASSINFO” decorator. It registers the class as the base configurable class and adds the following classmethods: “create”, “createNode”, “createChoice”, “createList”, “getSchema” and “getRegisteredClasses”. It has no parameters. Example:
@KARABO_CONFIGURATION_BASE_CLASS @KARABO_CLASSINFO(“Shape”,”1.0”) class Shape(object):
…
-
class
karabo.bound.
Configurator
(classid)¶ Provides factorized configuration
Configurator is the singleton class that keeps methods for registration and creation other classes that are configurable classes
-
create
(*args)¶ The factory method to create the instance of class with “classId” that inherits from base class given to constructor using “input” configuration. The last argument is a flag to determine if the input configuration should be validated.
Example:
- instance = Configurator(Shape).create(“EditableCircle”,
- Hash(“radius”, 12.345))
The factory method to create instance of class that inherits from base class given to constructor using input “configuration”. The configuration should have “classId” of class to be created as a root element. The last argument is a flag to determine if the input “configuration” should be validated.
Example:
configuration = Hash(“EditableCircle.radius”, 12.345) instance = Configurator(Shape).create(configuration)Parameters: args – thus can have an arity of one to three: - class id string - config with classId as root key - class id string, config - config with classId as root key, validation flag - class id string, config, validation flag
-
createChoice
(choicename, configuration, validation=True)¶ The helper method to create the instance of class derived from base class given to constructor using “choiceName” and input “configuration”. The last argument is a flag to determine if the input configuration should be validated.
-
createList
(listname, input, validation=True)¶ The helper method to create the list of instances of classes derived from base class given to constructor using “listName” used as a key to the list and “input” configuration. The last argument is a flag to determine if the input configuration should be validated.
-
createNode
(nodename, classid, configuration, validation=True)¶ The helper method to create instance of class specified by “classId” and derived from class given to constructor using sub-configuration specified by “nodeName” which has to be a part of input “configuration”.
The last argument is a flag to determine if the input “configuration” should be validated.
-
static
getRegisteredBaseClasses
()¶ Returns all classid’s of base classes registered in Configurator.
-
getRegisteredClasses
()¶ Returns list of “classid“‘s for all registered classes derived from base class given to constructor.
-
getSchema
(classid, rules=<MagicMock name='mock.AssemblyRules()' id='140105518627616'>)¶ Get schema for class with “classid” derived from base class given to constructor using assembly “rules”. Example:
schema = Configurator(Shape).getSchema(“Rectangle”)
-
static
registerAsBaseClass
(theClass)¶ Register a class as a base class in the configurator
Parameters: theClass – to be registered
-
registerClass
(derived)¶ Register a derived class, i.e. a class deriving from a registered base class in the configuration system. :param derived: :return:
-