Skip to content

Commit

Permalink
doc: fixes and add sync_struct docstrings
Browse files Browse the repository at this point in the history
sbourdeauducq committed Jan 19, 2015
1 parent 0c2e960 commit 56ea62b
Showing 3 changed files with 78 additions and 9 deletions.
68 changes: 68 additions & 0 deletions artiq/protocols/sync_struct.py
Original file line number Diff line number Diff line change
@@ -1,3 +1,16 @@
"""This module helps synchronizing a mutable Python structure owned and
modified by one process (the *publisher*) with copies of it (the
*subscribers*) in different processes and possibly different machines.
Synchronization is achieved by sending a full copy of the structure to each
subscriber upon connection (*initialization*), followed by dictionaries
describing each modification made to the structure (*mods*).
Structures must be PYON serializable and contain only lists, dicts, and
immutable types. Lists and dicts can be nested arbitrarily.
"""

import asyncio
from operator import getitem

@@ -9,6 +22,9 @@


def process_mod(target, mod):
"""Apply a *mod* to the target, mutating it.
"""
for key in mod["path"]:
target = getitem(target, key)
action = mod["action"]
@@ -27,6 +43,16 @@ def process_mod(target, mod):


class Subscriber:
"""An asyncio-based client to connect to a ``Publisher``.
:param notifier_name: Name of the notifier to subscribe to.
:param target_builder: A function called during initialization that takes
the object received from the publisher and returns the corresponding
local structure to use. Can be identity.
:param notify_cb: An optional function called every time a mod is received
from the publisher. The mod is passed as parameter.
"""
def __init__(self, notifier_name, target_builder, notify_cb=None):
self.notifier_name = notifier_name
self.target_builder = target_builder
@@ -78,6 +104,29 @@ def _receive_cr(self):


class Notifier:
"""Encapsulates a structure whose changes need to be published.
All mutations to the structure must be made through the ``Notifier``. The
original structure must only be accessed for reads.
In addition to the list methods below, the ``Notifier`` supports the index
syntax for modification and deletion of elements. Modification of nested
structures can be also done using the index syntax, for example:
>>> n = Notifier([])
>>> n.append([])
>>> n[0].append(42)
>>> n.read
[[42]]
This class does not perform any network I/O and is meant to be used with
e.g. the ``Publisher`` for this purpose. Only one publisher at most can be
associated with a ``Notifier``.
:param backing_struct: Structure to encapsulate. For convenience, it
also becomes available as the ``read`` property of the ``Notifier``.
"""
def __init__(self, backing_struct, root=None, path=[]):
self.read = backing_struct
if root is None:
@@ -92,20 +141,31 @@ def __init__(self, backing_struct, root=None, path=[]):
# All modifications must go through them!

def append(self, x):
"""Append to a list.
"""
self._backing_struct.append(x)
if self.root.publish is not None:
self.root.publish(self.root, {"action": "append",
"path": self._path,
"x": x})

def insert(self, i, x):
"""Insert an element into a list.
"""
self._backing_struct.insert(i, x)
if self.root.publish is not None:
self.root.publish(self.root, {"action": "insert",
"path": self._path,
"i": i, "x": x})

def pop(self, i=-1):
"""Pop an element from a list. The returned element is not
encapsulated in a ``Notifier`` and its mutations are no longer
tracked.
"""
r = self._backing_struct.pop(i)
if self.root.publish is not None:
self.root.publish(self.root, {"action": "pop",
@@ -134,6 +194,14 @@ def __getitem__(self, key):


class Publisher(AsyncioServer):
"""A network server that publish changes to structures encapsulated in
``Notifiers``.
:param notifiers: A dictionary containing the notifiers to associate with
the ``Publisher``. The keys of the dictionary are the names of the
notifiers to be used with ``Subscriber``.
"""
def __init__(self, notifiers):
AsyncioServer.__init__(self)
self.notifiers = notifiers
6 changes: 3 additions & 3 deletions doc/manual/core_language_reference.rst
Original file line number Diff line number Diff line change
@@ -9,10 +9,10 @@ The most commonly used features from those modules can be imported with ``from a
.. automodule:: artiq.language.core
:members:

:mod:`artiq.language.context` module
------------------------------------
:mod:`artiq.language.db` module
-------------------------------

.. automodule:: artiq.language.context
.. automodule:: artiq.language.db
:members:

:mod:`artiq.language.units` module
13 changes: 7 additions & 6 deletions doc/manual/protocols_reference.rst
Original file line number Diff line number Diff line change
@@ -1,16 +1,17 @@
Management reference
====================

:mod:`artiq.protocols.pyon` module
----------------------------------
:mod:`artiq.protocols.asyncio_server` module
--------------------------------------------

.. automodule:: artiq.protocols.pyon
.. automodule:: artiq.protocols.asyncio_server
:members:

:mod:`artiq.protocols.tools` module
-----------------------------------

.. automodule:: artiq.protocols.tools
:mod:`artiq.protocols.pyon` module
----------------------------------

.. automodule:: artiq.protocols.pyon
:members:


0 comments on commit 56ea62b

Please sign in to comment.