v.io/jiri@v0.0.0-20160715023856-abfb8b131290/gerrit/multipart_test.go (about)

     1  // Copyright 2016 The Vanadium Authors. All rights reserved.
     2  // Use of this source code is governed by a BSD-style
     3  // license that can be found in the LICENSE file.
     4  
     5  package gerrit
     6  
     7  import (
     8  	"reflect"
     9  	"testing"
    10  )
    11  
    12  func checkMultiPartCLSet(t *testing.T, expectedTotal int, expectedCLsByPart map[int]Change, set *MultiPartCLSet) {
    13  	if expectedTotal != set.expectedTotal {
    14  		t.Fatalf("total: want %v, got %v", expectedTotal, set.expectedTotal)
    15  	}
    16  	if !reflect.DeepEqual(expectedCLsByPart, set.parts) {
    17  		t.Fatalf("clsByPart: want %+v, got %+v", expectedCLsByPart, set.parts)
    18  	}
    19  }
    20  
    21  func TestMultiPartCLSet(t *testing.T) {
    22  	set := NewMultiPartCLSet()
    23  	checkMultiPartCLSet(t, -1, map[int]Change{}, set)
    24  
    25  	// Add a non-multipart cl.
    26  	cl := GenCL(1000, 1, "release.go.core")
    27  	if err := set.AddCL(cl); err == nil {
    28  		t.Fatalf("expected AddCL(%v) to fail and it did not", cl)
    29  	}
    30  	checkMultiPartCLSet(t, -1, map[int]Change{}, set)
    31  
    32  	// Add a multi part cl.
    33  	cl.MultiPart = &MultiPartCLInfo{
    34  		Topic: "test",
    35  		Index: 1,
    36  		Total: 2,
    37  	}
    38  	if err := set.AddCL(cl); err != nil {
    39  		t.Fatalf("AddCL(%v) failed: %v", cl, err)
    40  	}
    41  	checkMultiPartCLSet(t, 2, map[int]Change{
    42  		1: cl,
    43  	}, set)
    44  
    45  	// Test incomplete.
    46  	if expected, got := false, set.Complete(); expected != got {
    47  		t.Fatalf("want %v, got %v", expected, got)
    48  	}
    49  
    50  	// Add another multi part cl with the wrong "Total" number.
    51  	cl2 := GenMultiPartCL(1050, 2, "release.js.core", "test", 2, 3)
    52  	if err := set.AddCL(cl2); err == nil {
    53  		t.Fatalf("expected AddCL(%v) to fail and it did not", cl)
    54  	}
    55  	checkMultiPartCLSet(t, 2, map[int]Change{
    56  		1: cl,
    57  	}, set)
    58  
    59  	// Add another multi part cl with duplicated "Index" number.
    60  	cl3 := GenMultiPartCL(1052, 2, "release.js.core", "Test", 1, 2)
    61  	if err := set.AddCL(cl3); err == nil {
    62  		t.Fatalf("expected AddCL(%v) to fail and it did not", cl)
    63  	}
    64  	checkMultiPartCLSet(t, 2, map[int]Change{
    65  		1: cl,
    66  	}, set)
    67  
    68  	// Add another multi part cl with the wrong "Topic".
    69  	cl4 := GenMultiPartCL(1062, 2, "release.js.core", "test123", 1, 2)
    70  	if err := set.AddCL(cl4); err == nil {
    71  		t.Fatalf("expected AddCL(%v) to fail and it did not", cl)
    72  	}
    73  	checkMultiPartCLSet(t, 2, map[int]Change{
    74  		1: cl,
    75  	}, set)
    76  
    77  	// Add a valid multi part cl.
    78  	cl5 := GenMultiPartCL(1072, 2, "release.js.core", "test", 2, 2)
    79  	if err := set.AddCL(cl5); err != nil {
    80  		t.Fatalf("AddCL(%v) failed: %v", cl, err)
    81  	}
    82  	checkMultiPartCLSet(t, 2, map[int]Change{
    83  		1: cl,
    84  		2: cl5,
    85  	}, set)
    86  
    87  	// Test complete.
    88  	if expected, got := true, set.Complete(); expected != got {
    89  		t.Fatalf("want %v, got %v", expected, got)
    90  	}
    91  
    92  	// Test cls.
    93  	if expected, got := (CLList{cl, cl5}), set.CLs(); !reflect.DeepEqual(expected, got) {
    94  		t.Fatalf("want %v, got %v", expected, got)
    95  	}
    96  }
    97  
    98  func TestNewOpenCLs(t *testing.T) {
    99  	nonMultiPartCLs := CLList{
   100  		GenCL(1010, 1, "release.go.core"),
   101  		GenCL(1020, 2, "release.go.tools"),
   102  		GenCL(1030, 3, "release.js.core"),
   103  
   104  		GenMultiPartCL(1000, 1, "release.js.core", "T1", 1, 2),
   105  		GenMultiPartCL(1001, 1, "release.go.core", "T1", 2, 2),
   106  		GenMultiPartCL(1002, 2, "release.go.core", "T2", 2, 2),
   107  		GenMultiPartCL(1001, 2, "release.go.core", "T1", 2, 2),
   108  	}
   109  	multiPartCLs := CLList{
   110  		// Multi part CLs.
   111  		// The first two form a complete set for topic T1.
   112  		// The third one looks like the second one, but has a different topic.
   113  		// The last one has a larger patchset than the second one.
   114  		GenMultiPartCL(1000, 1, "release.js.core", "T1", 1, 2),
   115  		GenMultiPartCL(1001, 1, "release.go.core", "T1", 2, 2),
   116  		GenMultiPartCL(1002, 2, "release.go.core", "T2", 2, 2),
   117  		GenMultiPartCL(1001, 2, "release.go.core", "T1", 2, 2),
   118  	}
   119  
   120  	type testCase struct {
   121  		prevCLsMap CLRefMap
   122  		curCLs     CLList
   123  		expected   []CLList
   124  	}
   125  	testCases := []testCase{
   126  		////////////////////////////////
   127  		// Tests for non-multipart CLs.
   128  
   129  		// Both prevCLsMap and curCLs are empty.
   130  		testCase{
   131  			prevCLsMap: CLRefMap{},
   132  			curCLs:     CLList{},
   133  			expected:   []CLList{},
   134  		},
   135  		// prevCLsMap is empty, curCLs is not.
   136  		testCase{
   137  			prevCLsMap: CLRefMap{},
   138  			curCLs:     CLList{nonMultiPartCLs[0], nonMultiPartCLs[1]},
   139  			expected:   []CLList{CLList{nonMultiPartCLs[0]}, CLList{nonMultiPartCLs[1]}},
   140  		},
   141  		// prevCLsMap is not empty, curCLs is.
   142  		testCase{
   143  			prevCLsMap: CLRefMap{nonMultiPartCLs[0].Reference(): nonMultiPartCLs[0]},
   144  			curCLs:     CLList{},
   145  			expected:   []CLList{},
   146  		},
   147  		// prevCLsMap and curCLs are not empty, and they have overlapping refs.
   148  		testCase{
   149  			prevCLsMap: CLRefMap{
   150  				nonMultiPartCLs[0].Reference(): nonMultiPartCLs[0],
   151  				nonMultiPartCLs[1].Reference(): nonMultiPartCLs[1],
   152  			},
   153  			curCLs:   CLList{nonMultiPartCLs[1], nonMultiPartCLs[2]},
   154  			expected: []CLList{CLList{nonMultiPartCLs[2]}},
   155  		},
   156  		// prevCLsMap and curCLs are not empty, and they have NO overlapping refs.
   157  		testCase{
   158  			prevCLsMap: CLRefMap{nonMultiPartCLs[0].Reference(): nonMultiPartCLs[0]},
   159  			curCLs:     CLList{nonMultiPartCLs[1]},
   160  			expected:   []CLList{CLList{nonMultiPartCLs[1]}},
   161  		},
   162  
   163  		////////////////////////////////
   164  		// Tests for multi part CLs.
   165  
   166  		// len(curCLs) > len(prevCLsMap).
   167  		// And the CLs in curCLs have different topics.
   168  		testCase{
   169  			prevCLsMap: CLRefMap{multiPartCLs[0].Reference(): multiPartCLs[0]},
   170  			curCLs:     CLList{multiPartCLs[0], multiPartCLs[2]},
   171  			expected:   []CLList{},
   172  		},
   173  		// len(curCLs) > len(prevCLsMap).
   174  		// And the CLs in curCLs form a complete multi part cls set.
   175  		testCase{
   176  			prevCLsMap: CLRefMap{multiPartCLs[0].Reference(): multiPartCLs[0]},
   177  			curCLs:     CLList{multiPartCLs[0], multiPartCLs[1]},
   178  			expected:   []CLList{CLList{multiPartCLs[0], multiPartCLs[1]}},
   179  		},
   180  		// len(curCLs) == len(prevCLsMap).
   181  		// And cl[6] has a larger patchset than multiPartCLs[4] with identical cl number.
   182  		testCase{
   183  			prevCLsMap: CLRefMap{
   184  				multiPartCLs[0].Reference(): multiPartCLs[0],
   185  				multiPartCLs[1].Reference(): multiPartCLs[1],
   186  			},
   187  			curCLs:   CLList{multiPartCLs[0], multiPartCLs[3]},
   188  			expected: []CLList{CLList{multiPartCLs[0], multiPartCLs[3]}},
   189  		},
   190  
   191  		////////////////////////////////
   192  		// Tests for mixed.
   193  		testCase{
   194  			prevCLsMap: CLRefMap{
   195  				multiPartCLs[0].Reference(): multiPartCLs[0],
   196  				multiPartCLs[1].Reference(): multiPartCLs[1],
   197  			},
   198  			curCLs: CLList{nonMultiPartCLs[0], multiPartCLs[0], multiPartCLs[3]},
   199  			expected: []CLList{
   200  				CLList{nonMultiPartCLs[0]},
   201  				CLList{multiPartCLs[0], multiPartCLs[3]},
   202  			},
   203  		},
   204  	}
   205  
   206  	for index, test := range testCases {
   207  		got, errs := NewOpenCLs(test.prevCLsMap, test.curCLs)
   208  		if !reflect.DeepEqual(test.expected, got) {
   209  			t.Fatalf("case %d: want: %v, got: %v", index, test.expected, got)
   210  		}
   211  		if len(errs) != 0 {
   212  			t.Fatalf("case %d: multi-part errors: ", index, errs)
   213  		}
   214  	}
   215  }