diff options
author | Patrick Steinhardt <psteinhardt@gitlab.com> | 2023-01-19 11:18:53 +0300 |
---|---|---|
committer | Patrick Steinhardt <psteinhardt@gitlab.com> | 2023-01-26 12:21:25 +0300 |
commit | 9c7bcdd95e67318d9b42154aa7b31fab07b98a5a (patch) | |
tree | edb8760ec278b8fed23a7fe7fe77ca3db1be3f93 | |
parent | 3669e7b87917d62b8de19d8ee2a55ce0ffef4b13 (diff) |
git/stats: Expose information about whether a repo is an object pool
Move the information whether a repository is an object pool or not into
the `RepositoryInfo` structure. Like this, the optimization strategies
really only need a `RepositoryInfo` as input and nothing else. Also,
this enables reporting of this information via our logging mechanism.
-rw-r--r-- | internal/git/housekeeping/optimization_strategy.go | 8 | ||||
-rw-r--r-- | internal/git/housekeeping/optimization_strategy_test.go | 8 | ||||
-rw-r--r-- | internal/git/objectpool/fetch_test.go | 6 | ||||
-rw-r--r-- | internal/git/stats/repository_info.go | 4 |
4 files changed, 16 insertions, 10 deletions
diff --git a/internal/git/housekeeping/optimization_strategy.go b/internal/git/housekeeping/optimization_strategy.go index 7790664d5..d4fe4a7ce 100644 --- a/internal/git/housekeeping/optimization_strategy.go +++ b/internal/git/housekeeping/optimization_strategy.go @@ -30,8 +30,7 @@ type OptimizationStrategy interface { // HeuristicalOptimizationStrategy is an optimization strategy that is based on a set of // heuristics. type HeuristicalOptimizationStrategy struct { - info stats.RepositoryInfo - isObjectPool bool + info stats.RepositoryInfo } // NewHeuristicalOptimizationStrategy constructs a heuristicalOptimizationStrategy for the given @@ -41,7 +40,6 @@ func NewHeuristicalOptimizationStrategy(ctx context.Context, repo *localrepo.Rep var strategy HeuristicalOptimizationStrategy var err error - strategy.isObjectPool = stats.IsPoolRepository(repo) strategy.info, err = stats.RepositoryInfoForRepository(repo) if err != nil { return HeuristicalOptimizationStrategy{}, fmt.Errorf("deriving repository info: %w", err) @@ -112,7 +110,7 @@ func (s HeuristicalOptimizationStrategy) ShouldRepackObjects(context.Context) (b // This is a heuristic and thus imperfect by necessity. We may tune it as we gain experience // with the way it behaves. lowerLimit, log := 5.0, 1.3 - if s.isObjectPool { + if s.info.IsObjectPool { lowerLimit, log = 2.0, 10.0 } @@ -192,7 +190,7 @@ func (s HeuristicalOptimizationStrategy) ShouldWriteCommitGraph(ctx context.Cont func (s HeuristicalOptimizationStrategy) ShouldPruneObjects(context.Context) bool { // Pool repositories must never prune any objects, or otherwise we may corrupt members of // that pool if they still refer to that object. - if s.isObjectPool { + if s.info.IsObjectPool { return false } diff --git a/internal/git/housekeeping/optimization_strategy_test.go b/internal/git/housekeeping/optimization_strategy_test.go index 4c4bb7f75..ea05bfa5f 100644 --- a/internal/git/housekeeping/optimization_strategy_test.go +++ b/internal/git/housekeeping/optimization_strategy_test.go @@ -315,7 +315,7 @@ func TestNewHeuristicalOptimizationStrategy_variousParameters(t *testing.T) { repoProto := tc.setup(t, relativePath) repo := localrepo.NewTestRepo(t, cfg, repoProto) - tc.expectedStrategy.isObjectPool = stats.IsPoolRepository(repo) + tc.expectedStrategy.info.IsObjectPool = stats.IsPoolRepository(repo) strategy, err := NewHeuristicalOptimizationStrategy(ctx, repo) require.NoError(t, err) @@ -467,6 +467,7 @@ func TestHeuristicalOptimizationStrategy_ShouldRepackObjects(t *testing.T) { t.Run(tc.desc, func(t *testing.T) { strategy := HeuristicalOptimizationStrategy{ info: stats.RepositoryInfo{ + IsObjectPool: tc.isPool, Packfiles: stats.PackfilesInfo{ Size: outerTC.packfileSizeInMB * 1024 * 1024, Count: tc.requiredPackfiles - 1, @@ -476,7 +477,6 @@ func TestHeuristicalOptimizationStrategy_ShouldRepackObjects(t *testing.T) { }, Alternates: tc.alternates, }, - isObjectPool: tc.isPool, } repackNeeded, _ := strategy.ShouldRepackObjects(ctx) @@ -539,6 +539,7 @@ func TestHeuristicalOptimizationStrategy_ShouldRepackObjects(t *testing.T) { t.Run(tc.desc, func(t *testing.T) { strategy := HeuristicalOptimizationStrategy{ info: stats.RepositoryInfo{ + IsObjectPool: tc.isPool, LooseObjects: stats.LooseObjectsInfo{ Count: outerTC.looseObjects, }, @@ -550,7 +551,6 @@ func TestHeuristicalOptimizationStrategy_ShouldRepackObjects(t *testing.T) { }, }, }, - isObjectPool: tc.isPool, } repackNeeded, repackCfg := strategy.ShouldRepackObjects(ctx) @@ -620,7 +620,7 @@ func TestHeuristicalOptimizationStrategy_ShouldPruneObjects(t *testing.T) { t.Run("object pool", func(t *testing.T) { strategy := tc.strategy - strategy.isObjectPool = true + strategy.info.IsObjectPool = true require.False(t, strategy.ShouldPruneObjects(ctx)) }) }) diff --git a/internal/git/objectpool/fetch_test.go b/internal/git/objectpool/fetch_test.go index 517b91d9f..06e097a36 100644 --- a/internal/git/objectpool/fetch_test.go +++ b/internal/git/objectpool/fetch_test.go @@ -291,7 +291,9 @@ func TestObjectPool_logStats(t *testing.T) { expectedFields: logrus.Fields{ "references.dangling": referencedObjectTypes{}, "references.normal": referencedObjectTypes{}, - "repository_info": stats.RepositoryInfo{}, + "repository_info": stats.RepositoryInfo{ + IsObjectPool: true, + }, }, }, { @@ -307,6 +309,7 @@ func TestObjectPool_logStats(t *testing.T) { Commits: 1, }, "repository_info": stats.RepositoryInfo{ + IsObjectPool: true, LooseObjects: stats.LooseObjectsInfo{ Count: 2, Size: 142, @@ -330,6 +333,7 @@ func TestObjectPool_logStats(t *testing.T) { }, "references.normal": referencedObjectTypes{}, "repository_info": stats.RepositoryInfo{ + IsObjectPool: true, LooseObjects: stats.LooseObjectsInfo{ Count: 2, Size: 142, diff --git a/internal/git/stats/repository_info.go b/internal/git/stats/repository_info.go index a0083f88a..87e7fb8b9 100644 --- a/internal/git/stats/repository_info.go +++ b/internal/git/stats/repository_info.go @@ -55,6 +55,8 @@ func LogRepositoryInfo(ctx context.Context, repo *localrepo.Repo) { // RepositoryInfo contains information about the repository. type RepositoryInfo struct { + // IsObjectPool determines whether the repository is an object pool or a normal repository. + IsObjectPool bool `json:"is_object_pool"` // LooseObjects contains information about loose objects. LooseObjects LooseObjectsInfo `json:"loose_objects"` // Packfiles contains information about packfiles. @@ -78,6 +80,8 @@ func RepositoryInfoForRepository(repo *localrepo.Repo) (RepositoryInfo, error) { return RepositoryInfo{}, err } + info.IsObjectPool = IsPoolRepository(repo) + info.LooseObjects, err = LooseObjectsInfoForRepository(repo, time.Now().Add(StaleObjectsGracePeriod)) if err != nil { return RepositoryInfo{}, fmt.Errorf("counting loose objects: %w", err) |