aboutsummaryrefslogtreecommitdiffstats
path: root/plumbing
diff options
context:
space:
mode:
authorMáximo Cuadros <mcuadros@gmail.com>2017-07-28 18:45:18 +0200
committerGitHub <noreply@github.com>2017-07-28 18:45:18 +0200
commite4a931cc533f743368e4c77aeb718272e1fad777 (patch)
tree501339c0f099e4daa674caf49cfe642593b8aced /plumbing
parent86f33ed017b55898758bf8900a085f355b2793d0 (diff)
parenta9c3fdc8d70e580173ef21f5c3def8eeca35dcd7 (diff)
downloadgo-git-e4a931cc533f743368e4c77aeb718272e1fad777.tar.gz
Merge pull request #516 from smola/revlist-perf
revlist: ignore all objects reachable from ignored objects
Diffstat (limited to 'plumbing')
-rw-r--r--plumbing/revlist/revlist.go29
1 files changed, 28 insertions, 1 deletions
diff --git a/plumbing/revlist/revlist.go b/plumbing/revlist/revlist.go
index 1bda2fa..f56cf28 100644
--- a/plumbing/revlist/revlist.go
+++ b/plumbing/revlist/revlist.go
@@ -16,7 +16,26 @@ import (
// the reachable objects from the given objects. Ignore param are object hashes
// that we want to ignore on the result. All that objects must be accessible
// from the object storer.
-func Objects(s storer.EncodedObjectStorer, objects, ignore []plumbing.Hash) ([]plumbing.Hash, error) {
+func Objects(
+ s storer.EncodedObjectStorer,
+ objs,
+ ignore []plumbing.Hash,
+) ([]plumbing.Hash, error) {
+ ignore, err := objects(s, ignore, nil, true)
+ if err != nil {
+ return nil, err
+ }
+
+ return objects(s, objs, ignore, false)
+}
+
+func objects(
+ s storer.EncodedObjectStorer,
+ objects,
+ ignore []plumbing.Hash,
+ allowMissingObjects bool,
+) ([]plumbing.Hash, error) {
+
seen := hashListToSet(ignore)
result := make(map[plumbing.Hash]bool)
@@ -29,6 +48,10 @@ func Objects(s storer.EncodedObjectStorer, objects, ignore []plumbing.Hash) ([]p
for _, h := range objects {
if err := processObject(s, h, seen, ignore, walkerFunc); err != nil {
+ if allowMissingObjects && err == plumbing.ErrObjectNotFound {
+ continue
+ }
+
return nil, err
}
}
@@ -44,6 +67,10 @@ func processObject(
ignore []plumbing.Hash,
walkerFunc func(h plumbing.Hash),
) error {
+ if seen[h] {
+ return nil
+ }
+
o, err := s.EncodedObject(plumbing.AnyObject, h)
if err != nil {
return err