Generate RegionBackendService in terraform

Signed-off-by: Modular Magician <magic-modules@google.com>
This commit is contained in:
Sam Levenick 2019-05-01 22:20:15 +00:00 committed by Modular Magician
parent 78ef2f545b
commit 3cbbc66b99
6 changed files with 748 additions and 444 deletions

View File

@ -176,7 +176,6 @@ func ResourceMapWithErrors() (map[string]*schema.Resource, error) {
"google_compute_network_peering": resourceComputeNetworkPeering(), "google_compute_network_peering": resourceComputeNetworkPeering(),
"google_compute_project_metadata": resourceComputeProjectMetadata(), "google_compute_project_metadata": resourceComputeProjectMetadata(),
"google_compute_project_metadata_item": resourceComputeProjectMetadataItem(), "google_compute_project_metadata_item": resourceComputeProjectMetadataItem(),
"google_compute_region_backend_service": resourceComputeRegionBackendService(),
"google_compute_region_instance_group_manager": resourceComputeRegionInstanceGroupManager(), "google_compute_region_instance_group_manager": resourceComputeRegionInstanceGroupManager(),
"google_compute_router_interface": resourceComputeRouterInterface(), "google_compute_router_interface": resourceComputeRouterInterface(),
"google_compute_router_nat": resourceComputeRouterNat(), "google_compute_router_nat": resourceComputeRouterNat(),

View File

@ -22,6 +22,7 @@ var GeneratedComputeResourcesMap = map[string]*schema.Resource{
"google_compute_backend_bucket": resourceComputeBackendBucket(), "google_compute_backend_bucket": resourceComputeBackendBucket(),
"google_compute_backend_bucket_signed_url_key": resourceComputeBackendBucketSignedUrlKey(), "google_compute_backend_bucket_signed_url_key": resourceComputeBackendBucketSignedUrlKey(),
"google_compute_backend_service": resourceComputeBackendService(), "google_compute_backend_service": resourceComputeBackendService(),
"google_compute_region_backend_service": resourceComputeRegionBackendService(),
"google_compute_backend_service_signed_url_key": resourceComputeBackendServiceSignedUrlKey(), "google_compute_backend_service_signed_url_key": resourceComputeBackendServiceSignedUrlKey(),
"google_compute_disk": resourceComputeDisk(), "google_compute_disk": resourceComputeDisk(),
"google_compute_firewall": resourceComputeFirewall(), "google_compute_firewall": resourceComputeFirewall(),

View File

@ -1,14 +1,28 @@
// ----------------------------------------------------------------------------
//
// *** AUTO GENERATED CODE *** AUTO GENERATED CODE ***
//
// ----------------------------------------------------------------------------
//
// This file is automatically generated by Magic Modules and manual
// changes will be clobbered when the file is regenerated.
//
// Please read more about how to change this file in
// .github/CONTRIBUTING.md.
//
// ----------------------------------------------------------------------------
package google package google
import ( import (
"bytes"
"errors"
"fmt" "fmt"
"log" "log"
"reflect"
"strconv"
"time"
"github.com/hashicorp/terraform/helper/hashcode"
"github.com/hashicorp/terraform/helper/schema" "github.com/hashicorp/terraform/helper/schema"
computeBeta "google.golang.org/api/compute/v0.beta" "github.com/hashicorp/terraform/helper/validation"
"google.golang.org/api/compute/v1" "google.golang.org/api/compute/v1"
) )
@ -19,93 +33,109 @@ func resourceComputeRegionBackendService() *schema.Resource {
Update: resourceComputeRegionBackendServiceUpdate, Update: resourceComputeRegionBackendServiceUpdate,
Delete: resourceComputeRegionBackendServiceDelete, Delete: resourceComputeRegionBackendServiceDelete,
Schema: map[string]*schema.Schema{ Importer: &schema.ResourceImporter{
"name": { State: resourceComputeRegionBackendServiceImport,
Type: schema.TypeString, },
Required: true,
ForceNew: true,
ValidateFunc: validateGCPName,
},
Timeouts: &schema.ResourceTimeout{
Create: schema.DefaultTimeout(240 * time.Second),
Update: schema.DefaultTimeout(240 * time.Second),
Delete: schema.DefaultTimeout(240 * time.Second),
},
SchemaVersion: 1,
Schema: map[string]*schema.Schema{
"health_checks": { "health_checks": {
Type: schema.TypeSet, Type: schema.TypeSet,
Elem: &schema.Schema{Type: schema.TypeString},
Set: schema.HashString,
Required: true, Required: true,
MinItems: 1, MinItems: 1,
MaxItems: 1, MaxItems: 1,
}, Elem: &schema.Schema{
Type: schema.TypeString,
"backend": {
Type: schema.TypeSet,
Elem: &schema.Resource{
Schema: map[string]*schema.Schema{
"group": {
Type: schema.TypeString,
Optional: true,
DiffSuppressFunc: compareSelfLinkRelativePaths,
},
"description": {
Type: schema.TypeString,
Optional: true,
},
},
}, },
Set: selfLinkRelativePathHash,
},
"name": {
Type: schema.TypeString,
Required: true,
ForceNew: true,
},
"backend": {
Type: schema.TypeSet,
Optional: true, Optional: true,
Set: resourceGoogleComputeRegionBackendServiceBackendHash, Elem: computeRegionBackendServiceBackendSchema(),
Set: resourceGoogleComputeBackendServiceBackendHash,
},
"connection_draining_timeout_sec": {
Type: schema.TypeInt,
Optional: true,
Default: 0,
}, },
"description": { "description": {
Type: schema.TypeString, Type: schema.TypeString,
Optional: true, Optional: true,
}, },
"load_balancing_scheme": {
Type: schema.TypeString,
Optional: true,
ValidateFunc: validation.StringInSlice([]string{"INTERNAL", ""}, false),
Default: "INTERNAL",
},
"protocol": {
Type: schema.TypeString,
Computed: true,
Optional: true,
ValidateFunc: validation.StringInSlice([]string{"TCP", "UDP", ""}, false),
},
"region": {
Type: schema.TypeString,
Computed: true,
Optional: true,
ForceNew: true,
DiffSuppressFunc: compareSelfLinkOrResourceName,
},
"session_affinity": {
Type: schema.TypeString,
Computed: true,
Optional: true,
ValidateFunc: validation.StringInSlice([]string{"NONE", "CLIENT_IP", "CLIENT_IP_PROTO", "CLIENT_IP_PORT_PROTO", ""}, false),
},
"timeout_sec": {
Type: schema.TypeInt,
Computed: true,
Optional: true,
},
"fingerprint": { "fingerprint": {
Type: schema.TypeString, Type: schema.TypeString,
Computed: true, Computed: true,
}, },
"project": { "project": {
Type: schema.TypeString, Type: schema.TypeString,
Optional: true, Optional: true,
Computed: true, Computed: true,
ForceNew: true, ForceNew: true,
}, },
"protocol": {
Type: schema.TypeString,
Optional: true,
Computed: true,
},
"session_affinity": {
Type: schema.TypeString,
Optional: true,
Computed: true,
},
"region": {
Type: schema.TypeString,
Optional: true,
Computed: true,
ForceNew: true,
},
"self_link": { "self_link": {
Type: schema.TypeString, Type: schema.TypeString,
Computed: true, Computed: true,
}, },
},
}
}
"timeout_sec": { func computeRegionBackendServiceBackendSchema() *schema.Resource {
Type: schema.TypeInt, return &schema.Resource{
Schema: map[string]*schema.Schema{
"description": {
Type: schema.TypeString,
Optional: true, Optional: true,
Computed: true,
}, },
"group": {
"connection_draining_timeout_sec": { Type: schema.TypeString,
Type: schema.TypeInt, Optional: true,
Optional: true, DiffSuppressFunc: compareSelfLinkRelativePaths,
Default: 0,
}, },
}, },
} }
@ -114,76 +144,113 @@ func resourceComputeRegionBackendService() *schema.Resource {
func resourceComputeRegionBackendServiceCreate(d *schema.ResourceData, meta interface{}) error { func resourceComputeRegionBackendServiceCreate(d *schema.ResourceData, meta interface{}) error {
config := meta.(*Config) config := meta.(*Config)
hc := d.Get("health_checks").(*schema.Set).List() obj := make(map[string]interface{})
healthChecks := make([]string, 0, len(hc)) nameProp, err := expandComputeRegionBackendServiceName(d.Get("name"), d, config)
for _, v := range hc { if err != nil {
healthChecks = append(healthChecks, v.(string)) return err
} else if v, ok := d.GetOkExists("name"); !isEmptyValue(reflect.ValueOf(nameProp)) && (ok || !reflect.DeepEqual(v, nameProp)) {
obj["name"] = nameProp
}
healthChecksProp, err := expandComputeRegionBackendServiceHealthChecks(d.Get("health_checks"), d, config)
if err != nil {
return err
} else if v, ok := d.GetOkExists("health_checks"); !isEmptyValue(reflect.ValueOf(healthChecksProp)) && (ok || !reflect.DeepEqual(v, healthChecksProp)) {
obj["healthChecks"] = healthChecksProp
}
backendsProp, err := expandComputeRegionBackendServiceBackend(d.Get("backend"), d, config)
if err != nil {
return err
} else if v, ok := d.GetOkExists("backend"); !isEmptyValue(reflect.ValueOf(backendsProp)) && (ok || !reflect.DeepEqual(v, backendsProp)) {
obj["backends"] = backendsProp
}
descriptionProp, err := expandComputeRegionBackendServiceDescription(d.Get("description"), d, config)
if err != nil {
return err
} else if v, ok := d.GetOkExists("description"); !isEmptyValue(reflect.ValueOf(descriptionProp)) && (ok || !reflect.DeepEqual(v, descriptionProp)) {
obj["description"] = descriptionProp
}
fingerprintProp, err := expandComputeRegionBackendServiceFingerprint(d.Get("fingerprint"), d, config)
if err != nil {
return err
} else if v, ok := d.GetOkExists("fingerprint"); !isEmptyValue(reflect.ValueOf(fingerprintProp)) && (ok || !reflect.DeepEqual(v, fingerprintProp)) {
obj["fingerprint"] = fingerprintProp
}
protocolProp, err := expandComputeRegionBackendServiceProtocol(d.Get("protocol"), d, config)
if err != nil {
return err
} else if v, ok := d.GetOkExists("protocol"); !isEmptyValue(reflect.ValueOf(protocolProp)) && (ok || !reflect.DeepEqual(v, protocolProp)) {
obj["protocol"] = protocolProp
}
sessionAffinityProp, err := expandComputeRegionBackendServiceSessionAffinity(d.Get("session_affinity"), d, config)
if err != nil {
return err
} else if v, ok := d.GetOkExists("session_affinity"); !isEmptyValue(reflect.ValueOf(sessionAffinityProp)) && (ok || !reflect.DeepEqual(v, sessionAffinityProp)) {
obj["sessionAffinity"] = sessionAffinityProp
}
regionProp, err := expandComputeRegionBackendServiceRegion(d.Get("region"), d, config)
if err != nil {
return err
} else if v, ok := d.GetOkExists("region"); !isEmptyValue(reflect.ValueOf(regionProp)) && (ok || !reflect.DeepEqual(v, regionProp)) {
obj["region"] = regionProp
}
timeoutSecProp, err := expandComputeRegionBackendServiceTimeoutSec(d.Get("timeout_sec"), d, config)
if err != nil {
return err
} else if v, ok := d.GetOkExists("timeout_sec"); !isEmptyValue(reflect.ValueOf(timeoutSecProp)) && (ok || !reflect.DeepEqual(v, timeoutSecProp)) {
obj["timeoutSec"] = timeoutSecProp
}
connectionDrainingProp, err := expandComputeRegionBackendServiceConnectionDraining(d, config)
if err != nil {
return err
} else if !isEmptyValue(reflect.ValueOf(connectionDrainingProp)) {
obj["connectionDraining"] = connectionDrainingProp
}
loadBalancingSchemeProp, err := expandComputeRegionBackendServiceLoadBalancingScheme(d.Get("load_balancing_scheme"), d, config)
if err != nil {
return err
} else if v, ok := d.GetOkExists("load_balancing_scheme"); !isEmptyValue(reflect.ValueOf(loadBalancingSchemeProp)) && (ok || !reflect.DeepEqual(v, loadBalancingSchemeProp)) {
obj["loadBalancingScheme"] = loadBalancingSchemeProp
} }
service := computeBeta.BackendService{ url, err := replaceVars(d, config, "https://www.googleapis.com/compute/v1/projects/{{project}}/regions/{{region}}/backendServices")
Name: d.Get("name").(string), if err != nil {
HealthChecks: healthChecks, return err
LoadBalancingScheme: "INTERNAL",
} }
var err error log.Printf("[DEBUG] Creating new RegionBackendService: %#v", obj)
if v, ok := d.GetOk("backend"); ok { res, err := sendRequestWithTimeout(config, "POST", url, obj, d.Timeout(schema.TimeoutCreate))
service.Backends, err = expandBackends(v.(*schema.Set).List()) if err != nil {
if err != nil { return fmt.Errorf("Error creating RegionBackendService: %s", err)
return err
}
} }
if v, ok := d.GetOk("description"); ok { // Store the ID now
service.Description = v.(string) id, err := replaceVars(d, config, "{{name}}")
} if err != nil {
return fmt.Errorf("Error constructing id: %s", err)
if v, ok := d.GetOk("protocol"); ok {
service.Protocol = v.(string)
}
if v, ok := d.GetOk("session_affinity"); ok {
service.SessionAffinity = v.(string)
}
if v, ok := d.GetOk("timeout_sec"); ok {
service.TimeoutSec = int64(v.(int))
}
if v, ok := d.GetOk("connection_draining_timeout_sec"); ok {
connectionDraining := &computeBeta.ConnectionDraining{
DrainingTimeoutSec: int64(v.(int)),
}
service.ConnectionDraining = connectionDraining
} }
d.SetId(id)
project, err := getProject(d, config) project, err := getProject(d, config)
if err != nil { if err != nil {
return err return err
} }
op := &compute.Operation{}
region, err := getRegion(d, config) err = Convert(res, op)
if err != nil { if err != nil {
return err return err
} }
log.Printf("[DEBUG] Creating new Region Backend Service: %#v", service) waitErr := computeOperationWaitTime(
config.clientCompute, op, project, "Creating RegionBackendService",
int(d.Timeout(schema.TimeoutCreate).Minutes()))
op, err := config.clientComputeBeta.RegionBackendServices.Insert( if waitErr != nil {
project, region, &service).Do() // The resource didn't actually create
if err != nil { d.SetId("")
return fmt.Errorf("Error creating backend service: %s", err) return fmt.Errorf("Error waiting to create RegionBackendService: %s", waitErr)
} }
log.Printf("[DEBUG] Waiting for new backend service, operation: %#v", op) log.Printf("[DEBUG] Finished creating RegionBackendService %q: %#v", d.Id(), res)
d.SetId(service.Name)
err = computeSharedOperationWait(config.clientCompute, op, project, "Creating Region Backend Service")
if err != nil {
return err
}
return resourceComputeRegionBackendServiceRead(d, meta) return resourceComputeRegionBackendServiceRead(d, meta)
} }
@ -191,36 +258,64 @@ func resourceComputeRegionBackendServiceCreate(d *schema.ResourceData, meta inte
func resourceComputeRegionBackendServiceRead(d *schema.ResourceData, meta interface{}) error { func resourceComputeRegionBackendServiceRead(d *schema.ResourceData, meta interface{}) error {
config := meta.(*Config) config := meta.(*Config)
url, err := replaceVars(d, config, "https://www.googleapis.com/compute/v1/projects/{{project}}/regions/{{region}}/backendServices/{{name}}")
if err != nil {
return err
}
res, err := sendRequest(config, "GET", url, nil)
if err != nil {
return handleNotFoundError(err, d, fmt.Sprintf("ComputeRegionBackendService %q", d.Id()))
}
project, err := getProject(d, config) project, err := getProject(d, config)
if err != nil { if err != nil {
return err return err
} }
if err := d.Set("project", project); err != nil {
region, err := getRegion(d, config) return fmt.Errorf("Error reading RegionBackendService: %s", err)
if err != nil {
return err
} }
service, err := config.clientCompute.RegionBackendServices.Get( if err := d.Set("name", flattenComputeRegionBackendServiceName(res["name"], d)); err != nil {
project, region, d.Id()).Do() return fmt.Errorf("Error reading RegionBackendService: %s", err)
if err != nil {
return handleNotFoundError(err, d, fmt.Sprintf("Region Backend Service %q", d.Get("name").(string)))
} }
if err := d.Set("health_checks", flattenComputeRegionBackendServiceHealthChecks(res["healthChecks"], d)); err != nil {
d.Set("description", service.Description) return fmt.Errorf("Error reading RegionBackendService: %s", err)
d.Set("protocol", service.Protocol) }
d.Set("session_affinity", service.SessionAffinity) if err := d.Set("backend", flattenComputeRegionBackendServiceBackend(res["backends"], d)); err != nil {
d.Set("timeout_sec", service.TimeoutSec) return fmt.Errorf("Error reading RegionBackendService: %s", err)
d.Set("connection_draining_timeout_sec", service.ConnectionDraining.DrainingTimeoutSec) }
d.Set("fingerprint", service.Fingerprint) if err := d.Set("description", flattenComputeRegionBackendServiceDescription(res["description"], d)); err != nil {
d.Set("self_link", service.SelfLink) return fmt.Errorf("Error reading RegionBackendService: %s", err)
err = d.Set("backend", flattenRegionBackends(service.Backends)) }
if err != nil { if err := d.Set("fingerprint", flattenComputeRegionBackendServiceFingerprint(res["fingerprint"], d)); err != nil {
return err return fmt.Errorf("Error reading RegionBackendService: %s", err)
}
if err := d.Set("protocol", flattenComputeRegionBackendServiceProtocol(res["protocol"], d)); err != nil {
return fmt.Errorf("Error reading RegionBackendService: %s", err)
}
if err := d.Set("session_affinity", flattenComputeRegionBackendServiceSessionAffinity(res["sessionAffinity"], d)); err != nil {
return fmt.Errorf("Error reading RegionBackendService: %s", err)
}
if err := d.Set("region", flattenComputeRegionBackendServiceRegion(res["region"], d)); err != nil {
return fmt.Errorf("Error reading RegionBackendService: %s", err)
}
if err := d.Set("timeout_sec", flattenComputeRegionBackendServiceTimeoutSec(res["timeoutSec"], d)); err != nil {
return fmt.Errorf("Error reading RegionBackendService: %s", err)
}
if v, ok := res["connectionDraining"].(map[string]interface{}); res["connectionDraining"] != nil && ok {
if err := d.Set("connection_draining_timeout_sec", flattenComputeRegionBackendServiceConnectionDrainingConnection_draining_timeout_sec(v["drainingTimeoutSec"], d)); err != nil {
return fmt.Errorf("Error reading RegionBackendService: %s", err)
}
} else {
d.Set("connection_draining_timeout_sec", nil)
}
if err := d.Set("load_balancing_scheme", flattenComputeRegionBackendServiceLoadBalancingScheme(res["loadBalancingScheme"], d)); err != nil {
return fmt.Errorf("Error reading RegionBackendService: %s", err)
}
if err := d.Set("self_link", ConvertSelfLinkToV1(res["selfLink"].(string))); err != nil {
return fmt.Errorf("Error reading RegionBackendService: %s", err)
} }
d.Set("health_checks", service.HealthChecks)
d.Set("project", project)
d.Set("region", region)
return nil return nil
} }
@ -228,67 +323,100 @@ func resourceComputeRegionBackendServiceRead(d *schema.ResourceData, meta interf
func resourceComputeRegionBackendServiceUpdate(d *schema.ResourceData, meta interface{}) error { func resourceComputeRegionBackendServiceUpdate(d *schema.ResourceData, meta interface{}) error {
config := meta.(*Config) config := meta.(*Config)
obj := make(map[string]interface{})
nameProp, err := expandComputeRegionBackendServiceName(d.Get("name"), d, config)
if err != nil {
return err
} else if v, ok := d.GetOkExists("name"); !isEmptyValue(reflect.ValueOf(v)) && (ok || !reflect.DeepEqual(v, nameProp)) {
obj["name"] = nameProp
}
healthChecksProp, err := expandComputeRegionBackendServiceHealthChecks(d.Get("health_checks"), d, config)
if err != nil {
return err
} else if v, ok := d.GetOkExists("health_checks"); !isEmptyValue(reflect.ValueOf(v)) && (ok || !reflect.DeepEqual(v, healthChecksProp)) {
obj["healthChecks"] = healthChecksProp
}
backendsProp, err := expandComputeRegionBackendServiceBackend(d.Get("backend"), d, config)
if err != nil {
return err
} else if v, ok := d.GetOkExists("backend"); !isEmptyValue(reflect.ValueOf(v)) && (ok || !reflect.DeepEqual(v, backendsProp)) {
obj["backends"] = backendsProp
}
descriptionProp, err := expandComputeRegionBackendServiceDescription(d.Get("description"), d, config)
if err != nil {
return err
} else if v, ok := d.GetOkExists("description"); !isEmptyValue(reflect.ValueOf(v)) && (ok || !reflect.DeepEqual(v, descriptionProp)) {
obj["description"] = descriptionProp
}
fingerprintProp, err := expandComputeRegionBackendServiceFingerprint(d.Get("fingerprint"), d, config)
if err != nil {
return err
} else if v, ok := d.GetOkExists("fingerprint"); !isEmptyValue(reflect.ValueOf(v)) && (ok || !reflect.DeepEqual(v, fingerprintProp)) {
obj["fingerprint"] = fingerprintProp
}
protocolProp, err := expandComputeRegionBackendServiceProtocol(d.Get("protocol"), d, config)
if err != nil {
return err
} else if v, ok := d.GetOkExists("protocol"); !isEmptyValue(reflect.ValueOf(v)) && (ok || !reflect.DeepEqual(v, protocolProp)) {
obj["protocol"] = protocolProp
}
sessionAffinityProp, err := expandComputeRegionBackendServiceSessionAffinity(d.Get("session_affinity"), d, config)
if err != nil {
return err
} else if v, ok := d.GetOkExists("session_affinity"); !isEmptyValue(reflect.ValueOf(v)) && (ok || !reflect.DeepEqual(v, sessionAffinityProp)) {
obj["sessionAffinity"] = sessionAffinityProp
}
regionProp, err := expandComputeRegionBackendServiceRegion(d.Get("region"), d, config)
if err != nil {
return err
} else if v, ok := d.GetOkExists("region"); !isEmptyValue(reflect.ValueOf(v)) && (ok || !reflect.DeepEqual(v, regionProp)) {
obj["region"] = regionProp
}
timeoutSecProp, err := expandComputeRegionBackendServiceTimeoutSec(d.Get("timeout_sec"), d, config)
if err != nil {
return err
} else if v, ok := d.GetOkExists("timeout_sec"); !isEmptyValue(reflect.ValueOf(v)) && (ok || !reflect.DeepEqual(v, timeoutSecProp)) {
obj["timeoutSec"] = timeoutSecProp
}
connectionDrainingProp, err := expandComputeRegionBackendServiceConnectionDraining(d, config)
if err != nil {
return err
} else if !isEmptyValue(reflect.ValueOf(connectionDrainingProp)) {
obj["connectionDraining"] = connectionDrainingProp
}
loadBalancingSchemeProp, err := expandComputeRegionBackendServiceLoadBalancingScheme(d.Get("load_balancing_scheme"), d, config)
if err != nil {
return err
} else if v, ok := d.GetOkExists("load_balancing_scheme"); !isEmptyValue(reflect.ValueOf(v)) && (ok || !reflect.DeepEqual(v, loadBalancingSchemeProp)) {
obj["loadBalancingScheme"] = loadBalancingSchemeProp
}
url, err := replaceVars(d, config, "https://www.googleapis.com/compute/v1/projects/{{project}}/regions/{{region}}/backendServices/{{name}}")
if err != nil {
return err
}
log.Printf("[DEBUG] Updating RegionBackendService %q: %#v", d.Id(), obj)
res, err := sendRequestWithTimeout(config, "PUT", url, obj, d.Timeout(schema.TimeoutUpdate))
if err != nil {
return fmt.Errorf("Error updating RegionBackendService %q: %s", d.Id(), err)
}
project, err := getProject(d, config) project, err := getProject(d, config)
if err != nil { if err != nil {
return err return err
} }
op := &compute.Operation{}
region, err := getRegion(d, config) err = Convert(res, op)
if err != nil { if err != nil {
return err return err
} }
hc := d.Get("health_checks").(*schema.Set).List() err = computeOperationWaitTime(
healthChecks := make([]string, 0, len(hc)) config.clientCompute, op, project, "Updating RegionBackendService",
for _, v := range hc { int(d.Timeout(schema.TimeoutUpdate).Minutes()))
healthChecks = append(healthChecks, v.(string))
}
service := computeBeta.BackendService{
Name: d.Get("name").(string),
Fingerprint: d.Get("fingerprint").(string),
HealthChecks: healthChecks,
LoadBalancingScheme: "INTERNAL",
}
// Optional things
if v, ok := d.GetOk("backend"); ok {
service.Backends, err = expandBackends(v.(*schema.Set).List())
if err != nil {
return err
}
}
if v, ok := d.GetOk("description"); ok {
service.Description = v.(string)
}
if v, ok := d.GetOk("protocol"); ok {
service.Protocol = v.(string)
}
if v, ok := d.GetOk("session_affinity"); ok {
service.SessionAffinity = v.(string)
}
if v, ok := d.GetOk("timeout_sec"); ok {
service.TimeoutSec = int64(v.(int))
}
if d.HasChange("connection_draining_timeout_sec") {
connectionDraining := &computeBeta.ConnectionDraining{
DrainingTimeoutSec: int64(d.Get("connection_draining_timeout_sec").(int)),
}
service.ConnectionDraining = connectionDraining
}
log.Printf("[DEBUG] Updating existing Backend Service %q: %#v", d.Id(), service)
op, err := config.clientComputeBeta.RegionBackendServices.Update(
project, region, d.Id(), &service).Do()
if err != nil {
return fmt.Errorf("Error updating backend service: %s", err)
}
d.SetId(service.Name)
err = computeSharedOperationWait(config.clientCompute, op, project, "Updating Backend Service")
if err != nil { if err != nil {
return err return err
} }
@ -299,124 +427,236 @@ func resourceComputeRegionBackendServiceUpdate(d *schema.ResourceData, meta inte
func resourceComputeRegionBackendServiceDelete(d *schema.ResourceData, meta interface{}) error { func resourceComputeRegionBackendServiceDelete(d *schema.ResourceData, meta interface{}) error {
config := meta.(*Config) config := meta.(*Config)
url, err := replaceVars(d, config, "https://www.googleapis.com/compute/v1/projects/{{project}}/regions/{{region}}/backendServices/{{name}}")
if err != nil {
return err
}
var obj map[string]interface{}
log.Printf("[DEBUG] Deleting RegionBackendService %q", d.Id())
res, err := sendRequestWithTimeout(config, "DELETE", url, obj, d.Timeout(schema.TimeoutDelete))
if err != nil {
return handleNotFoundError(err, d, "RegionBackendService")
}
project, err := getProject(d, config) project, err := getProject(d, config)
if err != nil { if err != nil {
return err return err
} }
op := &compute.Operation{}
region, err := getRegion(d, config) err = Convert(res, op)
if err != nil { if err != nil {
return err return err
} }
log.Printf("[DEBUG] Deleting backend service %s", d.Id()) err = computeOperationWaitTime(
op, err := config.clientCompute.RegionBackendServices.Delete( config.clientCompute, op, project, "Deleting RegionBackendService",
project, region, d.Id()).Do() int(d.Timeout(schema.TimeoutDelete).Minutes()))
if err != nil {
return fmt.Errorf("Error deleting backend service: %s", err)
}
err = computeOperationWait(config.clientCompute, op, project, "Deleting Backend Service")
if err != nil { if err != nil {
return err return err
} }
d.SetId("") log.Printf("[DEBUG] Finished deleting RegionBackendService %q: %#v", d.Id(), res)
return nil return nil
} }
func resourceGoogleComputeRegionBackendServiceBackendHash(v interface{}) int { func resourceComputeRegionBackendServiceImport(d *schema.ResourceData, meta interface{}) ([]*schema.ResourceData, error) {
config := meta.(*Config)
if err := parseImportId([]string{"projects/(?P<project>[^/]+)/regions/(?P<region>[^/]+)/backendServices/(?P<name>[^/]+)", "(?P<project>[^/]+)/(?P<region>[^/]+)/(?P<name>[^/]+)", "(?P<name>[^/]+)"}, d, config); err != nil {
return nil, err
}
// Replace import id for the resource id
id, err := replaceVars(d, config, "{{name}}")
if err != nil {
return nil, fmt.Errorf("Error constructing id: %s", err)
}
d.SetId(id)
return []*schema.ResourceData{d}, nil
}
func flattenComputeRegionBackendServiceName(v interface{}, d *schema.ResourceData) interface{} {
return v
}
func flattenComputeRegionBackendServiceHealthChecks(v interface{}, d *schema.ResourceData) interface{} {
if v == nil { if v == nil {
return 0 return v
} }
return convertAndMapStringArr(v.([]interface{}), ConvertSelfLinkToV1)
}
var buf bytes.Buffer func flattenComputeRegionBackendServiceBackend(v interface{}, d *schema.ResourceData) interface{} {
m := v.(map[string]interface{}) if v == nil {
return v
}
l := v.([]interface{})
transformed := schema.NewSet(resourceGoogleComputeBackendServiceBackendHash, []interface{}{})
for _, raw := range l {
original := raw.(map[string]interface{})
if len(original) < 1 {
// Do not include empty json objects coming back from the api
continue
}
transformed.Add(map[string]interface{}{
"description": flattenComputeRegionBackendServiceBackendDescription(original["description"], d),
"group": flattenComputeRegionBackendServiceBackendGroup(original["group"], d),
})
}
return transformed
}
func flattenComputeRegionBackendServiceBackendDescription(v interface{}, d *schema.ResourceData) interface{} {
return v
}
if group, err := getRelativePath(m["group"].(string)); err != nil { func flattenComputeRegionBackendServiceBackendGroup(v interface{}, d *schema.ResourceData) interface{} {
log.Printf("[WARN] Error on retrieving relative path of instance group: %s", err) if v == nil {
buf.WriteString(fmt.Sprintf("%s-", m["group"].(string))) return v
}
return ConvertSelfLinkToV1(v.(string))
}
func flattenComputeRegionBackendServiceDescription(v interface{}, d *schema.ResourceData) interface{} {
return v
}
func flattenComputeRegionBackendServiceFingerprint(v interface{}, d *schema.ResourceData) interface{} {
return v
}
func flattenComputeRegionBackendServiceProtocol(v interface{}, d *schema.ResourceData) interface{} {
return v
}
func flattenComputeRegionBackendServiceSessionAffinity(v interface{}, d *schema.ResourceData) interface{} {
return v
}
func flattenComputeRegionBackendServiceRegion(v interface{}, d *schema.ResourceData) interface{} {
if v == nil {
return v
}
return NameFromSelfLinkStateFunc(v)
}
func flattenComputeRegionBackendServiceTimeoutSec(v interface{}, d *schema.ResourceData) interface{} {
// Handles the string fixed64 format
if strVal, ok := v.(string); ok {
if intVal, err := strconv.ParseInt(strVal, 10, 64); err == nil {
return intVal
} // let terraform core handle it if we can't convert the string to an int.
}
return v
}
func flattenComputeRegionBackendServiceConnectionDrainingConnection_draining_timeout_sec(v interface{}, d *schema.ResourceData) interface{} {
// Handles the string fixed64 format
if strVal, ok := v.(string); ok {
if intVal, err := strconv.ParseInt(strVal, 10, 64); err == nil {
return intVal
} // let terraform core handle it if we can't convert the string to an int.
}
return v
}
func flattenComputeRegionBackendServiceLoadBalancingScheme(v interface{}, d *schema.ResourceData) interface{} {
return v
}
func expandComputeRegionBackendServiceName(v interface{}, d TerraformResourceData, config *Config) (interface{}, error) {
return v, nil
}
func expandComputeRegionBackendServiceHealthChecks(v interface{}, d TerraformResourceData, config *Config) (interface{}, error) {
v = v.(*schema.Set).List()
return v, nil
}
func expandComputeRegionBackendServiceBackend(v interface{}, d TerraformResourceData, config *Config) (interface{}, error) {
v = v.(*schema.Set).List()
l := v.([]interface{})
req := make([]interface{}, 0, len(l))
for _, raw := range l {
if raw == nil {
continue
}
original := raw.(map[string]interface{})
transformed := make(map[string]interface{})
transformedDescription, err := expandComputeRegionBackendServiceBackendDescription(original["description"], d, config)
if err != nil {
return nil, err
} else if val := reflect.ValueOf(transformedDescription); val.IsValid() && !isEmptyValue(val) {
transformed["description"] = transformedDescription
}
transformedGroup, err := expandComputeRegionBackendServiceBackendGroup(original["group"], d, config)
if err != nil {
return nil, err
} else if val := reflect.ValueOf(transformedGroup); val.IsValid() && !isEmptyValue(val) {
transformed["group"] = transformedGroup
}
req = append(req, transformed)
}
return req, nil
}
func expandComputeRegionBackendServiceBackendDescription(v interface{}, d TerraformResourceData, config *Config) (interface{}, error) {
return v, nil
}
func expandComputeRegionBackendServiceBackendGroup(v interface{}, d TerraformResourceData, config *Config) (interface{}, error) {
return v, nil
}
func expandComputeRegionBackendServiceDescription(v interface{}, d TerraformResourceData, config *Config) (interface{}, error) {
return v, nil
}
func expandComputeRegionBackendServiceFingerprint(v interface{}, d TerraformResourceData, config *Config) (interface{}, error) {
return v, nil
}
func expandComputeRegionBackendServiceProtocol(v interface{}, d TerraformResourceData, config *Config) (interface{}, error) {
return v, nil
}
func expandComputeRegionBackendServiceSessionAffinity(v interface{}, d TerraformResourceData, config *Config) (interface{}, error) {
return v, nil
}
func expandComputeRegionBackendServiceRegion(v interface{}, d TerraformResourceData, config *Config) (interface{}, error) {
f, err := parseGlobalFieldValue("regions", v.(string), "project", d, config, true)
if err != nil {
return nil, fmt.Errorf("Invalid value for region: %s", err)
}
return f.RelativeLink(), nil
}
func expandComputeRegionBackendServiceTimeoutSec(v interface{}, d TerraformResourceData, config *Config) (interface{}, error) {
return v, nil
}
func expandComputeRegionBackendServiceConnectionDraining(d TerraformResourceData, config *Config) (interface{}, error) {
transformed := make(map[string]interface{})
// Note that nesting flattened objects won't work because we don't handle them properly here.
transformedConnection_draining_timeout_sec, err := expandComputeRegionBackendServiceConnectionDrainingConnection_draining_timeout_sec(d.Get("connection_draining_timeout_sec"), d, config)
if err != nil {
return nil, err
} else { } else {
buf.WriteString(fmt.Sprintf("%s-", group)) transformed["drainingTimeoutSec"] = transformedConnection_draining_timeout_sec
} }
if v, ok := m["description"]; ok { return transformed, nil
buf.WriteString(fmt.Sprintf("%s-", v.(string)))
}
return hashcode.String(buf.String())
} }
func flattenRegionBackends(backends []*compute.Backend) []map[string]interface{} { func expandComputeRegionBackendServiceConnectionDrainingConnection_draining_timeout_sec(v interface{}, d TerraformResourceData, config *Config) (interface{}, error) {
result := make([]map[string]interface{}, 0, len(backends)) return v, nil
for _, b := range backends {
data := make(map[string]interface{})
data["description"] = b.Description
data["group"] = b.Group
result = append(result, data)
}
return result
} }
func expandBackends(configured []interface{}) ([]*computeBeta.Backend, error) { func expandComputeRegionBackendServiceLoadBalancingScheme(v interface{}, d TerraformResourceData, config *Config) (interface{}, error) {
backends := make([]*computeBeta.Backend, 0, len(configured)) return v, nil
for _, raw := range configured {
data := raw.(map[string]interface{})
g, ok := data["group"]
if !ok {
return nil, errors.New("google_compute_backend_service.backend.group must be set")
}
b := computeBeta.Backend{
Group: g.(string),
}
if v, ok := data["balancing_mode"]; ok {
b.BalancingMode = v.(string)
}
if v, ok := data["capacity_scaler"]; ok {
b.CapacityScaler = v.(float64)
b.ForceSendFields = append(b.ForceSendFields, "CapacityScaler")
}
if v, ok := data["description"]; ok {
b.Description = v.(string)
}
if v, ok := data["max_rate"]; ok {
b.MaxRate = int64(v.(int))
if b.MaxRate == 0 {
b.NullFields = append(b.NullFields, "MaxRate")
}
}
if v, ok := data["max_rate_per_instance"]; ok {
b.MaxRatePerInstance = v.(float64)
if b.MaxRatePerInstance == 0 {
b.NullFields = append(b.NullFields, "MaxRatePerInstance")
}
}
if v, ok := data["max_connections"]; ok {
b.MaxConnections = int64(v.(int))
if b.MaxConnections == 0 {
b.NullFields = append(b.NullFields, "MaxConnections")
}
}
if v, ok := data["max_connections_per_instance"]; ok {
b.MaxConnectionsPerInstance = int64(v.(int))
if b.MaxConnectionsPerInstance == 0 {
b.NullFields = append(b.NullFields, "MaxConnectionsPerInstance")
}
}
if v, ok := data["max_utilization"]; ok {
b.MaxUtilization = v.(float64)
b.ForceSendFields = append(b.ForceSendFields, "MaxUtilization")
}
backends = append(backends, &b)
}
return backends, nil
} }

View File

@ -0,0 +1,96 @@
// ----------------------------------------------------------------------------
//
// *** AUTO GENERATED CODE *** AUTO GENERATED CODE ***
//
// ----------------------------------------------------------------------------
//
// This file is automatically generated by Magic Modules and manual
// changes will be clobbered when the file is regenerated.
//
// Please read more about how to change this file in
// .github/CONTRIBUTING.md.
//
// ----------------------------------------------------------------------------
package google
import (
"fmt"
"strings"
"testing"
"github.com/hashicorp/terraform/helper/acctest"
"github.com/hashicorp/terraform/helper/resource"
"github.com/hashicorp/terraform/terraform"
)
func TestAccComputeRegionBackendService_regionBackendServiceBasicExample(t *testing.T) {
t.Parallel()
context := map[string]interface{}{
"random_suffix": acctest.RandString(10),
}
resource.Test(t, resource.TestCase{
PreCheck: func() { testAccPreCheck(t) },
Providers: testAccProviders,
CheckDestroy: testAccCheckComputeRegionBackendServiceDestroy,
Steps: []resource.TestStep{
{
Config: testAccComputeRegionBackendService_regionBackendServiceBasicExample(context),
},
{
ResourceName: "google_compute_region_backend_service.default",
ImportState: true,
ImportStateVerify: true,
},
},
})
}
func testAccComputeRegionBackendService_regionBackendServiceBasicExample(context map[string]interface{}) string {
return Nprintf(`
resource "google_compute_region_backend_service" "default" {
name = "region-backend-service-%{random_suffix}"
region = "us-central1"
health_checks = ["${google_compute_health_check.default.self_link}"]
connection_draining_timeout_sec = 10
session_affinity = "CLIENT_IP"
}
resource "google_compute_health_check" "default" {
name = "health-check-%{random_suffix}"
check_interval_sec = 1
timeout_sec = 1
tcp_health_check {
port = "80"
}
}
`, context)
}
func testAccCheckComputeRegionBackendServiceDestroy(s *terraform.State) error {
for name, rs := range s.RootModule().Resources {
if rs.Type != "google_compute_region_backend_service" {
continue
}
if strings.HasPrefix(name, "data.") {
continue
}
config := testAccProvider.Meta().(*Config)
url, err := replaceVarsForTest(rs, "https://www.googleapis.com/compute/v1/projects/{{project}}/regions/{{region}}/backendServices/{{name}}")
if err != nil {
return err
}
_, err = sendRequest(config, "GET", url, nil)
if err == nil {
return fmt.Errorf("ComputeRegionBackendService still exists at %s", url)
}
}
return nil
}

View File

@ -120,33 +120,6 @@ func TestAccComputeRegionBackendService_withBackendAndUpdate(t *testing.T) {
} }
} }
func TestAccComputeRegionBackendService_withConnectionDraining(t *testing.T) {
t.Parallel()
serviceName := fmt.Sprintf("tf-test-%s", acctest.RandString(10))
checkName := fmt.Sprintf("tf-test-%s", acctest.RandString(10))
var svc compute.BackendService
resource.Test(t, resource.TestCase{
PreCheck: func() { testAccPreCheck(t) },
Providers: testAccProviders,
CheckDestroy: testAccCheckComputeRegionBackendServiceDestroy,
Steps: []resource.TestStep{
{
Config: testAccComputeRegionBackendService_withConnectionDraining(serviceName, checkName, 10),
Check: resource.ComposeTestCheckFunc(
testAccCheckComputeRegionBackendServiceExists(
"google_compute_region_backend_service.foobar", &svc),
),
},
},
})
if svc.ConnectionDraining.DrainingTimeoutSec != 10 {
t.Errorf("Expected ConnectionDraining.DrainingTimeoutSec == 10, got %d", svc.ConnectionDraining.DrainingTimeoutSec)
}
}
func TestAccComputeRegionBackendService_withConnectionDrainingAndUpdate(t *testing.T) { func TestAccComputeRegionBackendService_withConnectionDrainingAndUpdate(t *testing.T) {
t.Parallel() t.Parallel()
@ -181,52 +154,6 @@ func TestAccComputeRegionBackendService_withConnectionDrainingAndUpdate(t *testi
} }
} }
func TestAccComputeRegionBackendService_withSessionAffinity(t *testing.T) {
t.Parallel()
serviceName := fmt.Sprintf("tf-test-%s", acctest.RandString(10))
checkName := fmt.Sprintf("tf-test-%s", acctest.RandString(10))
var svc compute.BackendService
resource.Test(t, resource.TestCase{
PreCheck: func() { testAccPreCheck(t) },
Providers: testAccProviders,
CheckDestroy: testAccCheckComputeRegionBackendServiceDestroy,
Steps: []resource.TestStep{
{
Config: testAccComputeRegionBackendService_withSessionAffinity(
serviceName, checkName),
Check: resource.ComposeTestCheckFunc(
testAccCheckComputeRegionBackendServiceExists(
"google_compute_region_backend_service.foobar", &svc),
),
},
},
})
if svc.SessionAffinity != "CLIENT_IP" {
t.Errorf("Expected Protocol to be CLIENT_IP, got %q", svc.SessionAffinity)
}
}
func testAccCheckComputeRegionBackendServiceDestroy(s *terraform.State) error {
config := testAccProvider.Meta().(*Config)
for _, rs := range s.RootModule().Resources {
if rs.Type != "google_compute_region_backend_service" {
continue
}
_, err := config.clientCompute.RegionBackendServices.Get(
config.Project, config.Region, rs.Primary.ID).Do()
if err == nil {
return fmt.Errorf("Backend service still exists")
}
}
return nil
}
func testAccCheckComputeRegionBackendServiceExists(n string, svc *compute.BackendService) resource.TestCheckFunc { func testAccCheckComputeRegionBackendServiceExists(n string, svc *compute.BackendService) resource.TestCheckFunc {
return func(s *terraform.State) error { return func(s *terraform.State) error {
rs, ok := s.RootModule().Resources[n] rs, ok := s.RootModule().Resources[n]
@ -361,28 +288,6 @@ resource "google_compute_health_check" "default" {
`, serviceName, timeout, igName, itName, checkName) `, serviceName, timeout, igName, itName, checkName)
} }
func testAccComputeRegionBackendService_withSessionAffinity(serviceName, checkName string) string {
return fmt.Sprintf(`
resource "google_compute_region_backend_service" "foobar" {
name = "%s"
health_checks = ["${google_compute_health_check.zero.self_link}"]
region = "us-central1"
session_affinity = "CLIENT_IP"
}
resource "google_compute_health_check" "zero" {
name = "%s"
check_interval_sec = 1
timeout_sec = 1
tcp_health_check {
port = "80"
}
}
`, serviceName, checkName)
}
func testAccComputeRegionBackendService_withConnectionDraining(serviceName, checkName string, drainingTimeout int64) string { func testAccComputeRegionBackendService_withConnectionDraining(serviceName, checkName string, drainingTimeout int64) string {
return fmt.Sprintf(` return fmt.Sprintf(`
resource "google_compute_region_backend_service" "foobar" { resource "google_compute_region_backend_service" "foobar" {

View File

@ -1,62 +1,59 @@
--- ---
# ----------------------------------------------------------------------------
#
# *** AUTO GENERATED CODE *** AUTO GENERATED CODE ***
#
# ----------------------------------------------------------------------------
#
# This file is automatically generated by Magic Modules and manual
# changes will be clobbered when the file is regenerated.
#
# Please read more about how to change this file in
# .github/CONTRIBUTING.md.
#
# ----------------------------------------------------------------------------
layout: "google" layout: "google"
page_title: "Google: google_compute_region_backend_service" page_title: "Google: google_compute_region_backend_service"
sidebar_current: "docs-google-compute-region-backend-service" sidebar_current: "docs-google-compute-region-backend-service"
description: |- description: |-
Creates a Region Backend Service resource for Google Compute Engine. A Region Backend Service defines a regionally-scoped group of virtual
machines that will serve traffic for load balancing.
--- ---
# google\_compute\_region\_backend\_service # google\_compute\_region\_backend\_service
A Region Backend Service defines a regionally-scoped group of virtual machines that will serve traffic for load balancing. A Region Backend Service defines a regionally-scoped group of virtual
For more information see [the official documentation](https://cloud.google.com/compute/docs/load-balancing/internal/) machines that will serve traffic for load balancing.
and [API](https://cloud.google.com/compute/docs/reference/latest/regionBackendServices).
~> **Note**: Region backend services can only be used when using internal load balancing. For external load balancing, use Region backend services can only be used when using internal load balancing.
[`google_compute_backend_service`](compute_backend_service.html) instead. For external load balancing, use a global backend service instead.
To get more information about RegionBackendService, see:
* [API documentation](https://cloud.google.com/compute/docs/reference/latest/regionBackendServices)
* How-to Guides
* [Internal TCP/UDP Load Balancing](https://cloud.google.com/compute/docs/load-balancing/internal/)
<div class = "oics-button" style="float: right; margin: 0 0 -15px">
<a href="https://console.cloud.google.com/cloudshell/open?cloudshell_git_repo=https%3A%2F%2Fgithub.com%2Fterraform-google-modules%2Fdocs-examples.git&cloudshell_working_dir=region_backend_service_basic&cloudshell_image=gcr.io%2Fgraphite-cloud-shell-images%2Fterraform%3Alatest&open_in_editor=main.tf&cloudshell_print=.%2Fmotd&cloudshell_tutorial=.%2Ftutorial.md" target="_blank">
<img alt="Open in Cloud Shell" src="//gstatic.com/cloudssh/images/open-btn.svg" style="max-height: 44px; margin: 32px auto; max-width: 100%;">
</a>
</div>
## Example Usage - Region Backend Service Basic
## Example Usage
```hcl ```hcl
resource "google_compute_region_backend_service" "foobar" { resource "google_compute_region_backend_service" "default" {
name = "blablah" name = "region-backend-service"
description = "Hello World 1234" region = "us-central1"
protocol = "TCP" health_checks = ["${google_compute_health_check.default.self_link}"]
timeout_sec = 10 connection_draining_timeout_sec = 10
session_affinity = "CLIENT_IP" session_affinity = "CLIENT_IP"
backend {
group = "${google_compute_region_instance_group_manager.foo.instance_group}"
}
health_checks = ["${google_compute_health_check.default.self_link}"]
}
resource "google_compute_region_instance_group_manager" "foo" {
name = "terraform-test"
instance_template = "${google_compute_instance_template.foobar.self_link}"
base_instance_name = "foobar"
region = "us-central1"
target_size = 1
}
resource "google_compute_instance_template" "foobar" {
name = "terraform-test"
machine_type = "n1-standard-1"
network_interface {
network = "default"
}
disk {
source_image = "debian-cloud/debian-9"
auto_delete = true
boot = true
}
} }
resource "google_compute_health_check" "default" { resource "google_compute_health_check" "default" {
name = "test" name = "health-check"
check_interval_sec = 1 check_interval_sec = 1
timeout_sec = 1 timeout_sec = 1
@ -70,51 +67,117 @@ resource "google_compute_health_check" "default" {
The following arguments are supported: The following arguments are supported:
* `name` - (Required) The name of the backend service.
* `health_checks` - (Required) Specifies a list of health checks * `name` -
for checking the health of the backend service. Currently at most (Required)
one health check can be specified, and a health check is required. Name of the resource. Provided by the client when the resource is
created. The name must be 1-63 characters long, and comply with
RFC1035. Specifically, the name must be 1-63 characters long and match
the regular expression `[a-z]([-a-z0-9]*[a-z0-9])?` which means the
first character must be a lowercase letter, and all following
characters must be a dash, lowercase letter, or digit, except the last
character, which cannot be a dash.
* `health_checks` -
(Required)
The list of HealthChecks for checking the health of the backend service.
Currently at most one health check can be specified, and a health check
is required.
- - - - - -
* `backend` - (Optional) The list of backends that serve this BackendService.
Structure is documented below.
* `description` - (Optional) The textual description for the backend service. * `backend` -
(Optional)
The list of backends that serve this RegionBackendService. Structure is documented below.
* `project` - (Optional) The ID of the project in which the resource belongs. If it * `description` -
is not provided, the provider project is used. (Optional)
An optional description of this resource.
* `protocol` - (Optional) The protocol for incoming requests. Defaults to * `protocol` -
`TCP`. (Optional)
The protocol this BackendService uses to communicate with backends.
The possible values are TCP and UDP, and the default is TCP.
* `session_affinity` - (Optional) How to distribute load. Options are `NONE` (no * `session_affinity` -
affinity), `CLIENT_IP`, `CLIENT_IP_PROTO`, or `CLIENT_IP_PORT_PROTO`. (Optional)
Defaults to `NONE`. Type of session affinity to use. The default is NONE.
Can be NONE, CLIENT_IP, CLIENT_IP_PROTO, or CLIENT_IP_PORT_PROTO.
When the protocol is UDP, this field is not used.
* `region` - (Optional) The Region in which the created address should reside. * `region` -
If it is not provided, the provider region is used. (Optional)
The Region in which the created backend service should reside.
If it is not provided, the provider region is used.
* `timeout_sec` - (Optional) The number of secs to wait for a backend to respond * `timeout_sec` -
to a request before considering the request failed. Defaults to `30`. (Optional)
How many seconds to wait for the backend before considering it a
failed request. Default is 30 seconds. Valid range is [1, 86400].
* `connection_draining_timeout_sec` -
(Optional)
Time for which instance will be drained (not accept new
connections, but still work to finish started).
* `load_balancing_scheme` -
(Optional)
This signifies what the ForwardingRule will be used for and can only
be INTERNAL for RegionBackendServices
* `project` - (Optional) The ID of the project in which the resource belongs.
If it is not provided, the provider project is used.
* `connection_draining_timeout_sec` - (Optional) Time for which instance will be drained
(not accept new connections, but still work to finish started ones). Defaults to `0`.
The `backend` block supports: The `backend` block supports:
* `group` - (Required) The name or URI of a Compute Engine instance group * `description` -
(`google_compute_region_instance_group_manager.xyz.instance_group`) that can (Optional)
receive traffic. Instance groups must contain at least one instance. An optional description of this resource.
Provide this property when you create the resource.
* `description` - (Optional) Textual description for the backend. * `group` -
(Optional)
The fully-qualified URL of an Instance Group. This defines the list
of instances that serve traffic. Member virtual machine
instances from each instance group must live in the same zone as
the instance group itself. No two backends in a backend service
are allowed to use same Instance Group resource.
Note that you must specify an Instance Group
resource using the fully-qualified URL, rather than a
partial URL.
The instance group must be within the same region as the BackendService.
## Attributes Reference ## Attributes Reference
In addition to the arguments listed above, the following computed attributes are In addition to the arguments listed above, the following computed attributes are exported:
exported:
* `fingerprint` - The fingerprint of the backend service.
* `fingerprint` -
Fingerprint of this resource. A hash of the contents stored in this
object. This field is used in optimistic locking.
* `self_link` - The URI of the created resource. * `self_link` - The URI of the created resource.
## Timeouts
This resource provides the following
[Timeouts](/docs/configuration/resources.html#timeouts) configuration options:
- `create` - Default is 4 minutes.
- `update` - Default is 4 minutes.
- `delete` - Default is 4 minutes.
## Import
RegionBackendService can be imported using any of these accepted formats:
```
$ terraform import google_compute_region_backend_service.default projects/{{project}}/regions/{{region}}/backendServices/{{name}}
$ terraform import google_compute_region_backend_service.default {{project}}/{{region}}/{{name}}
$ terraform import google_compute_region_backend_service.default {{name}}
```
-> If you're importing a resource with beta features, make sure to include `-provider=google-beta`
as an argument so that Terraform uses the correct provider to import your resource.