diff --git a/docs/resources/service_v1.md b/docs/resources/service_v1.md index 003f67cb6..e0c30a86a 100644 --- a/docs/resources/service_v1.md +++ b/docs/resources/service_v1.md @@ -236,7 +236,6 @@ $ terraform import fastly_service_v1.demo xxxxxxxxxxxxxxxxxxxx@2 ### Required -- **backend** (Block Set, Min: 1) (see [below for nested schema](#nestedblock--backend)) - **domain** (Block Set, Min: 1) A set of Domain names to serve as entry points for your Service (see [below for nested schema](#nestedblock--domain)) - **name** (String) The unique name for the Service to create @@ -244,6 +243,7 @@ $ terraform import fastly_service_v1.demo xxxxxxxxxxxxxxxxxxxx@2 - **acl** (Block Set) (see [below for nested schema](#nestedblock--acl)) - **activate** (Boolean) Conditionally prevents the Service from being activated. The apply step will continue to create a new draft version but will not activate it if this is set to `false`. Default `true` +- **backend** (Block Set) (see [below for nested schema](#nestedblock--backend)) - **bigquerylogging** (Block Set) (see [below for nested schema](#nestedblock--bigquerylogging)) - **blobstoragelogging** (Block Set) (see [below for nested schema](#nestedblock--blobstoragelogging)) - **cache_setting** (Block Set) (see [below for nested schema](#nestedblock--cache_setting)) @@ -295,6 +295,34 @@ $ terraform import fastly_service_v1.demo xxxxxxxxxxxxxxxxxxxx@2 - **active_version** (Number) The currently active version of your Fastly Service - **cloned_version** (Number) The latest cloned version by the provider + +### Nested Schema for `domain` + +Required: + +- **name** (String) The domain that this Service will respond to. It is important to note that changing this attribute will delete and recreate the resource. + +Optional: + +- **comment** (String) An optional comment about the Domain. + + + +### Nested Schema for `acl` + +Required: + +- **name** (String) A unique name to identify this ACL. It is important to note that changing this attribute will delete and recreate the ACL, and discard the current items in the ACL + +Optional: + +- **force_destroy** (Boolean) Allow the ACL to be deleted, even if it contains entries. Defaults to false. + +Read-Only: + +- **acl_id** (String) The ID of the ACL + + ### Nested Schema for `backend` @@ -330,34 +358,6 @@ Optional: - **weight** (Number) The [portion of traffic](https://docs.fastly.com/en/guides/load-balancing-configuration#how-weight-affects-load-balancing) to send to this Backend. Each Backend receives weight / total of the traffic. Default `100` - -### Nested Schema for `domain` - -Required: - -- **name** (String) The domain that this Service will respond to. It is important to note that changing this attribute will delete and recreate the resource. - -Optional: - -- **comment** (String) An optional comment about the Domain. - - - -### Nested Schema for `acl` - -Required: - -- **name** (String) A unique name to identify this ACL. It is important to note that changing this attribute will delete and recreate the ACL, and discard the current items in the ACL - -Optional: - -- **force_destroy** (Boolean) Allow the ACL to be deleted, even if it contains entries. Defaults to false. - -Read-Only: - -- **acl_id** (String) The ID of the ACL - - ### Nested Schema for `bigquerylogging` diff --git a/fastly/block_fastly_service_v1_backend.go b/fastly/block_fastly_service_v1_backend.go index 5f6f77de2..058f1e081 100644 --- a/fastly/block_fastly_service_v1_backend.go +++ b/fastly/block_fastly_service_v1_backend.go @@ -404,7 +404,12 @@ func (h *BackendServiceAttributeHandler) Register(s *schema.Resource) error { }, } + required := true + if h.GetServiceMetadata().serviceType == ServiceTypeVCL { + // backend is optional in VCL service + required = false + blockAttributes["request_condition"] = &schema.Schema{ Type: schema.TypeString, Optional: true, @@ -415,7 +420,8 @@ func (h *BackendServiceAttributeHandler) Register(s *schema.Resource) error { s.Schema[h.GetKey()] = &schema.Schema{ Type: schema.TypeSet, - Required: true, + Required: required, + Optional: !required, Elem: &schema.Resource{ Schema: blockAttributes, }, diff --git a/fastly/resource_fastly_service_v1_test.go b/fastly/resource_fastly_service_v1_test.go index e443ab21c..39ae6a1f3 100644 --- a/fastly/resource_fastly_service_v1_test.go +++ b/fastly/resource_fastly_service_v1_test.go @@ -349,6 +349,62 @@ func TestAccFastlyServiceV1_updateInvalidBackend(t *testing.T) { }) } +func TestAccFastlyServiceV1_createServiceWithStaticBackend(t *testing.T) { + var service gofastly.ServiceDetail + name := fmt.Sprintf("tf-test-%s", acctest.RandString(10)) + domain := fmt.Sprintf("fastly-test.tf-%s.com", acctest.RandString(10)) + snippet1 := ` + backend F_httpbin_org { + .always_use_host_header = true; + .between_bytes_timeout = 1s; + .connect_timeout = 1s; + .dynamic = true; + .first_byte_timeout = 1s; + .host = "httpbin.org"; + .host_header = "httpbin.org"; + .max_connections = 200; + .port = "443"; + .share_key = "foo"; + .ssl = true; + .ssl_cert_hostname = "httpbin.org"; + .ssl_check_cert = always; + .ssl_sni_hostname = "httpbin.org"; + .probe = { + .dummy = true; + .initial = 5; + .request = "HEAD / HTTP/1.1" "Host: httpbin.org" "Connection: close"; + .threshold = 1; + .timeout = 2s; + .window = 5; + } + } + ` + snippet2 := "# just a comment line" + + resource.ParallelTest(t, resource.TestCase{ + PreCheck: func() { testAccPreCheck(t) }, + ProviderFactories: testAccProviders, + CheckDestroy: testAccCheckServiceV1Destroy, + Steps: []resource.TestStep{ + { + Config: testAccServiceV1Config_staticBackend(name, domain, snippet1), + Check: resource.ComposeTestCheckFunc( + testAccCheckServiceV1Exists("fastly_service_v1.foo", &service), + testAccCheckFastlyServiceV1Attributes_backends(&service, name, []string{}), + resource.TestCheckResourceAttr( + "fastly_service_v1.foo", "active_version", "1"), + resource.TestCheckResourceAttr( + "fastly_service_v1.foo", "backend.#", "0"), + ), + }, + { + Config: testAccServiceV1Config_staticBackend(name, domain, snippet2), + ExpectError: regexp.MustCompile("No backends"), + }, + }, + }) +} + func TestAccFastlyServiceV1_basic(t *testing.T) { var service gofastly.ServiceDetail name := fmt.Sprintf("tf-test-%s", acctest.RandString(10)) @@ -847,6 +903,27 @@ resource "fastly_service_v1" "foo" { }`, name, domain, backend) } +func testAccServiceV1Config_staticBackend(name, domain, snippet string) string { + return fmt.Sprintf(` +resource "fastly_service_v1" "foo" { + name = "%s" + force_destroy = true + + domain { + name = "%s" + } + + snippet { + content = <<-EOT + %s + EOT + name = "vcl_init" + priority = 50 + type = "init" + } +}`, name, domain, snippet) +} + func testAccServiceV1Config_backendTTL(name, domain, backend string, ttl uint) string { return fmt.Sprintf(` resource "fastly_service_v1" "foo" {