[build_init] Ensure the input build is valid
Change-Id: Iffdf4fef330f87aa2e11709bdcd4dab19db1b584
diff --git a/cmd/build_init/main.go b/cmd/build_init/main.go
index c3abd31..decb6d8 100644
--- a/cmd/build_init/main.go
+++ b/cmd/build_init/main.go
@@ -96,9 +96,32 @@
if err != nil {
return fmt.Errorf("failed to read build.proto: %v", err)
}
+ if err := validateBuild(*build); err != nil {
+ return fmt.Errorf("invalid build message: %v", err)
+ }
return err
}
+func validateBuild(build buildbucketpb.Build) error {
+ if build.Input == nil {
+ return errors.New("build has no input")
+ }
+ if build.Input.GitilesCommit == nil {
+ return errors.New("build input has no Gitiles commit")
+ }
+ if build.Builder == nil {
+ return errors.New("input build has no builder information")
+ }
+ if build.Builder.Bucket == "" {
+ return errors.New("input build's builder has no bucket")
+ }
+ if build.Builder.Builder == "" {
+ return errors.New("input build's builder name is empty")
+ }
+ return nil
+}
+
+// Execute runs the program. Public for testing.
func execute(ctx context.Context) (code int) {
if err := checkout.Checkout(*build.Input, *specRepoURL); err != nil {
log.Printf("failed to checkout %s: %v", specRepoURL.String(), err)
diff --git a/cmd/build_init/main_test.go b/cmd/build_init/main_test.go
index 537fe11..111b8e7 100644
--- a/cmd/build_init/main_test.go
+++ b/cmd/build_init/main_test.go
@@ -71,3 +71,125 @@
t.Errorf("expected an error but got %v", output)
}
}
+
+func TestValidateBuild(t *testing.T) {
+ tests := []struct {
+ name string
+ build *buildbucketpb.Build
+ expectError bool
+ }{
+ {
+ name: "should err if builder property is nil",
+ build: &buildbucketpb.Build{
+ Input: &buildbucketpb.Build_Input{
+ GitilesCommit: &buildbucketpb.GitilesCommit{
+ Host: "host",
+ Project: "project",
+ Id: "id",
+ },
+ },
+ },
+ expectError: true,
+ },
+ {
+ name: "should err if builder bucket is empty",
+ build: &buildbucketpb.Build{
+ Builder: &buildbucketpb.BuilderID{
+ Project: "project",
+ Builder: "builder",
+ },
+ Input: &buildbucketpb.Build_Input{
+ GitilesCommit: &buildbucketpb.GitilesCommit{
+ Host: "host",
+ Project: "project",
+ Id: "id",
+ },
+ },
+ },
+ expectError: true,
+ },
+ {
+ name: "should err if builder name is empty",
+ build: &buildbucketpb.Build{
+ Builder: &buildbucketpb.BuilderID{
+ Project: "project",
+ Bucket: "bucket",
+ },
+ Input: &buildbucketpb.Build_Input{
+ GitilesCommit: &buildbucketpb.GitilesCommit{
+ Host: "host",
+ Project: "project",
+ Id: "id",
+ },
+ },
+ },
+ expectError: true,
+ },
+ {
+ name: "should err if the build input is nil",
+ build: &buildbucketpb.Build{
+ Builder: &buildbucketpb.BuilderID{
+ Project: "project",
+ Builder: "builder",
+ Bucket: "bucket",
+ },
+ },
+ expectError: true,
+ },
+ {
+ name: "should err if the build input has no GitilesCommit",
+ build: &buildbucketpb.Build{
+ Builder: &buildbucketpb.BuilderID{
+ Project: "project",
+ Builder: "builder",
+ Bucket: "bucket",
+ },
+ Input: &buildbucketpb.Build_Input{},
+ },
+ expectError: true,
+ },
+ {
+ name: "should err if the build input has a GerritChange but no GitilesCommit",
+ build: &buildbucketpb.Build{
+ Builder: &buildbucketpb.BuilderID{
+ Project: "project",
+ Builder: "builder",
+ Bucket: "bucket",
+ },
+ Input: &buildbucketpb.Build_Input{
+ GerritChanges: []*buildbucketpb.GerritChange{{}},
+ },
+ },
+ expectError: true,
+ },
+ {
+ name: "should return nil if all fields are non-nil and non-empty",
+ build: &buildbucketpb.Build{
+ Builder: &buildbucketpb.BuilderID{
+ Project: "project",
+ Bucket: "bucket",
+ Builder: "builder",
+ },
+ Input: &buildbucketpb.Build_Input{
+ GitilesCommit: &buildbucketpb.GitilesCommit{
+ Host: "host",
+ Project: "project",
+ Id: "id",
+ },
+ },
+ },
+ expectError: false,
+ },
+ }
+ for _, tt := range tests {
+ t.Run(tt.name, func(t *testing.T) {
+ err := validateBuild(*tt.build)
+ switch {
+ case err != nil && !tt.expectError:
+ t.Errorf("unexpected error: %v", err)
+ case err == nil && tt.expectError:
+ t.Errorf("wanted error but got nil")
+ }
+ })
+ }
+}