783
790
        index = self.make_index(1, nodes=[
 
784
791
            (('name', ), 'data', ([('ref', ), ('ref', )], )),
 
785
792
            (('ref', ), 'refdata', ([], ))])
 
786
 
        self.assertEqual(set([(index, ('name', ), 'data', ((('ref',),('ref',)),)),
 
787
 
            (index, ('ref', ), 'refdata', ((), ))]),
 
 
793
        self.assertEqual({(index, ('name', ), 'data', ((('ref',),('ref',)),)),
 
 
794
            (index, ('ref', ), 'refdata', ((), ))},
 
788
795
            set(index.iter_entries([('name',), ('ref',)])))
 
790
797
    def test_iter_entries_references_2_refs_resolved(self):
 
791
798
        index = self.make_index(2, nodes=[
 
792
799
            (('name', ), 'data', ([('ref', )], [('ref', )])),
 
793
800
            (('ref', ), 'refdata', ([], []))])
 
794
 
        self.assertEqual(set([(index, ('name', ), 'data', ((('ref',),), (('ref',),))),
 
795
 
            (index, ('ref', ), 'refdata', ((), ()))]),
 
 
801
        self.assertEqual({(index, ('name', ), 'data', ((('ref',),), (('ref',),))),
 
 
802
            (index, ('ref', ), 'refdata', ((), ()))},
 
796
803
            set(index.iter_entries([('name',), ('ref',)])))
 
798
805
    def test_iteration_absent_skipped(self):
 
799
806
        index = self.make_index(1, nodes=[
 
800
807
            (('name', ), 'data', ([('ref', )], ))])
 
801
 
        self.assertEqual(set([(index, ('name', ), 'data', ((('ref',),),))]),
 
 
808
        self.assertEqual({(index, ('name', ), 'data', ((('ref',),),))},
 
802
809
            set(index.iter_all_entries()))
 
803
 
        self.assertEqual(set([(index, ('name', ), 'data', ((('ref',),),))]),
 
 
810
        self.assertEqual({(index, ('name', ), 'data', ((('ref',),),))},
 
804
811
            set(index.iter_entries([('name', )])))
 
805
812
        self.assertEqual([], list(index.iter_entries([('ref', )])))
 
807
814
    def test_iteration_absent_skipped_2_element_keys(self):
 
808
815
        index = self.make_index(1, key_elements=2, nodes=[
 
809
816
            (('name', 'fin'), 'data', ([('ref', 'erence')], ))])
 
810
 
        self.assertEqual(set([(index, ('name', 'fin'), 'data', ((('ref', 'erence'),),))]),
 
 
817
        self.assertEqual({(index, ('name', 'fin'), 'data', ((('ref', 'erence'),),))},
 
811
818
            set(index.iter_all_entries()))
 
812
 
        self.assertEqual(set([(index, ('name', 'fin'), 'data', ((('ref', 'erence'),),))]),
 
 
819
        self.assertEqual({(index, ('name', 'fin'), 'data', ((('ref', 'erence'),),))},
 
813
820
            set(index.iter_entries([('name', 'fin')])))
 
814
821
        self.assertEqual([], list(index.iter_entries([('ref', 'erence')])))
 
 
1128
1136
                log.append(self._index)
 
1129
1137
                return self._index.clear_cache()
 
1131
 
        index = CombinedGraphIndex([])
 
1132
 
        index1 = self.make_index('name', 0, nodes=[(('key', ), '', ())])
 
1133
 
        index.insert_index(0, ClearCacheProxy(index1))
 
1134
 
        index2 = self.make_index('name', 0, nodes=[(('key', ), '', ())])
 
1135
 
        index.insert_index(1, ClearCacheProxy(index2))
 
 
1139
        idx = index.CombinedGraphIndex([])
 
 
1140
        idx1 = self.make_index('name', 0, nodes=[(('key', ), '', ())])
 
 
1141
        idx.insert_index(0, ClearCacheProxy(idx1))
 
 
1142
        idx2 = self.make_index('name', 0, nodes=[(('key', ), '', ())])
 
 
1143
        idx.insert_index(1, ClearCacheProxy(idx2))
 
1136
1144
        # CombinedGraphIndex should call 'clear_cache()' on all children
 
1138
 
        self.assertEqual(sorted([index1, index2]), sorted(log))
 
 
1146
        self.assertEqual(sorted([idx1, idx2]), sorted(log))
 
1140
1148
    def test_iter_all_entries_empty(self):
 
1141
 
        index = CombinedGraphIndex([])
 
1142
 
        self.assertEqual([], list(index.iter_all_entries()))
 
 
1149
        idx = index.CombinedGraphIndex([])
 
 
1150
        self.assertEqual([], list(idx.iter_all_entries()))
 
1144
1152
    def test_iter_all_entries_children_empty(self):
 
1145
 
        index1 = self.make_index('name')
 
1146
 
        index = CombinedGraphIndex([index1])
 
1147
 
        self.assertEqual([], list(index.iter_all_entries()))
 
 
1153
        idx1 = self.make_index('name')
 
 
1154
        idx = index.CombinedGraphIndex([idx1])
 
 
1155
        self.assertEqual([], list(idx.iter_all_entries()))
 
1149
1157
    def test_iter_all_entries_simple(self):
 
1150
 
        index1 = self.make_index('name', nodes=[(('name', ), 'data', ())])
 
1151
 
        index = CombinedGraphIndex([index1])
 
1152
 
        self.assertEqual([(index1, ('name', ), 'data')],
 
1153
 
            list(index.iter_all_entries()))
 
 
1158
        idx1 = self.make_index('name', nodes=[(('name', ), 'data', ())])
 
 
1159
        idx = index.CombinedGraphIndex([idx1])
 
 
1160
        self.assertEqual([(idx1, ('name', ), 'data')],
 
 
1161
            list(idx.iter_all_entries()))
 
1155
1163
    def test_iter_all_entries_two_indices(self):
 
1156
 
        index1 = self.make_index('name1', nodes=[(('name', ), 'data', ())])
 
1157
 
        index2 = self.make_index('name2', nodes=[(('2', ), '', ())])
 
1158
 
        index = CombinedGraphIndex([index1, index2])
 
1159
 
        self.assertEqual([(index1, ('name', ), 'data'),
 
1160
 
            (index2, ('2', ), '')],
 
1161
 
            list(index.iter_all_entries()))
 
 
1164
        idx1 = self.make_index('name1', nodes=[(('name', ), 'data', ())])
 
 
1165
        idx2 = self.make_index('name2', nodes=[(('2', ), '', ())])
 
 
1166
        idx = index.CombinedGraphIndex([idx1, idx2])
 
 
1167
        self.assertEqual([(idx1, ('name', ), 'data'),
 
 
1168
                          (idx2, ('2', ), '')],
 
 
1169
                         list(idx.iter_all_entries()))
 
1163
1171
    def test_iter_entries_two_indices_dup_key(self):
 
1164
 
        index1 = self.make_index('name1', nodes=[(('name', ), 'data', ())])
 
1165
 
        index2 = self.make_index('name2', nodes=[(('name', ), 'data', ())])
 
1166
 
        index = CombinedGraphIndex([index1, index2])
 
1167
 
        self.assertEqual([(index1, ('name', ), 'data')],
 
1168
 
            list(index.iter_entries([('name', )])))
 
 
1172
        idx1 = self.make_index('name1', nodes=[(('name', ), 'data', ())])
 
 
1173
        idx2 = self.make_index('name2', nodes=[(('name', ), 'data', ())])
 
 
1174
        idx = index.CombinedGraphIndex([idx1, idx2])
 
 
1175
        self.assertEqual([(idx1, ('name', ), 'data')],
 
 
1176
                         list(idx.iter_entries([('name', )])))
 
1170
1178
    def test_iter_all_entries_two_indices_dup_key(self):
 
1171
 
        index1 = self.make_index('name1', nodes=[(('name', ), 'data', ())])
 
1172
 
        index2 = self.make_index('name2', nodes=[(('name', ), 'data', ())])
 
1173
 
        index = CombinedGraphIndex([index1, index2])
 
1174
 
        self.assertEqual([(index1, ('name', ), 'data')],
 
1175
 
            list(index.iter_all_entries()))
 
 
1179
        idx1 = self.make_index('name1', nodes=[(('name', ), 'data', ())])
 
 
1180
        idx2 = self.make_index('name2', nodes=[(('name', ), 'data', ())])
 
 
1181
        idx = index.CombinedGraphIndex([idx1, idx2])
 
 
1182
        self.assertEqual([(idx1, ('name', ), 'data')],
 
 
1183
                         list(idx.iter_all_entries()))
 
1177
1185
    def test_iter_key_prefix_2_key_element_refs(self):
 
1178
 
        index1 = self.make_index('1', 1, key_elements=2, nodes=[
 
1179
 
            (('name', 'fin1'), 'data', ([('ref', 'erence')], ))])
 
1180
 
        index2 = self.make_index('2', 1, key_elements=2, nodes=[
 
1181
 
            (('name', 'fin2'), 'beta', ([], )),
 
1182
 
            (('ref', 'erence'), 'refdata', ([], ))])
 
1183
 
        index = CombinedGraphIndex([index1, index2])
 
1184
 
        self.assertEqual(set([(index1, ('name', 'fin1'), 'data', ((('ref', 'erence'),),)),
 
1185
 
            (index2, ('ref', 'erence'), 'refdata', ((), ))]),
 
1186
 
            set(index.iter_entries_prefix([('name', 'fin1'), ('ref', 'erence')])))
 
1187
 
        self.assertEqual(set([(index1, ('name', 'fin1'), 'data', ((('ref', 'erence'),),)),
 
1188
 
            (index2, ('name', 'fin2'), 'beta', ((), ))]),
 
1189
 
            set(index.iter_entries_prefix([('name', None)])))
 
 
1186
        idx1 = self.make_index('1', 1, key_elements=2, nodes=[
 
 
1187
                (('name', 'fin1'), 'data', ([('ref', 'erence')], ))])
 
 
1188
        idx2 = self.make_index('2', 1, key_elements=2, nodes=[
 
 
1189
                (('name', 'fin2'), 'beta', ([], )),
 
 
1190
                (('ref', 'erence'), 'refdata', ([], ))])
 
 
1191
        idx = index.CombinedGraphIndex([idx1, idx2])
 
 
1192
        self.assertEqual({(idx1, ('name', 'fin1'), 'data',
 
 
1193
                               ((('ref', 'erence'),),)),
 
 
1194
                              (idx2, ('ref', 'erence'), 'refdata', ((), ))},
 
 
1195
                         set(idx.iter_entries_prefix([('name', 'fin1'),
 
 
1196
                                                        ('ref', 'erence')])))
 
 
1197
        self.assertEqual({(idx1, ('name', 'fin1'), 'data',
 
 
1198
                               ((('ref', 'erence'),),)),
 
 
1199
                              (idx2, ('name', 'fin2'), 'beta', ((), ))},
 
 
1200
                         set(idx.iter_entries_prefix([('name', None)])))
 
1191
1202
    def test_iter_nothing_empty(self):
 
1192
 
        index = CombinedGraphIndex([])
 
1193
 
        self.assertEqual([], list(index.iter_entries([])))
 
 
1203
        idx = index.CombinedGraphIndex([])
 
 
1204
        self.assertEqual([], list(idx.iter_entries([])))
 
1195
1206
    def test_iter_nothing_children_empty(self):
 
1196
 
        index1 = self.make_index('name')
 
1197
 
        index = CombinedGraphIndex([index1])
 
1198
 
        self.assertEqual([], list(index.iter_entries([])))
 
 
1207
        idx1 = self.make_index('name')
 
 
1208
        idx = index.CombinedGraphIndex([idx1])
 
 
1209
        self.assertEqual([], list(idx.iter_entries([])))
 
1200
1211
    def test_iter_all_keys(self):
 
1201
 
        index1 = self.make_index('1', 1, nodes=[
 
1202
 
            (('name', ), 'data', ([('ref', )], ))])
 
1203
 
        index2 = self.make_index('2', 1, nodes=[
 
1204
 
            (('ref', ), 'refdata', ((), ))])
 
1205
 
        index = CombinedGraphIndex([index1, index2])
 
1206
 
        self.assertEqual(set([(index1, ('name', ), 'data', ((('ref', ), ), )),
 
1207
 
            (index2, ('ref', ), 'refdata', ((), ))]),
 
1208
 
            set(index.iter_entries([('name', ), ('ref', )])))
 
 
1212
        idx1 = self.make_index('1', 1, nodes=[(('name', ), 'data',
 
 
1214
        idx2 = self.make_index('2', 1, nodes=[(('ref', ), 'refdata', ((), ))])
 
 
1215
        idx = index.CombinedGraphIndex([idx1, idx2])
 
 
1216
        self.assertEqual({(idx1, ('name', ), 'data', ((('ref', ), ), )),
 
 
1217
                              (idx2, ('ref', ), 'refdata', ((), ))},
 
 
1218
                         set(idx.iter_entries([('name', ), ('ref', )])))
 
1210
1220
    def test_iter_all_keys_dup_entry(self):
 
1211
 
        index1 = self.make_index('1', 1, nodes=[
 
1212
 
            (('name', ), 'data', ([('ref', )], )),
 
1213
 
            (('ref', ), 'refdata', ([], ))])
 
1214
 
        index2 = self.make_index('2', 1, nodes=[
 
1215
 
            (('ref', ), 'refdata', ([], ))])
 
1216
 
        index = CombinedGraphIndex([index1, index2])
 
1217
 
        self.assertEqual(set([(index1, ('name', ), 'data', ((('ref',),),)),
 
1218
 
            (index1, ('ref', ), 'refdata', ((), ))]),
 
1219
 
            set(index.iter_entries([('name', ), ('ref', )])))
 
 
1221
        idx1 = self.make_index('1', 1, nodes=[(('name', ), 'data',
 
 
1223
                                                (('ref', ), 'refdata', ([], ))])
 
 
1224
        idx2 = self.make_index('2', 1, nodes=[(('ref', ), 'refdata', ([], ))])
 
 
1225
        idx = index.CombinedGraphIndex([idx1, idx2])
 
 
1226
        self.assertEqual({(idx1, ('name', ), 'data', ((('ref',),),)),
 
 
1227
                              (idx1, ('ref', ), 'refdata', ((), ))},
 
 
1228
                         set(idx.iter_entries([('name', ), ('ref', )])))
 
1221
1230
    def test_iter_missing_entry_empty(self):
 
1222
 
        index = CombinedGraphIndex([])
 
1223
 
        self.assertEqual([], list(index.iter_entries([('a', )])))
 
 
1231
        idx = index.CombinedGraphIndex([])
 
 
1232
        self.assertEqual([], list(idx.iter_entries([('a', )])))
 
1225
1234
    def test_iter_missing_entry_one_index(self):
 
1226
 
        index1 = self.make_index('1')
 
1227
 
        index = CombinedGraphIndex([index1])
 
1228
 
        self.assertEqual([], list(index.iter_entries([('a', )])))
 
 
1235
        idx1 = self.make_index('1')
 
 
1236
        idx = index.CombinedGraphIndex([idx1])
 
 
1237
        self.assertEqual([], list(idx.iter_entries([('a', )])))
 
1230
1239
    def test_iter_missing_entry_two_index(self):
 
1231
 
        index1 = self.make_index('1')
 
1232
 
        index2 = self.make_index('2')
 
1233
 
        index = CombinedGraphIndex([index1, index2])
 
1234
 
        self.assertEqual([], list(index.iter_entries([('a', )])))
 
 
1240
        idx1 = self.make_index('1')
 
 
1241
        idx2 = self.make_index('2')
 
 
1242
        idx = index.CombinedGraphIndex([idx1, idx2])
 
 
1243
        self.assertEqual([], list(idx.iter_entries([('a', )])))
 
1236
1245
    def test_iter_entry_present_one_index_only(self):
 
1237
 
        index1 = self.make_index('1', nodes=[(('key', ), '', ())])
 
1238
 
        index2 = self.make_index('2', nodes=[])
 
1239
 
        index = CombinedGraphIndex([index1, index2])
 
1240
 
        self.assertEqual([(index1, ('key', ), '')],
 
1241
 
            list(index.iter_entries([('key', )])))
 
 
1246
        idx1 = self.make_index('1', nodes=[(('key', ), '', ())])
 
 
1247
        idx2 = self.make_index('2', nodes=[])
 
 
1248
        idx = index.CombinedGraphIndex([idx1, idx2])
 
 
1249
        self.assertEqual([(idx1, ('key', ), '')],
 
 
1250
                         list(idx.iter_entries([('key', )])))
 
1242
1251
        # and in the other direction
 
1243
 
        index = CombinedGraphIndex([index2, index1])
 
1244
 
        self.assertEqual([(index1, ('key', ), '')],
 
1245
 
            list(index.iter_entries([('key', )])))
 
 
1252
        idx = index.CombinedGraphIndex([idx2, idx1])
 
 
1253
        self.assertEqual([(idx1, ('key', ), '')],
 
 
1254
                         list(idx.iter_entries([('key', )])))
 
1247
1256
    def test_key_count_empty(self):
 
1248
 
        index1 = self.make_index('1', nodes=[])
 
1249
 
        index2 = self.make_index('2', nodes=[])
 
1250
 
        index = CombinedGraphIndex([index1, index2])
 
1251
 
        self.assertEqual(0, index.key_count())
 
 
1257
        idx1 = self.make_index('1', nodes=[])
 
 
1258
        idx2 = self.make_index('2', nodes=[])
 
 
1259
        idx = index.CombinedGraphIndex([idx1, idx2])
 
 
1260
        self.assertEqual(0, idx.key_count())
 
1253
1262
    def test_key_count_sums_index_keys(self):
 
1254
 
        index1 = self.make_index('1', nodes=[
 
 
1263
        idx1 = self.make_index('1', nodes=[
 
1255
1264
            (('1',), '', ()),
 
1256
1265
            (('2',), '', ())])
 
1257
 
        index2 = self.make_index('2', nodes=[(('1',), '', ())])
 
1258
 
        index = CombinedGraphIndex([index1, index2])
 
1259
 
        self.assertEqual(3, index.key_count())
 
 
1266
        idx2 = self.make_index('2', nodes=[(('1',), '', ())])
 
 
1267
        idx = index.CombinedGraphIndex([idx1, idx2])
 
 
1268
        self.assertEqual(3, idx.key_count())
 
1261
1270
    def test_validate_bad_child_index_errors(self):
 
1262
1271
        trans = self.get_transport()
 
1263
1272
        trans.put_bytes('name', "not an index\n")
 
1264
 
        index1 = GraphIndex(trans, 'name', 13)
 
1265
 
        index = CombinedGraphIndex([index1])
 
1266
 
        self.assertRaises(errors.BadIndexFormatSignature, index.validate)
 
 
1273
        idx1 = index.GraphIndex(trans, 'name', 13)
 
 
1274
        idx = index.CombinedGraphIndex([idx1])
 
 
1275
        self.assertRaises(errors.BadIndexFormatSignature, idx.validate)
 
1268
1277
    def test_validate_empty(self):
 
1269
 
        index = CombinedGraphIndex([])
 
 
1278
        idx = index.CombinedGraphIndex([])
 
1272
1281
    def test_key_count_reloads(self):
 
1273
 
        index, reload_counter = self.make_combined_index_with_missing()
 
1274
 
        self.assertEqual(2, index.key_count())
 
 
1282
        idx, reload_counter = self.make_combined_index_with_missing()
 
 
1283
        self.assertEqual(2, idx.key_count())
 
1275
1284
        self.assertEqual([1, 1, 0], reload_counter)
 
1277
1286
    def test_key_count_no_reload(self):
 
1278
 
        index, reload_counter = self.make_combined_index_with_missing()
 
1279
 
        index._reload_func = None
 
 
1287
        idx, reload_counter = self.make_combined_index_with_missing()
 
 
1288
        idx._reload_func = None
 
1280
1289
        # Without a _reload_func we just raise the exception
 
1281
 
        self.assertRaises(errors.NoSuchFile, index.key_count)
 
 
1290
        self.assertRaises(errors.NoSuchFile, idx.key_count)
 
1283
1292
    def test_key_count_reloads_and_fails(self):
 
1284
1293
        # We have deleted all underlying indexes, so we will try to reload, but
 
1285
1294
        # still fail. This is mostly to test we don't get stuck in an infinite
 
1286
1295
        # loop trying to reload
 
1287
 
        index, reload_counter = self.make_combined_index_with_missing(
 
1289
 
        self.assertRaises(errors.NoSuchFile, index.key_count)
 
 
1296
        idx, reload_counter = self.make_combined_index_with_missing(
 
 
1298
        self.assertRaises(errors.NoSuchFile, idx.key_count)
 
1290
1299
        self.assertEqual([2, 1, 1], reload_counter)
 
1292
1301
    def test_iter_entries_reloads(self):