/brz/remove-bazaar

To get this branch, use:
bzr branch http://gegoxaren.bato24.eu/bzr/brz/remove-bazaar

« back to all changes in this revision

Viewing changes to breezy/plugins/git/interrepo.py

Merge test-run support.

Show diffs side-by-side

added added

removed removed

Lines of Context:
31
31
    CAPABILITY_THIN_PACK,
32
32
    ZERO_SHA,
33
33
    )
34
 
from dulwich.refs import (
35
 
    ANNOTATED_TAG_SUFFIX,
36
 
    SYMREF,
37
 
    )
 
34
from dulwich.refs import SYMREF
38
35
from dulwich.walk import Walker
39
36
 
40
 
from ..errors import (
 
37
from ...errors import (
41
38
    DivergedBranches,
42
39
    FetchLimitUnsupported,
43
40
    InvalidRevisionId,
45
42
    NoRoundtrippingSupport,
46
43
    NoSuchRevision,
47
44
    )
48
 
from ..repository import (
49
 
    FetchResult,
 
45
from ...repository import (
50
46
    InterRepository,
51
47
    )
52
 
from ..revision import (
 
48
from ...revision import (
53
49
    NULL_REVISION,
54
50
    )
55
 
from ..sixish import (
56
 
    viewitems,
57
 
    viewvalues,
58
 
    )
59
 
from .. import (
 
51
from ... import (
60
52
    config,
61
53
    trace,
62
54
    ui,
63
55
    )
 
56
from ...sixish import viewvalues
64
57
 
65
58
from .errors import (
66
59
    NoPushSupport,
80
73
    remote_divergence,
81
74
    )
82
75
from .refs import (
 
76
    get_refs_container,
83
77
    is_tag,
84
 
    ref_to_tag_name,
85
78
    )
86
79
from .repository import (
87
80
    GitRepository,
127
120
        raise NotImplementedError(self.fetch_refs)
128
121
 
129
122
    def search_missing_revision_ids(self,
130
 
                                    find_ghosts=True, revision_ids=None,
131
 
                                    if_present_ids=None, limit=None):
 
123
            find_ghosts=True, revision_ids=None, if_present_ids=None,
 
124
            limit=None):
132
125
        if limit is not None:
133
126
            raise FetchLimitUnsupported(self)
134
127
        git_shas = []
146
139
                except KeyError:
147
140
                    raise NoSuchRevision(revid, self.source)
148
141
                git_shas.append(git_sha)
149
 
            walker = Walker(
150
 
                self.source_store,
151
 
                include=git_shas,
152
 
                exclude=[
 
142
            walker = Walker(self.source_store,
 
143
                include=git_shas, exclude=[
153
144
                    sha for sha in self.target.controldir.get_refs_container().as_dict().values()
154
145
                    if sha != ZERO_SHA])
155
146
            missing_revids = set()
156
147
            for entry in walker:
157
 
                for (kind, type_data) in self.source_store.lookup_git_sha(
158
 
                        entry.commit.id):
 
148
                for (kind, type_data) in self.source_store.lookup_git_sha(entry.commit.id):
159
149
                    if kind == "commit":
160
150
                        missing_revids.add(type_data[0])
161
151
            return self.source.revision_ids_to_search_result(missing_revids)
218
208
                stop_revids.append(revid)
219
209
        missing = set()
220
210
        graph = self.source.get_graph()
221
 
        with ui.ui_factory.nested_progress_bar() as pb:
 
211
        pb = ui.ui_factory.nested_progress_bar()
 
212
        try:
222
213
            while stop_revids:
223
214
                new_stop_revids = []
224
215
                for revid in stop_revids:
225
216
                    sha1 = revid_sha_map.get(revid)
226
 
                    if (revid not in missing and
227
 
                            self._revision_needs_fetching(sha1, revid)):
 
217
                    if (not revid in missing and
 
218
                        self._revision_needs_fetching(sha1, revid)):
228
219
                        missing.add(revid)
229
220
                        new_stop_revids.append(revid)
230
221
                stop_revids = set()
231
222
                parent_map = graph.get_parent_map(new_stop_revids)
232
 
                for parent_revids in viewvalues(parent_map):
 
223
                for parent_revids in parent_map.itervalues():
233
224
                    stop_revids.update(parent_revids)
234
225
                pb.update("determining revisions to fetch", len(missing))
 
226
        finally:
 
227
            pb.finished()
235
228
        return graph.iter_topo_order(missing)
236
229
 
237
230
    def _get_target_bzr_refs(self):
241
234
            with Git SHA, Bazaar revid as values.
242
235
        """
243
236
        bzr_refs = {}
 
237
        refs = {}
244
238
        for k in self.target._git.refs.allkeys():
245
239
            try:
246
240
                v = self.target._git.refs.read_ref(k)
250
244
            revid = None
251
245
            if not v.startswith(SYMREF):
252
246
                try:
253
 
                    for (kind, type_data) in self.source_store.lookup_git_sha(
254
 
                            v):
255
 
                        if kind == "commit" and self.source.has_revision(
256
 
                                type_data[0]):
 
247
                    for (kind, type_data) in self.source_store.lookup_git_sha(v):
 
248
                        if kind == "commit" and self.source.has_revision(type_data[0]):
257
249
                            revid = type_data[0]
258
250
                            break
259
251
                except KeyError:
263
255
 
264
256
    def fetch_refs(self, update_refs, lossy, overwrite=False):
265
257
        self._warn_slow()
266
 
        result_refs = {}
267
258
        with self.source_store.lock_read():
268
259
            old_refs = self._get_target_bzr_refs()
269
260
            new_refs = update_refs(old_refs)
270
261
            revidmap = self.fetch_objects(
271
 
                [(git_sha, bzr_revid)
272
 
                 for (git_sha, bzr_revid) in new_refs.values()
273
 
                 if git_sha is None or not git_sha.startswith(SYMREF)],
274
 
                lossy=lossy)
275
 
            for name, (gitid, revid) in viewitems(new_refs):
 
262
                [(git_sha, bzr_revid) for (git_sha, bzr_revid) in new_refs.values() if git_sha is None or not git_sha.startswith(SYMREF)], lossy=lossy)
 
263
            for name, (gitid, revid) in new_refs.iteritems():
276
264
                if gitid is None:
277
265
                    try:
278
266
                        gitid = revidmap[revid][0]
279
267
                    except KeyError:
280
268
                        gitid = self.source_store._lookup_revision_sha1(revid)
281
269
                if gitid.startswith(SYMREF):
282
 
                    self.target_refs.set_symbolic_ref(
283
 
                        name, gitid[len(SYMREF):])
 
270
                    self.target_refs.set_symbolic_ref(name, gitid[len(SYMREF):])
284
271
                else:
285
272
                    try:
286
273
                        old_git_id = old_refs[name][0]
288
275
                        self.target_refs.add_if_new(name, gitid)
289
276
                    else:
290
277
                        self.target_refs.set_if_equals(name, old_git_id, gitid)
291
 
                    result_refs[name] = (gitid, revid if not lossy else self.mapping.revision_id_foreign_to_bzr(gitid))
292
 
        return revidmap, old_refs, result_refs
 
278
        return revidmap, old_refs, new_refs
293
279
 
294
280
    def fetch_objects(self, revs, lossy, limit=None):
295
281
        if not lossy and not self.mapping.roundtripping:
296
282
            for git_sha, bzr_revid in revs:
297
 
                if (bzr_revid is not None and
298
 
                        needs_roundtripping(self.source, bzr_revid)):
 
283
                if bzr_revid is not None and needs_roundtripping(self.source, bzr_revid):
299
284
                    raise NoPushSupport(self.source, self.target, self.mapping,
300
285
                                        bzr_revid)
301
286
        with self.source_store.lock_read():
302
287
            todo = list(self.missing_revisions(revs))[:limit]
303
288
            revidmap = {}
304
 
            with ui.ui_factory.nested_progress_bar() as pb:
 
289
            pb = ui.ui_factory.nested_progress_bar()
 
290
            try:
305
291
                object_generator = MissingObjectsIterator(
306
292
                    self.source_store, self.source, pb)
307
293
                for (old_revid, git_sha) in object_generator.import_revisions(
308
 
                        todo, lossy=lossy):
 
294
                    todo, lossy=lossy):
309
295
                    if lossy:
310
 
                        new_revid = self.mapping.revision_id_foreign_to_bzr(
311
 
                            git_sha)
 
296
                        new_revid = self.mapping.revision_id_foreign_to_bzr(git_sha)
312
297
                    else:
313
298
                        new_revid = old_revid
314
299
                        try:
319
304
                    revidmap[old_revid] = (git_sha, new_revid)
320
305
                self.target_store.add_objects(object_generator)
321
306
                return revidmap
 
307
            finally:
 
308
                pb.finished()
322
309
 
323
310
    def fetch(self, revision_id=None, pb=None, find_ghosts=False,
324
 
              fetch_spec=None, mapped_refs=None, lossy=False):
 
311
            fetch_spec=None, mapped_refs=None):
325
312
        if mapped_refs is not None:
326
313
            stop_revisions = mapped_refs
327
314
        elif revision_id is not None:
331
318
            if recipe[0] in ("search", "proxy-search"):
332
319
                stop_revisions = [(None, revid) for revid in recipe[1]]
333
320
            else:
334
 
                raise AssertionError(
335
 
                    "Unsupported search result type %s" % recipe[0])
 
321
                raise AssertionError("Unsupported search result type %s" % recipe[0])
336
322
        else:
337
 
            stop_revisions = [(None, revid)
338
 
                              for revid in self.source.all_revision_ids()]
 
323
            stop_revisions = [(None, revid) for revid in self.source.all_revision_ids()]
339
324
        self._warn_slow()
340
325
        try:
341
 
            revidmap = self.fetch_objects(stop_revisions, lossy=lossy)
 
326
            self.fetch_objects(stop_revisions, lossy=False)
342
327
        except NoPushSupport:
343
328
            raise NoRoundtrippingSupport(self.source, self.target)
344
 
        return FetchResult(revidmap)
345
329
 
346
330
    @staticmethod
347
331
    def is_compatible(source, target):
358
342
            raise NoPushSupport(self.source, self.target, self.mapping)
359
343
        unpeel_map = UnpeelMap.from_repository(self.source)
360
344
        revidmap = {}
361
 
 
362
 
        def git_update_refs(old_refs):
 
345
        def determine_wants(old_refs):
363
346
            ret = {}
364
 
            self.old_refs = {
365
 
                k: (v, None) for (k, v) in viewitems(old_refs)}
366
 
            new_refs = update_refs(self.old_refs)
367
 
            for name, (gitid, revid) in viewitems(new_refs):
 
347
            self.old_refs = dict([(k, (v, None)) for (k, v) in old_refs.iteritems()])
 
348
            self.new_refs = update_refs(self.old_refs)
 
349
            for name, (gitid, revid) in self.new_refs.iteritems():
368
350
                if gitid is None:
369
351
                    git_sha = self.source_store._lookup_revision_sha1(revid)
370
 
                    gitid = unpeel_map.re_unpeel_tag(
371
 
                        git_sha, old_refs.get(name))
 
352
                    gitid = unpeel_map.re_unpeel_tag(git_sha, old_refs.get(name))
372
353
                if not overwrite:
373
 
                    if remote_divergence(
374
 
                            old_refs.get(name), gitid, self.source_store):
 
354
                    if remote_divergence(old_refs.get(name), gitid, self.source_store):
375
355
                        raise DivergedBranches(self.source, self.target)
376
356
                ret[name] = gitid
377
357
            return ret
378
358
        self._warn_slow()
379
359
        with self.source_store.lock_read():
380
 
            new_refs = self.target.send_pack(
381
 
                git_update_refs, self.source_store.generate_lossy_pack_data)
 
360
            new_refs = self.target.send_pack(determine_wants,
 
361
                    self.source_store.generate_lossy_pack_data)
382
362
        # FIXME: revidmap?
383
 
        return revidmap, self.old_refs, new_refs
 
363
        return revidmap, self.old_refs, self.new_refs
384
364
 
385
365
    @staticmethod
386
366
    def is_compatible(source, target):
410
390
    def _target_has_shas(self, shas):
411
391
        raise NotImplementedError(self._target_has_shas)
412
392
 
413
 
    def get_determine_wants_heads(self, wants, include_tags=False, tag_selector=None):
 
393
    def get_determine_wants_heads(self, wants, include_tags=False):
414
394
        wants = set(wants)
415
 
 
416
395
        def determine_wants(refs):
417
 
            unpeel_lookup = {}
418
 
            for k, v in viewitems(refs):
419
 
                if k.endswith(ANNOTATED_TAG_SUFFIX):
420
 
                    unpeel_lookup[v] = refs[k[:-len(ANNOTATED_TAG_SUFFIX)]]
421
 
            potential = set([unpeel_lookup.get(w, w) for w in wants])
 
396
            potential = set(wants)
422
397
            if include_tags:
423
 
                for k, sha in viewitems(refs):
424
 
                    if k.endswith(ANNOTATED_TAG_SUFFIX):
425
 
                        continue
426
 
                    try:
427
 
                        tag_name = ref_to_tag_name(k)
428
 
                    except ValueError:
429
 
                        continue
430
 
                    if tag_selector and not tag_selector(tag_name):
431
 
                        continue
432
 
                    if sha == ZERO_SHA:
433
 
                        continue
434
 
                    potential.add(sha)
 
398
                for k, unpeeled in refs.iteritems():
 
399
                    if k.endswith("^{}"):
 
400
                        continue
 
401
                    if not is_tag(k):
 
402
                        continue
 
403
                    if unpeeled == ZERO_SHA:
 
404
                        continue
 
405
                    potential.add(unpeeled)
435
406
            return list(potential - self._target_has_shas(potential))
436
407
        return determine_wants
437
408
 
447
418
        self.fetch(revision_id, find_ghosts=False)
448
419
 
449
420
    def search_missing_revision_ids(self,
450
 
                                    find_ghosts=True, revision_ids=None,
451
 
                                    if_present_ids=None, limit=None):
 
421
            find_ghosts=True, revision_ids=None, if_present_ids=None,
 
422
            limit=None):
452
423
        if limit is not None:
453
424
            raise FetchLimitUnsupported(self)
454
425
        if revision_ids is None and if_present_ids is None:
489
460
 
490
461
    def determine_wants_all(self, refs):
491
462
        potential = set()
492
 
        for k, v in viewitems(refs):
 
463
        for k, v in refs.iteritems():
493
464
            # For non-git target repositories, only worry about peeled
494
465
            if v == ZERO_SHA:
495
466
                continue
496
467
            potential.add(self.source.controldir.get_peeled(k) or v)
497
468
        return list(potential - self._target_has_shas(potential))
498
469
 
 
470
    def get_determine_wants_heads(self, wants, include_tags=False):
 
471
        wants = set(wants)
 
472
        def determine_wants(refs):
 
473
            potential = set(wants)
 
474
            if include_tags:
 
475
                for k, unpeeled in refs.iteritems():
 
476
                    if not is_tag(k):
 
477
                        continue
 
478
                    if unpeeled == ZERO_SHA:
 
479
                        continue
 
480
                    potential.add(self.source.controldir.get_peeled(k) or unpeeled)
 
481
            return list(potential - self._target_has_shas(potential))
 
482
        return determine_wants
 
483
 
499
484
    def _warn_slow(self):
500
485
        if not config.GlobalConfig().suppress_warning('slow_intervcs_push'):
501
486
            trace.warning(
508
493
        :param determine_wants: determine_wants callback
509
494
        :param mapping: BzrGitMapping to use
510
495
        :param limit: Maximum number of commits to import.
511
 
        :return: Tuple with pack hint, last imported revision id and remote
512
 
            refs
 
496
        :return: Tuple with pack hint, last imported revision id and remote refs
513
497
        """
514
498
        raise NotImplementedError(self.fetch_objects)
515
499
 
516
 
    def get_determine_wants_revids(self, revids, include_tags=False, tag_selector=None):
 
500
    def get_determine_wants_revids(self, revids, include_tags=False):
517
501
        wants = set()
518
502
        for revid in set(revids):
519
503
            if self.target.has_revision(revid):
520
504
                continue
521
505
            git_sha, mapping = self.source.lookup_bzr_revision_id(revid)
522
506
            wants.add(git_sha)
523
 
        return self.get_determine_wants_heads(
524
 
            wants, include_tags=include_tags, tag_selector=tag_selector)
 
507
        return self.get_determine_wants_heads(wants, include_tags=include_tags)
525
508
 
526
509
    def fetch(self, revision_id=None, find_ghosts=False,
527
 
              mapping=None, fetch_spec=None, include_tags=False, lossy=False):
 
510
              mapping=None, fetch_spec=None, include_tags=False):
528
511
        if mapping is None:
529
512
            mapping = self.source.get_mapping()
530
513
        if revision_id is not None:
535
518
                interesting_heads = recipe[1]
536
519
            else:
537
520
                raise AssertionError("Unsupported search result type %s" %
538
 
                                     recipe[0])
 
521
                        recipe[0])
539
522
        else:
540
523
            interesting_heads = None
541
524
 
545
528
        else:
546
529
            determine_wants = self.determine_wants_all
547
530
 
548
 
        (pack_hint, _, remote_refs) = self.fetch_objects(
549
 
            determine_wants, mapping, lossy=lossy)
 
531
        (pack_hint, _, remote_refs) = self.fetch_objects(determine_wants,
 
532
            mapping)
550
533
        if pack_hint is not None and self.target._format.pack_compresses:
551
534
            self.target.pack(hint=pack_hint)
552
 
        result = FetchResult()
553
 
        result.refs = remote_refs
554
 
        return result
 
535
        return remote_refs
555
536
 
556
537
 
557
538
class InterRemoteGitNonGitRepository(InterGitNonGitRepository):
563
544
        all_revs = self.target.all_revision_ids()
564
545
        parent_map = self.target.get_parent_map(all_revs)
565
546
        all_parents = set()
566
 
        for values in viewvalues(parent_map):
567
 
            all_parents.update(values)
 
547
        map(all_parents.update, parent_map.itervalues())
568
548
        return set(all_revs) - all_parents
569
549
 
570
550
    def fetch_objects(self, determine_wants, mapping, limit=None, lossy=False):
578
558
                lambda sha: store[sha].parents)
579
559
            wants_recorder = DetermineWantsRecorder(determine_wants)
580
560
 
581
 
            with ui.ui_factory.nested_progress_bar() as pb:
 
561
            pb = ui.ui_factory.nested_progress_bar()
 
562
            try:
582
563
                objects_iter = self.source.fetch_objects(
583
564
                    wants_recorder, graph_walker, store.get_raw)
584
565
                trace.mutter("Importing %d new revisions",
585
566
                             len(wants_recorder.wants))
586
 
                (pack_hint, last_rev) = import_git_objects(
587
 
                    self.target, mapping, objects_iter, store,
588
 
                    wants_recorder.wants, pb, limit)
 
567
                (pack_hint, last_rev) = import_git_objects(self.target,
 
568
                    mapping, objects_iter, store, wants_recorder.wants, pb,
 
569
                    limit)
589
570
                return (pack_hint, last_rev, wants_recorder.remote_refs)
 
571
            finally:
 
572
                pb.finished()
590
573
 
591
574
    @staticmethod
592
575
    def is_compatible(source, target):
611
594
        self._warn_slow()
612
595
        remote_refs = self.source.controldir.get_refs_container().as_dict()
613
596
        wants = determine_wants(remote_refs)
 
597
        create_pb = None
 
598
        pb = ui.ui_factory.nested_progress_bar()
614
599
        target_git_object_retriever = get_object_store(self.target, mapping)
615
 
        with ui.ui_factory.nested_progress_bar() as pb:
 
600
        try:
616
601
            target_git_object_retriever.lock_write()
617
602
            try:
618
 
                (pack_hint, last_rev) = import_git_objects(
619
 
                    self.target, mapping, self.source._git.object_store,
 
603
                (pack_hint, last_rev) = import_git_objects(self.target,
 
604
                    mapping, self.source._git.object_store,
620
605
                    target_git_object_retriever, wants, pb, limit)
621
606
                return (pack_hint, last_rev, remote_refs)
622
607
            finally:
623
608
                target_git_object_retriever.unlock()
 
609
        finally:
 
610
            pb.finished()
624
611
 
625
612
    @staticmethod
626
613
    def is_compatible(source, target):
644
631
            raise LossyPushToSameVCS(self.source, self.target)
645
632
        old_refs = self.target.controldir.get_refs_container()
646
633
        ref_changes = {}
647
 
 
648
634
        def determine_wants(heads):
649
 
            old_refs = dict([(k, (v, None))
650
 
                             for (k, v) in viewitems(heads.as_dict())])
 
635
            old_refs = dict([(k, (v, None)) for (k, v) in heads.as_dict().iteritems()])
651
636
            new_refs = update_refs(old_refs)
652
637
            ref_changes.update(new_refs)
653
 
            return [sha1 for (sha1, bzr_revid) in viewvalues(new_refs)]
 
638
            return [sha1 for (sha1, bzr_revid) in new_refs.itervalues()]
654
639
        self.fetch_objects(determine_wants, lossy=lossy)
655
 
        for k, (git_sha, bzr_revid) in viewitems(ref_changes):
 
640
        for k, (git_sha, bzr_revid) in ref_changes.iteritems():
656
641
            self.target._git.refs[k] = git_sha
657
642
        new_refs = self.target.controldir.get_refs_container()
658
643
        return None, old_refs, new_refs
659
644
 
660
 
    def fetch_objects(self, determine_wants, mapping=None, limit=None,
661
 
                      lossy=False):
 
645
    def fetch_objects(self, determine_wants, mapping=None, limit=None, lossy=False):
662
646
        raise NotImplementedError(self.fetch_objects)
663
647
 
664
648
    def _target_has_shas(self, shas):
665
 
        return set(
666
 
            [sha for sha in shas if sha in self.target._git.object_store])
 
649
        return set([sha for sha in shas if sha in self.target._git.object_store])
667
650
 
668
651
    def fetch(self, revision_id=None, find_ghosts=False,
669
 
              mapping=None, fetch_spec=None, branches=None, limit=None,
670
 
              include_tags=False, lossy=False):
 
652
              mapping=None, fetch_spec=None, branches=None, limit=None, include_tags=False):
671
653
        if mapping is None:
672
654
            mapping = self.source.get_mapping()
673
655
        if revision_id is not None:
681
663
                    "Unsupported search result type %s" % recipe[0])
682
664
            args = heads
683
665
        if branches is not None:
684
 
            determine_wants = self.get_determine_wants_branches(
685
 
                branches, include_tags=include_tags)
 
666
            def determine_wants(refs):
 
667
                ret = []
 
668
                for name, value in refs.iteritems():
 
669
                    if value == ZERO_SHA:
 
670
                        continue
 
671
 
 
672
                    if name in branches or (include_tags and is_tag(name)):
 
673
                        ret.append(value)
 
674
                return ret
686
675
        elif fetch_spec is None and revision_id is None:
687
676
            determine_wants = self.determine_wants_all
688
677
        else:
689
 
            determine_wants = self.get_determine_wants_revids(
690
 
                args, include_tags=include_tags)
 
678
            determine_wants = self.get_determine_wants_revids(args, include_tags=include_tags)
691
679
        wants_recorder = DetermineWantsRecorder(determine_wants)
692
 
        self.fetch_objects(wants_recorder, mapping, limit=limit, lossy=lossy)
693
 
        result = FetchResult()
694
 
        result.refs = wants_recorder.remote_refs
695
 
        return result
 
680
        self.fetch_objects(wants_recorder, mapping, limit=limit)
 
681
        return wants_recorder.remote_refs
696
682
 
697
 
    def get_determine_wants_revids(self, revids, include_tags=False, tag_selector=None):
 
683
    def get_determine_wants_revids(self, revids, include_tags=False):
698
684
        wants = set()
699
685
        for revid in set(revids):
700
686
            if revid == NULL_REVISION:
701
687
                continue
702
688
            git_sha, mapping = self.source.lookup_bzr_revision_id(revid)
703
689
            wants.add(git_sha)
704
 
        return self.get_determine_wants_heads(wants, include_tags=include_tags, tag_selector=tag_selector)
705
 
 
706
 
    def get_determine_wants_branches(self, branches, include_tags=False):
707
 
        def determine_wants(refs):
708
 
            ret = []
709
 
            for name, value in viewitems(refs):
710
 
                if value == ZERO_SHA:
711
 
                    continue
712
 
 
713
 
                if name.endswith(ANNOTATED_TAG_SUFFIX):
714
 
                    continue
715
 
 
716
 
                if name in branches or (include_tags and is_tag(name)):
717
 
                    ret.append(value)
718
 
            return ret
719
 
        return determine_wants
 
690
        return self.get_determine_wants_heads(wants, include_tags=include_tags)
720
691
 
721
692
    def determine_wants_all(self, refs):
722
 
        potential = set([
723
 
            v for k, v in refs.items()
724
 
            if not v == ZERO_SHA and not k.endswith(ANNOTATED_TAG_SUFFIX)])
 
693
        potential = set([v for v in refs.values() if not v == ZERO_SHA])
725
694
        return list(potential - self._target_has_shas(potential))
726
695
 
727
696
 
728
697
class InterLocalGitLocalGitRepository(InterGitGitRepository):
729
698
 
730
 
    def fetch_objects(self, determine_wants, mapping=None, limit=None,
731
 
                      lossy=False):
 
699
    def fetch_objects(self, determine_wants, mapping=None, limit=None, lossy=False):
732
700
        if lossy:
733
701
            raise LossyPushToSameVCS(self.source, self.target)
734
702
        if limit is not None:
735
703
            raise FetchLimitUnsupported(self)
736
 
        from .remote import DefaultProgressReporter
737
 
        with ui.ui_factory.nested_progress_bar() as pb:
738
 
            progress = DefaultProgressReporter(pb).progress
739
 
            refs = self.source._git.fetch(
740
 
                self.target._git, determine_wants,
741
 
                progress=progress)
 
704
        refs = self.source._git.fetch(self.target._git, determine_wants)
742
705
        return (None, None, refs)
743
706
 
744
707
    @staticmethod
750
713
 
751
714
class InterRemoteGitLocalGitRepository(InterGitGitRepository):
752
715
 
753
 
    def fetch_objects(self, determine_wants, mapping=None, limit=None,
754
 
                      lossy=False):
 
716
    def fetch_objects(self, determine_wants, mapping=None, limit=None, lossy=False):
755
717
        if lossy:
756
718
            raise LossyPushToSameVCS(self.source, self.target)
757
719
        if limit is not None:
758
720
            raise FetchLimitUnsupported(self)
759
721
        graphwalker = self.target._git.get_graph_walker()
760
 
        if (CAPABILITY_THIN_PACK in
761
 
                self.source.controldir._client._fetch_capabilities):
 
722
        if CAPABILITY_THIN_PACK in self.source.controldir._client._fetch_capabilities:
762
723
            # TODO(jelmer): Avoid reading entire file into memory and
763
724
            # only processing it after the whole file has been fetched.
764
725
            f = BytesIO()