github.com/vtorhonen/terraform@v0.9.0-beta2.0.20170307220345-5d894e4ffda7/builtin/providers/aws/resource_aws_codebuild_project.go (about)

     1  package aws
     2  
     3  import (
     4  	"bytes"
     5  	"fmt"
     6  	"log"
     7  	"regexp"
     8  	"time"
     9  
    10  	"github.com/aws/aws-sdk-go/aws"
    11  	"github.com/aws/aws-sdk-go/service/codebuild"
    12  	"github.com/hashicorp/terraform/helper/hashcode"
    13  	"github.com/hashicorp/terraform/helper/resource"
    14  	"github.com/hashicorp/terraform/helper/schema"
    15  )
    16  
    17  func resourceAwsCodeBuildProject() *schema.Resource {
    18  	return &schema.Resource{
    19  		Create: resourceAwsCodeBuildProjectCreate,
    20  		Read:   resourceAwsCodeBuildProjectRead,
    21  		Update: resourceAwsCodeBuildProjectUpdate,
    22  		Delete: resourceAwsCodeBuildProjectDelete,
    23  
    24  		Schema: map[string]*schema.Schema{
    25  			"artifacts": &schema.Schema{
    26  				Type:     schema.TypeSet,
    27  				Required: true,
    28  				MaxItems: 1,
    29  				Elem: &schema.Resource{
    30  					Schema: map[string]*schema.Schema{
    31  						"name": {
    32  							Type:     schema.TypeString,
    33  							Optional: true,
    34  						},
    35  						"location": {
    36  							Type:     schema.TypeString,
    37  							Optional: true,
    38  						},
    39  						"namespace_type": {
    40  							Type:         schema.TypeString,
    41  							Optional:     true,
    42  							ValidateFunc: validateAwsCodeBuildArifactsNamespaceType,
    43  						},
    44  						"packaging": {
    45  							Type:     schema.TypeString,
    46  							Optional: true,
    47  						},
    48  						"path": {
    49  							Type:     schema.TypeString,
    50  							Optional: true,
    51  						},
    52  						"type": {
    53  							Type:         schema.TypeString,
    54  							Required:     true,
    55  							ValidateFunc: validateAwsCodeBuildArifactsType,
    56  						},
    57  					},
    58  				},
    59  				Set: resourceAwsCodeBuildProjectArtifactsHash,
    60  			},
    61  			"description": {
    62  				Type:         schema.TypeString,
    63  				Optional:     true,
    64  				Computed:     true,
    65  				ValidateFunc: validateAwsCodeBuildProjectDescription,
    66  			},
    67  			"encryption_key": {
    68  				Type:     schema.TypeString,
    69  				Optional: true,
    70  				Computed: true,
    71  			},
    72  			"environment": &schema.Schema{
    73  				Type:     schema.TypeSet,
    74  				Required: true,
    75  				MaxItems: 1,
    76  				Elem: &schema.Resource{
    77  					Schema: map[string]*schema.Schema{
    78  						"compute_type": {
    79  							Type:         schema.TypeString,
    80  							Required:     true,
    81  							ValidateFunc: validateAwsCodeBuildEnvironmentComputeType,
    82  						},
    83  						"environment_variable": &schema.Schema{
    84  							Type:     schema.TypeList,
    85  							Optional: true,
    86  							Computed: true,
    87  							Elem: &schema.Resource{
    88  								Schema: map[string]*schema.Schema{
    89  									"name": {
    90  										Type:     schema.TypeString,
    91  										Required: true,
    92  									},
    93  									"value": {
    94  										Type:     schema.TypeString,
    95  										Required: true,
    96  									},
    97  								},
    98  							},
    99  						},
   100  						"image": {
   101  							Type:     schema.TypeString,
   102  							Required: true,
   103  						},
   104  						"type": {
   105  							Type:         schema.TypeString,
   106  							Required:     true,
   107  							ValidateFunc: validateAwsCodeBuildEnvironmentType,
   108  						},
   109  					},
   110  				},
   111  				Set: resourceAwsCodeBuildProjectEnvironmentHash,
   112  			},
   113  			"name": {
   114  				Type:         schema.TypeString,
   115  				Required:     true,
   116  				ForceNew:     true,
   117  				ValidateFunc: validateAwsCodeBuildProjectName,
   118  			},
   119  			"service_role": {
   120  				Type:     schema.TypeString,
   121  				Optional: true,
   122  				Computed: true,
   123  			},
   124  			"source": &schema.Schema{
   125  				Type: schema.TypeSet,
   126  				Elem: &schema.Resource{
   127  					Schema: map[string]*schema.Schema{
   128  						"auth": &schema.Schema{
   129  							Type: schema.TypeSet,
   130  							Elem: &schema.Resource{
   131  								Schema: map[string]*schema.Schema{
   132  									"resource": {
   133  										Type:     schema.TypeString,
   134  										Optional: true,
   135  									},
   136  									"type": {
   137  										Type:         schema.TypeString,
   138  										Required:     true,
   139  										ValidateFunc: validateAwsCodeBuildSourceAuthType,
   140  									},
   141  								},
   142  							},
   143  							Optional: true,
   144  						},
   145  						"buildspec": {
   146  							Type:     schema.TypeString,
   147  							Optional: true,
   148  						},
   149  						"location": {
   150  							Type:     schema.TypeString,
   151  							Optional: true,
   152  						},
   153  						"type": {
   154  							Type:         schema.TypeString,
   155  							Required:     true,
   156  							ValidateFunc: validateAwsCodeBuildSourceType,
   157  						},
   158  					},
   159  				},
   160  				Required: true,
   161  				MaxItems: 1,
   162  			},
   163  			"timeout": {
   164  				Type:         schema.TypeInt,
   165  				Optional:     true,
   166  				ValidateFunc: validateAwsCodeBuildTimeout,
   167  			},
   168  			"tags": tagsSchema(),
   169  		},
   170  	}
   171  }
   172  
   173  func resourceAwsCodeBuildProjectCreate(d *schema.ResourceData, meta interface{}) error {
   174  	conn := meta.(*AWSClient).codebuildconn
   175  
   176  	projectEnv := expandProjectEnvironment(d)
   177  	projectSource := expandProjectSource(d)
   178  	projectArtifacts := expandProjectArtifacts(d)
   179  
   180  	params := &codebuild.CreateProjectInput{
   181  		Environment: projectEnv,
   182  		Name:        aws.String(d.Get("name").(string)),
   183  		Source:      &projectSource,
   184  		Artifacts:   &projectArtifacts,
   185  	}
   186  
   187  	if v, ok := d.GetOk("description"); ok {
   188  		params.Description = aws.String(v.(string))
   189  	}
   190  
   191  	if v, ok := d.GetOk("encryption_key"); ok {
   192  		params.EncryptionKey = aws.String(v.(string))
   193  	}
   194  
   195  	if v, ok := d.GetOk("service_role"); ok {
   196  		params.ServiceRole = aws.String(v.(string))
   197  	}
   198  
   199  	if v, ok := d.GetOk("timeout"); ok {
   200  		params.TimeoutInMinutes = aws.Int64(int64(v.(int)))
   201  	}
   202  
   203  	if v, ok := d.GetOk("tags"); ok {
   204  		params.Tags = tagsFromMapCodeBuild(v.(map[string]interface{}))
   205  	}
   206  
   207  	var resp *codebuild.CreateProjectOutput
   208  	err := resource.Retry(2*time.Minute, func() *resource.RetryError {
   209  		var err error
   210  
   211  		resp, err = conn.CreateProject(params)
   212  
   213  		if err != nil {
   214  			return resource.RetryableError(err)
   215  		}
   216  
   217  		return resource.NonRetryableError(err)
   218  	})
   219  
   220  	if err != nil {
   221  		return fmt.Errorf("[ERROR] Error creating CodeBuild project: %s", err)
   222  	}
   223  
   224  	d.SetId(*resp.Project.Arn)
   225  
   226  	return resourceAwsCodeBuildProjectUpdate(d, meta)
   227  }
   228  
   229  func expandProjectArtifacts(d *schema.ResourceData) codebuild.ProjectArtifacts {
   230  	configs := d.Get("artifacts").(*schema.Set).List()
   231  	data := configs[0].(map[string]interface{})
   232  
   233  	projectArtifacts := codebuild.ProjectArtifacts{
   234  		Type: aws.String(data["type"].(string)),
   235  	}
   236  
   237  	if data["location"].(string) != "" {
   238  		projectArtifacts.Location = aws.String(data["location"].(string))
   239  	}
   240  
   241  	if data["name"].(string) != "" {
   242  		projectArtifacts.Name = aws.String(data["name"].(string))
   243  	}
   244  
   245  	if data["namespace_type"].(string) != "" {
   246  		projectArtifacts.NamespaceType = aws.String(data["namespace_type"].(string))
   247  	}
   248  
   249  	if data["packaging"].(string) != "" {
   250  		projectArtifacts.Packaging = aws.String(data["packaging"].(string))
   251  	}
   252  
   253  	if data["path"].(string) != "" {
   254  		projectArtifacts.Path = aws.String(data["path"].(string))
   255  	}
   256  
   257  	return projectArtifacts
   258  }
   259  
   260  func expandProjectEnvironment(d *schema.ResourceData) *codebuild.ProjectEnvironment {
   261  	configs := d.Get("environment").(*schema.Set).List()
   262  	projectEnv := &codebuild.ProjectEnvironment{}
   263  
   264  	envConfig := configs[0].(map[string]interface{})
   265  
   266  	if v := envConfig["compute_type"]; v != nil {
   267  		projectEnv.ComputeType = aws.String(v.(string))
   268  	}
   269  
   270  	if v := envConfig["image"]; v != nil {
   271  		projectEnv.Image = aws.String(v.(string))
   272  	}
   273  
   274  	if v := envConfig["type"]; v != nil {
   275  		projectEnv.Type = aws.String(v.(string))
   276  	}
   277  
   278  	if v := envConfig["environment_variable"]; v != nil {
   279  		envVariables := v.([]interface{})
   280  		if len(envVariables) > 0 {
   281  			projectEnvironmentVariables := make([]*codebuild.EnvironmentVariable, 0, len(envVariables))
   282  
   283  			for _, envVariablesConfig := range envVariables {
   284  				config := envVariablesConfig.(map[string]interface{})
   285  
   286  				projectEnvironmentVar := &codebuild.EnvironmentVariable{}
   287  
   288  				if v := config["name"].(string); v != "" {
   289  					projectEnvironmentVar.Name = &v
   290  				}
   291  
   292  				if v := config["value"].(string); v != "" {
   293  					projectEnvironmentVar.Value = &v
   294  				}
   295  
   296  				projectEnvironmentVariables = append(projectEnvironmentVariables, projectEnvironmentVar)
   297  			}
   298  
   299  			projectEnv.EnvironmentVariables = projectEnvironmentVariables
   300  		}
   301  	}
   302  
   303  	return projectEnv
   304  }
   305  
   306  func expandProjectSource(d *schema.ResourceData) codebuild.ProjectSource {
   307  	configs := d.Get("source").(*schema.Set).List()
   308  	projectSource := codebuild.ProjectSource{}
   309  
   310  	for _, configRaw := range configs {
   311  		data := configRaw.(map[string]interface{})
   312  
   313  		sourceType := data["type"].(string)
   314  		location := data["location"].(string)
   315  		buildspec := data["buildspec"].(string)
   316  
   317  		projectSource = codebuild.ProjectSource{
   318  			Type:      &sourceType,
   319  			Location:  &location,
   320  			Buildspec: &buildspec,
   321  		}
   322  
   323  		if v, ok := data["auth"]; ok {
   324  			if len(v.(*schema.Set).List()) > 0 {
   325  				auth := v.(*schema.Set).List()[0].(map[string]interface{})
   326  
   327  				projectSource.Auth = &codebuild.SourceAuth{
   328  					Type:     aws.String(auth["type"].(string)),
   329  					Resource: aws.String(auth["resource"].(string)),
   330  				}
   331  			}
   332  		}
   333  	}
   334  
   335  	return projectSource
   336  }
   337  
   338  func resourceAwsCodeBuildProjectRead(d *schema.ResourceData, meta interface{}) error {
   339  	conn := meta.(*AWSClient).codebuildconn
   340  
   341  	resp, err := conn.BatchGetProjects(&codebuild.BatchGetProjectsInput{
   342  		Names: []*string{
   343  			aws.String(d.Id()),
   344  		},
   345  	})
   346  
   347  	if err != nil {
   348  		return fmt.Errorf("[ERROR] Error retreiving Projects: %q", err)
   349  	}
   350  
   351  	// if nothing was found, then return no state
   352  	if len(resp.Projects) == 0 {
   353  		log.Printf("[INFO]: No projects were found, removing from state")
   354  		d.SetId("")
   355  		return nil
   356  	}
   357  
   358  	project := resp.Projects[0]
   359  
   360  	if err := d.Set("artifacts", flattenAwsCodebuildProjectArtifacts(project.Artifacts)); err != nil {
   361  		return err
   362  	}
   363  
   364  	if err := d.Set("environment", schema.NewSet(resourceAwsCodeBuildProjectEnvironmentHash, flattenAwsCodebuildProjectEnvironment(project.Environment))); err != nil {
   365  		return err
   366  	}
   367  
   368  	if err := d.Set("source", flattenAwsCodebuildProjectSource(project.Source)); err != nil {
   369  		return err
   370  	}
   371  
   372  	d.Set("description", project.Description)
   373  	d.Set("encryption_key", project.EncryptionKey)
   374  	d.Set("name", project.Name)
   375  	d.Set("service_role", project.ServiceRole)
   376  	d.Set("timeout", project.TimeoutInMinutes)
   377  
   378  	if err := d.Set("tags", tagsToMapCodeBuild(project.Tags)); err != nil {
   379  		return err
   380  	}
   381  
   382  	return nil
   383  }
   384  
   385  func resourceAwsCodeBuildProjectUpdate(d *schema.ResourceData, meta interface{}) error {
   386  	conn := meta.(*AWSClient).codebuildconn
   387  
   388  	params := &codebuild.UpdateProjectInput{
   389  		Name: aws.String(d.Get("name").(string)),
   390  	}
   391  
   392  	if d.HasChange("environment") {
   393  		projectEnv := expandProjectEnvironment(d)
   394  		params.Environment = projectEnv
   395  	}
   396  
   397  	if d.HasChange("source") {
   398  		projectSource := expandProjectSource(d)
   399  		params.Source = &projectSource
   400  	}
   401  
   402  	if d.HasChange("artifacts") {
   403  		projectArtifacts := expandProjectArtifacts(d)
   404  		params.Artifacts = &projectArtifacts
   405  	}
   406  
   407  	if d.HasChange("description") {
   408  		params.Description = aws.String(d.Get("description").(string))
   409  	}
   410  
   411  	if d.HasChange("encryption_key") {
   412  		params.EncryptionKey = aws.String(d.Get("encryption_key").(string))
   413  	}
   414  
   415  	if d.HasChange("service_role") {
   416  		params.ServiceRole = aws.String(d.Get("service_role").(string))
   417  	}
   418  
   419  	if d.HasChange("timeout") {
   420  		params.TimeoutInMinutes = aws.Int64(int64(d.Get("timeout").(int)))
   421  	}
   422  
   423  	// The documentation clearly says "The replacement set of tags for this build project."
   424  	// But its a slice of pointers so if not set for every update, they get removed.
   425  	params.Tags = tagsFromMapCodeBuild(d.Get("tags").(map[string]interface{}))
   426  
   427  	_, err := conn.UpdateProject(params)
   428  
   429  	if err != nil {
   430  		return fmt.Errorf(
   431  			"[ERROR] Error updating CodeBuild project (%s): %s",
   432  			d.Id(), err)
   433  	}
   434  
   435  	return resourceAwsCodeBuildProjectRead(d, meta)
   436  }
   437  
   438  func resourceAwsCodeBuildProjectDelete(d *schema.ResourceData, meta interface{}) error {
   439  	conn := meta.(*AWSClient).codebuildconn
   440  
   441  	_, err := conn.DeleteProject(&codebuild.DeleteProjectInput{
   442  		Name: aws.String(d.Id()),
   443  	})
   444  
   445  	if err != nil {
   446  		return err
   447  	}
   448  
   449  	d.SetId("")
   450  
   451  	return nil
   452  }
   453  
   454  func flattenAwsCodebuildProjectArtifacts(artifacts *codebuild.ProjectArtifacts) *schema.Set {
   455  
   456  	artifactSet := schema.Set{
   457  		F: resourceAwsCodeBuildProjectArtifactsHash,
   458  	}
   459  
   460  	values := map[string]interface{}{}
   461  
   462  	values["type"] = *artifacts.Type
   463  
   464  	if artifacts.Location != nil {
   465  		values["location"] = *artifacts.Location
   466  	}
   467  
   468  	if artifacts.Name != nil {
   469  		values["name"] = *artifacts.Name
   470  	}
   471  
   472  	if artifacts.NamespaceType != nil {
   473  		values["namespace_type"] = *artifacts.NamespaceType
   474  	}
   475  
   476  	if artifacts.Packaging != nil {
   477  		values["packaging"] = *artifacts.Packaging
   478  	}
   479  
   480  	if artifacts.Path != nil {
   481  		values["path"] = *artifacts.Path
   482  	}
   483  
   484  	artifactSet.Add(values)
   485  
   486  	return &artifactSet
   487  }
   488  
   489  func flattenAwsCodebuildProjectEnvironment(environment *codebuild.ProjectEnvironment) []interface{} {
   490  	envConfig := map[string]interface{}{}
   491  
   492  	envConfig["type"] = *environment.Type
   493  	envConfig["compute_type"] = *environment.ComputeType
   494  	envConfig["image"] = *environment.Image
   495  
   496  	if environment.EnvironmentVariables != nil {
   497  		envConfig["environment_variable"] = environmentVariablesToMap(environment.EnvironmentVariables)
   498  	}
   499  
   500  	return []interface{}{envConfig}
   501  
   502  }
   503  
   504  func flattenAwsCodebuildProjectSource(source *codebuild.ProjectSource) *schema.Set {
   505  
   506  	sourceSet := schema.Set{
   507  		F: resourceAwsCodeBuildProjectSourceHash,
   508  	}
   509  
   510  	authSet := schema.Set{
   511  		F: resourceAwsCodeBuildProjectSourceAuthHash,
   512  	}
   513  
   514  	sourceConfig := map[string]interface{}{}
   515  
   516  	sourceConfig["type"] = *source.Type
   517  
   518  	if source.Auth != nil {
   519  		authSet.Add(sourceAuthToMap(source.Auth))
   520  		sourceConfig["auth"] = &authSet
   521  	}
   522  
   523  	if source.Buildspec != nil {
   524  		sourceConfig["buildspec"] = *source.Buildspec
   525  	}
   526  
   527  	if source.Location != nil {
   528  		sourceConfig["location"] = *source.Location
   529  	}
   530  
   531  	sourceSet.Add(sourceConfig)
   532  
   533  	return &sourceSet
   534  
   535  }
   536  
   537  func resourceAwsCodeBuildProjectArtifactsHash(v interface{}) int {
   538  	var buf bytes.Buffer
   539  	m := v.(map[string]interface{})
   540  
   541  	artifactType := m["type"].(string)
   542  
   543  	buf.WriteString(fmt.Sprintf("%s-", artifactType))
   544  
   545  	return hashcode.String(buf.String())
   546  }
   547  
   548  func resourceAwsCodeBuildProjectEnvironmentHash(v interface{}) int {
   549  	var buf bytes.Buffer
   550  	m := v.(map[string]interface{})
   551  
   552  	environmentType := m["type"].(string)
   553  	computeType := m["compute_type"].(string)
   554  	image := m["image"].(string)
   555  	environmentVariables := m["environment_variable"].([]interface{})
   556  	buf.WriteString(fmt.Sprintf("%s-", environmentType))
   557  	buf.WriteString(fmt.Sprintf("%s-", computeType))
   558  	buf.WriteString(fmt.Sprintf("%s-", image))
   559  	for _, e := range environmentVariables {
   560  		if e != nil { // Old statefiles might have nil values in them
   561  			ev := e.(map[string]interface{})
   562  			buf.WriteString(fmt.Sprintf("%s:%s-", ev["name"].(string), ev["value"].(string)))
   563  		}
   564  	}
   565  
   566  	return hashcode.String(buf.String())
   567  }
   568  
   569  func resourceAwsCodeBuildProjectSourceHash(v interface{}) int {
   570  	var buf bytes.Buffer
   571  	m := v.(map[string]interface{})
   572  
   573  	sourceType := m["type"].(string)
   574  	buildspec := m["buildspec"].(string)
   575  	location := m["location"].(string)
   576  
   577  	buf.WriteString(fmt.Sprintf("%s-", sourceType))
   578  	buf.WriteString(fmt.Sprintf("%s-", buildspec))
   579  	buf.WriteString(fmt.Sprintf("%s-", location))
   580  
   581  	return hashcode.String(buf.String())
   582  }
   583  
   584  func resourceAwsCodeBuildProjectSourceAuthHash(v interface{}) int {
   585  	var buf bytes.Buffer
   586  	m := v.(map[string]interface{})
   587  
   588  	authType := m["type"].(string)
   589  	authResource := m["resource"].(string)
   590  
   591  	buf.WriteString(fmt.Sprintf("%s-", authType))
   592  	buf.WriteString(fmt.Sprintf("%s-", authResource))
   593  
   594  	return hashcode.String(buf.String())
   595  }
   596  
   597  func environmentVariablesToMap(environmentVariables []*codebuild.EnvironmentVariable) []interface{} {
   598  
   599  	envVariables := []interface{}{}
   600  	if len(environmentVariables) > 0 {
   601  		for _, env := range environmentVariables {
   602  			item := map[string]interface{}{}
   603  			item["name"] = *env.Name
   604  			item["value"] = *env.Value
   605  			envVariables = append(envVariables, item)
   606  		}
   607  	}
   608  
   609  	return envVariables
   610  }
   611  
   612  func sourceAuthToMap(sourceAuth *codebuild.SourceAuth) map[string]interface{} {
   613  
   614  	auth := map[string]interface{}{}
   615  	auth["type"] = *sourceAuth.Type
   616  
   617  	if sourceAuth.Resource != nil {
   618  		auth["resource"] = *sourceAuth.Resource
   619  	}
   620  
   621  	return auth
   622  }
   623  
   624  func validateAwsCodeBuildArifactsType(v interface{}, k string) (ws []string, errors []error) {
   625  	value := v.(string)
   626  	types := map[string]bool{
   627  		"CODEPIPELINE": true,
   628  		"NO_ARTIFACTS": true,
   629  		"S3":           true,
   630  	}
   631  
   632  	if !types[value] {
   633  		errors = append(errors, fmt.Errorf("CodeBuild: Arifacts Type can only be CODEPIPELINE / NO_ARTIFACTS / S3"))
   634  	}
   635  	return
   636  }
   637  
   638  func validateAwsCodeBuildArifactsNamespaceType(v interface{}, k string) (ws []string, errors []error) {
   639  	value := v.(string)
   640  	types := map[string]bool{
   641  		"NONE":     true,
   642  		"BUILD_ID": true,
   643  	}
   644  
   645  	if !types[value] {
   646  		errors = append(errors, fmt.Errorf("CodeBuild: Arifacts Namespace Type can only be NONE / BUILD_ID"))
   647  	}
   648  	return
   649  }
   650  
   651  func validateAwsCodeBuildProjectName(v interface{}, k string) (ws []string, errors []error) {
   652  	value := v.(string)
   653  	if !regexp.MustCompile(`^[A-Za-z0-9]`).MatchString(value) {
   654  		errors = append(errors, fmt.Errorf(
   655  			"first character of %q must be a letter or number", value))
   656  	}
   657  
   658  	if !regexp.MustCompile(`^[A-Za-z0-9\-_]+$`).MatchString(value) {
   659  		errors = append(errors, fmt.Errorf(
   660  			"only alphanumeric characters, hyphens and underscores allowed in %q", value))
   661  	}
   662  
   663  	if len(value) > 255 {
   664  		errors = append(errors, fmt.Errorf(
   665  			"%q cannot be greater than 255 characters", value))
   666  	}
   667  
   668  	return
   669  }
   670  
   671  func validateAwsCodeBuildProjectDescription(v interface{}, k string) (ws []string, errors []error) {
   672  	value := v.(string)
   673  	if len(value) > 255 {
   674  		errors = append(errors, fmt.Errorf("%q cannot be greater than 255 characters", value))
   675  	}
   676  	return
   677  }
   678  
   679  func validateAwsCodeBuildEnvironmentComputeType(v interface{}, k string) (ws []string, errors []error) {
   680  	value := v.(string)
   681  	types := map[string]bool{
   682  		"BUILD_GENERAL1_SMALL":  true,
   683  		"BUILD_GENERAL1_MEDIUM": true,
   684  		"BUILD_GENERAL1_LARGE":  true,
   685  	}
   686  
   687  	if !types[value] {
   688  		errors = append(errors, fmt.Errorf("CodeBuild: Environment Compute Type can only be BUILD_GENERAL1_SMALL / BUILD_GENERAL1_MEDIUM / BUILD_GENERAL1_LARGE"))
   689  	}
   690  	return
   691  }
   692  
   693  func validateAwsCodeBuildEnvironmentType(v interface{}, k string) (ws []string, errors []error) {
   694  	value := v.(string)
   695  	types := map[string]bool{
   696  		"LINUX_CONTAINER": true,
   697  	}
   698  
   699  	if !types[value] {
   700  		errors = append(errors, fmt.Errorf("CodeBuild: Environment Type can only be LINUX_CONTAINER"))
   701  	}
   702  	return
   703  }
   704  
   705  func validateAwsCodeBuildSourceType(v interface{}, k string) (ws []string, errors []error) {
   706  	value := v.(string)
   707  	types := map[string]bool{
   708  		"CODECOMMIT":   true,
   709  		"CODEPIPELINE": true,
   710  		"GITHUB":       true,
   711  		"S3":           true,
   712  	}
   713  
   714  	if !types[value] {
   715  		errors = append(errors, fmt.Errorf("CodeBuild: Source Type can only be CODECOMMIT / CODEPIPELINE / GITHUB / S3"))
   716  	}
   717  	return
   718  }
   719  
   720  func validateAwsCodeBuildSourceAuthType(v interface{}, k string) (ws []string, errors []error) {
   721  	value := v.(string)
   722  	types := map[string]bool{
   723  		"OAUTH": true,
   724  	}
   725  
   726  	if !types[value] {
   727  		errors = append(errors, fmt.Errorf("CodeBuild: Source Auth Type can only be OAUTH"))
   728  	}
   729  	return
   730  }
   731  
   732  func validateAwsCodeBuildTimeout(v interface{}, k string) (ws []string, errors []error) {
   733  	value := v.(int)
   734  
   735  	if value < 5 || value > 480 {
   736  		errors = append(errors, fmt.Errorf("%q must be greater than 5 minutes and less than 480 minutes (8 hours)", value))
   737  	}
   738  	return
   739  }