// resourceAwsLambdaFunction maps to: // CreateFunction in the API / SDK func resourceAwsLambdaFunctionCreate(d *schema.ResourceData, meta interface{}) error { conn := meta.(*AWSClient).lambdaconn functionName := d.Get("function_name").(string) iamRole := d.Get("role").(string) log.Printf("[DEBUG] Creating Lambda Function %s with role %s", functionName, iamRole) var functionCode *lambda.FunctionCode if v, ok := d.GetOk("filename"); ok { file, err := loadFileContent(v.(string)) if err != nil { return fmt.Errorf("Unable to load %q: %s", v.(string), err) } functionCode = &lambda.FunctionCode{ ZipFile: file, } } else { s3Bucket, bucketOk := d.GetOk("s3_bucket") s3Key, keyOk := d.GetOk("s3_key") s3ObjectVersion, versionOk := d.GetOk("s3_object_version") if !bucketOk || !keyOk { return errors.New("s3_bucket and s3_key must all be set while using S3 code source") } functionCode = &lambda.FunctionCode{ S3Bucket: aws.String(s3Bucket.(string)), S3Key: aws.String(s3Key.(string)), } if versionOk { functionCode.S3ObjectVersion = aws.String(s3ObjectVersion.(string)) } } params := &lambda.CreateFunctionInput{ Code: functionCode, Description: aws.String(d.Get("description").(string)), FunctionName: aws.String(functionName), Handler: aws.String(d.Get("handler").(string)), MemorySize: aws.Int64(int64(d.Get("memory_size").(int))), Role: aws.String(iamRole), Runtime: aws.String(d.Get("runtime").(string)), Timeout: aws.Int64(int64(d.Get("timeout").(int))), } if v, ok := d.GetOk("vpc_config"); ok { config, err := validateVPCConfig(v) if err != nil { return err } var subnetIds []*string for _, id := range config["subnet_ids"].(*schema.Set).List() { subnetIds = append(subnetIds, aws.String(id.(string))) } var securityGroupIds []*string for _, id := range config["security_group_ids"].(*schema.Set).List() { securityGroupIds = append(securityGroupIds, aws.String(id.(string))) } params.VpcConfig = &lambda.VpcConfig{ SubnetIds: subnetIds, SecurityGroupIds: securityGroupIds, } } // IAM profiles can take ~10 seconds to propagate in AWS: // http://docs.aws.amazon.com/AWSEC2/latest/UserGuide/iam-roles-for-amazon-ec2.html#launch-instance-with-role-console // Error creating Lambda function: InvalidParameterValueException: The role defined for the task cannot be assumed by Lambda. err := resource.Retry(1*time.Minute, func() *resource.RetryError { _, err := conn.CreateFunction(params) if err != nil { log.Printf("[ERROR] Received %q, retrying CreateFunction", err) if awserr, ok := err.(awserr.Error); ok { if awserr.Code() == "InvalidParameterValueException" { log.Printf("[DEBUG] InvalidParameterValueException creating Lambda Function: %s", awserr) return resource.RetryableError(awserr) } } log.Printf("[DEBUG] Error creating Lambda Function: %s", err) return resource.NonRetryableError(err) } return nil }) if err != nil { return fmt.Errorf("Error creating Lambda function: %s", err) } d.SetId(d.Get("function_name").(string)) return resourceAwsLambdaFunctionRead(d, meta) }
// resourceAwsLambdaFunction maps to: // CreateFunction in the API / SDK func resourceAwsLambdaFunctionCreate(d *schema.ResourceData, meta interface{}) error { conn := meta.(*AWSClient).lambdaconn functionName := d.Get("function_name").(string) iamRole := d.Get("role").(string) log.Printf("[DEBUG] Creating Lambda Function %s with role %s", functionName, iamRole) filename, hasFilename := d.GetOk("filename") s3Bucket, bucketOk := d.GetOk("s3_bucket") s3Key, keyOk := d.GetOk("s3_key") s3ObjectVersion, versionOk := d.GetOk("s3_object_version") if !hasFilename && !bucketOk && !keyOk && !versionOk { return errors.New("filename or s3_* attributes must be set") } var functionCode *lambda.FunctionCode if hasFilename { // Grab an exclusive lock so that we're only reading one function into // memory at a time. // See https://github.com/hashicorp/terraform/issues/9364 awsMutexKV.Lock(awsMutexLambdaKey) defer awsMutexKV.Unlock(awsMutexLambdaKey) file, err := loadFileContent(filename.(string)) if err != nil { return fmt.Errorf("Unable to load %q: %s", filename.(string), err) } functionCode = &lambda.FunctionCode{ ZipFile: file, } } else { if !bucketOk || !keyOk { return errors.New("s3_bucket and s3_key must all be set while using S3 code source") } functionCode = &lambda.FunctionCode{ S3Bucket: aws.String(s3Bucket.(string)), S3Key: aws.String(s3Key.(string)), } if versionOk { functionCode.S3ObjectVersion = aws.String(s3ObjectVersion.(string)) } } params := &lambda.CreateFunctionInput{ Code: functionCode, Description: aws.String(d.Get("description").(string)), FunctionName: aws.String(functionName), Handler: aws.String(d.Get("handler").(string)), MemorySize: aws.Int64(int64(d.Get("memory_size").(int))), Role: aws.String(iamRole), Runtime: aws.String(d.Get("runtime").(string)), Timeout: aws.Int64(int64(d.Get("timeout").(int))), Publish: aws.Bool(d.Get("publish").(bool)), } if v, ok := d.GetOk("vpc_config"); ok { config, err := validateVPCConfig(v) if err != nil { return err } if config != nil { var subnetIds []*string for _, id := range config["subnet_ids"].(*schema.Set).List() { subnetIds = append(subnetIds, aws.String(id.(string))) } var securityGroupIds []*string for _, id := range config["security_group_ids"].(*schema.Set).List() { securityGroupIds = append(securityGroupIds, aws.String(id.(string))) } params.VpcConfig = &lambda.VpcConfig{ SubnetIds: subnetIds, SecurityGroupIds: securityGroupIds, } } } if v, ok := d.GetOk("environment"); ok { environments := v.([]interface{}) environment, ok := environments[0].(map[string]interface{}) if !ok { return errors.New("At least one field is expected inside environment") } if environmentVariables, ok := environment["variables"]; ok { variables := readEnvironmentVariables(environmentVariables.(map[string]interface{})) params.Environment = &lambda.Environment{ Variables: aws.StringMap(variables), } } } if v, ok := d.GetOk("kms_key_arn"); ok { params.KMSKeyArn = aws.String(v.(string)) } // IAM profiles can take ~10 seconds to propagate in AWS: // http://docs.aws.amazon.com/AWSEC2/latest/UserGuide/iam-roles-for-amazon-ec2.html#launch-instance-with-role-console // Error creating Lambda function: InvalidParameterValueException: The role defined for the task cannot be assumed by Lambda. err := resource.Retry(10*time.Minute, func() *resource.RetryError { _, err := conn.CreateFunction(params) if err != nil { log.Printf("[ERROR] Received %q, retrying CreateFunction", err) if awserr, ok := err.(awserr.Error); ok { if awserr.Code() == "InvalidParameterValueException" { log.Printf("[DEBUG] InvalidParameterValueException creating Lambda Function: %s", awserr) return resource.RetryableError(awserr) } } log.Printf("[DEBUG] Error creating Lambda Function: %s", err) return resource.NonRetryableError(err) } return nil }) if err != nil { return fmt.Errorf("Error creating Lambda function: %s", err) } d.SetId(d.Get("function_name").(string)) return resourceAwsLambdaFunctionRead(d, meta) }