17
17
"""Tests for indices."""
29
class ErrorTests(tests.TestCase):
31
def test_bad_index_format_signature(self):
32
error = _mod_index.BadIndexFormatSignature("foo", "bar")
33
self.assertEqual("foo is not an index of type bar.",
36
def test_bad_index_data(self):
37
error = _mod_index.BadIndexData("foo")
38
self.assertEqual("Error in data for index foo.",
41
def test_bad_index_duplicate_key(self):
42
error = _mod_index.BadIndexDuplicateKey("foo", "bar")
43
self.assertEqual("The key 'foo' is already in index 'bar'.",
46
def test_bad_index_key(self):
47
error = _mod_index.BadIndexKey("foo")
48
self.assertEqual("The key 'foo' is not a valid key.",
51
def test_bad_index_options(self):
52
error = _mod_index.BadIndexOptions("foo")
53
self.assertEqual("Could not parse options for index foo.",
56
def test_bad_index_value(self):
57
error = _mod_index.BadIndexValue("foo")
58
self.assertEqual("The value 'foo' is not a valid value.",
62
27
class TestGraphIndexBuilder(tests.TestCaseWithMemoryTransport):
64
29
def test_build_index_empty(self):
65
builder = _mod_index.GraphIndexBuilder()
30
builder = index.GraphIndexBuilder()
66
31
stream = builder.finish()
67
32
contents = stream.read()
69
b"Bazaar Graph Index 1\nnode_ref_lists=0\nkey_elements=1\nlen=0\n\n",
34
"Bazaar Graph Index 1\nnode_ref_lists=0\nkey_elements=1\nlen=0\n\n",
72
37
def test_build_index_empty_two_element_keys(self):
73
builder = _mod_index.GraphIndexBuilder(key_elements=2)
38
builder = index.GraphIndexBuilder(key_elements=2)
74
39
stream = builder.finish()
75
40
contents = stream.read()
77
b"Bazaar Graph Index 1\nnode_ref_lists=0\nkey_elements=2\nlen=0\n\n",
42
"Bazaar Graph Index 1\nnode_ref_lists=0\nkey_elements=2\nlen=0\n\n",
80
45
def test_build_index_one_reference_list_empty(self):
81
builder = _mod_index.GraphIndexBuilder(reference_lists=1)
46
builder = index.GraphIndexBuilder(reference_lists=1)
82
47
stream = builder.finish()
83
48
contents = stream.read()
85
b"Bazaar Graph Index 1\nnode_ref_lists=1\nkey_elements=1\nlen=0\n\n",
50
"Bazaar Graph Index 1\nnode_ref_lists=1\nkey_elements=1\nlen=0\n\n",
88
53
def test_build_index_two_reference_list_empty(self):
89
builder = _mod_index.GraphIndexBuilder(reference_lists=2)
54
builder = index.GraphIndexBuilder(reference_lists=2)
90
55
stream = builder.finish()
91
56
contents = stream.read()
93
b"Bazaar Graph Index 1\nnode_ref_lists=2\nkey_elements=1\nlen=0\n\n",
58
"Bazaar Graph Index 1\nnode_ref_lists=2\nkey_elements=1\nlen=0\n\n",
96
61
def test_build_index_one_node_no_refs(self):
97
builder = _mod_index.GraphIndexBuilder()
98
builder.add_node((b'akey', ), b'data')
62
builder = index.GraphIndexBuilder()
63
builder.add_node(('akey', ), 'data')
99
64
stream = builder.finish()
100
65
contents = stream.read()
102
b"Bazaar Graph Index 1\nnode_ref_lists=0\nkey_elements=1\nlen=1\n"
103
b"akey\x00\x00\x00data\n\n", contents)
67
"Bazaar Graph Index 1\nnode_ref_lists=0\nkey_elements=1\nlen=1\n"
68
"akey\x00\x00\x00data\n\n", contents)
105
70
def test_build_index_one_node_no_refs_accepts_empty_reflist(self):
106
builder = _mod_index.GraphIndexBuilder()
107
builder.add_node((b'akey', ), b'data', ())
71
builder = index.GraphIndexBuilder()
72
builder.add_node(('akey', ), 'data', ())
108
73
stream = builder.finish()
109
74
contents = stream.read()
111
b"Bazaar Graph Index 1\nnode_ref_lists=0\nkey_elements=1\nlen=1\n"
112
b"akey\x00\x00\x00data\n\n", contents)
76
"Bazaar Graph Index 1\nnode_ref_lists=0\nkey_elements=1\nlen=1\n"
77
"akey\x00\x00\x00data\n\n", contents)
114
79
def test_build_index_one_node_2_element_keys(self):
115
80
# multipart keys are separated by \x00 - because they are fixed length,
116
81
# not variable this does not cause any issues, and seems clearer to the
118
builder = _mod_index.GraphIndexBuilder(key_elements=2)
119
builder.add_node((b'akey', b'secondpart'), b'data')
83
builder = index.GraphIndexBuilder(key_elements=2)
84
builder.add_node(('akey', 'secondpart'), 'data')
120
85
stream = builder.finish()
121
86
contents = stream.read()
123
b"Bazaar Graph Index 1\nnode_ref_lists=0\nkey_elements=2\nlen=1\n"
124
b"akey\x00secondpart\x00\x00\x00data\n\n", contents)
88
"Bazaar Graph Index 1\nnode_ref_lists=0\nkey_elements=2\nlen=1\n"
89
"akey\x00secondpart\x00\x00\x00data\n\n", contents)
126
91
def test_add_node_empty_value(self):
127
builder = _mod_index.GraphIndexBuilder()
128
builder.add_node((b'akey', ), b'')
92
builder = index.GraphIndexBuilder()
93
builder.add_node(('akey', ), '')
129
94
stream = builder.finish()
130
95
contents = stream.read()
132
b"Bazaar Graph Index 1\nnode_ref_lists=0\nkey_elements=1\nlen=1\n"
133
b"akey\x00\x00\x00\n\n", contents)
97
"Bazaar Graph Index 1\nnode_ref_lists=0\nkey_elements=1\nlen=1\n"
98
"akey\x00\x00\x00\n\n", contents)
135
100
def test_build_index_nodes_sorted(self):
136
101
# the highest sorted node comes first.
137
builder = _mod_index.GraphIndexBuilder()
102
builder = index.GraphIndexBuilder()
138
103
# use three to have a good chance of glitching dictionary hash
139
104
# lookups etc. Insert in randomish order that is not correct
140
105
# and not the reverse of the correct order.
141
builder.add_node((b'2002', ), b'data')
142
builder.add_node((b'2000', ), b'data')
143
builder.add_node((b'2001', ), b'data')
106
builder.add_node(('2002', ), 'data')
107
builder.add_node(('2000', ), 'data')
108
builder.add_node(('2001', ), 'data')
144
109
stream = builder.finish()
145
110
contents = stream.read()
146
111
self.assertEqual(
147
b"Bazaar Graph Index 1\nnode_ref_lists=0\nkey_elements=1\nlen=3\n"
148
b"2000\x00\x00\x00data\n"
149
b"2001\x00\x00\x00data\n"
150
b"2002\x00\x00\x00data\n"
112
"Bazaar Graph Index 1\nnode_ref_lists=0\nkey_elements=1\nlen=3\n"
113
"2000\x00\x00\x00data\n"
114
"2001\x00\x00\x00data\n"
115
"2002\x00\x00\x00data\n"
153
118
def test_build_index_2_element_key_nodes_sorted(self):
154
119
# multiple element keys are sorted first-key, second-key.
155
builder = _mod_index.GraphIndexBuilder(key_elements=2)
120
builder = index.GraphIndexBuilder(key_elements=2)
156
121
# use three values of each key element, to have a good chance of
157
122
# glitching dictionary hash lookups etc. Insert in randomish order that
158
123
# is not correct and not the reverse of the correct order.
159
builder.add_node((b'2002', b'2002'), b'data')
160
builder.add_node((b'2002', b'2000'), b'data')
161
builder.add_node((b'2002', b'2001'), b'data')
162
builder.add_node((b'2000', b'2002'), b'data')
163
builder.add_node((b'2000', b'2000'), b'data')
164
builder.add_node((b'2000', b'2001'), b'data')
165
builder.add_node((b'2001', b'2002'), b'data')
166
builder.add_node((b'2001', b'2000'), b'data')
167
builder.add_node((b'2001', b'2001'), b'data')
124
builder.add_node(('2002', '2002'), 'data')
125
builder.add_node(('2002', '2000'), 'data')
126
builder.add_node(('2002', '2001'), 'data')
127
builder.add_node(('2000', '2002'), 'data')
128
builder.add_node(('2000', '2000'), 'data')
129
builder.add_node(('2000', '2001'), 'data')
130
builder.add_node(('2001', '2002'), 'data')
131
builder.add_node(('2001', '2000'), 'data')
132
builder.add_node(('2001', '2001'), 'data')
168
133
stream = builder.finish()
169
134
contents = stream.read()
170
135
self.assertEqual(
171
b"Bazaar Graph Index 1\nnode_ref_lists=0\nkey_elements=2\nlen=9\n"
172
b"2000\x002000\x00\x00\x00data\n"
173
b"2000\x002001\x00\x00\x00data\n"
174
b"2000\x002002\x00\x00\x00data\n"
175
b"2001\x002000\x00\x00\x00data\n"
176
b"2001\x002001\x00\x00\x00data\n"
177
b"2001\x002002\x00\x00\x00data\n"
178
b"2002\x002000\x00\x00\x00data\n"
179
b"2002\x002001\x00\x00\x00data\n"
180
b"2002\x002002\x00\x00\x00data\n"
136
"Bazaar Graph Index 1\nnode_ref_lists=0\nkey_elements=2\nlen=9\n"
137
"2000\x002000\x00\x00\x00data\n"
138
"2000\x002001\x00\x00\x00data\n"
139
"2000\x002002\x00\x00\x00data\n"
140
"2001\x002000\x00\x00\x00data\n"
141
"2001\x002001\x00\x00\x00data\n"
142
"2001\x002002\x00\x00\x00data\n"
143
"2002\x002000\x00\x00\x00data\n"
144
"2002\x002001\x00\x00\x00data\n"
145
"2002\x002002\x00\x00\x00data\n"
183
148
def test_build_index_reference_lists_are_included_one(self):
184
builder = _mod_index.GraphIndexBuilder(reference_lists=1)
185
builder.add_node((b'key', ), b'data', ([], ))
149
builder = index.GraphIndexBuilder(reference_lists=1)
150
builder.add_node(('key', ), 'data', ([], ))
186
151
stream = builder.finish()
187
152
contents = stream.read()
188
153
self.assertEqual(
189
b"Bazaar Graph Index 1\nnode_ref_lists=1\nkey_elements=1\nlen=1\n"
190
b"key\x00\x00\x00data\n"
154
"Bazaar Graph Index 1\nnode_ref_lists=1\nkey_elements=1\nlen=1\n"
155
"key\x00\x00\x00data\n"
193
158
def test_build_index_reference_lists_with_2_element_keys(self):
194
builder = _mod_index.GraphIndexBuilder(
195
reference_lists=1, key_elements=2)
196
builder.add_node((b'key', b'key2'), b'data', ([], ))
159
builder = index.GraphIndexBuilder(reference_lists=1, key_elements=2)
160
builder.add_node(('key', 'key2'), 'data', ([], ))
197
161
stream = builder.finish()
198
162
contents = stream.read()
199
163
self.assertEqual(
200
b"Bazaar Graph Index 1\nnode_ref_lists=1\nkey_elements=2\nlen=1\n"
201
b"key\x00key2\x00\x00\x00data\n"
164
"Bazaar Graph Index 1\nnode_ref_lists=1\nkey_elements=2\nlen=1\n"
165
"key\x00key2\x00\x00\x00data\n"
204
168
def test_build_index_reference_lists_are_included_two(self):
205
builder = _mod_index.GraphIndexBuilder(reference_lists=2)
206
builder.add_node((b'key', ), b'data', ([], []))
169
builder = index.GraphIndexBuilder(reference_lists=2)
170
builder.add_node(('key', ), 'data', ([], []))
207
171
stream = builder.finish()
208
172
contents = stream.read()
209
173
self.assertEqual(
210
b"Bazaar Graph Index 1\nnode_ref_lists=2\nkey_elements=1\nlen=1\n"
211
b"key\x00\x00\t\x00data\n"
174
"Bazaar Graph Index 1\nnode_ref_lists=2\nkey_elements=1\nlen=1\n"
175
"key\x00\x00\t\x00data\n"
214
178
def test_clear_cache(self):
215
builder = _mod_index.GraphIndexBuilder(reference_lists=2)
179
builder = index.GraphIndexBuilder(reference_lists=2)
216
180
# This is a no-op, but the api should exist
217
181
builder.clear_cache()
219
183
def test_node_references_are_byte_offsets(self):
220
builder = _mod_index.GraphIndexBuilder(reference_lists=1)
221
builder.add_node((b'reference', ), b'data', ([], ))
222
builder.add_node((b'key', ), b'data', ([(b'reference', )], ))
184
builder = index.GraphIndexBuilder(reference_lists=1)
185
builder.add_node(('reference', ), 'data', ([], ))
186
builder.add_node(('key', ), 'data', ([('reference', )], ))
223
187
stream = builder.finish()
224
188
contents = stream.read()
225
189
self.assertEqual(
226
b"Bazaar Graph Index 1\nnode_ref_lists=1\nkey_elements=1\nlen=2\n"
227
b"key\x00\x0072\x00data\n"
228
b"reference\x00\x00\x00data\n"
190
"Bazaar Graph Index 1\nnode_ref_lists=1\nkey_elements=1\nlen=2\n"
191
"key\x00\x0072\x00data\n"
192
"reference\x00\x00\x00data\n"
231
195
def test_node_references_are_cr_delimited(self):
232
builder = _mod_index.GraphIndexBuilder(reference_lists=1)
233
builder.add_node((b'reference', ), b'data', ([], ))
234
builder.add_node((b'reference2', ), b'data', ([], ))
235
builder.add_node((b'key', ), b'data',
236
([(b'reference', ), (b'reference2', )], ))
196
builder = index.GraphIndexBuilder(reference_lists=1)
197
builder.add_node(('reference', ), 'data', ([], ))
198
builder.add_node(('reference2', ), 'data', ([], ))
199
builder.add_node(('key', ), 'data',
200
([('reference', ), ('reference2', )], ))
237
201
stream = builder.finish()
238
202
contents = stream.read()
239
203
self.assertEqual(
240
b"Bazaar Graph Index 1\nnode_ref_lists=1\nkey_elements=1\nlen=3\n"
241
b"key\x00\x00077\r094\x00data\n"
242
b"reference\x00\x00\x00data\n"
243
b"reference2\x00\x00\x00data\n"
204
"Bazaar Graph Index 1\nnode_ref_lists=1\nkey_elements=1\nlen=3\n"
205
"key\x00\x00077\r094\x00data\n"
206
"reference\x00\x00\x00data\n"
207
"reference2\x00\x00\x00data\n"
246
210
def test_multiple_reference_lists_are_tab_delimited(self):
247
builder = _mod_index.GraphIndexBuilder(reference_lists=2)
248
builder.add_node((b'keference', ), b'data', ([], []))
249
builder.add_node((b'rey', ), b'data',
250
([(b'keference', )], [(b'keference', )]))
211
builder = index.GraphIndexBuilder(reference_lists=2)
212
builder.add_node(('keference', ), 'data', ([], []))
213
builder.add_node(('rey', ), 'data',
214
([('keference', )], [('keference', )]))
251
215
stream = builder.finish()
252
216
contents = stream.read()
253
217
self.assertEqual(
254
b"Bazaar Graph Index 1\nnode_ref_lists=2\nkey_elements=1\nlen=2\n"
255
b"keference\x00\x00\t\x00data\n"
256
b"rey\x00\x0059\t59\x00data\n"
218
"Bazaar Graph Index 1\nnode_ref_lists=2\nkey_elements=1\nlen=2\n"
219
"keference\x00\x00\t\x00data\n"
220
"rey\x00\x0059\t59\x00data\n"
259
223
def test_add_node_referencing_missing_key_makes_absent(self):
260
builder = _mod_index.GraphIndexBuilder(reference_lists=1)
261
builder.add_node((b'rey', ), b'data',
262
([(b'beference', ), (b'aeference2', )], ))
224
builder = index.GraphIndexBuilder(reference_lists=1)
225
builder.add_node(('rey', ), 'data',
226
([('beference', ), ('aeference2', )], ))
263
227
stream = builder.finish()
264
228
contents = stream.read()
265
229
self.assertEqual(
266
b"Bazaar Graph Index 1\nnode_ref_lists=1\nkey_elements=1\nlen=1\n"
267
b"aeference2\x00a\x00\x00\n"
268
b"beference\x00a\x00\x00\n"
269
b"rey\x00\x00074\r059\x00data\n"
230
"Bazaar Graph Index 1\nnode_ref_lists=1\nkey_elements=1\nlen=1\n"
231
"aeference2\x00a\x00\x00\n"
232
"beference\x00a\x00\x00\n"
233
"rey\x00\x00074\r059\x00data\n"
272
236
def test_node_references_three_digits(self):
273
237
# test the node digit expands as needed.
274
builder = _mod_index.GraphIndexBuilder(reference_lists=1)
275
references = [((b"%d" % val), ) for val in range(8, -1, -1)]
276
builder.add_node((b'2-key', ), b'', (references, ))
238
builder = index.GraphIndexBuilder(reference_lists=1)
239
references = [(str(val), ) for val in reversed(range(9))]
240
builder.add_node(('2-key', ), '', (references, ))
277
241
stream = builder.finish()
278
242
contents = stream.read()
279
243
self.assertEqualDiff(
280
b"Bazaar Graph Index 1\nnode_ref_lists=1\nkey_elements=1\nlen=1\n"
284
b"2-key\x00\x00151\r145\r139\r133\r127\r121\r071\r065\r059\x00\n"
244
"Bazaar Graph Index 1\nnode_ref_lists=1\nkey_elements=1\nlen=1\n"
248
"2-key\x00\x00151\r145\r139\r133\r127\r121\r071\r065\r059\x00\n"
293
257
def test_absent_has_no_reference_overhead(self):
294
258
# the offsets after an absent record should be correct when there are
295
259
# >1 reference lists.
296
builder = _mod_index.GraphIndexBuilder(reference_lists=2)
297
builder.add_node((b'parent', ), b'', ([(b'aail', ), (b'zther', )], []))
260
builder = index.GraphIndexBuilder(reference_lists=2)
261
builder.add_node(('parent', ), '', ([('aail', ), ('zther', )], []))
298
262
stream = builder.finish()
299
263
contents = stream.read()
300
264
self.assertEqual(
301
b"Bazaar Graph Index 1\nnode_ref_lists=2\nkey_elements=1\nlen=1\n"
302
b"aail\x00a\x00\x00\n"
303
b"parent\x00\x0059\r84\t\x00\n"
304
b"zther\x00a\x00\x00\n"
265
"Bazaar Graph Index 1\nnode_ref_lists=2\nkey_elements=1\nlen=1\n"
266
"aail\x00a\x00\x00\n"
267
"parent\x00\x0059\r84\t\x00\n"
268
"zther\x00a\x00\x00\n"
307
271
def test_add_node_bad_key(self):
308
builder = _mod_index.GraphIndexBuilder()
309
for bad_char in bytearray(b'\t\n\x0b\x0c\r\x00 '):
310
self.assertRaises(_mod_index.BadIndexKey, builder.add_node,
311
(b'a%skey' % bytes([bad_char]), ), b'data')
312
self.assertRaises(_mod_index.BadIndexKey, builder.add_node,
314
self.assertRaises(_mod_index.BadIndexKey, builder.add_node,
315
b'not-a-tuple', b'data')
272
builder = index.GraphIndexBuilder()
273
for bad_char in '\t\n\x0b\x0c\r\x00 ':
274
self.assertRaises(errors.BadIndexKey, builder.add_node,
275
('a%skey' % bad_char, ), 'data')
276
self.assertRaises(errors.BadIndexKey, builder.add_node,
278
self.assertRaises(errors.BadIndexKey, builder.add_node,
279
'not-a-tuple', 'data')
316
280
# not enough length
317
self.assertRaises(_mod_index.BadIndexKey, builder.add_node,
281
self.assertRaises(errors.BadIndexKey, builder.add_node,
320
self.assertRaises(_mod_index.BadIndexKey, builder.add_node,
321
(b'primary', b'secondary'), b'data')
284
self.assertRaises(errors.BadIndexKey, builder.add_node,
285
('primary', 'secondary'), 'data')
322
286
# secondary key elements get checked too:
323
builder = _mod_index.GraphIndexBuilder(key_elements=2)
324
for bad_char in bytearray(b'\t\n\x0b\x0c\r\x00 '):
325
self.assertRaises(_mod_index.BadIndexKey, builder.add_node,
326
(b'prefix', b'a%skey' % bytes([bad_char])), b'data')
287
builder = index.GraphIndexBuilder(key_elements=2)
288
for bad_char in '\t\n\x0b\x0c\r\x00 ':
289
self.assertRaises(errors.BadIndexKey, builder.add_node,
290
('prefix', 'a%skey' % bad_char), 'data')
328
292
def test_add_node_bad_data(self):
329
builder = _mod_index.GraphIndexBuilder()
330
self.assertRaises(_mod_index.BadIndexValue, builder.add_node, (b'akey', ),
332
self.assertRaises(_mod_index.BadIndexValue, builder.add_node, (b'akey', ),
293
builder = index.GraphIndexBuilder()
294
self.assertRaises(errors.BadIndexValue, builder.add_node, ('akey', ),
296
self.assertRaises(errors.BadIndexValue, builder.add_node, ('akey', ),
335
299
def test_add_node_bad_mismatched_ref_lists_length(self):
336
builder = _mod_index.GraphIndexBuilder()
337
self.assertRaises(_mod_index.BadIndexValue, builder.add_node, (b'akey', ),
339
builder = _mod_index.GraphIndexBuilder(reference_lists=1)
340
self.assertRaises(_mod_index.BadIndexValue, builder.add_node, (b'akey', ),
342
self.assertRaises(_mod_index.BadIndexValue, builder.add_node, (b'akey', ),
344
self.assertRaises(_mod_index.BadIndexValue, builder.add_node, (b'akey', ),
345
b'data aa', ([], []))
346
builder = _mod_index.GraphIndexBuilder(reference_lists=2)
347
self.assertRaises(_mod_index.BadIndexValue, builder.add_node, (b'akey', ),
349
self.assertRaises(_mod_index.BadIndexValue, builder.add_node, (b'akey', ),
351
self.assertRaises(_mod_index.BadIndexValue, builder.add_node, (b'akey', ),
352
b'data aa', ([], [], []))
300
builder = index.GraphIndexBuilder()
301
self.assertRaises(errors.BadIndexValue, builder.add_node, ('akey', ),
303
builder = index.GraphIndexBuilder(reference_lists=1)
304
self.assertRaises(errors.BadIndexValue, builder.add_node, ('akey', ),
306
self.assertRaises(errors.BadIndexValue, builder.add_node, ('akey', ),
308
self.assertRaises(errors.BadIndexValue, builder.add_node, ('akey', ),
310
builder = index.GraphIndexBuilder(reference_lists=2)
311
self.assertRaises(errors.BadIndexValue, builder.add_node, ('akey', ),
313
self.assertRaises(errors.BadIndexValue, builder.add_node, ('akey', ),
315
self.assertRaises(errors.BadIndexValue, builder.add_node, ('akey', ),
316
'data aa', ([], [], []))
354
318
def test_add_node_bad_key_in_reference_lists(self):
355
319
# first list, first key - trivial
356
builder = _mod_index.GraphIndexBuilder(reference_lists=1)
357
self.assertRaises(_mod_index.BadIndexKey, builder.add_node, (b'akey', ),
358
b'data aa', ([(b'a key', )], ))
320
builder = index.GraphIndexBuilder(reference_lists=1)
321
self.assertRaises(errors.BadIndexKey, builder.add_node, ('akey', ),
322
'data aa', ([('a key', )], ))
359
323
# references keys must be tuples too
360
self.assertRaises(_mod_index.BadIndexKey, builder.add_node, (b'akey', ),
361
b'data aa', (['not-a-tuple'], ))
324
self.assertRaises(errors.BadIndexKey, builder.add_node, ('akey', ),
325
'data aa', (['not-a-tuple'], ))
362
326
# not enough length
363
self.assertRaises(_mod_index.BadIndexKey, builder.add_node, (b'akey', ),
364
b'data aa', ([()], ))
327
self.assertRaises(errors.BadIndexKey, builder.add_node, ('akey', ),
366
self.assertRaises(_mod_index.BadIndexKey, builder.add_node, (b'akey', ),
367
b'data aa', ([(b'primary', b'secondary')], ))
330
self.assertRaises(errors.BadIndexKey, builder.add_node, ('akey', ),
331
'data aa', ([('primary', 'secondary')], ))
368
332
# need to check more than the first key in the list
369
self.assertRaises(_mod_index.BadIndexKey, builder.add_node, (b'akey', ),
370
b'data aa', ([(b'agoodkey', ), (b'that is a bad key', )], ))
333
self.assertRaises(errors.BadIndexKey, builder.add_node, ('akey', ),
334
'data aa', ([('agoodkey', ), ('that is a bad key', )], ))
371
335
# and if there is more than one list it should be getting checked
373
builder = _mod_index.GraphIndexBuilder(reference_lists=2)
374
self.assertRaises(_mod_index.BadIndexKey, builder.add_node, (b'akey', ),
375
b'data aa', ([], ['a bad key']))
337
builder = index.GraphIndexBuilder(reference_lists=2)
338
self.assertRaises(errors.BadIndexKey, builder.add_node, ('akey', ),
339
'data aa', ([], ['a bad key']))
377
341
def test_add_duplicate_key(self):
378
builder = _mod_index.GraphIndexBuilder()
379
builder.add_node((b'key', ), b'data')
380
self.assertRaises(_mod_index.BadIndexDuplicateKey,
381
builder.add_node, (b'key', ), b'data')
342
builder = index.GraphIndexBuilder()
343
builder.add_node(('key', ), 'data')
344
self.assertRaises(errors.BadIndexDuplicateKey,
345
builder.add_node, ('key', ), 'data')
383
347
def test_add_duplicate_key_2_elements(self):
384
builder = _mod_index.GraphIndexBuilder(key_elements=2)
385
builder.add_node((b'key', b'key'), b'data')
386
self.assertRaises(_mod_index.BadIndexDuplicateKey, builder.add_node,
387
(b'key', b'key'), b'data')
348
builder = index.GraphIndexBuilder(key_elements=2)
349
builder.add_node(('key', 'key'), 'data')
350
self.assertRaises(errors.BadIndexDuplicateKey, builder.add_node,
351
('key', 'key'), 'data')
389
353
def test_add_key_after_referencing_key(self):
390
builder = _mod_index.GraphIndexBuilder(reference_lists=1)
391
builder.add_node((b'key', ), b'data', ([(b'reference', )], ))
392
builder.add_node((b'reference', ), b'data', ([],))
354
builder = index.GraphIndexBuilder(reference_lists=1)
355
builder.add_node(('key', ), 'data', ([('reference', )], ))
356
builder.add_node(('reference', ), 'data', ([],))
394
358
def test_add_key_after_referencing_key_2_elements(self):
395
builder = _mod_index.GraphIndexBuilder(
396
reference_lists=1, key_elements=2)
397
builder.add_node((b'k', b'ey'), b'data',
398
([(b'reference', b'tokey')], ))
399
builder.add_node((b'reference', b'tokey'), b'data', ([],))
359
builder = index.GraphIndexBuilder(reference_lists=1, key_elements=2)
360
builder.add_node(('k', 'ey'), 'data', ([('reference', 'tokey')], ))
361
builder.add_node(('reference', 'tokey'), 'data', ([],))
401
363
def test_set_optimize(self):
402
builder = _mod_index.GraphIndexBuilder(
403
reference_lists=1, key_elements=2)
364
builder = index.GraphIndexBuilder(reference_lists=1, key_elements=2)
404
365
builder.set_optimize(for_size=True)
405
366
self.assertTrue(builder._optimize_for_size)
406
367
builder.set_optimize(for_size=False)
829
787
def test_iter_entries_references_resolved(self):
830
788
index = self.make_index(1, nodes=[
831
((b'name', ), b'data', ([(b'ref', ), (b'ref', )], )),
832
((b'ref', ), b'refdata', ([], ))])
833
self.assertEqual({(index, (b'name', ), b'data', (((b'ref',), (b'ref',)),)),
834
(index, (b'ref', ), b'refdata', ((), ))},
835
set(index.iter_entries([(b'name',), (b'ref',)])))
789
(('name', ), 'data', ([('ref', ), ('ref', )], )),
790
(('ref', ), 'refdata', ([], ))])
791
self.assertEqual(set([(index, ('name', ), 'data', ((('ref',),('ref',)),)),
792
(index, ('ref', ), 'refdata', ((), ))]),
793
set(index.iter_entries([('name',), ('ref',)])))
837
795
def test_iter_entries_references_2_refs_resolved(self):
838
796
index = self.make_index(2, nodes=[
839
((b'name', ), b'data', ([(b'ref', )], [(b'ref', )])),
840
((b'ref', ), b'refdata', ([], []))])
841
self.assertEqual({(index, (b'name', ), b'data', (((b'ref',),), ((b'ref',),))),
842
(index, (b'ref', ), b'refdata', ((), ()))},
843
set(index.iter_entries([(b'name',), (b'ref',)])))
797
(('name', ), 'data', ([('ref', )], [('ref', )])),
798
(('ref', ), 'refdata', ([], []))])
799
self.assertEqual(set([(index, ('name', ), 'data', ((('ref',),), (('ref',),))),
800
(index, ('ref', ), 'refdata', ((), ()))]),
801
set(index.iter_entries([('name',), ('ref',)])))
845
803
def test_iteration_absent_skipped(self):
846
804
index = self.make_index(1, nodes=[
847
((b'name', ), b'data', ([(b'ref', )], ))])
848
self.assertEqual({(index, (b'name', ), b'data', (((b'ref',),),))},
849
set(index.iter_all_entries()))
850
self.assertEqual({(index, (b'name', ), b'data', (((b'ref',),),))},
851
set(index.iter_entries([(b'name', )])))
852
self.assertEqual([], list(index.iter_entries([(b'ref', )])))
805
(('name', ), 'data', ([('ref', )], ))])
806
self.assertEqual(set([(index, ('name', ), 'data', ((('ref',),),))]),
807
set(index.iter_all_entries()))
808
self.assertEqual(set([(index, ('name', ), 'data', ((('ref',),),))]),
809
set(index.iter_entries([('name', )])))
810
self.assertEqual([], list(index.iter_entries([('ref', )])))
854
812
def test_iteration_absent_skipped_2_element_keys(self):
855
813
index = self.make_index(1, key_elements=2, nodes=[
856
((b'name', b'fin'), b'data', ([(b'ref', b'erence')], ))])
857
self.assertEqual([(index, (b'name', b'fin'), b'data', (((b'ref', b'erence'),),))],
858
list(index.iter_all_entries()))
859
self.assertEqual([(index, (b'name', b'fin'), b'data', (((b'ref', b'erence'),),))],
860
list(index.iter_entries([(b'name', b'fin')])))
861
self.assertEqual([], list(index.iter_entries([(b'ref', b'erence')])))
814
(('name', 'fin'), 'data', ([('ref', 'erence')], ))])
815
self.assertEqual(set([(index, ('name', 'fin'), 'data', ((('ref', 'erence'),),))]),
816
set(index.iter_all_entries()))
817
self.assertEqual(set([(index, ('name', 'fin'), 'data', ((('ref', 'erence'),),))]),
818
set(index.iter_entries([('name', 'fin')])))
819
self.assertEqual([], list(index.iter_entries([('ref', 'erence')])))
863
821
def test_iter_all_keys(self):
864
822
index = self.make_index(1, nodes=[
865
((b'name', ), b'data', ([(b'ref', )], )),
866
((b'ref', ), b'refdata', ([], ))])
867
self.assertEqual({(index, (b'name', ), b'data', (((b'ref',),),)),
868
(index, (b'ref', ), b'refdata', ((), ))},
869
set(index.iter_entries([(b'name', ), (b'ref', )])))
823
(('name', ), 'data', ([('ref', )], )),
824
(('ref', ), 'refdata', ([], ))])
825
self.assertEqual(set([(index, ('name', ), 'data', ((('ref',),),)),
826
(index, ('ref', ), 'refdata', ((), ))]),
827
set(index.iter_entries([('name', ), ('ref', )])))
871
829
def test_iter_nothing_empty(self):
872
830
index = self.make_index()
875
833
def test_iter_missing_entry_empty(self):
876
834
index = self.make_index()
877
self.assertEqual([], list(index.iter_entries([(b'a', )])))
835
self.assertEqual([], list(index.iter_entries([('a', )])))
879
837
def test_iter_missing_entry_empty_no_size(self):
880
838
idx = self.make_index()
881
idx = _mod_index.GraphIndex(idx._transport, 'index', None)
882
self.assertEqual([], list(idx.iter_entries([(b'a', )])))
839
idx = index.GraphIndex(idx._transport, 'index', None)
840
self.assertEqual([], list(idx.iter_entries([('a', )])))
884
842
def test_iter_key_prefix_1_element_key_None(self):
885
843
index = self.make_index()
886
self.assertRaises(_mod_index.BadIndexKey, list,
887
index.iter_entries_prefix([(None, )]))
844
self.assertRaises(errors.BadIndexKey, list,
845
index.iter_entries_prefix([(None, )]))
889
847
def test_iter_key_prefix_wrong_length(self):
890
848
index = self.make_index()
891
self.assertRaises(_mod_index.BadIndexKey, list,
892
index.iter_entries_prefix([(b'foo', None)]))
849
self.assertRaises(errors.BadIndexKey, list,
850
index.iter_entries_prefix([('foo', None)]))
893
851
index = self.make_index(key_elements=2)
894
self.assertRaises(_mod_index.BadIndexKey, list,
895
index.iter_entries_prefix([(b'foo', )]))
896
self.assertRaises(_mod_index.BadIndexKey, list,
897
index.iter_entries_prefix([(b'foo', None, None)]))
852
self.assertRaises(errors.BadIndexKey, list,
853
index.iter_entries_prefix([('foo', )]))
854
self.assertRaises(errors.BadIndexKey, list,
855
index.iter_entries_prefix([('foo', None, None)]))
899
857
def test_iter_key_prefix_1_key_element_no_refs(self):
900
index = self.make_index(nodes=[
901
((b'name', ), b'data', ()),
902
((b'ref', ), b'refdata', ())])
903
self.assertEqual({(index, (b'name', ), b'data'),
904
(index, (b'ref', ), b'refdata')},
905
set(index.iter_entries_prefix([(b'name', ), (b'ref', )])))
858
index = self.make_index( nodes=[
859
(('name', ), 'data', ()),
860
(('ref', ), 'refdata', ())])
861
self.assertEqual(set([(index, ('name', ), 'data'),
862
(index, ('ref', ), 'refdata')]),
863
set(index.iter_entries_prefix([('name', ), ('ref', )])))
907
865
def test_iter_key_prefix_1_key_element_refs(self):
908
866
index = self.make_index(1, nodes=[
909
((b'name', ), b'data', ([(b'ref', )], )),
910
((b'ref', ), b'refdata', ([], ))])
911
self.assertEqual({(index, (b'name', ), b'data', (((b'ref',),),)),
912
(index, (b'ref', ), b'refdata', ((), ))},
913
set(index.iter_entries_prefix([(b'name', ), (b'ref', )])))
867
(('name', ), 'data', ([('ref', )], )),
868
(('ref', ), 'refdata', ([], ))])
869
self.assertEqual(set([(index, ('name', ), 'data', ((('ref',),),)),
870
(index, ('ref', ), 'refdata', ((), ))]),
871
set(index.iter_entries_prefix([('name', ), ('ref', )])))
915
873
def test_iter_key_prefix_2_key_element_no_refs(self):
916
874
index = self.make_index(key_elements=2, nodes=[
917
((b'name', b'fin1'), b'data', ()),
918
((b'name', b'fin2'), b'beta', ()),
919
((b'ref', b'erence'), b'refdata', ())])
920
self.assertEqual({(index, (b'name', b'fin1'), b'data'),
921
(index, (b'ref', b'erence'), b'refdata')},
922
set(index.iter_entries_prefix([(b'name', b'fin1'), (b'ref', b'erence')])))
923
self.assertEqual({(index, (b'name', b'fin1'), b'data'),
924
(index, (b'name', b'fin2'), b'beta')},
925
set(index.iter_entries_prefix([(b'name', None)])))
875
(('name', 'fin1'), 'data', ()),
876
(('name', 'fin2'), 'beta', ()),
877
(('ref', 'erence'), 'refdata', ())])
878
self.assertEqual(set([(index, ('name', 'fin1'), 'data'),
879
(index, ('ref', 'erence'), 'refdata')]),
880
set(index.iter_entries_prefix([('name', 'fin1'), ('ref', 'erence')])))
881
self.assertEqual(set([(index, ('name', 'fin1'), 'data'),
882
(index, ('name', 'fin2'), 'beta')]),
883
set(index.iter_entries_prefix([('name', None)])))
927
885
def test_iter_key_prefix_2_key_element_refs(self):
928
886
index = self.make_index(1, key_elements=2, nodes=[
929
((b'name', b'fin1'), b'data', ([(b'ref', b'erence')], )),
930
((b'name', b'fin2'), b'beta', ([], )),
931
((b'ref', b'erence'), b'refdata', ([], ))])
932
self.assertEqual({(index, (b'name', b'fin1'), b'data', (((b'ref', b'erence'),),)),
933
(index, (b'ref', b'erence'), b'refdata', ((), ))},
934
set(index.iter_entries_prefix([(b'name', b'fin1'), (b'ref', b'erence')])))
935
self.assertEqual({(index, (b'name', b'fin1'), b'data', (((b'ref', b'erence'),),)),
936
(index, (b'name', b'fin2'), b'beta', ((), ))},
937
set(index.iter_entries_prefix([(b'name', None)])))
887
(('name', 'fin1'), 'data', ([('ref', 'erence')], )),
888
(('name', 'fin2'), 'beta', ([], )),
889
(('ref', 'erence'), 'refdata', ([], ))])
890
self.assertEqual(set([(index, ('name', 'fin1'), 'data', ((('ref', 'erence'),),)),
891
(index, ('ref', 'erence'), 'refdata', ((), ))]),
892
set(index.iter_entries_prefix([('name', 'fin1'), ('ref', 'erence')])))
893
self.assertEqual(set([(index, ('name', 'fin1'), 'data', ((('ref', 'erence'),),)),
894
(index, ('name', 'fin2'), 'beta', ((), ))]),
895
set(index.iter_entries_prefix([('name', None)])))
939
897
def test_key_count_empty(self):
940
898
index = self.make_index()
941
899
self.assertEqual(0, index.key_count())
943
901
def test_key_count_one(self):
944
index = self.make_index(nodes=[((b'name', ), b'', ())])
902
index = self.make_index(nodes=[(('name', ), '', ())])
945
903
self.assertEqual(1, index.key_count())
947
905
def test_key_count_two(self):
948
906
index = self.make_index(nodes=[
949
((b'name', ), b'', ()), ((b'foo', ), b'', ())])
907
(('name', ), '', ()), (('foo', ), '', ())])
950
908
self.assertEqual(2, index.key_count())
952
910
def test_read_and_parse_tracks_real_read_value(self):
1179
1134
log.append(self._index)
1180
1135
return self._index.clear_cache()
1182
idx = _mod_index.CombinedGraphIndex([])
1183
idx1 = self.make_index('name', 0, nodes=[((b'key', ), b'', ())])
1137
idx = index.CombinedGraphIndex([])
1138
idx1 = self.make_index('name', 0, nodes=[(('key', ), '', ())])
1184
1139
idx.insert_index(0, ClearCacheProxy(idx1))
1185
idx2 = self.make_index('name', 0, nodes=[((b'key', ), b'', ())])
1140
idx2 = self.make_index('name', 0, nodes=[(('key', ), '', ())])
1186
1141
idx.insert_index(1, ClearCacheProxy(idx2))
1187
1142
# CombinedGraphIndex should call 'clear_cache()' on all children
1188
1143
idx.clear_cache()
1189
1144
self.assertEqual(sorted([idx1, idx2]), sorted(log))
1191
1146
def test_iter_all_entries_empty(self):
1192
idx = _mod_index.CombinedGraphIndex([])
1147
idx = index.CombinedGraphIndex([])
1193
1148
self.assertEqual([], list(idx.iter_all_entries()))
1195
1150
def test_iter_all_entries_children_empty(self):
1196
1151
idx1 = self.make_index('name')
1197
idx = _mod_index.CombinedGraphIndex([idx1])
1152
idx = index.CombinedGraphIndex([idx1])
1198
1153
self.assertEqual([], list(idx.iter_all_entries()))
1200
1155
def test_iter_all_entries_simple(self):
1201
idx1 = self.make_index('name', nodes=[((b'name', ), b'data', ())])
1202
idx = _mod_index.CombinedGraphIndex([idx1])
1203
self.assertEqual([(idx1, (b'name', ), b'data')],
1204
list(idx.iter_all_entries()))
1156
idx1 = self.make_index('name', nodes=[(('name', ), 'data', ())])
1157
idx = index.CombinedGraphIndex([idx1])
1158
self.assertEqual([(idx1, ('name', ), 'data')],
1159
list(idx.iter_all_entries()))
1206
1161
def test_iter_all_entries_two_indices(self):
1207
idx1 = self.make_index('name1', nodes=[((b'name', ), b'data', ())])
1208
idx2 = self.make_index('name2', nodes=[((b'2', ), b'', ())])
1209
idx = _mod_index.CombinedGraphIndex([idx1, idx2])
1210
self.assertEqual([(idx1, (b'name', ), b'data'),
1211
(idx2, (b'2', ), b'')],
1162
idx1 = self.make_index('name1', nodes=[(('name', ), 'data', ())])
1163
idx2 = self.make_index('name2', nodes=[(('2', ), '', ())])
1164
idx = index.CombinedGraphIndex([idx1, idx2])
1165
self.assertEqual([(idx1, ('name', ), 'data'),
1166
(idx2, ('2', ), '')],
1212
1167
list(idx.iter_all_entries()))
1214
1169
def test_iter_entries_two_indices_dup_key(self):
1215
idx1 = self.make_index('name1', nodes=[((b'name', ), b'data', ())])
1216
idx2 = self.make_index('name2', nodes=[((b'name', ), b'data', ())])
1217
idx = _mod_index.CombinedGraphIndex([idx1, idx2])
1218
self.assertEqual([(idx1, (b'name', ), b'data')],
1219
list(idx.iter_entries([(b'name', )])))
1170
idx1 = self.make_index('name1', nodes=[(('name', ), 'data', ())])
1171
idx2 = self.make_index('name2', nodes=[(('name', ), 'data', ())])
1172
idx = index.CombinedGraphIndex([idx1, idx2])
1173
self.assertEqual([(idx1, ('name', ), 'data')],
1174
list(idx.iter_entries([('name', )])))
1221
1176
def test_iter_all_entries_two_indices_dup_key(self):
1222
idx1 = self.make_index('name1', nodes=[((b'name', ), b'data', ())])
1223
idx2 = self.make_index('name2', nodes=[((b'name', ), b'data', ())])
1224
idx = _mod_index.CombinedGraphIndex([idx1, idx2])
1225
self.assertEqual([(idx1, (b'name', ), b'data')],
1177
idx1 = self.make_index('name1', nodes=[(('name', ), 'data', ())])
1178
idx2 = self.make_index('name2', nodes=[(('name', ), 'data', ())])
1179
idx = index.CombinedGraphIndex([idx1, idx2])
1180
self.assertEqual([(idx1, ('name', ), 'data')],
1226
1181
list(idx.iter_all_entries()))
1228
1183
def test_iter_key_prefix_2_key_element_refs(self):
1229
1184
idx1 = self.make_index('1', 1, key_elements=2, nodes=[
1230
((b'name', b'fin1'), b'data', ([(b'ref', b'erence')], ))])
1185
(('name', 'fin1'), 'data', ([('ref', 'erence')], ))])
1231
1186
idx2 = self.make_index('2', 1, key_elements=2, nodes=[
1232
((b'name', b'fin2'), b'beta', ([], )),
1233
((b'ref', b'erence'), b'refdata', ([], ))])
1234
idx = _mod_index.CombinedGraphIndex([idx1, idx2])
1235
self.assertEqual({(idx1, (b'name', b'fin1'), b'data',
1236
(((b'ref', b'erence'),),)),
1237
(idx2, (b'ref', b'erence'), b'refdata', ((), ))},
1238
set(idx.iter_entries_prefix([(b'name', b'fin1'),
1239
(b'ref', b'erence')])))
1240
self.assertEqual({(idx1, (b'name', b'fin1'), b'data',
1241
(((b'ref', b'erence'),),)),
1242
(idx2, (b'name', b'fin2'), b'beta', ((), ))},
1243
set(idx.iter_entries_prefix([(b'name', None)])))
1187
(('name', 'fin2'), 'beta', ([], )),
1188
(('ref', 'erence'), 'refdata', ([], ))])
1189
idx = index.CombinedGraphIndex([idx1, idx2])
1190
self.assertEqual(set([(idx1, ('name', 'fin1'), 'data',
1191
((('ref', 'erence'),),)),
1192
(idx2, ('ref', 'erence'), 'refdata', ((), ))]),
1193
set(idx.iter_entries_prefix([('name', 'fin1'),
1194
('ref', 'erence')])))
1195
self.assertEqual(set([(idx1, ('name', 'fin1'), 'data',
1196
((('ref', 'erence'),),)),
1197
(idx2, ('name', 'fin2'), 'beta', ((), ))]),
1198
set(idx.iter_entries_prefix([('name', None)])))
1245
1200
def test_iter_nothing_empty(self):
1246
idx = _mod_index.CombinedGraphIndex([])
1201
idx = index.CombinedGraphIndex([])
1247
1202
self.assertEqual([], list(idx.iter_entries([])))
1249
1204
def test_iter_nothing_children_empty(self):
1250
1205
idx1 = self.make_index('name')
1251
idx = _mod_index.CombinedGraphIndex([idx1])
1206
idx = index.CombinedGraphIndex([idx1])
1252
1207
self.assertEqual([], list(idx.iter_entries([])))
1254
1209
def test_iter_all_keys(self):
1255
idx1 = self.make_index('1', 1, nodes=[((b'name', ), b'data',
1257
idx2 = self.make_index(
1258
'2', 1, nodes=[((b'ref', ), b'refdata', ((), ))])
1259
idx = _mod_index.CombinedGraphIndex([idx1, idx2])
1260
self.assertEqual({(idx1, (b'name', ), b'data', (((b'ref', ), ), )),
1261
(idx2, (b'ref', ), b'refdata', ((), ))},
1262
set(idx.iter_entries([(b'name', ), (b'ref', )])))
1210
idx1 = self.make_index('1', 1, nodes=[(('name', ), 'data',
1212
idx2 = self.make_index('2', 1, nodes=[(('ref', ), 'refdata', ((), ))])
1213
idx = index.CombinedGraphIndex([idx1, idx2])
1214
self.assertEqual(set([(idx1, ('name', ), 'data', ((('ref', ), ), )),
1215
(idx2, ('ref', ), 'refdata', ((), ))]),
1216
set(idx.iter_entries([('name', ), ('ref', )])))
1264
1218
def test_iter_all_keys_dup_entry(self):
1265
idx1 = self.make_index('1', 1, nodes=[((b'name', ), b'data',
1267
((b'ref', ), b'refdata', ([], ))])
1268
idx2 = self.make_index(
1269
'2', 1, nodes=[((b'ref', ), b'refdata', ([], ))])
1270
idx = _mod_index.CombinedGraphIndex([idx1, idx2])
1271
self.assertEqual({(idx1, (b'name', ), b'data', (((b'ref',),),)),
1272
(idx1, (b'ref', ), b'refdata', ((), ))},
1273
set(idx.iter_entries([(b'name', ), (b'ref', )])))
1219
idx1 = self.make_index('1', 1, nodes=[(('name', ), 'data',
1221
(('ref', ), 'refdata', ([], ))])
1222
idx2 = self.make_index('2', 1, nodes=[(('ref', ), 'refdata', ([], ))])
1223
idx = index.CombinedGraphIndex([idx1, idx2])
1224
self.assertEqual(set([(idx1, ('name', ), 'data', ((('ref',),),)),
1225
(idx1, ('ref', ), 'refdata', ((), ))]),
1226
set(idx.iter_entries([('name', ), ('ref', )])))
1275
1228
def test_iter_missing_entry_empty(self):
1276
idx = _mod_index.CombinedGraphIndex([])
1229
idx = index.CombinedGraphIndex([])
1277
1230
self.assertEqual([], list(idx.iter_entries([('a', )])))
1279
1232
def test_iter_missing_entry_one_index(self):
1280
1233
idx1 = self.make_index('1')
1281
idx = _mod_index.CombinedGraphIndex([idx1])
1282
self.assertEqual([], list(idx.iter_entries([(b'a', )])))
1234
idx = index.CombinedGraphIndex([idx1])
1235
self.assertEqual([], list(idx.iter_entries([('a', )])))
1284
1237
def test_iter_missing_entry_two_index(self):
1285
1238
idx1 = self.make_index('1')
1286
1239
idx2 = self.make_index('2')
1287
idx = _mod_index.CombinedGraphIndex([idx1, idx2])
1240
idx = index.CombinedGraphIndex([idx1, idx2])
1288
1241
self.assertEqual([], list(idx.iter_entries([('a', )])))
1290
1243
def test_iter_entry_present_one_index_only(self):
1291
idx1 = self.make_index('1', nodes=[((b'key', ), b'', ())])
1244
idx1 = self.make_index('1', nodes=[(('key', ), '', ())])
1292
1245
idx2 = self.make_index('2', nodes=[])
1293
idx = _mod_index.CombinedGraphIndex([idx1, idx2])
1294
self.assertEqual([(idx1, (b'key', ), b'')],
1295
list(idx.iter_entries([(b'key', )])))
1246
idx = index.CombinedGraphIndex([idx1, idx2])
1247
self.assertEqual([(idx1, ('key', ), '')],
1248
list(idx.iter_entries([('key', )])))
1296
1249
# and in the other direction
1297
idx = _mod_index.CombinedGraphIndex([idx2, idx1])
1298
self.assertEqual([(idx1, (b'key', ), b'')],
1299
list(idx.iter_entries([(b'key', )])))
1250
idx = index.CombinedGraphIndex([idx2, idx1])
1251
self.assertEqual([(idx1, ('key', ), '')],
1252
list(idx.iter_entries([('key', )])))
1301
1254
def test_key_count_empty(self):
1302
1255
idx1 = self.make_index('1', nodes=[])
1303
1256
idx2 = self.make_index('2', nodes=[])
1304
idx = _mod_index.CombinedGraphIndex([idx1, idx2])
1257
idx = index.CombinedGraphIndex([idx1, idx2])
1305
1258
self.assertEqual(0, idx.key_count())
1307
1260
def test_key_count_sums_index_keys(self):
1308
1261
idx1 = self.make_index('1', nodes=[
1310
((b'2',), b'', ())])
1311
idx2 = self.make_index('2', nodes=[((b'1',), b'', ())])
1312
idx = _mod_index.CombinedGraphIndex([idx1, idx2])
1264
idx2 = self.make_index('2', nodes=[(('1',), '', ())])
1265
idx = index.CombinedGraphIndex([idx1, idx2])
1313
1266
self.assertEqual(3, idx.key_count())
1315
1268
def test_validate_bad_child_index_errors(self):
1316
1269
trans = self.get_transport()
1317
trans.put_bytes('name', b"not an index\n")
1318
idx1 = _mod_index.GraphIndex(trans, 'name', 13)
1319
idx = _mod_index.CombinedGraphIndex([idx1])
1320
self.assertRaises(_mod_index.BadIndexFormatSignature, idx.validate)
1270
trans.put_bytes('name', "not an index\n")
1271
idx1 = index.GraphIndex(trans, 'name', 13)
1272
idx = index.CombinedGraphIndex([idx1])
1273
self.assertRaises(errors.BadIndexFormatSignature, idx.validate)
1322
1275
def test_validate_empty(self):
1323
idx = _mod_index.CombinedGraphIndex([])
1276
idx = index.CombinedGraphIndex([])
1326
1279
def test_key_count_reloads(self):
1521
1475
self.assertEqual(set(), missing_keys)
1523
1477
def test_find_ancestors_missing_keys(self):
1528
1482
index1 = self.make_index('12', ref_lists=1, nodes=[
1529
(key1, b'value', ([],)),
1530
(key2, b'value', ([key1],)),
1483
(key1, 'value', ([],)),
1484
(key2, 'value', ([key1],)),
1532
1486
index2 = self.make_index('34', ref_lists=1, nodes=[
1533
(key3, b'value', ([key2],)),
1487
(key3, 'value', ([key2],)),
1535
c_index = _mod_index.CombinedGraphIndex([index1, index2])
1489
c_index = index.CombinedGraphIndex([index1, index2])
1536
1490
# Searching for a key which is actually not present at all should
1537
1491
# eventually converge
1538
1492
parent_map, missing_keys = c_index.find_ancestry([key4], 0)
1539
1493
self.assertEqual({}, parent_map)
1540
self.assertEqual({key4}, missing_keys)
1494
self.assertEqual(set([key4]), missing_keys)
1542
1496
def test_find_ancestors_no_indexes(self):
1543
c_index = _mod_index.CombinedGraphIndex([])
1497
c_index = index.CombinedGraphIndex([])
1545
1499
parent_map, missing_keys = c_index.find_ancestry([key1], 0)
1546
1500
self.assertEqual({}, parent_map)
1547
self.assertEqual({key1}, missing_keys)
1501
self.assertEqual(set([key1]), missing_keys)
1549
1503
def test_find_ancestors_ghost_parent(self):
1554
1508
index1 = self.make_index('12', ref_lists=1, nodes=[
1555
(key1, b'value', ([],)),
1556
(key2, b'value', ([key1],)),
1509
(key1, 'value', ([],)),
1510
(key2, 'value', ([key1],)),
1558
1512
index2 = self.make_index('34', ref_lists=1, nodes=[
1559
(key4, b'value', ([key2, key3],)),
1513
(key4, 'value', ([key2, key3],)),
1561
c_index = _mod_index.CombinedGraphIndex([index1, index2])
1515
c_index = index.CombinedGraphIndex([index1, index2])
1562
1516
# Searching for a key which is actually not present at all should
1563
1517
# eventually converge
1564
1518
parent_map, missing_keys = c_index.find_ancestry([key4], 0)
1565
1519
self.assertEqual({key4: (key2, key3), key2: (key1,), key1: ()},
1567
self.assertEqual({key3}, missing_keys)
1521
self.assertEqual(set([key3]), missing_keys)
1569
1523
def test__find_ancestors_empty_index(self):
1570
1524
idx = self.make_index('test', ref_lists=1, key_elements=1, nodes=[])
1571
1525
parent_map = {}
1572
1526
missing_keys = set()
1573
search_keys = idx._find_ancestors([(b'one',), (b'two',)], 0, parent_map,
1527
search_keys = idx._find_ancestors([('one',), ('two',)], 0, parent_map,
1575
1529
self.assertEqual(set(), search_keys)
1576
1530
self.assertEqual({}, parent_map)
1577
self.assertEqual({(b'one',), (b'two',)}, missing_keys)
1531
self.assertEqual(set([('one',), ('two',)]), missing_keys)
1580
1534
class TestInMemoryGraphIndex(tests.TestCaseWithMemoryTransport):
1582
1536
def make_index(self, ref_lists=0, key_elements=1, nodes=[]):
1583
result = _mod_index.InMemoryGraphIndex(
1584
ref_lists, key_elements=key_elements)
1537
result = index.InMemoryGraphIndex(ref_lists, key_elements=key_elements)
1585
1538
result.add_nodes(nodes)
1588
1541
def test_add_nodes_no_refs(self):
1589
1542
index = self.make_index(0)
1590
index.add_nodes([((b'name', ), b'data')])
1591
index.add_nodes([((b'name2', ), b''), ((b'name3', ), b'')])
1593
(index, (b'name', ), b'data'),
1594
(index, (b'name2', ), b''),
1595
(index, (b'name3', ), b''),
1596
}, set(index.iter_all_entries()))
1543
index.add_nodes([(('name', ), 'data')])
1544
index.add_nodes([(('name2', ), ''), (('name3', ), '')])
1545
self.assertEqual(set([
1546
(index, ('name', ), 'data'),
1547
(index, ('name2', ), ''),
1548
(index, ('name3', ), ''),
1549
]), set(index.iter_all_entries()))
1598
1551
def test_add_nodes(self):
1599
1552
index = self.make_index(1)
1600
index.add_nodes([((b'name', ), b'data', ([],))])
1601
index.add_nodes([((b'name2', ), b'', ([],)),
1602
((b'name3', ), b'', ([(b'r', )],))])
1604
(index, (b'name', ), b'data', ((),)),
1605
(index, (b'name2', ), b'', ((),)),
1606
(index, (b'name3', ), b'', (((b'r', ), ), )),
1607
}, set(index.iter_all_entries()))
1553
index.add_nodes([(('name', ), 'data', ([],))])
1554
index.add_nodes([(('name2', ), '', ([],)), (('name3', ), '', ([('r', )],))])
1555
self.assertEqual(set([
1556
(index, ('name', ), 'data', ((),)),
1557
(index, ('name2', ), '', ((),)),
1558
(index, ('name3', ), '', ((('r', ), ), )),
1559
]), set(index.iter_all_entries()))
1609
1561
def test_iter_all_entries_empty(self):
1610
1562
index = self.make_index()
1611
1563
self.assertEqual([], list(index.iter_all_entries()))
1613
1565
def test_iter_all_entries_simple(self):
1614
index = self.make_index(nodes=[((b'name', ), b'data')])
1615
self.assertEqual([(index, (b'name', ), b'data')],
1616
list(index.iter_all_entries()))
1566
index = self.make_index(nodes=[(('name', ), 'data')])
1567
self.assertEqual([(index, ('name', ), 'data')],
1568
list(index.iter_all_entries()))
1618
1570
def test_iter_all_entries_references(self):
1619
1571
index = self.make_index(1, nodes=[
1620
((b'name', ), b'data', ([(b'ref', )], )),
1621
((b'ref', ), b'refdata', ([], ))])
1622
self.assertEqual({(index, (b'name', ), b'data', (((b'ref', ),),)),
1623
(index, (b'ref', ), b'refdata', ((), ))},
1624
set(index.iter_all_entries()))
1572
(('name', ), 'data', ([('ref', )], )),
1573
(('ref', ), 'refdata', ([], ))])
1574
self.assertEqual(set([(index, ('name', ), 'data', ((('ref', ),),)),
1575
(index, ('ref', ), 'refdata', ((), ))]),
1576
set(index.iter_all_entries()))
1626
1578
def test_iteration_absent_skipped(self):
1627
1579
index = self.make_index(1, nodes=[
1628
((b'name', ), b'data', ([(b'ref', )], ))])
1629
self.assertEqual({(index, (b'name', ), b'data', (((b'ref',),),))},
1630
set(index.iter_all_entries()))
1631
self.assertEqual({(index, (b'name', ), b'data', (((b'ref',),),))},
1632
set(index.iter_entries([(b'name', )])))
1633
self.assertEqual([], list(index.iter_entries([(b'ref', )])))
1580
(('name', ), 'data', ([('ref', )], ))])
1581
self.assertEqual(set([(index, ('name', ), 'data', ((('ref',),),))]),
1582
set(index.iter_all_entries()))
1583
self.assertEqual(set([(index, ('name', ), 'data', ((('ref',),),))]),
1584
set(index.iter_entries([('name', )])))
1585
self.assertEqual([], list(index.iter_entries([('ref', )])))
1635
1587
def test_iter_all_keys(self):
1636
1588
index = self.make_index(1, nodes=[
1637
((b'name', ), b'data', ([(b'ref', )], )),
1638
((b'ref', ), b'refdata', ([], ))])
1639
self.assertEqual({(index, (b'name', ), b'data', (((b'ref',),),)),
1640
(index, (b'ref', ), b'refdata', ((), ))},
1641
set(index.iter_entries([(b'name', ), (b'ref', )])))
1589
(('name', ), 'data', ([('ref', )], )),
1590
(('ref', ), 'refdata', ([], ))])
1591
self.assertEqual(set([(index, ('name', ), 'data', ((('ref',),),)),
1592
(index, ('ref', ), 'refdata', ((), ))]),
1593
set(index.iter_entries([('name', ), ('ref', )])))
1643
1595
def test_iter_key_prefix_1_key_element_no_refs(self):
1644
index = self.make_index(nodes=[
1645
((b'name', ), b'data'),
1646
((b'ref', ), b'refdata')])
1647
self.assertEqual({(index, (b'name', ), b'data'),
1648
(index, (b'ref', ), b'refdata')},
1649
set(index.iter_entries_prefix([(b'name', ), (b'ref', )])))
1596
index = self.make_index( nodes=[
1597
(('name', ), 'data'),
1598
(('ref', ), 'refdata')])
1599
self.assertEqual(set([(index, ('name', ), 'data'),
1600
(index, ('ref', ), 'refdata')]),
1601
set(index.iter_entries_prefix([('name', ), ('ref', )])))
1651
1603
def test_iter_key_prefix_1_key_element_refs(self):
1652
1604
index = self.make_index(1, nodes=[
1653
((b'name', ), b'data', ([(b'ref', )], )),
1654
((b'ref', ), b'refdata', ([], ))])
1655
self.assertEqual({(index, (b'name', ), b'data', (((b'ref',),),)),
1656
(index, (b'ref', ), b'refdata', ((), ))},
1657
set(index.iter_entries_prefix([(b'name', ), (b'ref', )])))
1605
(('name', ), 'data', ([('ref', )], )),
1606
(('ref', ), 'refdata', ([], ))])
1607
self.assertEqual(set([(index, ('name', ), 'data', ((('ref',),),)),
1608
(index, ('ref', ), 'refdata', ((), ))]),
1609
set(index.iter_entries_prefix([('name', ), ('ref', )])))
1659
1611
def test_iter_key_prefix_2_key_element_no_refs(self):
1660
1612
index = self.make_index(key_elements=2, nodes=[
1661
((b'name', b'fin1'), b'data'),
1662
((b'name', b'fin2'), b'beta'),
1663
((b'ref', b'erence'), b'refdata')])
1664
self.assertEqual({(index, (b'name', b'fin1'), b'data'),
1665
(index, (b'ref', b'erence'), b'refdata')},
1666
set(index.iter_entries_prefix([(b'name', b'fin1'), (b'ref', b'erence')])))
1667
self.assertEqual({(index, (b'name', b'fin1'), b'data'),
1668
(index, (b'name', b'fin2'), b'beta')},
1669
set(index.iter_entries_prefix([(b'name', None)])))
1613
(('name', 'fin1'), 'data'),
1614
(('name', 'fin2'), 'beta'),
1615
(('ref', 'erence'), 'refdata')])
1616
self.assertEqual(set([(index, ('name', 'fin1'), 'data'),
1617
(index, ('ref', 'erence'), 'refdata')]),
1618
set(index.iter_entries_prefix([('name', 'fin1'), ('ref', 'erence')])))
1619
self.assertEqual(set([(index, ('name', 'fin1'), 'data'),
1620
(index, ('name', 'fin2'), 'beta')]),
1621
set(index.iter_entries_prefix([('name', None)])))
1671
1623
def test_iter_key_prefix_2_key_element_refs(self):
1672
1624
index = self.make_index(1, key_elements=2, nodes=[
1673
((b'name', b'fin1'), b'data', ([(b'ref', b'erence')], )),
1674
((b'name', b'fin2'), b'beta', ([], )),
1675
((b'ref', b'erence'), b'refdata', ([], ))])
1676
self.assertEqual({(index, (b'name', b'fin1'), b'data', (((b'ref', b'erence'),),)),
1677
(index, (b'ref', b'erence'), b'refdata', ((), ))},
1678
set(index.iter_entries_prefix([(b'name', b'fin1'), (b'ref', b'erence')])))
1679
self.assertEqual({(index, (b'name', b'fin1'), b'data', (((b'ref', b'erence'),),)),
1680
(index, (b'name', b'fin2'), b'beta', ((), ))},
1681
set(index.iter_entries_prefix([(b'name', None)])))
1625
(('name', 'fin1'), 'data', ([('ref', 'erence')], )),
1626
(('name', 'fin2'), 'beta', ([], )),
1627
(('ref', 'erence'), 'refdata', ([], ))])
1628
self.assertEqual(set([(index, ('name', 'fin1'), 'data', ((('ref', 'erence'),),)),
1629
(index, ('ref', 'erence'), 'refdata', ((), ))]),
1630
set(index.iter_entries_prefix([('name', 'fin1'), ('ref', 'erence')])))
1631
self.assertEqual(set([(index, ('name', 'fin1'), 'data', ((('ref', 'erence'),),)),
1632
(index, ('name', 'fin2'), 'beta', ((), ))]),
1633
set(index.iter_entries_prefix([('name', None)])))
1683
1635
def test_iter_nothing_empty(self):
1684
1636
index = self.make_index()
1714
1666
def make_index(self, ref_lists=1, key_elements=2, nodes=[],
1715
1667
add_callback=False):
1716
result = _mod_index.InMemoryGraphIndex(
1717
ref_lists, key_elements=key_elements)
1668
result = index.InMemoryGraphIndex(ref_lists, key_elements=key_elements)
1718
1669
result.add_nodes(nodes)
1719
1670
if add_callback:
1720
1671
add_nodes_callback = result.add_nodes
1722
1673
add_nodes_callback = None
1723
adapter = _mod_index.GraphIndexPrefixAdapter(
1724
result, (b'prefix', ), key_elements - 1,
1674
adapter = index.GraphIndexPrefixAdapter(
1675
result, ('prefix', ), key_elements - 1,
1725
1676
add_nodes_callback=add_nodes_callback)
1726
1677
return result, adapter
1728
1679
def test_add_node(self):
1729
1680
index, adapter = self.make_index(add_callback=True)
1730
adapter.add_node((b'key',), b'value', (((b'ref',),),))
1731
self.assertEqual({(index, (b'prefix', b'key'), b'value',
1732
(((b'prefix', b'ref'),),))},
1733
set(index.iter_all_entries()))
1681
adapter.add_node(('key',), 'value', ((('ref',),),))
1682
self.assertEqual(set([(index, ('prefix', 'key'), 'value',
1683
((('prefix', 'ref'),),))]),
1684
set(index.iter_all_entries()))
1735
1686
def test_add_nodes(self):
1736
1687
index, adapter = self.make_index(add_callback=True)
1737
1688
adapter.add_nodes((
1738
((b'key',), b'value', (((b'ref',),),)),
1739
((b'key2',), b'value2', ((),)),
1689
(('key',), 'value', ((('ref',),),)),
1690
(('key2',), 'value2', ((),)),
1742
(index, (b'prefix', b'key2'), b'value2', ((),)),
1743
(index, (b'prefix', b'key'), b'value', (((b'prefix', b'ref'),),))
1692
self.assertEqual(set([
1693
(index, ('prefix', 'key2'), 'value2', ((),)),
1694
(index, ('prefix', 'key'), 'value', ((('prefix', 'ref'),),))
1745
1696
set(index.iter_all_entries()))
1747
1698
def test_construct(self):
1748
idx = _mod_index.InMemoryGraphIndex()
1749
adapter = _mod_index.GraphIndexPrefixAdapter(idx, (b'prefix', ), 1)
1699
idx = index.InMemoryGraphIndex()
1700
adapter = index.GraphIndexPrefixAdapter(idx, ('prefix', ), 1)
1751
1702
def test_construct_with_callback(self):
1752
idx = _mod_index.InMemoryGraphIndex()
1753
adapter = _mod_index.GraphIndexPrefixAdapter(idx, (b'prefix', ), 1,
1703
idx = index.InMemoryGraphIndex()
1704
adapter = index.GraphIndexPrefixAdapter(idx, ('prefix', ), 1,
1756
1707
def test_iter_all_entries_cross_prefix_map_errors(self):
1757
1708
index, adapter = self.make_index(nodes=[
1758
((b'prefix', b'key1'), b'data1', (((b'prefixaltered', b'key2'),),))])
1759
self.assertRaises(_mod_index.BadIndexData, list,
1760
adapter.iter_all_entries())
1709
(('prefix', 'key1'), 'data1', ((('prefixaltered', 'key2'),),))])
1710
self.assertRaises(errors.BadIndexData, list, adapter.iter_all_entries())
1762
1712
def test_iter_all_entries(self):
1763
1713
index, adapter = self.make_index(nodes=[
1764
((b'notprefix', b'key1'), b'data', ((), )),
1765
((b'prefix', b'key1'), b'data1', ((), )),
1766
((b'prefix', b'key2'), b'data2', (((b'prefix', b'key1'),),))])
1767
self.assertEqual({(index, (b'key1', ), b'data1', ((),)),
1768
(index, (b'key2', ), b'data2', (((b'key1',),),))},
1769
set(adapter.iter_all_entries()))
1714
(('notprefix', 'key1'), 'data', ((), )),
1715
(('prefix', 'key1'), 'data1', ((), )),
1716
(('prefix', 'key2'), 'data2', ((('prefix', 'key1'),),))])
1717
self.assertEqual(set([(index, ('key1', ), 'data1', ((),)),
1718
(index, ('key2', ), 'data2', ((('key1',),),))]),
1719
set(adapter.iter_all_entries()))
1771
1721
def test_iter_entries(self):
1772
1722
index, adapter = self.make_index(nodes=[
1773
((b'notprefix', b'key1'), b'data', ((), )),
1774
((b'prefix', b'key1'), b'data1', ((), )),
1775
((b'prefix', b'key2'), b'data2', (((b'prefix', b'key1'),),))])
1723
(('notprefix', 'key1'), 'data', ((), )),
1724
(('prefix', 'key1'), 'data1', ((), )),
1725
(('prefix', 'key2'), 'data2', ((('prefix', 'key1'),),))])
1776
1726
# ask for many - get all
1777
self.assertEqual({(index, (b'key1', ), b'data1', ((),)),
1778
(index, (b'key2', ), b'data2', (((b'key1', ),),))},
1779
set(adapter.iter_entries([(b'key1', ), (b'key2', )])))
1727
self.assertEqual(set([(index, ('key1', ), 'data1', ((),)),
1728
(index, ('key2', ), 'data2', ((('key1', ),),))]),
1729
set(adapter.iter_entries([('key1', ), ('key2', )])))
1780
1730
# ask for one, get one
1781
self.assertEqual({(index, (b'key1', ), b'data1', ((),))},
1782
set(adapter.iter_entries([(b'key1', )])))
1731
self.assertEqual(set([(index, ('key1', ), 'data1', ((),))]),
1732
set(adapter.iter_entries([('key1', )])))
1783
1733
# ask for missing, get none
1784
1734
self.assertEqual(set(),
1785
set(adapter.iter_entries([(b'key3', )])))
1735
set(adapter.iter_entries([('key3', )])))
1787
1737
def test_iter_entries_prefix(self):
1788
1738
index, adapter = self.make_index(key_elements=3, nodes=[
1789
((b'notprefix', b'foo', b'key1'), b'data', ((), )),
1790
((b'prefix', b'prefix2', b'key1'), b'data1', ((), )),
1791
((b'prefix', b'prefix2', b'key2'), b'data2', (((b'prefix', b'prefix2', b'key1'),),))])
1739
(('notprefix', 'foo', 'key1'), 'data', ((), )),
1740
(('prefix', 'prefix2', 'key1'), 'data1', ((), )),
1741
(('prefix', 'prefix2', 'key2'), 'data2', ((('prefix', 'prefix2', 'key1'),),))])
1792
1742
# ask for a prefix, get the results for just that prefix, adjusted.
1793
self.assertEqual({(index, (b'prefix2', b'key1', ), b'data1', ((),)),
1794
(index, (b'prefix2', b'key2', ), b'data2', (((b'prefix2', b'key1', ),),))},
1795
set(adapter.iter_entries_prefix([(b'prefix2', None)])))
1743
self.assertEqual(set([(index, ('prefix2', 'key1', ), 'data1', ((),)),
1744
(index, ('prefix2', 'key2', ), 'data2', ((('prefix2', 'key1', ),),))]),
1745
set(adapter.iter_entries_prefix([('prefix2', None)])))
1797
1747
def test_key_count_no_matching_keys(self):
1798
1748
index, adapter = self.make_index(nodes=[
1799
((b'notprefix', b'key1'), b'data', ((), ))])
1749
(('notprefix', 'key1'), 'data', ((), ))])
1800
1750
self.assertEqual(0, adapter.key_count())
1802
1752
def test_key_count_some_keys(self):
1803
1753
index, adapter = self.make_index(nodes=[
1804
((b'notprefix', b'key1'), b'data', ((), )),
1805
((b'prefix', b'key1'), b'data1', ((), )),
1806
((b'prefix', b'key2'), b'data2', (((b'prefix', b'key1'),),))])
1754
(('notprefix', 'key1'), 'data', ((), )),
1755
(('prefix', 'key1'), 'data1', ((), )),
1756
(('prefix', 'key2'), 'data2', ((('prefix', 'key1'),),))])
1807
1757
self.assertEqual(2, adapter.key_count())
1809
1759
def test_validate(self):
1810
1760
index, adapter = self.make_index()
1813
1762
def validate():
1814
1763
calls.append('called')
1815
1764
index.validate = validate