aboutsummaryrefslogtreecommitdiffstats
path: root/storage
diff options
context:
space:
mode:
authorPaulo Gomes <pjbgf@linux.com>2023-05-04 22:38:41 +0100
committerGitHub <noreply@github.com>2023-05-04 22:38:41 +0100
commit2f3db9de0c31de26303eb389b3f3133f7aa67a04 (patch)
treea3886211d04192124377ae2b03760d02acb3202e /storage
parent191f4ba946c768221dd914fcf0675572fc36c55d (diff)
parent7d183c99d041ecf5f98d6b4c7eb25449e21a5153 (diff)
downloadgo-git-2f3db9de0c31de26303eb389b3f3133f7aa67a04.tar.gz
Merge pull request #722 from AriehSchneier/populate-index
storage: filesystem, Populate index before use. Fixes #148
Diffstat (limited to 'storage')
-rw-r--r--storage/filesystem/object.go10
-rw-r--r--storage/filesystem/object_test.go15
2 files changed, 25 insertions, 0 deletions
diff --git a/storage/filesystem/object.go b/storage/filesystem/object.go
index 21667fa..846a7b8 100644
--- a/storage/filesystem/object.go
+++ b/storage/filesystem/object.go
@@ -537,14 +537,21 @@ func (s *ObjectStorage) findObjectInPackfile(h plumbing.Hash) (plumbing.Hash, pl
return plumbing.ZeroHash, plumbing.ZeroHash, -1
}
+// HashesWithPrefix returns all objects with a hash that starts with a prefix by searching for
+// them in the packfile and the git object directories.
func (s *ObjectStorage) HashesWithPrefix(prefix []byte) ([]plumbing.Hash, error) {
hashes, err := s.dir.ObjectsWithPrefix(prefix)
if err != nil {
return nil, err
}
+ seen := hashListAsMap(hashes)
+
// TODO: This could be faster with some idxfile changes,
// or diving into the packfile.
+ if err := s.requireIndex(); err != nil {
+ return nil, err
+ }
for _, index := range s.index {
ei, err := index.Entries()
if err != nil {
@@ -558,6 +565,9 @@ func (s *ObjectStorage) HashesWithPrefix(prefix []byte) ([]plumbing.Hash, error)
return nil, err
}
if bytes.HasPrefix(e.Hash[:], prefix) {
+ if _, ok := seen[e.Hash]; ok {
+ continue
+ }
hashes = append(hashes, e.Hash)
}
}
diff --git a/storage/filesystem/object_test.go b/storage/filesystem/object_test.go
index 19a7914..b5f137f 100644
--- a/storage/filesystem/object_test.go
+++ b/storage/filesystem/object_test.go
@@ -406,6 +406,21 @@ func (s *FsSuite) TestHashesWithPrefix(c *C) {
c.Assert(hashes[0].String(), Equals, "f3dfe29d268303fc6e1bbce268605fc99573406e")
}
+func (s *FsSuite) TestHashesWithPrefixFromPackfile(c *C) {
+ // Same setup as TestGetFromPackfile
+ fixtures.Basic().ByTag(".git").Test(c, func(f *fixtures.Fixture) {
+ fs := f.DotGit()
+ o := NewObjectStorage(dotgit.New(fs), cache.NewObjectLRUDefault())
+
+ expected := plumbing.NewHash("6ecf0ef2c2dffb796033e5a02219af86ec6584e5")
+ // Only pass the first 8 bytes
+ hashes, err := o.HashesWithPrefix(expected[:8])
+ c.Assert(err, IsNil)
+ c.Assert(hashes, HasLen, 1)
+ c.Assert(hashes[0], Equals, expected)
+ })
+}
+
func BenchmarkPackfileIter(b *testing.B) {
defer fixtures.Clean()