github.com/munnerz/test-infra@v0.0.0-20190108210205-ce3d181dc989/prow/cmd/mkpj/main.go (about)

     1  /*
     2  Copyright 2017 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 main
    18  
    19  import (
    20  	"errors"
    21  	"flag"
    22  	"fmt"
    23  	"os"
    24  	"strings"
    25  
    26  	"github.com/sirupsen/logrus"
    27  	"sigs.k8s.io/yaml"
    28  
    29  	"k8s.io/test-infra/prow/config"
    30  	"k8s.io/test-infra/prow/kube"
    31  	"k8s.io/test-infra/prow/pjutil"
    32  )
    33  
    34  type options struct {
    35  	jobName       string
    36  	configPath    string
    37  	jobConfigPath string
    38  
    39  	baseRef    string
    40  	baseSha    string
    41  	pullNumber int
    42  	pullSha    string
    43  	pullAuthor string
    44  }
    45  
    46  func (o *options) Validate() error {
    47  	if o.jobName == "" {
    48  		return errors.New("required flag --job was unset")
    49  	}
    50  
    51  	if o.configPath == "" {
    52  		return errors.New("required flag --config-path was unset")
    53  	}
    54  
    55  	return nil
    56  }
    57  
    58  func gatherOptions() options {
    59  	o := options{}
    60  	flag.StringVar(&o.jobName, "job", "", "Job to run.")
    61  	flag.StringVar(&o.configPath, "config-path", "", "Path to config.yaml.")
    62  	flag.StringVar(&o.jobConfigPath, "job-config-path", "", "Path to prow job configs.")
    63  	flag.StringVar(&o.baseRef, "base-ref", "", "Git base ref under test")
    64  	flag.StringVar(&o.baseSha, "base-sha", "", "Git base SHA under test")
    65  	flag.IntVar(&o.pullNumber, "pull-number", 0, "Git pull number under test")
    66  	flag.StringVar(&o.pullSha, "pull-sha", "", "Git pull SHA under test")
    67  	flag.StringVar(&o.pullAuthor, "pull-author", "", "Git pull author under test")
    68  	flag.Parse()
    69  	return o
    70  }
    71  
    72  func main() {
    73  	o := gatherOptions()
    74  	if err := o.Validate(); err != nil {
    75  		logrus.Fatalf("Invalid options: %v", err)
    76  	}
    77  
    78  	conf, err := config.Load(o.configPath, o.jobConfigPath)
    79  	if err != nil {
    80  		logrus.WithError(err).Fatal("Error loading config.")
    81  	}
    82  
    83  	var pjs kube.ProwJobSpec
    84  	var labels map[string]string
    85  	var found bool
    86  	var needsBaseRef bool
    87  	var needsPR bool
    88  	for fullRepoName, ps := range conf.Presubmits {
    89  		org, repo, err := splitRepoName(fullRepoName)
    90  		if err != nil {
    91  			logrus.WithError(err).Warnf("Invalid repo name %s.", fullRepoName)
    92  			continue
    93  		}
    94  		for _, p := range ps {
    95  			if p.Name == o.jobName {
    96  				pjs = pjutil.PresubmitSpec(p, kube.Refs{
    97  					Org:     org,
    98  					Repo:    repo,
    99  					BaseRef: o.baseRef,
   100  					BaseSHA: o.baseSha,
   101  					Pulls: []kube.Pull{{
   102  						Author: o.pullAuthor,
   103  						Number: o.pullNumber,
   104  						SHA:    o.pullSha,
   105  					}},
   106  				})
   107  				labels = p.Labels
   108  				found = true
   109  				needsBaseRef = true
   110  				needsPR = true
   111  			}
   112  		}
   113  	}
   114  	for fullRepoName, ps := range conf.Postsubmits {
   115  		org, repo, err := splitRepoName(fullRepoName)
   116  		if err != nil {
   117  			logrus.WithError(err).Warnf("Invalid repo name %s.", fullRepoName)
   118  			continue
   119  		}
   120  		for _, p := range ps {
   121  			if p.Name == o.jobName {
   122  				pjs = pjutil.PostsubmitSpec(p, kube.Refs{
   123  					Org:     org,
   124  					Repo:    repo,
   125  					BaseRef: o.baseRef,
   126  					BaseSHA: o.baseSha,
   127  				})
   128  				labels = p.Labels
   129  				found = true
   130  				needsBaseRef = true
   131  			}
   132  		}
   133  	}
   134  	for _, p := range conf.Periodics {
   135  		if p.Name == o.jobName {
   136  			pjs = pjutil.PeriodicSpec(p)
   137  			labels = p.Labels
   138  			found = true
   139  		}
   140  	}
   141  	if !found {
   142  		logrus.Fatalf("Job %s not found.", o.jobName)
   143  	}
   144  	if needsBaseRef {
   145  		if pjs.Refs.BaseRef == "" {
   146  			fmt.Fprint(os.Stderr, "Base ref (e.g. master): ")
   147  			fmt.Scanln(&pjs.Refs.BaseRef)
   148  		}
   149  		if pjs.Refs.BaseSHA == "" {
   150  			fmt.Fprint(os.Stderr, "Base SHA (e.g. 72bcb5d80): ")
   151  			fmt.Scanln(&pjs.Refs.BaseSHA)
   152  		}
   153  	}
   154  	if needsPR {
   155  		if pjs.Refs.Pulls[0].Number == 0 {
   156  			fmt.Fprint(os.Stderr, "PR Number: ")
   157  			fmt.Scanln(&pjs.Refs.Pulls[0].Number)
   158  		}
   159  		if pjs.Refs.Pulls[0].Author == "" {
   160  			fmt.Fprint(os.Stderr, "PR author: ")
   161  			fmt.Scanln(&pjs.Refs.Pulls[0].Author)
   162  		}
   163  		if pjs.Refs.Pulls[0].SHA == "" {
   164  			fmt.Fprint(os.Stderr, "PR SHA (e.g. 72bcb5d80): ")
   165  			fmt.Scanln(&pjs.Refs.Pulls[0].SHA)
   166  		}
   167  	}
   168  	pj := pjutil.NewProwJob(pjs, labels)
   169  	b, err := yaml.Marshal(&pj)
   170  	if err != nil {
   171  		logrus.WithError(err).Fatal("Error marshalling YAML.")
   172  	}
   173  	fmt.Print(string(b))
   174  }
   175  
   176  func splitRepoName(repo string) (string, string, error) {
   177  	s := strings.SplitN(repo, "/", 2)
   178  	if len(s) != 2 {
   179  		return "", "", fmt.Errorf("repo %s cannot be split into org/repo", repo)
   180  	}
   181  	return s[0], s[1], nil
   182  }