| 1 | import unittest |
|---|
| 2 | |
|---|
| 3 | from trac.test import EnvironmentStub, Mock |
|---|
| 4 | from tractags.api import TagEngine |
|---|
| 5 | import time |
|---|
| 6 | |
|---|
| 7 | # We need to fake time (heh), otherwise the ticket saves violate column |
|---|
| 8 | # constraints because the time for two discrete changes is the same. |
|---|
| 9 | class fake_time(object): |
|---|
| 10 | _the_time = 0 |
|---|
| 11 | |
|---|
| 12 | def __call__(self): |
|---|
| 13 | self._the_time += 1 |
|---|
| 14 | return self._the_time |
|---|
| 15 | time.time = fake_time() |
|---|
| 16 | |
|---|
| 17 | try: |
|---|
| 18 | set = set |
|---|
| 19 | except: |
|---|
| 20 | from sets import Set as set |
|---|
| 21 | |
|---|
| 22 | class TagApiTestCase(unittest.TestCase): |
|---|
| 23 | test_data = (('wiki', 'WikiStart', ('foo', 'bar')), |
|---|
| 24 | ('wiki', 'SandBox', ('bar', 'war')), |
|---|
| 25 | ('ticket', 1, ('war', 'death')), |
|---|
| 26 | ('ticket', 2, ('death', 'destruction')), |
|---|
| 27 | ('ticket', 3, ('foo', 'bar', 'destruction')) |
|---|
| 28 | ) |
|---|
| 29 | |
|---|
| 30 | req = Mock(perm=Mock(assert_permission=lambda x: True), |
|---|
| 31 | authname='anonymous') |
|---|
| 32 | |
|---|
| 33 | def _populate_tags(self, ts): |
|---|
| 34 | for tagspace, target, tags in self.test_data: |
|---|
| 35 | tagspace = ts.tagspace(tagspace) |
|---|
| 36 | tagspace.add_tags(self.req, target, tags) |
|---|
| 37 | yield tagspace, target, tags |
|---|
| 38 | |
|---|
| 39 | def setUp(self): |
|---|
| 40 | self.env = EnvironmentStub(default_data=True) |
|---|
| 41 | self.env.path = '/' |
|---|
| 42 | self.tag_engine = TagEngine(self.env) |
|---|
| 43 | self.tag_engine.upgrade_environment(self.env.get_db_cnx()) |
|---|
| 44 | # Insert some test tickets |
|---|
| 45 | from trac.ticket.model import Ticket |
|---|
| 46 | for id in (1, 2, 3): |
|---|
| 47 | ticket = Ticket(self.env) |
|---|
| 48 | ticket['summary'] = 'Test ticket %i' % id |
|---|
| 49 | ticket['description'] = 'Test ticket %i description' % id |
|---|
| 50 | ticket.insert() |
|---|
| 51 | |
|---|
| 52 | def test_tagspaces(self): |
|---|
| 53 | tagspaces = set(self.tag_engine.tagspaces) |
|---|
| 54 | self.assertEqual(tagspaces, set(('ticket', 'wiki'))) |
|---|
| 55 | |
|---|
| 56 | def test_insert(self): |
|---|
| 57 | ts = self.tag_engine.tagspace |
|---|
| 58 | for tagspace, target, tags in self._populate_tags(ts): |
|---|
| 59 | found_tags = tagspace.get_tags([target]) |
|---|
| 60 | self.assertEqual(found_tags, set(tags)) |
|---|
| 61 | |
|---|
| 62 | def test_remove(self): |
|---|
| 63 | ts = self.tag_engine.tagspace |
|---|
| 64 | for tagspace, target, tags in self._populate_tags(ts): |
|---|
| 65 | target_tags = tagspace.get_name_tags(target) |
|---|
| 66 | tag = iter(target_tags).next() |
|---|
| 67 | tagspace.remove_tags(self.req, target, (tag,)) |
|---|
| 68 | target_tags.discard(tag) |
|---|
| 69 | self.assertEqual(tagspace.get_name_tags(target), target_tags) |
|---|
| 70 | |
|---|
| 71 | def test_remove_all(self): |
|---|
| 72 | ts = self.tag_engine.tagspace |
|---|
| 73 | for tagspace, target, tags in self._populate_tags(ts): |
|---|
| 74 | tagspace.remove_all_tags(self.req, target) |
|---|
| 75 | |
|---|
| 76 | def test_replace(self): |
|---|
| 77 | ts = self.tag_engine.tagspace |
|---|
| 78 | test_set = set(('foozle', 'stick')) |
|---|
| 79 | for tagspace, target, tags in self._populate_tags(ts): |
|---|
| 80 | found_tags = tagspace.get_tags([target]) |
|---|
| 81 | tagspace.replace_tags(self.req, target, test_set) |
|---|
| 82 | self.assertEqual(test_set, tagspace.get_name_tags(target)) |
|---|
| 83 | |
|---|
| 84 | def test_add(self): |
|---|
| 85 | ts = self.tag_engine.tagspace |
|---|
| 86 | test_set = set(('foozle', 'stick')) |
|---|
| 87 | for tagspace, target, tags in self._populate_tags(ts): |
|---|
| 88 | found_tags = tagspace.get_tags([target]) |
|---|
| 89 | tagspace.add_tags(self.req, target, test_set) |
|---|
| 90 | self.assertEqual(test_set.union(found_tags), tagspace.get_name_tags(target)) |
|---|
| 91 | |
|---|
| 92 | def test_walk(self): |
|---|
| 93 | engine = self.tag_engine |
|---|
| 94 | compare_data = {} |
|---|
| 95 | for tagspace, target, tags in self._populate_tags(engine.tagspace): |
|---|
| 96 | compare_data.setdefault(tagspace.tagspace, {})[target] = set(tags) |
|---|
| 97 | tag_data = {} |
|---|
| 98 | for tagspace, name, tags in engine.walk_tagged_names(): |
|---|
| 99 | tag_data.setdefault(tagspace, {})[name] = tags |
|---|
| 100 | self.assertEqual(compare_data, tag_data) |
|---|
| 101 | |
|---|
| 102 | def test_get_tagged_union(self): |
|---|
| 103 | ts = self.tag_engine.tagspace |
|---|
| 104 | for tagspace, target, tags in self._populate_tags(ts): pass |
|---|
| 105 | self.assertEqual(self.tag_engine.get_tagged_names(tags=('foo', 'bar'), operation='union'), |
|---|
| 106 | {'wiki': set([u'WikiStart', u'SandBox']), 'ticket': set([3])}) |
|---|
| 107 | |
|---|
| 108 | def test_get_tagged_intersection(self): |
|---|
| 109 | ts = self.tag_engine.tagspace |
|---|
| 110 | for tagspace, target, tags in self._populate_tags(ts): pass |
|---|
| 111 | self.assertEqual(self.tag_engine.get_tagged_names(tags=('foo', 'bar'), operation='intersection'), |
|---|
| 112 | {'wiki': set(['WikiStart']), 'ticket': set([3])}) |
|---|
| 113 | |
|---|
| 114 | def test_get_tags_union(self): |
|---|
| 115 | ts = self.tag_engine.tagspace |
|---|
| 116 | for tagspace, target, tags in self._populate_tags(ts): pass |
|---|
| 117 | self.assertEqual(self.tag_engine.get_tags(names=('WikiStart', 1), operation='union'), |
|---|
| 118 | set(['death', 'bar', 'war', 'foo'])) |
|---|
| 119 | |
|---|
| 120 | def test_get_tags_intersection(self): |
|---|
| 121 | ts = self.tag_engine.tagspace |
|---|
| 122 | for tagspace, target, tags in self._populate_tags(ts): pass |
|---|
| 123 | self.assertEqual(self.tag_engine.get_tags(names=('WikiStart', 3), operation='intersection'), |
|---|
| 124 | set(['bar', 'foo'])) |
|---|
| 125 | |
|---|
| 126 | def test_tagspace_get_tagged_union(self): |
|---|
| 127 | ts = self.tag_engine.tagspace |
|---|
| 128 | for tagspace, target, tags in self._populate_tags(ts): pass |
|---|
| 129 | self.assertEqual(self.tag_engine.tagspace.wiki.get_tagged_names(tags=('foo', 'bar'), operation='union'), |
|---|
| 130 | set([u'WikiStart', u'SandBox'])) |
|---|
| 131 | |
|---|
| 132 | def test_tagspace_get_tagged_intersection(self): |
|---|
| 133 | ts = self.tag_engine.tagspace |
|---|
| 134 | for tagspace, target, tags in self._populate_tags(ts): pass |
|---|
| 135 | self.assertEqual(self.tag_engine.tagspace.wiki.get_tagged_names(tags=('bar',), operation='intersection'), |
|---|
| 136 | set([u'WikiStart', u'SandBox'])) |
|---|
| 137 | |
|---|
| 138 | def test_tagspace_get_tags_union(self): |
|---|
| 139 | ts = self.tag_engine.tagspace |
|---|
| 140 | for tagspace, target, tags in self._populate_tags(ts): pass |
|---|
| 141 | self.assertEqual(self.tag_engine.tagspace.wiki.get_tags(names=('WikiStart', 'SandBox'), operation='union'), |
|---|
| 142 | set(['bar', 'war', 'foo'])) |
|---|
| 143 | |
|---|
| 144 | def test_tagspace_get_tags_intersection(self): |
|---|
| 145 | ts = self.tag_engine.tagspace |
|---|
| 146 | for tagspace, target, tags in self._populate_tags(ts): pass |
|---|
| 147 | self.assertEqual(self.tag_engine.tagspace.wiki.get_tags(names=('WikiStart', 'SandBox'), operation='intersection'), |
|---|
| 148 | set(['bar'])) |
|---|
| 149 | |
|---|
| 150 | # Detailed |
|---|
| 151 | def test_detailed_get_tagged_union(self): |
|---|
| 152 | ts = self.tag_engine.tagspace |
|---|
| 153 | for tagspace, target, tags in self._populate_tags(ts): pass |
|---|
| 154 | self.assertEqual(self.tag_engine.get_tagged_names(tags=('foo', 'bar'), operation='union', detailed=True), |
|---|
| 155 | {'wiki': {'WikiStart': set(('foo', 'bar')), |
|---|
| 156 | 'SandBox': set(('bar', 'war'))}, |
|---|
| 157 | 'ticket': {3: set(('foo', 'bar', 'destruction'))}}) |
|---|
| 158 | |
|---|
| 159 | def test_detailed_get_tagged_intersection(self): |
|---|
| 160 | ts = self.tag_engine.tagspace |
|---|
| 161 | for tagspace, target, tags in self._populate_tags(ts): pass |
|---|
| 162 | self.assertEqual(self.tag_engine.get_tagged_names(tags=('foo', 'bar'), operation='intersection', detailed=True), |
|---|
| 163 | {'wiki': {'WikiStart': set(('foo', 'bar'))}, |
|---|
| 164 | 'ticket': {3: set(('foo', 'bar', 'destruction'))}}) |
|---|
| 165 | |
|---|
| 166 | def test_detailed_get_tags_union(self): |
|---|
| 167 | ts = self.tag_engine.tagspace |
|---|
| 168 | for tagspace, target, tags in self._populate_tags(ts): pass |
|---|
| 169 | self.assertEqual(self.tag_engine.get_tags(names=('WikiStart', 1), operation='union', detailed=True), |
|---|
| 170 | {'death': set([('ticket', 1)]), |
|---|
| 171 | 'bar': set([('wiki', 'WikiStart')]), |
|---|
| 172 | 'war': set([('ticket', 1)]), |
|---|
| 173 | 'foo': set([('wiki', 'WikiStart')])}) |
|---|
| 174 | |
|---|
| 175 | def test_detailed_get_tags_intersection(self): |
|---|
| 176 | ts = self.tag_engine.tagspace |
|---|
| 177 | for tagspace, target, tags in self._populate_tags(ts): pass |
|---|
| 178 | self.assertEqual(self.tag_engine.get_tags(names=('WikiStart', 3, 'SandBox'), operation='intersection', detailed=True), |
|---|
| 179 | {'bar': set([('wiki', 'SandBox'), ('wiki', 'WikiStart'), ('ticket', 3)])}) |
|---|
| 180 | |
|---|
| 181 | def test_detailed_tagspace_get_tagged_union(self): |
|---|
| 182 | ts = self.tag_engine.tagspace |
|---|
| 183 | for tagspace, target, tags in self._populate_tags(ts): pass |
|---|
| 184 | self.assertEqual(self.tag_engine.tagspace.wiki.get_tagged_names(tags=('foo', 'bar'), operation='union', detailed=True), |
|---|
| 185 | {'WikiStart': set(['foo', 'bar']), |
|---|
| 186 | 'SandBox': set(['bar', 'war'])}) |
|---|
| 187 | |
|---|
| 188 | def test_detailed_tagspace_get_tagged_intersection(self): |
|---|
| 189 | ts = self.tag_engine.tagspace |
|---|
| 190 | for tagspace, target, tags in self._populate_tags(ts): pass |
|---|
| 191 | self.assertEqual(self.tag_engine.tagspace.wiki.get_tagged_names(tags=('bar',), operation='intersection', detailed=True), |
|---|
| 192 | {'WikiStart': set(['foo', 'bar']), 'SandBox': set(['bar', 'war'])}) |
|---|
| 193 | |
|---|
| 194 | def test_detailed_tagspace_get_tags_union(self): |
|---|
| 195 | ts = self.tag_engine.tagspace |
|---|
| 196 | for tagspace, target, tags in self._populate_tags(ts): pass |
|---|
| 197 | self.assertEqual(self.tag_engine.tagspace.wiki.get_tags(names=('WikiStart', 'SandBox'), operation='union', detailed=True), |
|---|
| 198 | {'foo': set(['WikiStart']), |
|---|
| 199 | 'bar': set(['WikiStart', 'SandBox']), |
|---|
| 200 | 'war': set(['SandBox'])}) |
|---|
| 201 | |
|---|
| 202 | def test_detailed_tagspace_get_tags_intersection(self): |
|---|
| 203 | ts = self.tag_engine.tagspace |
|---|
| 204 | for tagspace, target, tags in self._populate_tags(ts): pass |
|---|
| 205 | self.assertEqual(self.tag_engine.tagspace.wiki.get_tags(names=('WikiStart', 'SandBox'), operation='intersection', detailed=True), |
|---|
| 206 | {'bar': set(['WikiStart', 'SandBox'])}) |
|---|
| 207 | def suite(): |
|---|
| 208 | suite = unittest.TestSuite() |
|---|
| 209 | suite.addTest(unittest.makeSuite(TagApiTestCase, 'test')) |
|---|
| 210 | return suite |
|---|
| 211 | |
|---|
| 212 | if __name__ == '__main__': |
|---|
| 213 | unittest.main(defaultTest='suite') |
|---|