diff options
author | Simo Sorce <simo@redhat.com> | 2015-09-28 10:23:24 -0400 |
---|---|---|
committer | Simo Sorce <simo@redhat.com> | 2015-10-19 12:17:42 -0400 |
commit | 1d813cc53b9c03636967600f0e31e0cafb14813c (patch) | |
tree | 0f2ae59cdd510f17171e6fff568b4e01bcd2269b | |
parent | bd2e62767e6287dcaf5275362338682fc555d4ce (diff) | |
download | custodia-1d813cc53b9c03636967600f0e31e0cafb14813c.tar.gz custodia-1d813cc53b9c03636967600f0e31e0cafb14813c.tar.xz custodia-1d813cc53b9c03636967600f0e31e0cafb14813c.zip |
Extend store interface to create namespaces
Use a new verb, "span" to create namespaces/containers.
This will be needed for the Etcd plugin which need to distinguish between
a directory and a key.
The sqlite/enclite just pass the request to their set() method.
Signed-off-by: Simo Sorce <simo@redhat.com>
Reviewed-by: Christian Heimes <cheimes@redhat.com>
-rw-r--r-- | custodia/secrets.py | 6 | ||||
-rw-r--r-- | custodia/store/interface.py | 3 | ||||
-rw-r--r-- | custodia/store/sqlite.py | 37 |
3 files changed, 43 insertions, 3 deletions
diff --git a/custodia/secrets.py b/custodia/secrets.py index b2979d0..a009dcb 100644 --- a/custodia/secrets.py +++ b/custodia/secrets.py @@ -63,7 +63,7 @@ class Secrets(HTTPConsumer): # create default namespace if it is the only missing piece if len(trail) == 2 and default == trail[0]: container = self._db_container_key(default, '') - self.root.store.set(container, '') + self.root.store.span(container) return True return False @@ -117,7 +117,7 @@ class Secrets(HTTPConsumer): if not ok: raise HTTPError(404) - self.root.store.set(basename, '') + self.root.store.span(basename) except CSStoreExists: raise HTTPError(409) except CSStoreError: @@ -133,7 +133,7 @@ class Secrets(HTTPConsumer): raise HTTPError(404) if len(keylist) != 0: raise HTTPError(409) - ret = self.root.store.cut(basename) + ret = self.root.store.cut(basename.rstrip('/')) except CSStoreError: raise HTTPError(500) diff --git a/custodia/store/interface.py b/custodia/store/interface.py index 11c2e36..850fc91 100644 --- a/custodia/store/interface.py +++ b/custodia/store/interface.py @@ -23,6 +23,9 @@ class CSStore(object): def set(self, key, value, replace=False): raise NotImplementedError + def span(self, key): + raise NotImplementedError + def list(self, keyfilter=None): raise NotImplementedError diff --git a/custodia/store/sqlite.py b/custodia/store/sqlite.py index 482787a..0a50651 100644 --- a/custodia/store/sqlite.py +++ b/custodia/store/sqlite.py @@ -57,6 +57,8 @@ class SqliteStore(CSStore): cur.execute(create) def set(self, key, value, replace=False): + if key.endswith('/'): + raise ValueError('Invalid Key name, cannot end in "/"') if replace: query = "INSERT OR REPLACE into %s VALUES (?, ?)" else: @@ -74,6 +76,22 @@ class SqliteStore(CSStore): log_error("Error storing key %s: [%r]" % (key, repr(err))) raise CSStoreError('Error occurred while trying to store key') + def span(self, key): + name = key.rstrip('/') + query = "INSERT into %s VALUES (?, '')" + setdata = query % (self.table,) + try: + conn = sqlite3.connect(self.dburi) + with conn: + c = conn.cursor() + self._create(c) + c.execute(setdata, (name,)) + except sqlite3.IntegrityError as err: + raise CSStoreExists(str(err)) + except sqlite3.Error as err: + log_error("Error creating key %s: [%r]" % (name, repr(err))) + raise CSStoreError('Error occurred while trying to span container') + def list(self, keyfilter=''): path = keyfilter.rstrip('/') child_prefix = path if path == '' else path + '/' @@ -209,3 +227,22 @@ class SqliteStoreTests(unittest.TestCase): def test_6_cut_2_empty(self): ret = self.store.cut('keycut') self.assertEqual(ret, False) + + def test_7_span_1(self): + self.store.span('/span') + value = self.store.list('/span') + self.assertEqual(value, []) + + def test_7_span_2(self): + self.store.span('/span/2') + self.store.span('/span/2/span') + value = self.store.list('/span') + self.assertEqual(value, ['2', '2/span']) + value = self.store.list('/span/2') + self.assertEqual(value, ['span']) + value = self.store.list('/span/2/span') + self.assertEqual(value, []) + + def test_8_cut_span(self): + ret = self.store.cut('/span/2') + self.assertEqual(ret, True) |