Skip to content

Commit 8eb19a5

Browse files
committed
Refactor GetDiff/Path functions to let it more flexible
1 parent fbe6d9d commit 8eb19a5

File tree

3 files changed

+71
-59
lines changed

3 files changed

+71
-59
lines changed

modules/git/repo_compare.go

Lines changed: 41 additions & 54 deletions
Original file line numberDiff line numberDiff line change
@@ -234,71 +234,73 @@ func parseDiffStat(stdout string) (numFiles, totalAdditions, totalDeletions int,
234234
}
235235

236236
// GetDiffOrPatch generates either diff or formatted patch data between given revisions
237-
func (repo *Repository) GetDiffOrPatch(base, head string, w io.Writer, patch, binary bool) error {
237+
func (repo *Repository) GetDiffOrPatch(compareString string, w io.Writer, patch, binary bool) error {
238238
if patch {
239-
return repo.GetPatch(base, head, w)
239+
return repo.GetPatch(compareString, w)
240240
}
241241
if binary {
242-
return repo.GetDiffBinary(base, head, w)
242+
return repo.GetDiffBinary(compareString, w)
243243
}
244-
return repo.GetDiff(base, head, w)
244+
return repo.GetDiff(compareString, w)
245+
}
246+
247+
func parseCompareArgs(compareArgs string) (args []string) {
248+
parts := strings.Split(compareArgs, "...")
249+
if len(parts) == 2 {
250+
return []string{compareArgs}
251+
}
252+
parts = strings.Split(compareArgs, "..")
253+
if len(parts) == 2 {
254+
return parts
255+
}
256+
parts = strings.Fields(compareArgs)
257+
if len(parts) == 2 {
258+
return parts
259+
}
260+
261+
return nil
245262
}
246263

247264
// GetDiff generates and returns patch data between given revisions, optimized for human readability
248-
func (repo *Repository) GetDiff(base, head string, w io.Writer) error {
265+
func (repo *Repository) GetDiff(compareArgs string, w io.Writer) error {
266+
args := parseCompareArgs(compareArgs)
267+
if len(args) == 0 {
268+
return fmt.Errorf("invalid compareArgs: %s", compareArgs)
269+
}
249270
stderr := new(bytes.Buffer)
250-
err := NewCommand(repo.Ctx, "diff", "-p").AddDynamicArguments(base + "..." + head).
271+
return NewCommand(repo.Ctx, "diff", "-p").AddDynamicArguments(args...).
251272
Run(&RunOpts{
252273
Dir: repo.Path,
253274
Stdout: w,
254275
Stderr: stderr,
255276
})
256-
if err != nil && bytes.Contains(stderr.Bytes(), []byte("no merge base")) {
257-
return NewCommand(repo.Ctx, "diff", "-p").AddDynamicArguments(base, head).
258-
Run(&RunOpts{
259-
Dir: repo.Path,
260-
Stdout: w,
261-
})
262-
}
263-
return err
264277
}
265278

266279
// GetDiffBinary generates and returns patch data between given revisions, including binary diffs.
267-
func (repo *Repository) GetDiffBinary(base, head string, w io.Writer) error {
268-
stderr := new(bytes.Buffer)
269-
err := NewCommand(repo.Ctx, "diff", "-p", "--binary", "--histogram").AddDynamicArguments(base + "..." + head).
270-
Run(&RunOpts{
271-
Dir: repo.Path,
272-
Stdout: w,
273-
Stderr: stderr,
274-
})
275-
if err != nil && bytes.Contains(stderr.Bytes(), []byte("no merge base")) {
276-
return NewCommand(repo.Ctx, "diff", "-p", "--binary", "--histogram").AddDynamicArguments(base, head).
277-
Run(&RunOpts{
278-
Dir: repo.Path,
279-
Stdout: w,
280-
})
280+
func (repo *Repository) GetDiffBinary(compareArgs string, w io.Writer) error {
281+
args := parseCompareArgs(compareArgs)
282+
if len(args) == 0 {
283+
return fmt.Errorf("invalid compareArgs: %s", compareArgs)
281284
}
282-
return err
285+
return NewCommand(repo.Ctx, "diff", "-p", "--binary", "--histogram").AddDynamicArguments(args...).Run(&RunOpts{
286+
Dir: repo.Path,
287+
Stdout: w,
288+
})
283289
}
284290

285291
// GetPatch generates and returns format-patch data between given revisions, able to be used with `git apply`
286-
func (repo *Repository) GetPatch(base, head string, w io.Writer) error {
292+
func (repo *Repository) GetPatch(compareArgs string, w io.Writer) error {
293+
args := parseCompareArgs(compareArgs)
294+
if len(args) == 0 {
295+
return fmt.Errorf("invalid compareArgs: %s", compareArgs)
296+
}
287297
stderr := new(bytes.Buffer)
288-
err := NewCommand(repo.Ctx, "format-patch", "--binary", "--stdout").AddDynamicArguments(base + "..." + head).
298+
return NewCommand(repo.Ctx, "format-patch", "--binary", "--stdout").AddDynamicArguments(args...).
289299
Run(&RunOpts{
290300
Dir: repo.Path,
291301
Stdout: w,
292302
Stderr: stderr,
293303
})
294-
if err != nil && bytes.Contains(stderr.Bytes(), []byte("no merge base")) {
295-
return NewCommand(repo.Ctx, "format-patch", "--binary", "--stdout").AddDynamicArguments(base, head).
296-
Run(&RunOpts{
297-
Dir: repo.Path,
298-
Stdout: w,
299-
})
300-
}
301-
return err
302304
}
303305

304306
// GetFilesChangedBetween returns a list of all files that have been changed between the given commits
@@ -329,21 +331,6 @@ func (repo *Repository) GetFilesChangedBetween(base, head string) ([]string, err
329331
return split, err
330332
}
331333

332-
// GetDiffFromMergeBase generates and return patch data from merge base to head
333-
func (repo *Repository) GetDiffFromMergeBase(base, head string, w io.Writer) error {
334-
stderr := new(bytes.Buffer)
335-
err := NewCommand(repo.Ctx, "diff", "-p", "--binary").AddDynamicArguments(base + "..." + head).
336-
Run(&RunOpts{
337-
Dir: repo.Path,
338-
Stdout: w,
339-
Stderr: stderr,
340-
})
341-
if err != nil && bytes.Contains(stderr.Bytes(), []byte("no merge base")) {
342-
return repo.GetDiffBinary(base, head, w)
343-
}
344-
return err
345-
}
346-
347334
// ReadPatchCommit will check if a diff patch exists and return stats
348335
func (repo *Repository) ReadPatchCommit(prID int64) (commitSHA string, err error) {
349336
// Migrated repositories download patches to "pulls" location

modules/git/repo_compare_test.go

Lines changed: 26 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,31 @@ import (
1212
"github.com/stretchr/testify/assert"
1313
)
1414

15+
func Test_parseCompareArgs(t *testing.T) {
16+
testCases := []struct {
17+
compareString string
18+
expected []string
19+
}{
20+
{
21+
"master..develop",
22+
[]string{"master", "develop"},
23+
},
24+
{
25+
"master HEAD",
26+
[]string{"master", "HEAD"},
27+
},
28+
{
29+
"HEAD...develop",
30+
[]string{"HEAD...develop"},
31+
},
32+
}
33+
34+
for _, tc := range testCases {
35+
args := parseCompareArgs(tc.compareString)
36+
assert.Equal(t, tc.expected, args)
37+
}
38+
}
39+
1540
func TestGetFormatPatch(t *testing.T) {
1641
bareRepo1Path := filepath.Join(testReposDir, "repo1_bare")
1742
clonedPath, err := cloneRepo(t, bareRepo1Path)
@@ -28,7 +53,7 @@ func TestGetFormatPatch(t *testing.T) {
2853
defer repo.Close()
2954

3055
rd := &bytes.Buffer{}
31-
err = repo.GetPatch("8d92fc95^", "8d92fc95", rd)
56+
err = repo.GetPatch("8d92fc95^ 8d92fc95", rd)
3257
if err != nil {
3358
assert.NoError(t, err)
3459
return

services/pull/patch.go

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -42,9 +42,9 @@ func DownloadDiffOrPatch(ctx context.Context, pr *issues_model.PullRequest, w io
4242
}
4343
defer closer.Close()
4444

45-
if err := gitRepo.GetDiffOrPatch(pr.MergeBase, pr.GetGitRefName(), w, patch, binary); err != nil {
46-
log.Error("Unable to get patch file from %s to %s in %s Error: %v", pr.MergeBase, pr.HeadBranch, pr.BaseRepo.FullName(), err)
47-
return fmt.Errorf("Unable to get patch file from %s to %s in %s Error: %w", pr.MergeBase, pr.HeadBranch, pr.BaseRepo.FullName(), err)
45+
if err := gitRepo.GetDiffOrPatch(pr.MergeBase+".."+pr.GetGitRefName(), w, patch, binary); err != nil {
46+
log.Error("unable to get patch file from %s to %s in %s Error: %v", pr.MergeBase, pr.HeadBranch, pr.BaseRepo.FullName(), err)
47+
return fmt.Errorf("unable to get patch file from %s to %s in %s Error: %w", pr.MergeBase, pr.HeadBranch, pr.BaseRepo.FullName(), err)
4848
}
4949
return nil
5050
}
@@ -355,7 +355,7 @@ func checkConflicts(ctx context.Context, pr *issues_model.PullRequest, gitRepo *
355355
_ = util.Remove(tmpPatchFile.Name())
356356
}()
357357

358-
if err := gitRepo.GetDiffBinary(pr.MergeBase, "tracking", tmpPatchFile); err != nil {
358+
if err := gitRepo.GetDiffBinary(pr.MergeBase+"..tracking", tmpPatchFile); err != nil {
359359
tmpPatchFile.Close()
360360
log.Error("Unable to get patch file from %s to %s in %s Error: %v", pr.MergeBase, pr.HeadBranch, pr.BaseRepo.FullName(), err)
361361
return false, fmt.Errorf("unable to get patch file from %s to %s in %s Error: %w", pr.MergeBase, pr.HeadBranch, pr.BaseRepo.FullName(), err)

0 commit comments

Comments
 (0)