Mercurial > libervia-pubsub
view idavoll/test/test_storage.py @ 162:84cfe9fe38c5
Comply with the access model 'open'.
Currently, the only implemented access model is 'open', so we should not check
for the subscription of the requestor for item retrieval. We do reject
outcasts.
author | Ralph Meijer <ralphm@ik.nu> |
---|---|
date | Wed, 06 Sep 2006 12:57:53 +0000 |
parents | 21fcfb86433f |
children | ef22e4150caa |
line wrap: on
line source
# Copyright (c) 2003-2006 Ralph Meijer # See LICENSE for details. from twisted.trial import unittest from twisted.words.protocols.jabber import jid from twisted.internet import defer from twisted.words.xish import domish from idavoll import storage, pubsub OWNER = jid.JID('owner@example.com') SUBSCRIBER = jid.JID('subscriber@example.com/Home') SUBSCRIBER_NEW = jid.JID('new@example.com/Home') SUBSCRIBER_TO_BE_DELETED = jid.JID('to_be_deleted@example.com/Home') SUBSCRIBER_PENDING = jid.JID('pending@example.com/Home') PUBLISHER = jid.JID('publisher@example.com') ITEM = domish.Element((pubsub.NS_PUBSUB, 'item'), pubsub.NS_PUBSUB) ITEM['id'] = 'current' ITEM.addElement(('testns', 'test'), content=u'Test \u2083 item') ITEM_NEW = domish.Element((pubsub.NS_PUBSUB, 'item'), pubsub.NS_PUBSUB) ITEM_NEW['id'] = 'new' ITEM_NEW.addElement(('testns', 'test'), content=u'Test \u2083 item') ITEM_UPDATED = domish.Element((pubsub.NS_PUBSUB, 'item'), pubsub.NS_PUBSUB) ITEM_UPDATED['id'] = 'current' ITEM_UPDATED.addElement(('testns', 'test'), content=u'Test \u2084 item') ITEM_TO_BE_DELETED = domish.Element((pubsub.NS_PUBSUB, 'item'), pubsub.NS_PUBSUB) ITEM_TO_BE_DELETED['id'] = 'to-be-deleted' ITEM_TO_BE_DELETED.addElement(('testns', 'test'), content=u'Test \u2083 item') def decode(object): if isinstance(object, str): object = object.decode('utf-8') return object class StorageTests: def _assignTestNode(self, node): self.node = node def setUpClass(self): d = self.s.get_node('pre-existing') d.addCallback(self._assignTestNode) return d def testGetNode(self): return self.s.get_node('pre-existing') def testGetNonExistingNode(self): d = self.s.get_node('non-existing') self.assertFailure(d, storage.NodeNotFound) return d def testGetNodeIDs(self): def cb(node_ids): self.assertIn('pre-existing', node_ids) self.assertNotIn('non-existing', node_ids) return self.s.get_node_ids().addCallback(cb) def testCreateExistingNode(self): d = self.s.create_node('pre-existing', OWNER) self.assertFailure(d, storage.NodeExists) return d def testCreateNode(self): def cb(void): d = self.s.get_node('new 1') return d d = self.s.create_node('new 1', OWNER) d.addCallback(cb) return d def testDeleteNonExistingNode(self): d = self.s.delete_node('non-existing') self.assertFailure(d, storage.NodeNotFound) return d def testDeleteNode(self): def cb(void): d = self.s.get_node('to-be-deleted') self.assertFailure(d, storage.NodeNotFound) return d d = self.s.delete_node('to-be-deleted') d.addCallback(cb) return d def testGetAffiliations(self): def cb(affiliations): self.assertIn(('pre-existing', 'owner'), affiliations) d = self.s.get_affiliations(OWNER) d.addCallback(cb) return d def testGetSubscriptions(self): def cb(subscriptions): self.assertIn(('pre-existing', SUBSCRIBER, 'subscribed'), subscriptions) d = self.s.get_subscriptions(SUBSCRIBER) d.addCallback(cb) return d # Node tests def testGetType(self): self.assertEqual(self.node.get_type(), 'leaf') def testGetConfiguration(self): config = self.node.get_configuration() self.assertIn('pubsub#persist_items', config.iterkeys()) self.assertIn('pubsub#deliver_payloads', config.iterkeys()) self.assertEqual(config['pubsub#persist_items'], True) self.assertEqual(config['pubsub#deliver_payloads'], True) def testSetConfiguration(self): def get_config(node): d = node.set_configuration({'pubsub#persist_items': False}) d.addCallback(lambda _: node) return d def check_object_config(node): config = node.get_configuration() self.assertEqual(config['pubsub#persist_items'], False) def get_node(void): return self.s.get_node('to-be-reconfigured') def check_storage_config(node): config = node.get_configuration() self.assertEqual(config['pubsub#persist_items'], False) d = self.s.get_node('to-be-reconfigured') d.addCallback(get_config) d.addCallback(check_object_config) d.addCallback(get_node) d.addCallback(check_storage_config) return d def testGetMetaData(self): meta_data = self.node.get_meta_data() for key, value in self.node.get_configuration().iteritems(): self.assertIn(key, meta_data.iterkeys()) self.assertEqual(value, meta_data[key]) self.assertIn('pubsub#node_type', meta_data.iterkeys()) self.assertEqual(meta_data['pubsub#node_type'], 'leaf') def testGetAffiliation(self): def cb(affiliation): self.assertEqual(affiliation, 'owner') d = self.node.get_affiliation(OWNER) d.addCallback(cb) return d def testGetNonExistingAffiliation(self): def cb(affiliation): self.assertEqual(affiliation, None) d = self.node.get_affiliation(SUBSCRIBER) d.addCallback(cb) return d def testAddSubscription(self): def cb1(void): return self.node.get_subscription(SUBSCRIBER_NEW) def cb2(state): self.assertEqual(state, 'pending') d = self.node.add_subscription(SUBSCRIBER_NEW, 'pending') d.addCallback(cb1) d.addCallback(cb2) return d def testAddExistingSubscription(self): d = self.node.add_subscription(SUBSCRIBER, 'pending') self.assertFailure(d, storage.SubscriptionExists) return d def testGetSubscription(self): def cb(subscriptions): self.assertEquals(subscriptions[0][1], 'subscribed') self.assertEquals(subscriptions[1][1], 'pending') self.assertEquals(subscriptions[2][1], None) d = defer.DeferredList([self.node.get_subscription(SUBSCRIBER), self.node.get_subscription(SUBSCRIBER_PENDING), self.node.get_subscription(OWNER)]) d.addCallback(cb) return d def testRemoveSubscription(self): return self.node.remove_subscription(SUBSCRIBER_TO_BE_DELETED) def testRemoveNonExistingSubscription(self): d = self.node.remove_subscription(OWNER) self.assertFailure(d, storage.SubscriptionNotFound) return d def testGetSubscribers(self): def cb(subscribers): self.assertIn(SUBSCRIBER, subscribers) self.assertNotIn(SUBSCRIBER_PENDING, subscribers) self.assertNotIn(OWNER, subscribers) d = self.node.get_subscribers() d.addCallback(cb) return d def testIsSubscriber(self): def cb(subscribed): self.assertEquals(subscribed[0][1], True) self.assertEquals(subscribed[1][1], True) self.assertEquals(subscribed[2][1], False) self.assertEquals(subscribed[3][1], False) d = defer.DeferredList([self.node.is_subscribed(SUBSCRIBER), self.node.is_subscribed(SUBSCRIBER.userhostJID()), self.node.is_subscribed(SUBSCRIBER_PENDING), self.node.is_subscribed(OWNER)]) d.addCallback(cb) return d def testStoreItems(self): def cb1(void): return self.node.get_items_by_id(['new']) def cb2(result): self.assertEqual(result[0], decode(ITEM_NEW.toXml())) d = self.node.store_items([ITEM_NEW], PUBLISHER) d.addCallback(cb1) d.addCallback(cb2) return d def testStoreUpdatedItems(self): def cb1(void): return self.node.get_items_by_id(['current']) def cb2(result): self.assertEqual(result[0], decode(ITEM_UPDATED.toXml())) d = self.node.store_items([ITEM_UPDATED], PUBLISHER) d.addCallback(cb1) d.addCallback(cb2) return d def testRemoveItems(self): def cb1(result): self.assertEqual(result, ['to-be-deleted']) return self.node.get_items_by_id(['to-be-deleted']) def cb2(result): self.assertEqual(len(result), 0) d = self.node.remove_items(['to-be-deleted']) d.addCallback(cb1) d.addCallback(cb2) return d def testRemoveNonExistingItems(self): def cb(result): self.assertEqual(result, []) d = self.node.remove_items(['non-existing']) d.addCallback(cb) return d def testGetItems(self): def cb(result): self.assertIn(decode(ITEM.toXml()), result) d = self.node.get_items() d.addCallback(cb) return d def testLastItem(self): def cb(result): self.assertEqual([decode(ITEM.toXml())], result) d = self.node.get_items(1) d.addCallback(cb) return d def testGetItemsById(self): def cb(result): self.assertEqual(len(result), 1) d = self.node.get_items_by_id(['current']) d.addCallback(cb) return d def testGetNonExistingItemsById(self): def cb(result): self.assertEqual(len(result), 0) d = self.node.get_items_by_id(['non-existing']) d.addCallback(cb) return d def testPurge(self): def cb1(node): d = node.purge() d.addCallback(lambda _: node) return d def cb2(node): return node.get_items() def cb3(result): self.assertEqual([], result) d = self.s.get_node('to-be-purged') d.addCallback(cb1) d.addCallback(cb2) d.addCallback(cb3) return d def testGetNodeAffilatiations(self): def cb1(node): return node.get_affiliations() def cb2(affiliations): affiliations = dict(((a[0].full(), a[1]) for a in affiliations)) self.assertEquals(affiliations[OWNER.full()], 'owner') d = self.s.get_node('pre-existing') d.addCallback(cb1) d.addCallback(cb2) return d class MemoryStorageStorageTestCase(unittest.TestCase, StorageTests): def setUpClass(self): from idavoll.memory_storage import Storage, LeafNode, Subscription, \ default_config self.s = Storage() self.s._nodes['pre-existing'] = \ LeafNode('pre-existing', OWNER, default_config) self.s._nodes['to-be-deleted'] = \ LeafNode('to-be-deleted', OWNER, None) self.s._nodes['to-be-reconfigured'] = \ LeafNode('to-be-reconfigured', OWNER, default_config) self.s._nodes['to-be-purged'] = \ LeafNode('to-be-purged', OWNER, None) subscriptions = self.s._nodes['pre-existing']._subscriptions subscriptions[SUBSCRIBER.full()] = Subscription('subscribed') subscriptions[SUBSCRIBER_TO_BE_DELETED.full()] = \ Subscription('subscribed') subscriptions[SUBSCRIBER_PENDING.full()] = \ Subscription('pending') item = (decode(ITEM_TO_BE_DELETED.toXml()), PUBLISHER) self.s._nodes['pre-existing']._items['to-be-deleted'] = item self.s._nodes['pre-existing']._itemlist.append(item) self.s._nodes['to-be-purged']._items['to-be-deleted'] = item self.s._nodes['to-be-purged']._itemlist.append(item) item = (decode(ITEM.toXml()), PUBLISHER) self.s._nodes['pre-existing']._items['current'] = item self.s._nodes['pre-existing']._itemlist.append(item) return StorageTests.setUpClass(self) class PgsqlStorageStorageTestCase(unittest.TestCase, StorageTests): def _callSuperSetUpClass(self, void): return StorageTests.setUpClass(self) def setUpClass(self): from idavoll.pgsql_storage import Storage self.s = Storage('ralphm', 'pubsub_test') self.s._dbpool.start() d = self.s._dbpool.runInteraction(self.init) d.addCallback(self._callSuperSetUpClass) return d def tearDownClass(self): #return self.s._dbpool.runInteraction(self.cleandb) pass def init(self, cursor): self.cleandb(cursor) cursor.execute("""INSERT INTO nodes (node) VALUES ('pre-existing')""") cursor.execute("""INSERT INTO nodes (node) VALUES ('to-be-deleted')""") cursor.execute("""INSERT INTO nodes (node) VALUES ('to-be-reconfigured')""") cursor.execute("""INSERT INTO nodes (node) VALUES ('to-be-purged')""") cursor.execute("""INSERT INTO entities (jid) VALUES (%s)""", OWNER.userhost()) cursor.execute("""INSERT INTO affiliations (node_id, entity_id, affiliation) SELECT nodes.id, entities.id, 'owner' FROM nodes, entities WHERE node='pre-existing' AND jid=%s""", OWNER.userhost()) cursor.execute("""INSERT INTO entities (jid) VALUES (%s)""", SUBSCRIBER.userhost()) cursor.execute("""INSERT INTO subscriptions (node_id, entity_id, resource, subscription) SELECT nodes.id, entities.id, %s, 'subscribed' FROM nodes, entities WHERE node='pre-existing' AND jid=%s""", (SUBSCRIBER.resource, SUBSCRIBER.userhost())) cursor.execute("""INSERT INTO entities (jid) VALUES (%s)""", SUBSCRIBER_TO_BE_DELETED.userhost()) cursor.execute("""INSERT INTO subscriptions (node_id, entity_id, resource, subscription) SELECT nodes.id, entities.id, %s, 'subscribed' FROM nodes, entities WHERE node='pre-existing' AND jid=%s""", (SUBSCRIBER_TO_BE_DELETED.resource, SUBSCRIBER_TO_BE_DELETED.userhost())) cursor.execute("""INSERT INTO entities (jid) VALUES (%s)""", SUBSCRIBER_PENDING.userhost()) cursor.execute("""INSERT INTO subscriptions (node_id, entity_id, resource, subscription) SELECT nodes.id, entities.id, %s, 'pending' FROM nodes, entities WHERE node='pre-existing' AND jid=%s""", (SUBSCRIBER_PENDING.resource, SUBSCRIBER_PENDING.userhost())) cursor.execute("""INSERT INTO entities (jid) VALUES (%s)""", PUBLISHER.userhost()) cursor.execute("""INSERT INTO items (node_id, publisher, item, data, date) SELECT nodes.id, %s, 'to-be-deleted', %s, now() - interval '1 day' FROM nodes WHERE node='pre-existing'""", (PUBLISHER.userhost(), ITEM_TO_BE_DELETED.toXml())) cursor.execute("""INSERT INTO items (node_id, publisher, item, data) SELECT nodes.id, %s, 'to-be-deleted', %s FROM nodes WHERE node='to-be-purged'""", (PUBLISHER.userhost(), ITEM_TO_BE_DELETED.toXml())) cursor.execute("""INSERT INTO items (node_id, publisher, item, data) SELECT nodes.id, %s, 'current', %s FROM nodes WHERE node='pre-existing'""", (PUBLISHER.userhost(), ITEM.toXml())) def cleandb(self, cursor): cursor.execute("""DELETE FROM nodes WHERE node in ('non-existing', 'pre-existing', 'to-be-deleted', 'new 1', 'new 2', 'new 3', 'to-be-reconfigured', 'to-be-purged')""") cursor.execute("""DELETE FROM entities WHERE jid=%s""", OWNER.userhost()) cursor.execute("""DELETE FROM entities WHERE jid=%s""", SUBSCRIBER.userhost()) cursor.execute("""DELETE FROM entities WHERE jid=%s""", SUBSCRIBER_TO_BE_DELETED.userhost()) cursor.execute("""DELETE FROM entities WHERE jid=%s""", SUBSCRIBER_PENDING.userhost()) cursor.execute("""DELETE FROM entities WHERE jid=%s""", PUBLISHER.userhost())