github.com/recobe182/terraform@v0.8.5-0.20170117231232-49ab22a935b7/builtin/providers/aws/resource_aws_lambda_function_test.go (about) 1 package aws 2 3 import ( 4 "archive/zip" 5 "fmt" 6 "io/ioutil" 7 "os" 8 "path/filepath" 9 "regexp" 10 "strings" 11 "testing" 12 13 "github.com/aws/aws-sdk-go/aws" 14 "github.com/aws/aws-sdk-go/service/lambda" 15 "github.com/hashicorp/terraform/helper/acctest" 16 "github.com/hashicorp/terraform/helper/resource" 17 "github.com/hashicorp/terraform/terraform" 18 ) 19 20 func TestAccAWSLambdaFunction_basic(t *testing.T) { 21 var conf lambda.GetFunctionOutput 22 23 rSt := acctest.RandString(5) 24 rName := fmt.Sprintf("tf_test_%s", rSt) 25 26 resource.Test(t, resource.TestCase{ 27 PreCheck: func() { testAccPreCheck(t) }, 28 Providers: testAccProviders, 29 CheckDestroy: testAccCheckLambdaFunctionDestroy, 30 Steps: []resource.TestStep{ 31 { 32 Config: testAccAWSLambdaConfigBasic(rName, rSt), 33 Check: resource.ComposeTestCheckFunc( 34 testAccCheckAwsLambdaFunctionExists("aws_lambda_function.lambda_function_test", rName, &conf), 35 testAccCheckAwsLambdaFunctionName(&conf, rName), 36 testAccCheckAwsLambdaFunctionArnHasSuffix(&conf, ":"+rName), 37 ), 38 }, 39 }, 40 }) 41 } 42 43 func TestAccAWSLambdaFunction_expectFilenameAndS3Attributes(t *testing.T) { 44 rSt := acctest.RandString(5) 45 rName := fmt.Sprintf("tf_test_%s", rSt) 46 47 resource.Test(t, resource.TestCase{ 48 PreCheck: func() { testAccPreCheck(t) }, 49 Providers: testAccProviders, 50 CheckDestroy: testAccCheckLambdaFunctionDestroy, 51 Steps: []resource.TestStep{ 52 { 53 Config: testAccAWSLambdaConfigWithoutFilenameAndS3Attributes(rName, rSt), 54 ExpectError: regexp.MustCompile(`filename or s3_\* attributes must be set`), 55 }, 56 }, 57 }) 58 } 59 60 func TestAccAWSLambdaFunction_envVariables(t *testing.T) { 61 var conf lambda.GetFunctionOutput 62 63 rSt := acctest.RandString(5) 64 rName := fmt.Sprintf("tf_test_%s", rSt) 65 66 resource.Test(t, resource.TestCase{ 67 PreCheck: func() { testAccPreCheck(t) }, 68 Providers: testAccProviders, 69 CheckDestroy: testAccCheckLambdaFunctionDestroy, 70 Steps: []resource.TestStep{ 71 { 72 Config: testAccAWSLambdaConfigBasic(rName, rSt), 73 Check: resource.ComposeTestCheckFunc( 74 testAccCheckAwsLambdaFunctionExists("aws_lambda_function.lambda_function_test", rName, &conf), 75 testAccCheckAwsLambdaFunctionName(&conf, rName), 76 testAccCheckAwsLambdaFunctionArnHasSuffix(&conf, ":"+rName), 77 resource.TestCheckResourceAttr("aws_lambda_function.lambda_function_test", "environment.#", "0"), 78 ), 79 }, 80 { 81 Config: testAccAWSLambdaConfigEnvVariables(rName, rSt), 82 Check: resource.ComposeTestCheckFunc( 83 testAccCheckAwsLambdaFunctionExists("aws_lambda_function.lambda_function_test", rName, &conf), 84 testAccCheckAwsLambdaFunctionName(&conf, rName), 85 testAccCheckAwsLambdaFunctionArnHasSuffix(&conf, ":"+rName), 86 resource.TestCheckResourceAttr("aws_lambda_function.lambda_function_test", "environment.0.variables.foo", "bar"), 87 ), 88 }, 89 { 90 Config: testAccAWSLambdaConfigEnvVariablesModified(rName, rSt), 91 Check: resource.ComposeTestCheckFunc( 92 testAccCheckAwsLambdaFunctionExists("aws_lambda_function.lambda_function_test", rName, &conf), 93 testAccCheckAwsLambdaFunctionName(&conf, rName), 94 testAccCheckAwsLambdaFunctionArnHasSuffix(&conf, ":"+rName), 95 resource.TestCheckResourceAttr("aws_lambda_function.lambda_function_test", "environment.0.variables.foo", "baz"), 96 resource.TestCheckResourceAttr("aws_lambda_function.lambda_function_test", "environment.0.variables.foo1", "bar1"), 97 ), 98 }, 99 { 100 Config: testAccAWSLambdaConfigEnvVariablesModifiedWithoutEnvironment(rName, rSt), 101 Check: resource.ComposeTestCheckFunc( 102 testAccCheckAwsLambdaFunctionExists("aws_lambda_function.lambda_function_test", rName, &conf), 103 testAccCheckAwsLambdaFunctionName(&conf, rName), 104 testAccCheckAwsLambdaFunctionArnHasSuffix(&conf, ":"+rName), 105 resource.TestCheckResourceAttr("aws_lambda_function.lambda_function_test", "environment.0.variables.foo", ""), 106 resource.TestCheckResourceAttr("aws_lambda_function.lambda_function_test", "environment.0.variables.foo1", ""), 107 ), 108 }, 109 }, 110 }) 111 } 112 113 func TestAccAWSLambdaFunction_encryptedEnvVariables(t *testing.T) { 114 var conf lambda.GetFunctionOutput 115 116 rSt := acctest.RandString(5) 117 rName := fmt.Sprintf("tf_test_%s", rSt) 118 keyRegex := regexp.MustCompile("^arn:aws:kms:") 119 120 resource.Test(t, resource.TestCase{ 121 PreCheck: func() { testAccPreCheck(t) }, 122 Providers: testAccProviders, 123 CheckDestroy: testAccCheckLambdaFunctionDestroy, 124 Steps: []resource.TestStep{ 125 { 126 Config: testAccAWSLambdaConfigEncryptedEnvVariables(rName, rSt), 127 Check: resource.ComposeTestCheckFunc( 128 testAccCheckAwsLambdaFunctionExists("aws_lambda_function.lambda_function_test", rName, &conf), 129 testAccCheckAwsLambdaFunctionName(&conf, rName), 130 testAccCheckAwsLambdaFunctionArnHasSuffix(&conf, ":"+rName), 131 resource.TestCheckResourceAttr("aws_lambda_function.lambda_function_test", "environment.0.variables.foo", "bar"), 132 resource.TestMatchResourceAttr("aws_lambda_function.lambda_function_test", "kms_key_arn", keyRegex), 133 ), 134 }, 135 { 136 Config: testAccAWSLambdaConfigEncryptedEnvVariablesModified(rName, rSt), 137 Check: resource.ComposeTestCheckFunc( 138 testAccCheckAwsLambdaFunctionExists("aws_lambda_function.lambda_function_test", rName, &conf), 139 testAccCheckAwsLambdaFunctionName(&conf, rName), 140 testAccCheckAwsLambdaFunctionArnHasSuffix(&conf, ":"+rName), 141 resource.TestCheckResourceAttr("aws_lambda_function.lambda_function_test", "environment.0.variables.foo", "bar"), 142 resource.TestCheckResourceAttr("aws_lambda_function.lambda_function_test", "kms_key_arn", ""), 143 ), 144 }, 145 }, 146 }) 147 } 148 149 func TestAccAWSLambdaFunction_versioned(t *testing.T) { 150 var conf lambda.GetFunctionOutput 151 152 rSt := acctest.RandString(5) 153 rName := fmt.Sprintf("tf_test_%s", rSt) 154 155 resource.Test(t, resource.TestCase{ 156 PreCheck: func() { testAccPreCheck(t) }, 157 Providers: testAccProviders, 158 CheckDestroy: testAccCheckLambdaFunctionDestroy, 159 Steps: []resource.TestStep{ 160 { 161 Config: testAccAWSLambdaConfigVersioned(rName, rSt), 162 Check: resource.ComposeTestCheckFunc( 163 testAccCheckAwsLambdaFunctionExists("aws_lambda_function.lambda_function_test", rName, &conf), 164 testAccCheckAwsLambdaFunctionName(&conf, rName), 165 testAccCheckAwsLambdaFunctionArnHasSuffix(&conf, ":"+rName), 166 resource.TestMatchResourceAttr("aws_lambda_function.lambda_function_test", "version", 167 regexp.MustCompile("^[0-9]+$")), 168 resource.TestMatchResourceAttr("aws_lambda_function.lambda_function_test", "qualified_arn", 169 regexp.MustCompile(":"+rName+":[0-9]+$")), 170 ), 171 }, 172 }, 173 }) 174 } 175 176 func TestAccAWSLambdaFunction_VPC(t *testing.T) { 177 var conf lambda.GetFunctionOutput 178 179 rSt := acctest.RandString(5) 180 rName := fmt.Sprintf("tf_test_%s", rSt) 181 182 resource.Test(t, resource.TestCase{ 183 PreCheck: func() { testAccPreCheck(t) }, 184 Providers: testAccProviders, 185 CheckDestroy: testAccCheckLambdaFunctionDestroy, 186 Steps: []resource.TestStep{ 187 { 188 Config: testAccAWSLambdaConfigWithVPC(rName, rSt), 189 Check: resource.ComposeTestCheckFunc( 190 testAccCheckAwsLambdaFunctionExists("aws_lambda_function.lambda_function_test", rName, &conf), 191 testAccCheckAwsLambdaFunctionName(&conf, rName), 192 testAccCheckAwsLambdaFunctionArnHasSuffix(&conf, ":"+rName), 193 testAccCheckAWSLambdaFunctionVersion(&conf, "$LATEST"), 194 resource.TestCheckResourceAttr("aws_lambda_function.lambda_function_test", "vpc_config.#", "1"), 195 resource.TestCheckResourceAttr("aws_lambda_function.lambda_function_test", "vpc_config.0.subnet_ids.#", "1"), 196 resource.TestCheckResourceAttr("aws_lambda_function.lambda_function_test", "vpc_config.0.security_group_ids.#", "1"), 197 resource.TestMatchResourceAttr("aws_lambda_function.lambda_function_test", "vpc_config.0.vpc_id", regexp.MustCompile("^vpc-")), 198 ), 199 }, 200 }, 201 }) 202 } 203 204 func TestAccAWSLambdaFunction_s3(t *testing.T) { 205 var conf lambda.GetFunctionOutput 206 rSt := acctest.RandString(5) 207 rName := fmt.Sprintf("tf_test_%s", rSt) 208 209 resource.Test(t, resource.TestCase{ 210 PreCheck: func() { testAccPreCheck(t) }, 211 Providers: testAccProviders, 212 CheckDestroy: testAccCheckLambdaFunctionDestroy, 213 Steps: []resource.TestStep{ 214 { 215 Config: testAccAWSLambdaConfigS3(rName, rSt), 216 Check: resource.ComposeTestCheckFunc( 217 testAccCheckAwsLambdaFunctionExists("aws_lambda_function.lambda_function_s3test", rName, &conf), 218 testAccCheckAwsLambdaFunctionName(&conf, rName), 219 testAccCheckAwsLambdaFunctionArnHasSuffix(&conf, ":"+rName), 220 testAccCheckAWSLambdaFunctionVersion(&conf, "$LATEST"), 221 ), 222 }, 223 }, 224 }) 225 } 226 227 func TestAccAWSLambdaFunction_localUpdate(t *testing.T) { 228 var conf lambda.GetFunctionOutput 229 230 path, zipFile, err := createTempFile("lambda_localUpdate") 231 if err != nil { 232 t.Fatal(err) 233 } 234 defer os.Remove(path) 235 236 resource.Test(t, resource.TestCase{ 237 PreCheck: func() { testAccPreCheck(t) }, 238 Providers: testAccProviders, 239 CheckDestroy: testAccCheckLambdaFunctionDestroy, 240 Steps: []resource.TestStep{ 241 { 242 PreConfig: func() { 243 testAccCreateZipFromFiles(map[string]string{"test-fixtures/lambda_func.js": "lambda.js"}, zipFile) 244 }, 245 Config: genAWSLambdaFunctionConfig_local(path), 246 Check: resource.ComposeTestCheckFunc( 247 testAccCheckAwsLambdaFunctionExists("aws_lambda_function.lambda_function_local", "tf_acc_lambda_name_local", &conf), 248 testAccCheckAwsLambdaFunctionName(&conf, "tf_acc_lambda_name_local"), 249 testAccCheckAwsLambdaFunctionArnHasSuffix(&conf, "tf_acc_lambda_name_local"), 250 testAccCheckAwsLambdaSourceCodeHash(&conf, "8DPiX+G1l2LQ8hjBkwRchQFf1TSCEvPrYGRKlM9UoyY="), 251 ), 252 }, 253 { 254 PreConfig: func() { 255 testAccCreateZipFromFiles(map[string]string{"test-fixtures/lambda_func_modified.js": "lambda.js"}, zipFile) 256 }, 257 Config: genAWSLambdaFunctionConfig_local(path), 258 Check: resource.ComposeTestCheckFunc( 259 testAccCheckAwsLambdaFunctionExists("aws_lambda_function.lambda_function_local", "tf_acc_lambda_name_local", &conf), 260 testAccCheckAwsLambdaFunctionName(&conf, "tf_acc_lambda_name_local"), 261 testAccCheckAwsLambdaFunctionArnHasSuffix(&conf, "tf_acc_lambda_name_local"), 262 testAccCheckAwsLambdaSourceCodeHash(&conf, "0tdaP9H9hsk9c2CycSwOG/sa/x5JyAmSYunA/ce99Pg="), 263 ), 264 }, 265 }, 266 }) 267 } 268 269 func TestAccAWSLambdaFunction_localUpdate_nameOnly(t *testing.T) { 270 var conf lambda.GetFunctionOutput 271 272 path, zipFile, err := createTempFile("lambda_localUpdate") 273 if err != nil { 274 t.Fatal(err) 275 } 276 defer os.Remove(path) 277 278 updatedPath, updatedZipFile, err := createTempFile("lambda_localUpdate_name_change") 279 if err != nil { 280 t.Fatal(err) 281 } 282 defer os.Remove(updatedPath) 283 284 resource.Test(t, resource.TestCase{ 285 PreCheck: func() { testAccPreCheck(t) }, 286 Providers: testAccProviders, 287 CheckDestroy: testAccCheckLambdaFunctionDestroy, 288 Steps: []resource.TestStep{ 289 { 290 PreConfig: func() { 291 testAccCreateZipFromFiles(map[string]string{"test-fixtures/lambda_func.js": "lambda.js"}, zipFile) 292 }, 293 Config: genAWSLambdaFunctionConfig_local_name_only(path), 294 Check: resource.ComposeTestCheckFunc( 295 testAccCheckAwsLambdaFunctionExists("aws_lambda_function.lambda_function_local", "tf_acc_lambda_name_local", &conf), 296 testAccCheckAwsLambdaFunctionName(&conf, "tf_acc_lambda_name_local"), 297 testAccCheckAwsLambdaFunctionArnHasSuffix(&conf, "tf_acc_lambda_name_local"), 298 testAccCheckAwsLambdaSourceCodeHash(&conf, "8DPiX+G1l2LQ8hjBkwRchQFf1TSCEvPrYGRKlM9UoyY="), 299 ), 300 }, 301 { 302 PreConfig: func() { 303 testAccCreateZipFromFiles(map[string]string{"test-fixtures/lambda_func_modified.js": "lambda.js"}, updatedZipFile) 304 }, 305 Config: genAWSLambdaFunctionConfig_local_name_only(updatedPath), 306 Check: resource.ComposeTestCheckFunc( 307 testAccCheckAwsLambdaFunctionExists("aws_lambda_function.lambda_function_local", "tf_acc_lambda_name_local", &conf), 308 testAccCheckAwsLambdaFunctionName(&conf, "tf_acc_lambda_name_local"), 309 testAccCheckAwsLambdaFunctionArnHasSuffix(&conf, "tf_acc_lambda_name_local"), 310 testAccCheckAwsLambdaSourceCodeHash(&conf, "0tdaP9H9hsk9c2CycSwOG/sa/x5JyAmSYunA/ce99Pg="), 311 ), 312 }, 313 }, 314 }) 315 } 316 317 func TestAccAWSLambdaFunction_s3Update(t *testing.T) { 318 var conf lambda.GetFunctionOutput 319 320 path, zipFile, err := createTempFile("lambda_s3Update") 321 if err != nil { 322 t.Fatal(err) 323 } 324 defer os.Remove(path) 325 326 bucketName := fmt.Sprintf("tf-acc-lambda-s3-deployments-%d", randomInteger) 327 key := "lambda-func.zip" 328 329 resource.Test(t, resource.TestCase{ 330 PreCheck: func() { testAccPreCheck(t) }, 331 Providers: testAccProviders, 332 CheckDestroy: testAccCheckLambdaFunctionDestroy, 333 Steps: []resource.TestStep{ 334 { 335 PreConfig: func() { 336 // Upload 1st version 337 testAccCreateZipFromFiles(map[string]string{"test-fixtures/lambda_func.js": "lambda.js"}, zipFile) 338 }, 339 Config: genAWSLambdaFunctionConfig_s3(bucketName, key, path), 340 Check: resource.ComposeTestCheckFunc( 341 testAccCheckAwsLambdaFunctionExists("aws_lambda_function.lambda_function_s3", "tf_acc_lambda_name_s3", &conf), 342 testAccCheckAwsLambdaFunctionName(&conf, "tf_acc_lambda_name_s3"), 343 testAccCheckAwsLambdaFunctionArnHasSuffix(&conf, "tf_acc_lambda_name_s3"), 344 testAccCheckAwsLambdaSourceCodeHash(&conf, "8DPiX+G1l2LQ8hjBkwRchQFf1TSCEvPrYGRKlM9UoyY="), 345 ), 346 }, 347 { 348 ExpectNonEmptyPlan: true, 349 PreConfig: func() { 350 // Upload 2nd version 351 testAccCreateZipFromFiles(map[string]string{"test-fixtures/lambda_func_modified.js": "lambda.js"}, zipFile) 352 }, 353 Config: genAWSLambdaFunctionConfig_s3(bucketName, key, path), 354 }, 355 // Extra step because of missing ComputedWhen 356 // See https://github.com/hashicorp/terraform/pull/4846 & https://github.com/hashicorp/terraform/pull/5330 357 { 358 Config: genAWSLambdaFunctionConfig_s3(bucketName, key, path), 359 Check: resource.ComposeTestCheckFunc( 360 testAccCheckAwsLambdaFunctionExists("aws_lambda_function.lambda_function_s3", "tf_acc_lambda_name_s3", &conf), 361 testAccCheckAwsLambdaFunctionName(&conf, "tf_acc_lambda_name_s3"), 362 testAccCheckAwsLambdaFunctionArnHasSuffix(&conf, "tf_acc_lambda_name_s3"), 363 testAccCheckAwsLambdaSourceCodeHash(&conf, "0tdaP9H9hsk9c2CycSwOG/sa/x5JyAmSYunA/ce99Pg="), 364 ), 365 }, 366 }, 367 }) 368 } 369 370 func TestAccAWSLambdaFunction_s3Update_unversioned(t *testing.T) { 371 var conf lambda.GetFunctionOutput 372 373 path, zipFile, err := createTempFile("lambda_s3Update") 374 if err != nil { 375 t.Fatal(err) 376 } 377 defer os.Remove(path) 378 379 bucketName := fmt.Sprintf("tf-acc-lambda-s3-deployments-%d", randomInteger) 380 key := "lambda-func.zip" 381 key2 := "lambda-func-modified.zip" 382 383 resource.Test(t, resource.TestCase{ 384 PreCheck: func() { testAccPreCheck(t) }, 385 Providers: testAccProviders, 386 CheckDestroy: testAccCheckLambdaFunctionDestroy, 387 Steps: []resource.TestStep{ 388 { 389 PreConfig: func() { 390 // Upload 1st version 391 testAccCreateZipFromFiles(map[string]string{"test-fixtures/lambda_func.js": "lambda.js"}, zipFile) 392 }, 393 Config: genAWSLambdaFunctionConfig_s3_unversioned(bucketName, key, path), 394 Check: resource.ComposeTestCheckFunc( 395 testAccCheckAwsLambdaFunctionExists("aws_lambda_function.lambda_function_s3", "tf_acc_lambda_name_s3_unversioned", &conf), 396 testAccCheckAwsLambdaFunctionName(&conf, "tf_acc_lambda_name_s3_unversioned"), 397 testAccCheckAwsLambdaFunctionArnHasSuffix(&conf, "tf_acc_lambda_name_s3_unversioned"), 398 testAccCheckAwsLambdaSourceCodeHash(&conf, "8DPiX+G1l2LQ8hjBkwRchQFf1TSCEvPrYGRKlM9UoyY="), 399 ), 400 }, 401 { 402 PreConfig: func() { 403 // Upload 2nd version 404 testAccCreateZipFromFiles(map[string]string{"test-fixtures/lambda_func_modified.js": "lambda.js"}, zipFile) 405 }, 406 Config: genAWSLambdaFunctionConfig_s3_unversioned(bucketName, key2, path), 407 Check: resource.ComposeTestCheckFunc( 408 testAccCheckAwsLambdaFunctionExists("aws_lambda_function.lambda_function_s3", "tf_acc_lambda_name_s3_unversioned", &conf), 409 testAccCheckAwsLambdaFunctionName(&conf, "tf_acc_lambda_name_s3_unversioned"), 410 testAccCheckAwsLambdaFunctionArnHasSuffix(&conf, "tf_acc_lambda_name_s3_unversioned"), 411 testAccCheckAwsLambdaSourceCodeHash(&conf, "0tdaP9H9hsk9c2CycSwOG/sa/x5JyAmSYunA/ce99Pg="), 412 ), 413 }, 414 }, 415 }) 416 } 417 418 func TestAccAWSLambdaFunction_runtimeValidation_noRuntime(t *testing.T) { 419 rSt := acctest.RandString(5) 420 rName := fmt.Sprintf("tf_test_%s", rSt) 421 422 resource.Test(t, resource.TestCase{ 423 PreCheck: func() { testAccPreCheck(t) }, 424 Providers: testAccProviders, 425 CheckDestroy: testAccCheckLambdaFunctionDestroy, 426 Steps: []resource.TestStep{ 427 { 428 Config: testAccAWSLambdaConfigNoRuntime(rName, rSt), 429 ExpectError: regexp.MustCompile(`\\"runtime\\": required field is not set`), 430 }, 431 }, 432 }) 433 } 434 435 func TestAccAWSLambdaFunction_runtimeValidation_nodeJs(t *testing.T) { 436 rSt := acctest.RandString(5) 437 rName := fmt.Sprintf("tf_test_%s", rSt) 438 439 resource.Test(t, resource.TestCase{ 440 PreCheck: func() { testAccPreCheck(t) }, 441 Providers: testAccProviders, 442 CheckDestroy: testAccCheckLambdaFunctionDestroy, 443 Steps: []resource.TestStep{ 444 { 445 Config: testAccAWSLambdaConfigNodeJsRuntime(rName, rSt), 446 ExpectError: regexp.MustCompile(fmt.Sprintf("%s has reached end of life since October 2016 and has been deprecated in favor of %s", lambda.RuntimeNodejs, lambda.RuntimeNodejs43)), 447 }, 448 }, 449 }) 450 } 451 452 func TestAccAWSLambdaFunction_runtimeValidation_nodeJs43(t *testing.T) { 453 var conf lambda.GetFunctionOutput 454 rSt := acctest.RandString(5) 455 rName := fmt.Sprintf("tf_test_%s", rSt) 456 457 resource.Test(t, resource.TestCase{ 458 PreCheck: func() { testAccPreCheck(t) }, 459 Providers: testAccProviders, 460 CheckDestroy: testAccCheckLambdaFunctionDestroy, 461 Steps: []resource.TestStep{ 462 { 463 Config: testAccAWSLambdaConfigNodeJs43Runtime(rName, rSt), 464 Check: resource.ComposeTestCheckFunc( 465 testAccCheckAwsLambdaFunctionExists("aws_lambda_function.lambda_function_test", rName, &conf), 466 resource.TestCheckResourceAttr("aws_lambda_function.lambda_function_test", "runtime", lambda.RuntimeNodejs43), 467 ), 468 }, 469 }, 470 }) 471 } 472 473 func TestAccAWSLambdaFunction_runtimeValidation_python27(t *testing.T) { 474 var conf lambda.GetFunctionOutput 475 rSt := acctest.RandString(5) 476 rName := fmt.Sprintf("tf_test_%s", rSt) 477 478 resource.Test(t, resource.TestCase{ 479 PreCheck: func() { testAccPreCheck(t) }, 480 Providers: testAccProviders, 481 CheckDestroy: testAccCheckLambdaFunctionDestroy, 482 Steps: []resource.TestStep{ 483 { 484 Config: testAccAWSLambdaConfigPython27Runtime(rName, rSt), 485 Check: resource.ComposeTestCheckFunc( 486 testAccCheckAwsLambdaFunctionExists("aws_lambda_function.lambda_function_test", rName, &conf), 487 resource.TestCheckResourceAttr("aws_lambda_function.lambda_function_test", "runtime", lambda.RuntimePython27), 488 ), 489 }, 490 }, 491 }) 492 } 493 494 func TestAccAWSLambdaFunction_runtimeValidation_java8(t *testing.T) { 495 var conf lambda.GetFunctionOutput 496 rSt := acctest.RandString(5) 497 rName := fmt.Sprintf("tf_test_%s", rSt) 498 499 resource.Test(t, resource.TestCase{ 500 PreCheck: func() { testAccPreCheck(t) }, 501 Providers: testAccProviders, 502 CheckDestroy: testAccCheckLambdaFunctionDestroy, 503 Steps: []resource.TestStep{ 504 { 505 Config: testAccAWSLambdaConfigJava8Runtime(rName, rSt), 506 Check: resource.ComposeTestCheckFunc( 507 testAccCheckAwsLambdaFunctionExists("aws_lambda_function.lambda_function_test", rName, &conf), 508 resource.TestCheckResourceAttr("aws_lambda_function.lambda_function_test", "runtime", lambda.RuntimeJava8), 509 ), 510 }, 511 }, 512 }) 513 } 514 515 func testAccCheckLambdaFunctionDestroy(s *terraform.State) error { 516 conn := testAccProvider.Meta().(*AWSClient).lambdaconn 517 518 for _, rs := range s.RootModule().Resources { 519 if rs.Type != "aws_lambda_function" { 520 continue 521 } 522 523 _, err := conn.GetFunction(&lambda.GetFunctionInput{ 524 FunctionName: aws.String(rs.Primary.ID), 525 }) 526 527 if err == nil { 528 return fmt.Errorf("Lambda Function still exists") 529 } 530 531 } 532 533 return nil 534 535 } 536 537 func testAccCheckAwsLambdaFunctionExists(res, funcName string, function *lambda.GetFunctionOutput) resource.TestCheckFunc { 538 // Wait for IAM role 539 return func(s *terraform.State) error { 540 rs, ok := s.RootModule().Resources[res] 541 if !ok { 542 return fmt.Errorf("Lambda function not found: %s", res) 543 } 544 545 if rs.Primary.ID == "" { 546 return fmt.Errorf("Lambda function ID not set") 547 } 548 549 conn := testAccProvider.Meta().(*AWSClient).lambdaconn 550 551 params := &lambda.GetFunctionInput{ 552 FunctionName: aws.String(funcName), 553 } 554 555 getFunction, err := conn.GetFunction(params) 556 if err != nil { 557 return err 558 } 559 560 *function = *getFunction 561 562 return nil 563 } 564 } 565 566 func testAccCheckAwsLambdaFunctionName(function *lambda.GetFunctionOutput, expectedName string) resource.TestCheckFunc { 567 return func(s *terraform.State) error { 568 c := function.Configuration 569 if *c.FunctionName != expectedName { 570 return fmt.Errorf("Expected function name %s, got %s", expectedName, *c.FunctionName) 571 } 572 573 return nil 574 } 575 } 576 577 func testAccCheckAWSLambdaFunctionVersion(function *lambda.GetFunctionOutput, expectedVersion string) resource.TestCheckFunc { 578 return func(s *terraform.State) error { 579 c := function.Configuration 580 if *c.Version != expectedVersion { 581 return fmt.Errorf("Expected version %s, got %s", expectedVersion, *c.Version) 582 } 583 return nil 584 } 585 } 586 587 func testAccCheckAwsLambdaFunctionArnHasSuffix(function *lambda.GetFunctionOutput, arnSuffix string) resource.TestCheckFunc { 588 return func(s *terraform.State) error { 589 c := function.Configuration 590 if !strings.HasSuffix(*c.FunctionArn, arnSuffix) { 591 return fmt.Errorf("Expected function ARN %s to have suffix %s", *c.FunctionArn, arnSuffix) 592 } 593 594 return nil 595 } 596 } 597 598 func testAccCheckAwsLambdaSourceCodeHash(function *lambda.GetFunctionOutput, expectedHash string) resource.TestCheckFunc { 599 return func(s *terraform.State) error { 600 c := function.Configuration 601 if *c.CodeSha256 != expectedHash { 602 return fmt.Errorf("Expected code hash %s, got %s", expectedHash, *c.CodeSha256) 603 } 604 605 return nil 606 } 607 } 608 609 func testAccCreateZipFromFiles(files map[string]string, zipFile *os.File) error { 610 zipFile.Truncate(0) 611 zipFile.Seek(0, 0) 612 613 w := zip.NewWriter(zipFile) 614 615 for source, destination := range files { 616 f, err := w.Create(destination) 617 if err != nil { 618 return err 619 } 620 621 fileContent, err := ioutil.ReadFile(source) 622 if err != nil { 623 return err 624 } 625 626 _, err = f.Write(fileContent) 627 if err != nil { 628 return err 629 } 630 } 631 632 err := w.Close() 633 if err != nil { 634 return err 635 } 636 637 return w.Flush() 638 } 639 640 func createTempFile(prefix string) (string, *os.File, error) { 641 f, err := ioutil.TempFile(os.TempDir(), prefix) 642 if err != nil { 643 return "", nil, err 644 } 645 646 pathToFile, err := filepath.Abs(f.Name()) 647 if err != nil { 648 return "", nil, err 649 } 650 return pathToFile, f, nil 651 } 652 653 func baseAccAWSLambdaConfig(rst string) string { 654 return fmt.Sprintf(` 655 resource "aws_iam_role_policy" "iam_policy_for_lambda" { 656 name = "iam_policy_for_lambda_%s" 657 role = "${aws_iam_role.iam_for_lambda.id}" 658 policy = <<EOF 659 { 660 "Version": "2012-10-17", 661 "Statement": [ 662 { 663 "Effect": "Allow", 664 "Action": [ 665 "logs:CreateLogGroup", 666 "logs:CreateLogStream", 667 "logs:PutLogEvents" 668 ], 669 "Resource": "arn:aws:logs:*:*:*" 670 }, 671 { 672 "Effect": "Allow", 673 "Action": [ 674 "ec2:CreateNetworkInterface" 675 ], 676 "Resource": [ 677 "*" 678 ] 679 } 680 ] 681 } 682 EOF 683 } 684 685 resource "aws_iam_role" "iam_for_lambda" { 686 name = "iam_for_lambda_%s" 687 assume_role_policy = <<EOF 688 { 689 "Version": "2012-10-17", 690 "Statement": [ 691 { 692 "Action": "sts:AssumeRole", 693 "Principal": { 694 "Service": "lambda.amazonaws.com" 695 }, 696 "Effect": "Allow", 697 "Sid": "" 698 } 699 ] 700 } 701 EOF 702 } 703 704 resource "aws_vpc" "vpc_for_lambda" { 705 cidr_block = "10.0.0.0/16" 706 } 707 708 resource "aws_subnet" "subnet_for_lambda" { 709 vpc_id = "${aws_vpc.vpc_for_lambda.id}" 710 cidr_block = "10.0.1.0/24" 711 712 tags { 713 Name = "lambda" 714 } 715 } 716 717 resource "aws_security_group" "sg_for_lambda" { 718 name = "sg_for_lambda_%s" 719 description = "Allow all inbound traffic for lambda test" 720 vpc_id = "${aws_vpc.vpc_for_lambda.id}" 721 722 ingress { 723 from_port = 0 724 to_port = 0 725 protocol = "-1" 726 cidr_blocks = ["0.0.0.0/0"] 727 } 728 729 egress { 730 from_port = 0 731 to_port = 0 732 protocol = "-1" 733 cidr_blocks = ["0.0.0.0/0"] 734 } 735 }`, rst, rst, rst) 736 } 737 738 func testAccAWSLambdaConfigBasic(rName, rSt string) string { 739 return fmt.Sprintf(baseAccAWSLambdaConfig(rSt)+` 740 resource "aws_lambda_function" "lambda_function_test" { 741 filename = "test-fixtures/lambdatest.zip" 742 function_name = "%s" 743 role = "${aws_iam_role.iam_for_lambda.arn}" 744 handler = "exports.example" 745 runtime = "nodejs4.3" 746 } 747 `, rName) 748 } 749 750 func testAccAWSLambdaConfigWithoutFilenameAndS3Attributes(rName, rSt string) string { 751 return fmt.Sprintf(baseAccAWSLambdaConfig(rSt)+` 752 resource "aws_lambda_function" "lambda_function_test" { 753 function_name = "%s" 754 role = "${aws_iam_role.iam_for_lambda.arn}" 755 handler = "exports.example" 756 runtime = "nodejs4.3" 757 } 758 `, rName) 759 } 760 761 func testAccAWSLambdaConfigEnvVariables(rName, rSt string) string { 762 return fmt.Sprintf(baseAccAWSLambdaConfig(rSt)+` 763 resource "aws_lambda_function" "lambda_function_test" { 764 filename = "test-fixtures/lambdatest.zip" 765 function_name = "%s" 766 role = "${aws_iam_role.iam_for_lambda.arn}" 767 handler = "exports.example" 768 runtime = "nodejs4.3" 769 environment { 770 variables = { 771 foo = "bar" 772 } 773 } 774 } 775 `, rName) 776 } 777 778 func testAccAWSLambdaConfigEnvVariablesModified(rName, rSt string) string { 779 return fmt.Sprintf(baseAccAWSLambdaConfig(rSt)+` 780 resource "aws_lambda_function" "lambda_function_test" { 781 filename = "test-fixtures/lambdatest.zip" 782 function_name = "%s" 783 role = "${aws_iam_role.iam_for_lambda.arn}" 784 handler = "exports.example" 785 runtime = "nodejs4.3" 786 environment { 787 variables = { 788 foo = "baz" 789 foo1 = "bar1" 790 } 791 } 792 } 793 `, rName) 794 } 795 796 func testAccAWSLambdaConfigEnvVariablesModifiedWithoutEnvironment(rName, rSt string) string { 797 return fmt.Sprintf(baseAccAWSLambdaConfig(rSt)+` 798 resource "aws_lambda_function" "lambda_function_test" { 799 filename = "test-fixtures/lambdatest.zip" 800 function_name = "%s" 801 role = "${aws_iam_role.iam_for_lambda.arn}" 802 handler = "exports.example" 803 runtime = "nodejs4.3" 804 } 805 `, rName) 806 } 807 808 func testAccAWSLambdaConfigEncryptedEnvVariables(rName, rSt string) string { 809 return fmt.Sprintf(baseAccAWSLambdaConfig(rSt)+` 810 resource "aws_kms_key" "foo" { 811 description = "Terraform acc test %s" 812 policy = <<POLICY 813 { 814 "Version": "2012-10-17", 815 "Id": "kms-tf-1", 816 "Statement": [ 817 { 818 "Sid": "Enable IAM User Permissions", 819 "Effect": "Allow", 820 "Principal": { 821 "AWS": "*" 822 }, 823 "Action": "kms:*", 824 "Resource": "*" 825 } 826 ] 827 } 828 POLICY 829 } 830 831 resource "aws_lambda_function" "lambda_function_test" { 832 filename = "test-fixtures/lambdatest.zip" 833 function_name = "%s" 834 role = "${aws_iam_role.iam_for_lambda.arn}" 835 handler = "exports.example" 836 kms_key_arn = "${aws_kms_key.foo.arn}" 837 runtime = "nodejs4.3" 838 environment { 839 variables = { 840 foo = "bar" 841 } 842 } 843 } 844 `, rName, rName) 845 } 846 847 func testAccAWSLambdaConfigEncryptedEnvVariablesModified(rName, rSt string) string { 848 return fmt.Sprintf(baseAccAWSLambdaConfig(rSt)+` 849 resource "aws_lambda_function" "lambda_function_test" { 850 filename = "test-fixtures/lambdatest.zip" 851 function_name = "%s" 852 role = "${aws_iam_role.iam_for_lambda.arn}" 853 handler = "exports.example" 854 runtime = "nodejs4.3" 855 environment { 856 variables = { 857 foo = "bar" 858 } 859 } 860 } 861 `, rName) 862 } 863 864 func testAccAWSLambdaConfigVersioned(rName, rSt string) string { 865 return fmt.Sprintf(baseAccAWSLambdaConfig(rSt)+` 866 resource "aws_lambda_function" "lambda_function_test" { 867 filename = "test-fixtures/lambdatest.zip" 868 function_name = "%s" 869 publish = true 870 role = "${aws_iam_role.iam_for_lambda.arn}" 871 handler = "exports.example" 872 runtime = "nodejs4.3" 873 } 874 `, rName) 875 } 876 877 func testAccAWSLambdaConfigWithVPC(rName, rSt string) string { 878 return fmt.Sprintf(baseAccAWSLambdaConfig(rSt)+` 879 resource "aws_lambda_function" "lambda_function_test" { 880 filename = "test-fixtures/lambdatest.zip" 881 function_name = "%s" 882 role = "${aws_iam_role.iam_for_lambda.arn}" 883 handler = "exports.example" 884 runtime = "nodejs4.3" 885 886 vpc_config = { 887 subnet_ids = ["${aws_subnet.subnet_for_lambda.id}"] 888 security_group_ids = ["${aws_security_group.sg_for_lambda.id}"] 889 } 890 }`, rName) 891 } 892 893 func testAccAWSLambdaConfigS3(rName, rSt string) string { 894 return fmt.Sprintf(` 895 resource "aws_s3_bucket" "lambda_bucket" { 896 bucket = "tf-test-bucket-%d" 897 } 898 899 resource "aws_s3_bucket_object" "lambda_code" { 900 bucket = "${aws_s3_bucket.lambda_bucket.id}" 901 key = "lambdatest.zip" 902 source = "test-fixtures/lambdatest.zip" 903 } 904 905 resource "aws_iam_role" "iam_for_lambda" { 906 name = "iam_for_lambda_%s" 907 assume_role_policy = <<EOF 908 { 909 "Version": "2012-10-17", 910 "Statement": [ 911 { 912 "Action": "sts:AssumeRole", 913 "Principal": { 914 "Service": "lambda.amazonaws.com" 915 }, 916 "Effect": "Allow", 917 "Sid": "" 918 } 919 ] 920 } 921 EOF 922 } 923 924 resource "aws_lambda_function" "lambda_function_s3test" { 925 s3_bucket = "${aws_s3_bucket.lambda_bucket.id}" 926 s3_key = "${aws_s3_bucket_object.lambda_code.id}" 927 function_name = "%s" 928 role = "${aws_iam_role.iam_for_lambda.arn}" 929 handler = "exports.example" 930 runtime = "nodejs4.3" 931 } 932 `, acctest.RandInt(), rSt, rName) 933 } 934 935 func testAccAWSLambdaConfigNoRuntime(rName, rSt string) string { 936 return fmt.Sprintf(baseAccAWSLambdaConfig(rSt)+` 937 resource "aws_lambda_function" "lambda_function_test" { 938 filename = "test-fixtures/lambdatest.zip" 939 function_name = "%s" 940 role = "${aws_iam_role.iam_for_lambda.arn}" 941 handler = "exports.example" 942 runtime = "nodejs4.3" 943 } 944 `, rName) 945 } 946 947 func testAccAWSLambdaConfigNodeJsRuntime(rName, rSt string) string { 948 return fmt.Sprintf(baseAccAWSLambdaConfig(rSt)+` 949 resource "aws_lambda_function" "lambda_function_test" { 950 filename = "test-fixtures/lambdatest.zip" 951 function_name = "%s" 952 role = "${aws_iam_role.iam_for_lambda.arn}" 953 handler = "exports.example" 954 runtime = "nodejs4.3" 955 } 956 `, rName) 957 } 958 959 func testAccAWSLambdaConfigNodeJs43Runtime(rName, rSt string) string { 960 return fmt.Sprintf(baseAccAWSLambdaConfig(rSt)+` 961 resource "aws_lambda_function" "lambda_function_test" { 962 filename = "test-fixtures/lambdatest.zip" 963 function_name = "%s" 964 role = "${aws_iam_role.iam_for_lambda.arn}" 965 handler = "exports.example" 966 runtime = "nodejs4.3" 967 } 968 `, rName) 969 } 970 971 func testAccAWSLambdaConfigPython27Runtime(rName, rSt string) string { 972 return fmt.Sprintf(baseAccAWSLambdaConfig(rSt)+` 973 resource "aws_lambda_function" "lambda_function_test" { 974 filename = "test-fixtures/lambdatest.zip" 975 function_name = "%s" 976 role = "${aws_iam_role.iam_for_lambda.arn}" 977 handler = "exports.example" 978 runtime = "python2.7" 979 } 980 `, rName) 981 } 982 983 func testAccAWSLambdaConfigJava8Runtime(rName, rSt string) string { 984 return fmt.Sprintf(baseAccAWSLambdaConfig(rSt)+` 985 resource "aws_lambda_function" "lambda_function_test" { 986 filename = "test-fixtures/lambdatest.zip" 987 function_name = "%s" 988 role = "${aws_iam_role.iam_for_lambda.arn}" 989 handler = "exports.example" 990 runtime = "java8" 991 } 992 `, rName) 993 } 994 995 const testAccAWSLambdaFunctionConfig_local_tpl = ` 996 resource "aws_iam_role" "iam_for_lambda" { 997 name = "iam_for_lambda" 998 assume_role_policy = <<EOF 999 { 1000 "Version": "2012-10-17", 1001 "Statement": [ 1002 { 1003 "Action": "sts:AssumeRole", 1004 "Principal": { 1005 "Service": "lambda.amazonaws.com" 1006 }, 1007 "Effect": "Allow", 1008 "Sid": "" 1009 } 1010 ] 1011 } 1012 EOF 1013 } 1014 resource "aws_lambda_function" "lambda_function_local" { 1015 filename = "%s" 1016 source_code_hash = "${base64sha256(file("%s"))}" 1017 function_name = "tf_acc_lambda_name_local" 1018 role = "${aws_iam_role.iam_for_lambda.arn}" 1019 handler = "exports.example" 1020 runtime = "nodejs4.3" 1021 } 1022 ` 1023 1024 func genAWSLambdaFunctionConfig_local(filePath string) string { 1025 return fmt.Sprintf(testAccAWSLambdaFunctionConfig_local_tpl, 1026 filePath, filePath) 1027 } 1028 1029 func genAWSLambdaFunctionConfig_local_name_only(filePath string) string { 1030 return fmt.Sprintf(testAccAWSLambdaFunctionConfig_local_name_only_tpl, 1031 filePath) 1032 } 1033 1034 const testAccAWSLambdaFunctionConfig_local_name_only_tpl = ` 1035 resource "aws_iam_role" "iam_for_lambda" { 1036 name = "iam_for_lambda" 1037 assume_role_policy = <<EOF 1038 { 1039 "Version": "2012-10-17", 1040 "Statement": [ 1041 { 1042 "Action": "sts:AssumeRole", 1043 "Principal": { 1044 "Service": "lambda.amazonaws.com" 1045 }, 1046 "Effect": "Allow", 1047 "Sid": "" 1048 } 1049 ] 1050 } 1051 EOF 1052 } 1053 resource "aws_lambda_function" "lambda_function_local" { 1054 filename = "%s" 1055 function_name = "tf_acc_lambda_name_local" 1056 role = "${aws_iam_role.iam_for_lambda.arn}" 1057 handler = "exports.example" 1058 runtime = "nodejs4.3" 1059 } 1060 ` 1061 1062 const testAccAWSLambdaFunctionConfig_s3_tpl = ` 1063 resource "aws_s3_bucket" "artifacts" { 1064 bucket = "%s" 1065 acl = "private" 1066 force_destroy = true 1067 versioning { 1068 enabled = true 1069 } 1070 } 1071 resource "aws_s3_bucket_object" "o" { 1072 bucket = "${aws_s3_bucket.artifacts.bucket}" 1073 key = "%s" 1074 source = "%s" 1075 etag = "${md5(file("%s"))}" 1076 } 1077 resource "aws_iam_role" "iam_for_lambda" { 1078 name = "iam_for_lambda" 1079 assume_role_policy = <<EOF 1080 { 1081 "Version": "2012-10-17", 1082 "Statement": [ 1083 { 1084 "Action": "sts:AssumeRole", 1085 "Principal": { 1086 "Service": "lambda.amazonaws.com" 1087 }, 1088 "Effect": "Allow", 1089 "Sid": "" 1090 } 1091 ] 1092 } 1093 EOF 1094 } 1095 resource "aws_lambda_function" "lambda_function_s3" { 1096 s3_bucket = "${aws_s3_bucket_object.o.bucket}" 1097 s3_key = "${aws_s3_bucket_object.o.key}" 1098 s3_object_version = "${aws_s3_bucket_object.o.version_id}" 1099 function_name = "tf_acc_lambda_name_s3" 1100 role = "${aws_iam_role.iam_for_lambda.arn}" 1101 handler = "exports.example" 1102 runtime = "nodejs4.3" 1103 } 1104 ` 1105 1106 func genAWSLambdaFunctionConfig_s3(bucket, key, path string) string { 1107 return fmt.Sprintf(testAccAWSLambdaFunctionConfig_s3_tpl, 1108 bucket, key, path, path) 1109 } 1110 1111 const testAccAWSLambdaFunctionConfig_s3_unversioned_tpl = ` 1112 resource "aws_s3_bucket" "artifacts" { 1113 bucket = "%s" 1114 acl = "private" 1115 force_destroy = true 1116 } 1117 resource "aws_s3_bucket_object" "o" { 1118 bucket = "${aws_s3_bucket.artifacts.bucket}" 1119 key = "%s" 1120 source = "%s" 1121 etag = "${md5(file("%s"))}" 1122 } 1123 resource "aws_iam_role" "iam_for_lambda" { 1124 name = "iam_for_lambda" 1125 assume_role_policy = <<EOF 1126 { 1127 "Version": "2012-10-17", 1128 "Statement": [ 1129 { 1130 "Action": "sts:AssumeRole", 1131 "Principal": { 1132 "Service": "lambda.amazonaws.com" 1133 }, 1134 "Effect": "Allow", 1135 "Sid": "" 1136 } 1137 ] 1138 } 1139 EOF 1140 } 1141 resource "aws_lambda_function" "lambda_function_s3" { 1142 s3_bucket = "${aws_s3_bucket_object.o.bucket}" 1143 s3_key = "${aws_s3_bucket_object.o.key}" 1144 function_name = "tf_acc_lambda_name_s3_unversioned" 1145 role = "${aws_iam_role.iam_for_lambda.arn}" 1146 handler = "exports.example" 1147 runtime = "nodejs4.3" 1148 } 1149 ` 1150 1151 func genAWSLambdaFunctionConfig_s3_unversioned(bucket, key, path string) string { 1152 return fmt.Sprintf(testAccAWSLambdaFunctionConfig_s3_unversioned_tpl, 1153 bucket, key, path, path) 1154 }