Web   ·   Wiki   ·   Activities   ·   Blog   ·   Lists   ·   Chat   ·   Meeting   ·   Bugs   ·   Git   ·   Translate   ·   Archive   ·   People   ·   Donate
summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorSascha Silbe <sascha-pgp@silbe.org>2011-05-15 20:07:23 (GMT)
committer Sascha Silbe <sascha-pgp@silbe.org>2011-05-15 20:17:16 (GMT)
commitba4764c458db4be9798cd21a273c5bfda47fb4d4 (patch)
tree78bc8882ddce3dc167cd0804dd359dba7fa51131
parentde83019b12aa3ec7e39f8dd69d9fb5b418db9dde (diff)
Add and use signal distribution infrastructure
Once we have multiple D-Bus interfaces, we need to send signals on all of them. Signed-off-by: Sascha Silbe <sascha-pgp@silbe.org>
-rw-r--r--gdatastore/datastore.py39
1 files changed, 36 insertions, 3 deletions
diff --git a/gdatastore/datastore.py b/gdatastore/datastore.py
index b8cf032..9db437e 100644
--- a/gdatastore/datastore.py
+++ b/gdatastore/datastore.py
@@ -75,6 +75,10 @@ class DBusApiSugarV2(dbus.service.Object):
allow_replacement=False,
do_not_queue=True)
dbus.service.Object.__init__(self, bus_name, DBUS_PATH_SUGAR_V2)
+ self._internal_api.add_callback('change_metadata',
+ self.__change_metadata_cb)
+ self._internal_api.add_callback('delete', self.__delete_cb)
+ self._internal_api.add_callback('save', self.__save_cb)
@dbus.service.method(DBUS_INTERFACE_SUGAR_V2,
in_signature='a{sv}sb', out_signature='s',
@@ -83,7 +87,6 @@ class DBusApiSugarV2(dbus.service.Object):
def create(self, props, file_path, transfer_ownership,
async_cb, async_err_cb):
def success_cb(tree_id, child_id):
- self.Created(tree_id)
async_cb(tree_id)
self._internal_api.save(tree_id='', parent_id='', metadata=props,
@@ -104,7 +107,6 @@ class DBusApiSugarV2(dbus.service.Object):
def update(self, uid, props, file_path, transfer_ownership,
async_cb, async_err_cb):
def success_cb(tree_id, child_id):
- self.Updated(tree_id)
async_cb()
latest_versions = self._get_latest(uid)
@@ -187,7 +189,6 @@ class DBusApiSugarV2(dbus.service.Object):
raise ValueError('Entry %s does not exist' % (uid, ))
self._internal_api.delete((uid, latest_versions[0]['version_id']))
- self.Deleted(uid)
@dbus.service.signal(DBUS_INTERFACE_SUGAR_V2, signature='s')
def Deleted(self, uid):
@@ -227,10 +228,29 @@ class DBusApiSugarV2(dbus.service.Object):
child_checksum = calculate_checksum(child_data_path)
return parent_checksum == child_checksum
+ def __change_metadata_cb(self, (tree_id, version_id), metadata):
+ self.Updated(tree_id)
+
+ def __delete_cb(self, (tree_id, version_id)):
+ if self._get_latest(tree_id):
+ self.Updated(tree_id)
+ else:
+ self.Deleted(tree_id)
+
+ def __save_cb(self, tree_id, child_id, parent_id, metadata):
+ if parent_id:
+ self.Updated(tree_id)
+ else:
+ self.Created(tree_id)
+
class InternalApi(object):
+
+ SIGNALS = ['change_metadata', 'delete', 'save']
+
def __init__(self, base_dir):
self._base_dir = base_dir
+ self._callbacks = {}
self._checkouts_dir = os.path.join(base_dir, 'checkouts')
if not os.path.exists(self._checkouts_dir):
os.makedirs(self._checkouts_dir)
@@ -243,6 +263,12 @@ class InternalApi(object):
self._index = Index(os.path.join(self._base_dir, 'index'))
self._migrate()
+ def add_callback(self, signal, callback):
+ if signal not in InternalApi.SIGNALS:
+ raise ValueError('Invalid signal %r' % (signal, ))
+
+ self._callbacks.setdefault(signal, []).append(callback)
+
def change_metadata(self, object_id, metadata):
logging.debug('change_metadata(%r, %r)', object_id, metadata)
metadata['tree_id'], metadata['version_id'] = object_id
@@ -251,11 +277,13 @@ class InternalApi(object):
metadata['creation_time'] = old_metadata['creation_time']
self._index.store(object_id, metadata)
+ self._invoke_callbacks('change_metadata', object_id, metadata)
def delete(self, object_id):
logging.debug('delete(%r)', object_id)
self._index.delete(object_id)
self._git_call('update-ref', ['-d', _format_ref(*object_id)])
+ self._invoke_callbacks('delete', object_id)
def get_data_path(self, (tree_id, version_id), sender=None):
logging.debug('get_data_path((%r, %r), %r)', tree_id, version_id,
@@ -348,6 +376,7 @@ class InternalApi(object):
# TODO: check metadata for validity first (index?)
self._store_entry(tree_id, child_id, parent_id, path, metadata)
self._index.store((tree_id, child_id), metadata)
+ self._invoke_callbacks('save', tree_id, child_id, parent_id, metadata)
async_cb(tree_id, child_id)
def stop(self):
@@ -424,6 +453,10 @@ class InternalApi(object):
raise GitError(pipe.returncode, stderr)
return stdout
+ def _invoke_callbacks(self, signal, *args):
+ for callback in self._callbacks.get(signal, []):
+ callback(*args)
+
def _migrate(self):
if not os.path.exists(self._git_dir):
return self._create_repo()