From 8114cc4a40ae6910078f697029cea2cfa2fca625 Mon Sep 17 00:00:00 2001 From: David Pordomingo Date: Mon, 11 Feb 2019 20:18:31 +0100 Subject: [PATCH 1/3] Add a failing test of analyzing PR with changes in both base and candidate Signed-off-by: David Pordomingo --- cmd/server-test/only_pr_changes_test.go | 61 +++++++++++++++++++++++++ 1 file changed, 61 insertions(+) create mode 100644 cmd/server-test/only_pr_changes_test.go diff --git a/cmd/server-test/only_pr_changes_test.go b/cmd/server-test/only_pr_changes_test.go new file mode 100644 index 00000000..7acc4a0f --- /dev/null +++ b/cmd/server-test/only_pr_changes_test.go @@ -0,0 +1,61 @@ +// +build integration + +package server_test + +import ( + "testing" + "time" + + fixtures "github.com/src-d/lookout-test-fixtures" + "gopkg.in/src-d/lookout-sdk.v0/pb" + + "github.com/stretchr/testify/suite" +) + +func TestReviewOnlyPrChangesIntegrationSuite(t *testing.T) { + suite.Run(t, new(reviewOnlyPrChangesIntegrationSuite)) +} + +type reviewOnlyPrChangesIntegrationSuite struct { + IntegrationSuite +} + +func (suite *reviewOnlyPrChangesIntegrationSuite) SetupTest() { + suite.ResetDB() + + suite.StoppableCtx() + suite.r, suite.w = suite.StartLookoutd(dummyConfigFile) + + suite.StartDummy("--files") + suite.GrepTrue(suite.r, `msg="connection state changed to 'READY'" addr="ipv4://localhost:9930" analyzer=Dummy`) +} + +func (suite *reviewOnlyPrChangesIntegrationSuite) TearDownTest() { + // TODO: for integration tests with RabbitMQ we wait a bit so the queue + // is depleted. Ideally this would be done with something similar to ResetDB + time.Sleep(5 * time.Second) + suite.Stop() +} + +func (suite *reviewOnlyPrChangesIntegrationSuite) TestAnalyzerErr() { + fixtures := fixtures.GetByName("get-changes-from-outdated-pr") + jsonReviewEvent := &jsonReviewEvent{ + ReviewEvent: &pb.ReviewEvent{ + InternalID: "1", + Number: 1, + CommitRevision: *fixtures.GetCommitRevision(), + }, + } + + expectedComments := []string{ + `{"analyzer-name":"Dummy","file":"javascript.js",`, + `status=success`, + } + notExpectedComments := []string{ + `{"analyzer-name":"Dummy","file":"golang.go",`, + } + + suite.sendEvent(jsonReviewEvent.String()) + suite.GrepAndNotAll(suite.r, expectedComments, notExpectedComments) +} + From 8f655a96433715e6c7fcffcab46e31cca47f56c5 Mon Sep 17 00:00:00 2001 From: David Pordomingo Date: Fri, 15 Feb 2019 19:10:57 +0100 Subject: [PATCH 2/3] Add 'Three dots' feature in 'GetChanges' as default Signed-off-by: David Pordomingo --- service/git/service.go | 66 ++++++++- .../lookout-sdk.v0/pb/service_data.pb.go | 130 +++++++++++------- 2 files changed, 147 insertions(+), 49 deletions(-) diff --git a/service/git/service.go b/service/git/service.go index ba3a2e52..d84edecd 100644 --- a/service/git/service.go +++ b/service/git/service.go @@ -8,6 +8,7 @@ import ( errors "gopkg.in/src-d/go-errors.v1" "gopkg.in/src-d/go-git.v4/plumbing/object" + "gopkg.in/src-d/go-git.v4" ) // Service implements data service interface on top of go-git @@ -50,6 +51,49 @@ func validateReferences(ctx context.Context, validateRefName bool, refs ...*look return nil } +func (r *Service) getFrom( + ctx context.Context, + base, head *lookout.ReferencePointer, +) ( + *lookout.ReferencePointer, error, +) { + commits, err := r.loader.LoadCommits(ctx, *base, *head) + if err != nil { + return nil, err + } + + var commonAncestor *object.Commit + res, err := git.MergeBase(commits[0], commits[1]) + if err != nil { + return nil, err + } + + if len(res) == 0 { + // If there is no common ancestor between two commits it means that they + // don't have a common history. That PR won't be able to be created in + // GitHub, but in other situations (ie. with lookout-sdk), an analyzer + // could be interested in analyzing the difference between both commints. + return base, nil + } + + commonAncestor = res[0] + + /* + // TODO(dpordomingo): uncomment this after testing that it's not a problem + // returning commits without ReferenceName (see comment below) + if base.Hash == commonAncestor.Hash.String() { + return base, nil + } + */ + + return &lookout.ReferencePointer{ + InternalRepositoryURL: base.InternalRepositoryURL, + // ReferenceName can be undefined for a random commit inside that repository + ReferenceName: "", + Hash: commonAncestor.Hash.String(), + }, nil +} + // GetChanges returns a ChangeScanner that scans all changes according to the request. func (r *Service) GetChanges(ctx context.Context, req *lookout.ChangesRequest) ( lookout.ChangeScanner, error) { @@ -58,7 +102,25 @@ func (r *Service) GetChanges(ctx context.Context, req *lookout.ChangesRequest) ( return nil, err } - base, head, err := r.loadTrees(ctx, req.Base, req.Head) + var from *lookout.ReferencePointer + + // The standard behavior for getting the changes between two commits is like doing + // `git diff base...head`, also `git diff $(git merge-base base head) head` + // (as it appears in `Changes` tab in GitHub PRs) + // If it is desired to get all changes between `base` and `head`, + // (as done by `git diff base..head`) it must be sent `req.TwoDotsMode` as true + if req.TwoDotsMode { + from = req.Base + } else { + if req.Base != nil { + from, err = r.getFrom(ctx, req.Base, req.Head) + if err != nil { + return nil, err + } + } + } + + base, head, err := r.loadTrees(ctx, from, req.Head) if err != nil { return nil, err } @@ -111,8 +173,6 @@ func (r *Service) GetFiles(ctx context.Context, req *lookout.FilesRequest) ( return scanner, nil } -const maxResolveLength = 20 - func (r *Service) loadTrees(ctx context.Context, base, head *lookout.ReferencePointer) (*object.Tree, *object.Tree, error) { diff --git a/vendor/gopkg.in/src-d/lookout-sdk.v0/pb/service_data.pb.go b/vendor/gopkg.in/src-d/lookout-sdk.v0/pb/service_data.pb.go index bb96e519..e4c086e0 100644 --- a/vendor/gopkg.in/src-d/lookout-sdk.v0/pb/service_data.pb.go +++ b/vendor/gopkg.in/src-d/lookout-sdk.v0/pb/service_data.pb.go @@ -50,7 +50,7 @@ func (m *File) Reset() { *m = File{} } func (m *File) String() string { return proto.CompactTextString(m) } func (*File) ProtoMessage() {} func (*File) Descriptor() ([]byte, []int) { - return fileDescriptor_service_data_8336abc41c19202a, []int{0} + return fileDescriptor_service_data_cdd114f0940e7d0a, []int{0} } func (m *File) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -93,7 +93,7 @@ func (m *Change) Reset() { *m = Change{} } func (m *Change) String() string { return proto.CompactTextString(m) } func (*Change) ProtoMessage() {} func (*Change) Descriptor() ([]byte, []int) { - return fileDescriptor_service_data_8336abc41c19202a, []int{1} + return fileDescriptor_service_data_cdd114f0940e7d0a, []int{1} } func (m *Change) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -148,13 +148,17 @@ type ChangesRequest struct { // case insensitive. The list of language names is available at // https://github.com/github/linguist/blob/master/lib/linguist/languages.yml IncludeLanguages []string `protobuf:"bytes,9,rep,name=include_languages,json=includeLanguages,proto3" json:"include_languages,omitempty"` + // TwoDotsMode will calculate the changes between base..head + // Its default value is false, working as base...head, that calculates the + // changes introduced by head, not accessible by base. + TwoDotsMode bool `protobuf:"varint,10,opt,name=two_dots_mode,json=twoDotsMode,proto3" json:"two_dots_mode,omitempty"` } func (m *ChangesRequest) Reset() { *m = ChangesRequest{} } func (m *ChangesRequest) String() string { return proto.CompactTextString(m) } func (*ChangesRequest) ProtoMessage() {} func (*ChangesRequest) Descriptor() ([]byte, []int) { - return fileDescriptor_service_data_8336abc41c19202a, []int{2} + return fileDescriptor_service_data_cdd114f0940e7d0a, []int{2} } func (m *ChangesRequest) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -213,7 +217,7 @@ func (m *FilesRequest) Reset() { *m = FilesRequest{} } func (m *FilesRequest) String() string { return proto.CompactTextString(m) } func (*FilesRequest) ProtoMessage() {} func (*FilesRequest) Descriptor() ([]byte, []int) { - return fileDescriptor_service_data_8336abc41c19202a, []int{3} + return fileDescriptor_service_data_cdd114f0940e7d0a, []int{3} } func (m *FilesRequest) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -609,6 +613,16 @@ func (m *ChangesRequest) MarshalTo(dAtA []byte) (int, error) { i += copy(dAtA[i:], s) } } + if m.TwoDotsMode { + dAtA[i] = 0x50 + i++ + if m.TwoDotsMode { + dAtA[i] = 1 + } else { + dAtA[i] = 0 + } + i++ + } return i, nil } @@ -805,6 +819,9 @@ func (m *ChangesRequest) Size() (n int) { n += 1 + l + sovServiceData(uint64(l)) } } + if m.TwoDotsMode { + n += 2 + } return n } @@ -1458,6 +1475,26 @@ func (m *ChangesRequest) Unmarshal(dAtA []byte) error { } m.IncludeLanguages = append(m.IncludeLanguages, string(dAtA[iNdEx:postIndex])) iNdEx = postIndex + case 10: + if wireType != 0 { + return fmt.Errorf("proto: wrong wireType = %d for field TwoDotsMode", wireType) + } + var v int + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowServiceData + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + v |= (int(b) & 0x7F) << shift + if b < 0x80 { + break + } + } + m.TwoDotsMode = bool(v != 0) default: iNdEx = preIndex skippy, err := skipServiceData(dAtA[iNdEx:]) @@ -1835,48 +1872,49 @@ var ( ) func init() { - proto.RegisterFile("lookout/sdk/service_data.proto", fileDescriptor_service_data_8336abc41c19202a) + proto.RegisterFile("lookout/sdk/service_data.proto", fileDescriptor_service_data_cdd114f0940e7d0a) } -var fileDescriptor_service_data_8336abc41c19202a = []byte{ - // 615 bytes of a gzipped FileDescriptorProto - 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0x94, 0x94, 0xc1, 0x6e, 0xd3, 0x30, - 0x18, 0xc7, 0x9b, 0x36, 0xeb, 0x5c, 0xaf, 0x1b, 0xc3, 0x42, 0x22, 0xaa, 0xa6, 0xb4, 0x8c, 0x03, - 0x99, 0x26, 0x9c, 0x31, 0x6e, 0x5c, 0x10, 0x1b, 0x62, 0x17, 0x34, 0x4d, 0x81, 0xc1, 0x71, 0x38, - 0xcd, 0xb7, 0x24, 0x5a, 0x67, 0x97, 0xd8, 0x29, 0xdc, 0x79, 0x01, 0x1e, 0x81, 0x3d, 0x0b, 0x97, - 0x1d, 0x77, 0xe4, 0x34, 0x46, 0xfb, 0x22, 0xc8, 0x4e, 0xd2, 0xad, 0xd2, 0x80, 0x72, 0xb3, 0xff, - 0xdf, 0xcf, 0x9f, 0xed, 0xff, 0x3f, 0x0e, 0x76, 0x07, 0x42, 0x9c, 0x88, 0x5c, 0xf9, 0x32, 0x3a, - 0xf1, 0x25, 0x64, 0xa3, 0xb4, 0x0f, 0x47, 0x11, 0x53, 0x8c, 0x0e, 0x33, 0xa1, 0x04, 0xa9, 0x0f, - 0xc3, 0xce, 0xe3, 0x38, 0x55, 0x49, 0x1e, 0xd2, 0xbe, 0x38, 0xf5, 0x63, 0x11, 0x0b, 0xdf, 0x94, - 0xc2, 0xfc, 0xd8, 0xcc, 0xcc, 0xc4, 0x8c, 0x8a, 0x25, 0x9d, 0xcd, 0x58, 0x0c, 0x4f, 0x62, 0x9a, - 0x72, 0x3f, 0x0c, 0x07, 0xc7, 0x32, 0xd1, 0xad, 0xe9, 0xe8, 0x89, 0x9f, 0x33, 0xa9, 0xfc, 0x18, - 0x38, 0x64, 0x4c, 0x41, 0x54, 0xc2, 0xf7, 0x6f, 0xee, 0x0f, 0x23, 0xe0, 0xaa, 0x28, 0xac, 0x7f, - 0xb7, 0xb0, 0xfd, 0x2a, 0x1d, 0x00, 0x21, 0xd8, 0x1e, 0x32, 0x95, 0x38, 0x56, 0xcf, 0xf2, 0x5a, - 0x81, 0x19, 0x6b, 0xed, 0x54, 0x44, 0xe0, 0xd4, 0x7b, 0x96, 0xb7, 0x1c, 0x98, 0xb1, 0xd6, 0x12, - 0x26, 0x13, 0xa7, 0x51, 0x70, 0x7a, 0x4c, 0x1c, 0xbc, 0xd8, 0x17, 0x5c, 0x01, 0x57, 0x8e, 0xdd, - 0xb3, 0xbc, 0x76, 0x50, 0x4d, 0xc9, 0x73, 0x6c, 0xeb, 0xf3, 0x38, 0x0b, 0x3d, 0xcb, 0x5b, 0xda, - 0x7e, 0x40, 0xab, 0x33, 0xd3, 0xe2, 0xcc, 0xb4, 0x38, 0x33, 0xd5, 0x0c, 0xdd, 0x17, 0x11, 0xec, - 0xa0, 0xf1, 0x65, 0xd7, 0x3e, 0x7c, 0xf1, 0xe6, 0x6d, 0x60, 0x16, 0x92, 0x0e, 0x46, 0x03, 0xc6, - 0xe3, 0x9c, 0xc5, 0xe0, 0x34, 0xcd, 0x96, 0xd3, 0xf9, 0x33, 0xf4, 0xed, 0xac, 0x5b, 0xbb, 0x3a, - 0xeb, 0x5a, 0xeb, 0xfb, 0xb8, 0xb9, 0x9b, 0x30, 0x1e, 0x03, 0x59, 0xc3, 0x76, 0xc8, 0x24, 0x98, - 0x6b, 0x2c, 0x6d, 0x23, 0x3a, 0x0c, 0xa9, 0xbe, 0x5e, 0x60, 0x54, 0x5d, 0x4d, 0x80, 0x45, 0xe6, - 0x42, 0x33, 0x55, 0xad, 0xde, 0xe8, 0xf7, 0xa5, 0x81, 0x57, 0x8a, 0x86, 0x32, 0x80, 0x8f, 0x39, - 0x48, 0x45, 0xbc, 0x99, 0xc6, 0xf7, 0xf4, 0xd2, 0x00, 0x8e, 0x21, 0x03, 0xde, 0x87, 0x03, 0x91, - 0x72, 0x05, 0x59, 0xb9, 0x89, 0x37, 0xb3, 0xc9, 0x1f, 0x48, 0x4d, 0x90, 0x47, 0xf8, 0x4e, 0xca, - 0xfb, 0x83, 0x3c, 0x82, 0xa3, 0x21, 0x53, 0x0a, 0x32, 0x5e, 0xda, 0xba, 0x52, 0xca, 0x07, 0x85, - 0xaa, 0x41, 0xf8, 0x3c, 0x0b, 0xda, 0x05, 0x58, 0xca, 0x15, 0xb8, 0x81, 0x57, 0x2b, 0x70, 0x04, - 0x3c, 0x12, 0x19, 0x44, 0xc6, 0x7b, 0x14, 0x54, 0x0d, 0xde, 0x95, 0x32, 0x79, 0x88, 0x97, 0x3f, - 0x31, 0xae, 0x8e, 0xca, 0xa8, 0xa4, 0xb1, 0x17, 0x05, 0x6d, 0x2d, 0xee, 0x96, 0x1a, 0xd9, 0xc0, - 0x2d, 0x03, 0x99, 0x10, 0x17, 0x35, 0xb0, 0xd3, 0x1e, 0x5f, 0x76, 0xd1, 0x7b, 0xc6, 0x95, 0x49, - 0x09, 0xe9, 0xf2, 0xa1, 0x4e, 0xaa, 0xea, 0x37, 0x8d, 0x0b, 0x5d, 0xf7, 0x7b, 0x5d, 0x6a, 0x64, - 0x13, 0xdf, 0xad, 0x6e, 0x5c, 0x71, 0xd2, 0x69, 0xf5, 0x1a, 0x5e, 0x2b, 0x58, 0x2d, 0x0b, 0x15, - 0x2b, 0xd7, 0x7f, 0xd6, 0x71, 0x5b, 0xc7, 0x33, 0xcd, 0x60, 0x0b, 0xa3, 0x0c, 0x46, 0xa9, 0x4c, - 0x05, 0xff, 0x6b, 0x0e, 0x53, 0xea, 0x36, 0x87, 0xeb, 0xf3, 0x3a, 0xdc, 0x98, 0xdb, 0x61, 0x7b, - 0x4e, 0x87, 0x17, 0xfe, 0xe5, 0x70, 0xf3, 0xff, 0x1c, 0x5e, 0x9c, 0xd7, 0x61, 0x74, 0xbb, 0xc3, - 0xdb, 0x1f, 0xb0, 0xfd, 0x92, 0x29, 0x46, 0x28, 0xc6, 0x7b, 0xa0, 0xca, 0x2f, 0x9e, 0x10, 0x6d, - 0xea, 0xec, 0xe7, 0xdf, 0xc1, 0xd7, 0xda, 0x96, 0x45, 0x3c, 0x8c, 0xf6, 0x40, 0x99, 0x6c, 0xc8, - 0x6a, 0xf5, 0x8a, 0xa6, 0xec, 0xf4, 0x5d, 0x6d, 0x59, 0x3b, 0x6b, 0xe7, 0xbf, 0xdc, 0xda, 0xf9, - 0xd8, 0xb5, 0x2e, 0xc6, 0xae, 0x75, 0x35, 0x76, 0xad, 0xaf, 0x13, 0xb7, 0x76, 0x31, 0x71, 0x6b, - 0x3f, 0x26, 0x6e, 0x2d, 0x6c, 0x9a, 0x9f, 0xd0, 0xd3, 0xdf, 0x01, 0x00, 0x00, 0xff, 0xff, 0x66, - 0x7c, 0x6c, 0xeb, 0x1f, 0x05, 0x00, 0x00, +var fileDescriptor_service_data_cdd114f0940e7d0a = []byte{ + // 640 bytes of a gzipped FileDescriptorProto + 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0x94, 0x94, 0x4f, 0x53, 0xd3, 0x4e, + 0x18, 0xc7, 0x9b, 0x36, 0x94, 0x74, 0x29, 0xfc, 0xf8, 0xed, 0x38, 0x63, 0xa6, 0xc3, 0xa4, 0xb5, + 0x1e, 0x0c, 0xc3, 0xb8, 0x41, 0xbc, 0x79, 0x71, 0x04, 0x46, 0x2e, 0xca, 0x30, 0x51, 0xf4, 0x58, + 0x37, 0xcd, 0x43, 0x92, 0xa1, 0xec, 0xd6, 0xec, 0xa6, 0xf8, 0x32, 0x7c, 0x09, 0x72, 0xf2, 0x85, + 0x78, 0xe1, 0xc8, 0xd1, 0x13, 0x62, 0x79, 0x23, 0xce, 0x6e, 0xfe, 0x40, 0x67, 0x50, 0xeb, 0x6d, + 0xf7, 0xfb, 0x7c, 0xf7, 0xbb, 0x7f, 0x3e, 0x79, 0x82, 0x9c, 0x11, 0xe7, 0xc7, 0x3c, 0x93, 0x9e, + 0x08, 0x8f, 0x3d, 0x01, 0xe9, 0x24, 0x19, 0xc2, 0x20, 0xa4, 0x92, 0x92, 0x71, 0xca, 0x25, 0xc7, + 0xf5, 0x71, 0xd0, 0x79, 0x1c, 0x25, 0x32, 0xce, 0x02, 0x32, 0xe4, 0x27, 0x5e, 0xc4, 0x23, 0xee, + 0xe9, 0x52, 0x90, 0x1d, 0xe9, 0x99, 0x9e, 0xe8, 0x51, 0xbe, 0xa4, 0xb3, 0x11, 0xf1, 0xf1, 0x71, + 0x44, 0x12, 0xe6, 0x05, 0xc1, 0xe8, 0x48, 0xc4, 0x2a, 0x9a, 0x4c, 0x9e, 0x78, 0x19, 0x15, 0xd2, + 0x8b, 0x80, 0x41, 0x4a, 0x25, 0x84, 0x85, 0xf9, 0xfe, 0xed, 0xfd, 0x61, 0x02, 0x4c, 0xe6, 0x85, + 0xfe, 0x37, 0x03, 0x99, 0x2f, 0x93, 0x11, 0x60, 0x8c, 0xcc, 0x31, 0x95, 0xb1, 0x6d, 0xf4, 0x0c, + 0xb7, 0xe5, 0xeb, 0xb1, 0xd2, 0x4e, 0x78, 0x08, 0x76, 0xbd, 0x67, 0xb8, 0xcb, 0xbe, 0x1e, 0x2b, + 0x2d, 0xa6, 0x22, 0xb6, 0x1b, 0xb9, 0x4f, 0x8d, 0xb1, 0x8d, 0x16, 0x87, 0x9c, 0x49, 0x60, 0xd2, + 0x36, 0x7b, 0x86, 0xdb, 0xf6, 0xcb, 0x29, 0x7e, 0x8e, 0x4c, 0x75, 0x1e, 0x7b, 0xa1, 0x67, 0xb8, + 0x4b, 0x5b, 0x0f, 0x48, 0x79, 0x66, 0x92, 0x9f, 0x99, 0xe4, 0x67, 0x26, 0xca, 0x43, 0xf6, 0x79, + 0x08, 0xdb, 0xd6, 0xf4, 0xb2, 0x6b, 0x1e, 0xbe, 0x78, 0xf3, 0xd6, 0xd7, 0x0b, 0x71, 0x07, 0x59, + 0x23, 0xca, 0xa2, 0x8c, 0x46, 0x60, 0x37, 0xf5, 0x96, 0xd5, 0xfc, 0x99, 0xf5, 0xe5, 0xac, 0x5b, + 0xbb, 0x3a, 0xeb, 0x1a, 0xfd, 0x7d, 0xd4, 0xdc, 0x89, 0x29, 0x8b, 0x00, 0xaf, 0x21, 0x33, 0xa0, + 0x02, 0xf4, 0x35, 0x96, 0xb6, 0x2c, 0x32, 0x0e, 0x88, 0xba, 0x9e, 0xaf, 0x55, 0x55, 0x8d, 0x81, + 0x86, 0xfa, 0x42, 0x33, 0x55, 0xa5, 0xde, 0xca, 0xfb, 0xda, 0x40, 0x2b, 0x79, 0xa0, 0xf0, 0xe1, + 0x63, 0x06, 0x42, 0x62, 0x77, 0x26, 0xf8, 0x9e, 0x5a, 0xea, 0xc3, 0x11, 0xa4, 0xc0, 0x86, 0x70, + 0xc0, 0x13, 0x26, 0x21, 0x2d, 0x36, 0x71, 0x67, 0x36, 0xf9, 0x8d, 0x53, 0x39, 0xf0, 0x23, 0xf4, + 0x5f, 0xc2, 0x86, 0xa3, 0x2c, 0x84, 0xc1, 0x98, 0x4a, 0x09, 0x29, 0x2b, 0x9e, 0x75, 0xa5, 0x90, + 0x0f, 0x72, 0x55, 0x19, 0xe1, 0xd3, 0xac, 0xd1, 0xcc, 0x8d, 0x85, 0x5c, 0x1a, 0xd7, 0xd1, 0x6a, + 0x69, 0x9c, 0x00, 0x0b, 0x79, 0x0a, 0xa1, 0x7e, 0x7b, 0xcb, 0x2f, 0x03, 0xde, 0x15, 0x32, 0x7e, + 0x88, 0x96, 0x4f, 0x29, 0x93, 0x83, 0x02, 0x95, 0xd0, 0xcf, 0x6b, 0xf9, 0x6d, 0x25, 0xee, 0x14, + 0x1a, 0x5e, 0x47, 0x2d, 0x6d, 0xd2, 0x10, 0x17, 0x95, 0x61, 0xbb, 0x3d, 0xbd, 0xec, 0x5a, 0xef, + 0x29, 0x93, 0x9a, 0x92, 0xa5, 0xca, 0x87, 0x8a, 0x54, 0x99, 0x57, 0xe1, 0xb2, 0x6e, 0xf2, 0x5e, + 0x15, 0x1a, 0xde, 0x40, 0xff, 0x97, 0x37, 0x2e, 0x7d, 0xc2, 0x6e, 0xf5, 0x1a, 0x6e, 0xcb, 0x5f, + 0x2d, 0x0a, 0xa5, 0x57, 0xe0, 0x3e, 0x5a, 0x96, 0xa7, 0x7c, 0x10, 0x72, 0x29, 0x06, 0xfa, 0x3b, + 0x44, 0x3a, 0x71, 0x49, 0x9e, 0xf2, 0x5d, 0x2e, 0xc5, 0x6b, 0x1e, 0x42, 0xff, 0x47, 0x1d, 0xb5, + 0x15, 0xc2, 0x8a, 0xd3, 0x26, 0xb2, 0x52, 0x98, 0x24, 0x22, 0xe1, 0xec, 0x8f, 0xac, 0x2a, 0xd7, + 0x5d, 0x14, 0xea, 0xf3, 0x52, 0x68, 0xcc, 0x4d, 0xc1, 0x9c, 0x93, 0xc2, 0xc2, 0xdf, 0x28, 0x34, + 0xff, 0x8d, 0xc2, 0xe2, 0xbc, 0x14, 0xac, 0xbb, 0x29, 0x6c, 0x7d, 0x40, 0xe6, 0x2e, 0x95, 0x14, + 0x13, 0x84, 0xf6, 0x40, 0x16, 0x5d, 0x81, 0xb1, 0x7a, 0xd4, 0xd9, 0x16, 0xe9, 0xa0, 0x1b, 0x6d, + 0xd3, 0xc0, 0x2e, 0xb2, 0xf6, 0x40, 0x6a, 0x36, 0x78, 0xb5, 0xec, 0xb4, 0xca, 0x5b, 0xf5, 0xde, + 0xa6, 0xb1, 0xbd, 0x76, 0xfe, 0xd3, 0xa9, 0x9d, 0x4f, 0x1d, 0xe3, 0x62, 0xea, 0x18, 0x57, 0x53, + 0xc7, 0xf8, 0x7c, 0xed, 0xd4, 0x2e, 0xae, 0x9d, 0xda, 0xf7, 0x6b, 0xa7, 0x16, 0x34, 0xf5, 0x8f, + 0xea, 0xe9, 0xaf, 0x00, 0x00, 0x00, 0xff, 0xff, 0xe8, 0x3b, 0x87, 0x79, 0x43, 0x05, 0x00, 0x00, } From 9a4e7e2498ae486966bdcf5a8404bb2402ff07e6 Mon Sep 17 00:00:00 2001 From: David Pordomingo Date: Mon, 25 Mar 2019 20:34:27 +0100 Subject: [PATCH 3/3] WIP. Add vendored things Signed-off-by: David Pordomingo --- ...baa505b9f6fb2024b9999c140b75514718c988.tgz | Bin 0 -> 13140 bytes .../src-d/go-git-fixtures.v3/fixtures.go | 3 + vendor/gopkg.in/src-d/go-git.v4/merge_base.go | 211 ++++++++++++++++++ .../object/commit_walker_bfs_filtered.go | 176 +++++++++++++++ 4 files changed, 390 insertions(+) create mode 100644 vendor/gopkg.in/src-d/go-git-fixtures.v3/data/git-26baa505b9f6fb2024b9999c140b75514718c988.tgz create mode 100644 vendor/gopkg.in/src-d/go-git.v4/merge_base.go create mode 100644 vendor/gopkg.in/src-d/go-git.v4/plumbing/object/commit_walker_bfs_filtered.go diff --git a/vendor/gopkg.in/src-d/go-git-fixtures.v3/data/git-26baa505b9f6fb2024b9999c140b75514718c988.tgz b/vendor/gopkg.in/src-d/go-git-fixtures.v3/data/git-26baa505b9f6fb2024b9999c140b75514718c988.tgz new file mode 100644 index 0000000000000000000000000000000000000000..28daa33121e94e9055a7057971595505d9de124b GIT binary patch literal 13140 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