github.com/munnerz/test-infra@v0.0.0-20190108210205-ce3d181dc989/prow/gerrit/adapter/adapter_test.go (about) 1 /* 2 Copyright 2018 The Kubernetes Authors. 3 4 Licensed under the Apache License, Version 2.0 (the "License"); 5 you may not use this file except in compliance with the License. 6 You may obtain a copy of the License at 7 8 http://www.apache.org/licenses/LICENSE-2.0 9 10 Unless required by applicable law or agreed to in writing, software 11 distributed under the License is distributed on an "AS IS" BASIS, 12 WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 See the License for the specific language governing permissions and 14 limitations under the License. 15 */ 16 17 package adapter 18 19 import ( 20 "sync" 21 "testing" 22 "time" 23 24 "k8s.io/test-infra/prow/gerrit/client" 25 26 "k8s.io/test-infra/prow/config" 27 "k8s.io/test-infra/prow/kube" 28 ) 29 30 type fca struct { 31 sync.Mutex 32 c *config.Config 33 } 34 35 func (f *fca) Config() *config.Config { 36 f.Lock() 37 defer f.Unlock() 38 return f.c 39 } 40 41 type fkc struct { 42 sync.Mutex 43 prowjobs []kube.ProwJob 44 } 45 46 func (f *fkc) CreateProwJob(pj kube.ProwJob) (kube.ProwJob, error) { 47 f.Lock() 48 defer f.Unlock() 49 f.prowjobs = append(f.prowjobs, pj) 50 return pj, nil 51 } 52 53 type fgc struct{} 54 55 func (f *fgc) QueryChanges(lastUpdate time.Time, rateLimit int) map[string][]client.ChangeInfo { 56 return nil 57 } 58 59 func (f *fgc) SetReview(instance, id, revision, message string, labels map[string]string) error { 60 return nil 61 } 62 63 func (f *fgc) GetBranchRevision(instance, project, branch string) (string, error) { 64 return "abc", nil 65 } 66 67 func TestMakeCloneURI(t *testing.T) { 68 cases := []struct { 69 name string 70 instance string 71 project string 72 expected string 73 err bool 74 }{ 75 { 76 name: "happy case", 77 instance: "https://android.googlesource.com", 78 project: "platform/build", 79 expected: "https://android.googlesource.com/platform/build", 80 }, 81 { 82 name: "reject non urls", 83 instance: "!!!://", 84 project: "platform/build", 85 err: true, 86 }, 87 { 88 name: "require instance to specify host", 89 instance: "android.googlesource.com", 90 project: "platform/build", 91 err: true, 92 }, 93 { 94 name: "reject instances with paths", 95 instance: "https://android.googlesource.com/platform", 96 project: "build", 97 err: true, 98 }, 99 } 100 101 for _, tc := range cases { 102 t.Run(tc.name, func(t *testing.T) { 103 actual, err := makeCloneURI(tc.instance, tc.project) 104 switch { 105 case err != nil: 106 if !tc.err { 107 t.Errorf("unexpected error: %v", err) 108 } 109 case tc.err: 110 t.Error("failed to receive expected exception") 111 case actual.String() != tc.expected: 112 t.Errorf("actual %q != expected %q", actual.String(), tc.expected) 113 } 114 }) 115 } 116 } 117 118 func TestProcessChange(t *testing.T) { 119 var testcases = []struct { 120 name string 121 change client.ChangeInfo 122 numPJ int 123 pjRef string 124 shouldError bool 125 }{ 126 { 127 name: "no revisions", 128 change: client.ChangeInfo{ 129 CurrentRevision: "1", 130 Project: "test-infra", 131 Status: "NEW", 132 }, 133 shouldError: true, 134 }, 135 { 136 name: "wrong project", 137 change: client.ChangeInfo{ 138 CurrentRevision: "1", 139 Project: "woof", 140 Status: "NEW", 141 Revisions: map[string]client.RevisionInfo{ 142 "1": {}, 143 }, 144 }, 145 }, 146 { 147 name: "normal", 148 change: client.ChangeInfo{ 149 CurrentRevision: "1", 150 Project: "test-infra", 151 Status: "NEW", 152 Revisions: map[string]client.RevisionInfo{ 153 "1": { 154 Ref: "refs/changes/00/1/1", 155 }, 156 }, 157 }, 158 numPJ: 1, 159 pjRef: "refs/changes/00/1/1", 160 }, 161 { 162 name: "multiple revisions", 163 change: client.ChangeInfo{ 164 CurrentRevision: "2", 165 Project: "test-infra", 166 Status: "NEW", 167 Revisions: map[string]client.RevisionInfo{ 168 "1": { 169 Ref: "refs/changes/00/2/1", 170 }, 171 "2": { 172 Ref: "refs/changes/00/2/2", 173 }, 174 }, 175 }, 176 numPJ: 1, 177 pjRef: "refs/changes/00/2/2", 178 }, 179 { 180 name: "other-test-with-https", 181 change: client.ChangeInfo{ 182 CurrentRevision: "1", 183 Project: "other-repo", 184 Status: "NEW", 185 Revisions: map[string]client.RevisionInfo{ 186 "1": { 187 Ref: "refs/changes/00/1/1", 188 }, 189 }, 190 }, 191 numPJ: 1, 192 pjRef: "refs/changes/00/1/1", 193 }, 194 { 195 name: "merged change should trigger postsubmit", 196 change: client.ChangeInfo{ 197 CurrentRevision: "1", 198 Project: "postsubmits-project", 199 Status: "MERGED", 200 Revisions: map[string]client.RevisionInfo{ 201 "1": { 202 Ref: "refs/changes/00/1/1", 203 }, 204 }, 205 }, 206 numPJ: 1, 207 pjRef: "refs/changes/00/1/1", 208 }, 209 { 210 name: "merged change on project without postsubmits", 211 change: client.ChangeInfo{ 212 CurrentRevision: "1", 213 Project: "test-infra", 214 Status: "MERGED", 215 Revisions: map[string]client.RevisionInfo{ 216 "1": { 217 Ref: "refs/changes/00/1/1", 218 }, 219 }, 220 }, 221 }, 222 { 223 name: "presubmit runs when a file matches run_if_changed", 224 change: client.ChangeInfo{ 225 CurrentRevision: "1", 226 Project: "test-infra", 227 Status: "NEW", 228 Revisions: map[string]client.RevisionInfo{ 229 "1": { 230 Files: map[string]client.FileInfo{ 231 "bee-movie-script.txt": {}, 232 "africa-lyrics.txt": {}, 233 "important-code.go": {}, 234 }, 235 }, 236 }, 237 }, 238 numPJ: 2, 239 }, 240 { 241 name: "presubmit doesn't run when no files match run_if_changed", 242 change: client.ChangeInfo{ 243 CurrentRevision: "1", 244 Project: "test-infra", 245 Status: "NEW", 246 Revisions: map[string]client.RevisionInfo{ 247 "1": { 248 Files: map[string]client.FileInfo{ 249 "hacky-hack.sh": {}, 250 "README.md": {}, 251 "let-it-go.txt": {}, 252 }, 253 }, 254 }, 255 }, 256 numPJ: 1, 257 }, 258 } 259 260 for _, tc := range testcases { 261 testInfraPresubmits := []config.Presubmit{ 262 { 263 JobBase: config.JobBase{ 264 Name: "test-foo", 265 }, 266 }, 267 { 268 JobBase: config.JobBase{ 269 Name: "test-go", 270 }, 271 RegexpChangeMatcher: config.RegexpChangeMatcher{ 272 RunIfChanged: "\\.go", 273 }, 274 }, 275 } 276 if err := config.SetPresubmitRegexes(testInfraPresubmits); err != nil { 277 t.Fatalf("could not set regexes: %v", err) 278 } 279 280 fca := &fca{ 281 c: &config.Config{ 282 JobConfig: config.JobConfig{ 283 Presubmits: map[string][]config.Presubmit{ 284 "gerrit/test-infra": testInfraPresubmits, 285 "https://gerrit/other-repo": { 286 { 287 JobBase: config.JobBase{ 288 Name: "other-test", 289 }, 290 }, 291 }, 292 }, 293 Postsubmits: map[string][]config.Postsubmit{ 294 "gerrit/postsubmits-project": { 295 { 296 JobBase: config.JobBase{ 297 Name: "test-bar", 298 }, 299 }, 300 }, 301 }, 302 }, 303 }, 304 } 305 306 fkc := &fkc{} 307 308 c := &Controller{ 309 ca: fca, 310 kc: fkc, 311 gc: &fgc{}, 312 } 313 314 err := c.ProcessChange("https://gerrit", tc.change) 315 if err != nil && !tc.shouldError { 316 t.Errorf("tc %s, expect no error, but got %v", tc.name, err) 317 continue 318 } else if err == nil && tc.shouldError { 319 t.Errorf("tc %s, expect error, but got none", tc.name) 320 continue 321 } 322 323 if len(fkc.prowjobs) != tc.numPJ { 324 t.Errorf("tc %s - should make %d prowjob, got %d", tc.name, tc.numPJ, len(fkc.prowjobs)) 325 } 326 327 if len(fkc.prowjobs) > 0 { 328 refs := fkc.prowjobs[0].Spec.Refs 329 if refs.Org != "gerrit" { 330 t.Errorf("%s: org %s != gerrit", tc.name, refs.Org) 331 } 332 if refs.Repo != tc.change.Project { 333 t.Errorf("%s: repo %s != expected %s", tc.name, refs.Repo, tc.change.Project) 334 } 335 if fkc.prowjobs[0].Spec.Refs.Pulls[0].Ref != tc.pjRef { 336 t.Errorf("tc %s - ref should be %s, got %s", tc.name, tc.pjRef, fkc.prowjobs[0].Spec.Refs.Pulls[0].Ref) 337 } 338 if fkc.prowjobs[0].Spec.Refs.BaseSHA != "abc" { 339 t.Errorf("tc %s - BaseSHA should be abc, got %s", tc.name, fkc.prowjobs[0].Spec.Refs.BaseSHA) 340 } 341 } 342 } 343 }