diff options
author | Alejandro Rodríguez <alejorro70@gmail.com> | 2017-10-23 18:25:34 +0300 |
---|---|---|
committer | Alejandro Rodríguez <alejorro70@gmail.com> | 2017-10-23 18:25:34 +0300 |
commit | 17aa79bb7f8bce08d936aabb25c3ebd15c353a1f (patch) | |
tree | 97aa328790686ac7c377653f7e38e2e44aeca23d | |
parent | 3459b90bc68b7288e3020180c9d593db05d4886f (diff) | |
parent | 6f0bdab8969bdb5c5ee2224f5a960a845b5c082a (diff) |
Merge branch 'fix/use-git-alt-dirs-values-from-repository' into 'master'
Pass repo git alternate dirs to gitaly-ruby
Closes #682
See merge request gitlab-org/gitaly!421
-rw-r--r-- | CHANGELOG.md | 5 | ||||
-rw-r--r-- | internal/rubyserver/proxy.go | 12 | ||||
-rw-r--r-- | internal/rubyserver/rubyserver.go | 1 | ||||
-rw-r--r-- | internal/service/commit/find_commits_test.go | 105 | ||||
-rw-r--r-- | ruby/lib/gitaly_server.rb | 5 | ||||
-rw-r--r-- | ruby/lib/gitlab/git.rb | 14 |
6 files changed, 138 insertions, 4 deletions
diff --git a/CHANGELOG.md b/CHANGELOG.md index 72140fca6..1476227df 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,5 +1,10 @@ # Gitaly changelog +UNRELEASED + +- Pass repo git alternate dirs to gitaly-ruby + https://gitlab.com/gitlab-org/gitaly/merge_requests/421 + v0.49.0 - Use sentry fingerprinting to group exceptions diff --git a/internal/rubyserver/proxy.go b/internal/rubyserver/proxy.go index ee6ee137d..503d9ac8f 100644 --- a/internal/rubyserver/proxy.go +++ b/internal/rubyserver/proxy.go @@ -3,6 +3,8 @@ package rubyserver import ( "context" "io" + "os" + "strings" pb "gitlab.com/gitlab-org/gitaly-proto/go" "gitlab.com/gitlab-org/gitaly/internal/helper" @@ -17,7 +19,15 @@ func SetHeaders(ctx context.Context, repo *pb.Repository) (context.Context, erro return nil, err } - md := metadata.Pairs(repoPathHeader, repoPath, glRepositoryHeader, repo.GlRepository) + repoAltDirs := repo.GetGitAlternateObjectDirectories() + repoAltDirs = append(repoAltDirs, repo.GetGitObjectDirectory()) + repoAltDirsCombined := strings.Join(repoAltDirs, string(os.PathListSeparator)) + + md := metadata.Pairs( + repoPathHeader, repoPath, + glRepositoryHeader, repo.GlRepository, + repoAltDirsHeader, repoAltDirsCombined, + ) newCtx := metadata.NewOutgoingContext(ctx, md) return newCtx, nil } diff --git a/internal/rubyserver/rubyserver.go b/internal/rubyserver/rubyserver.go index dcbd7434c..9d0466115 100644 --- a/internal/rubyserver/rubyserver.go +++ b/internal/rubyserver/rubyserver.go @@ -26,6 +26,7 @@ import ( const ( repoPathHeader = "gitaly-repo-path" glRepositoryHeader = "gitaly-gl-repository" + repoAltDirsHeader = "gitaly-repo-alt-dirs" ) var ( diff --git a/internal/service/commit/find_commits_test.go b/internal/service/commit/find_commits_test.go index 788e3b1ac..0088ab928 100644 --- a/internal/service/commit/find_commits_test.go +++ b/internal/service/commit/find_commits_test.go @@ -2,7 +2,11 @@ package commit import ( "context" + "fmt" "io" + "os" + "os/exec" + "path" "testing" "google.golang.org/grpc/codes" @@ -218,6 +222,107 @@ func TestSuccessfulFindCommitsRequest(t *testing.T) { } } +func TestSuccessfulFindCommitsRequestWithAltGitObjectDirs(t *testing.T) { + server := startTestServices(t) + defer server.Stop() + + client, conn := newCommitServiceClient(t, serverSocketPath) + defer conn.Close() + + committerName := "Scrooge McDuck" + committerEmail := "scrooge@mcduck.com" + + storagePath := testhelper.GitlabTestStoragePath() + testRepoPath := path.Join(storagePath, testRepo.RelativePath) + testRepoCopyName := "find-commits-alt-test-repo" + testRepoCopyPath := path.Join(storagePath, testRepoCopyName) + altObjectsDir := "./alt-objects" + altObjectsPath := path.Join(testRepoCopyPath, ".git", altObjectsDir) + gitObjectEnv := []string{ + fmt.Sprintf("GIT_OBJECT_DIRECTORY=%s", altObjectsPath), + fmt.Sprintf("GIT_ALTERNATE_OBJECT_DIRECTORIES=%s", path.Join(testRepoCopyPath, ".git/objects")), + } + + // This clone will store its objects in the normal location: 'find-commits-alt-test-repo/.git/objects' + testhelper.MustRunCommand(t, nil, "git", "clone", testRepoPath, testRepoCopyPath) + defer os.RemoveAll(testRepoCopyPath) + + if err := os.Mkdir(altObjectsPath, 0777); err != nil { + t.Fatal(err) + } + + cmd := exec.Command("git", "-C", testRepoCopyPath, + "-c", fmt.Sprintf("user.name=%s", committerName), + "-c", fmt.Sprintf("user.email=%s", committerEmail), + "commit", "--allow-empty", "-m", "An empty commit") + // Because we set 'gitObjectEnv', the new objects created by this 'git commit' command will go + // into 'find-commits-alt-test-repo/.git/alt-objects'. + cmd.Env = gitObjectEnv + if _, err := cmd.Output(); err != nil { + stderr := err.(*exec.ExitError).Stderr + t.Fatalf("%s", stderr) + } + + cmd = exec.Command("git", "-C", testRepoCopyPath, "show", "--format=format:%H", "--no-patch", "HEAD") + cmd.Env = gitObjectEnv + currentHead, err := cmd.Output() + if err != nil { + t.Fatal(err) + } + + testCases := []struct { + desc string + altDirs []string + expectedCount int + }{ + { + desc: "present GIT_ALTERNATE_OBJECT_DIRECTORIES", + altDirs: []string{altObjectsDir}, + expectedCount: 1, + }, + { + desc: "empty GIT_ALTERNATE_OBJECT_DIRECTORIES", + altDirs: []string{}, + expectedCount: 0, + }, + } + + for _, testCase := range testCases { + t.Run(testCase.desc, func(t *testing.T) { + request := &pb.FindCommitsRequest{ + Repository: &pb.Repository{ + StorageName: testRepo.StorageName, + RelativePath: path.Join(testRepoCopyName, ".git"), + GitAlternateObjectDirectories: testCase.altDirs, + }, + Revision: currentHead, + Limit: 1, + } + + ctx, cancel := testhelper.Context() + defer cancel() + + c, err := client.FindCommits(ctx, request) + require.NoError(t, err) + + receivedCommits := []*pb.GitCommit{} + + for { + resp, err := c.Recv() + if err == io.EOF { + break + } else if err != nil { + t.Fatal(err) + } + + receivedCommits = append(receivedCommits, resp.GetCommits()...) + } + + require.Equal(t, testCase.expectedCount, len(receivedCommits), "number of commits received") + }) + } +} + func TestFailureFindCommitsRequest(t *testing.T) { server := startTestServices(t) defer server.Stop() diff --git a/ruby/lib/gitaly_server.rb b/ruby/lib/gitaly_server.rb index 2edac0876..32e47e4c1 100644 --- a/ruby/lib/gitaly_server.rb +++ b/ruby/lib/gitaly_server.rb @@ -13,6 +13,7 @@ require_relative 'gitaly_server/wiki_service.rb' module GitalyServer REPO_PATH_HEADER = 'gitaly-repo-path'.freeze GL_REPOSITORY_HEADER = 'gitaly-gl-repository'.freeze + REPO_ALT_DIRS_HEADER = 'gitaly-repo-alt-dirs'.freeze def self.repo_path(call) call.metadata.fetch(REPO_PATH_HEADER) @@ -22,6 +23,10 @@ module GitalyServer call.metadata.fetch(GL_REPOSITORY_HEADER) end + def self.repo_alt_dirs(call) + call.metadata.fetch(REPO_ALT_DIRS_HEADER) + end + def self.register_handlers(server) server.handle(CommitService.new) server.handle(DiffService.new) diff --git a/ruby/lib/gitlab/git.rb b/ruby/lib/gitlab/git.rb index ba98f07d1..1c8fccf09 100644 --- a/ruby/lib/gitlab/git.rb +++ b/ruby/lib/gitlab/git.rb @@ -72,13 +72,21 @@ module Gitlab module Git class Repository def self.from_call(call) - new(GitalyServer.repo_path(call), GitalyServer.gl_repository(call)) + new( + GitalyServer.repo_path(call), + GitalyServer.gl_repository(call), + GitalyServer.repo_alt_dirs(call) + ) end - def initialize(path, gl_repository) + def initialize(path, gl_repository, combined_alt_dirs="") + alt_dirs = combined_alt_dirs + .split(File::PATH_SEPARATOR) + .map { |d| File.join(path, d) } + @path = path @gl_repository = gl_repository - @rugged = Rugged::Repository.new(path) + @rugged = Rugged::Repository.new(path, alternates: alt_dirs) @attributes = Gitlab::Git::Attributes.new(path) end |