Remove deprecated resources for 1.0.0.

In advance of 1.0.0, let's take the opportunity to remove the fields on
resources that have been deprecated for a while.
This commit is contained in:
Paddy 2017-09-28 14:38:38 -07:00
parent 0b4158d1ea
commit f2f276ea0b
6 changed files with 153 additions and 277 deletions

View File

@ -88,10 +88,10 @@ func resourceComputeGlobalForwardingRule() *schema.Resource {
}, },
"region": &schema.Schema{ "region": &schema.Schema{
Type: schema.TypeString, Type: schema.TypeString,
Optional: true, Optional: true,
ForceNew: true, ForceNew: true,
Deprecated: "Please remove this attribute (it was never used)", Removed: "Please remove this attribute (it was never used)",
}, },
"self_link": &schema.Schema{ "self_link": &schema.Schema{

View File

@ -289,7 +289,7 @@ func resourceComputeInstance() *schema.Resource {
"network_interface": &schema.Schema{ "network_interface": &schema.Schema{
Type: schema.TypeList, Type: schema.TypeList,
Optional: true, Required: true,
ForceNew: true, ForceNew: true,
Elem: &schema.Resource{ Elem: &schema.Resource{
Schema: map[string]*schema.Schema{ Schema: map[string]*schema.Schema{
@ -371,10 +371,10 @@ func resourceComputeInstance() *schema.Resource {
}, },
"network": &schema.Schema{ "network": &schema.Schema{
Type: schema.TypeList, Type: schema.TypeList,
Optional: true, Optional: true,
ForceNew: true, ForceNew: true,
Deprecated: "Please use network_interface", Removed: "Please use network_interface",
Elem: &schema.Resource{ Elem: &schema.Resource{
Schema: map[string]*schema.Schema{ Schema: map[string]*schema.Schema{
"source": &schema.Schema{ "source": &schema.Schema{
@ -748,95 +748,51 @@ func resourceComputeInstanceCreate(d *schema.ResourceData, meta interface{}) err
disks = append(disks, &disk) disks = append(disks, &disk)
} }
networksCount := d.Get("network.#").(int) // Build up the list of networkInterfaces
networkInterfacesCount := d.Get("network_interface.#").(int) networkInterfaces := make([]*computeBeta.NetworkInterface, 0, networkInterfacesCount)
for i := 0; i < networkInterfacesCount; i++ {
prefix := fmt.Sprintf("network_interface.%d", i)
// Load up the name of this network_interface
networkName := d.Get(prefix + ".network").(string)
subnetworkName := d.Get(prefix + ".subnetwork").(string)
address := d.Get(prefix + ".address").(string)
var networkLink, subnetworkLink string
if networksCount > 0 && networkInterfacesCount > 0 { if networkName != "" && subnetworkName != "" {
return fmt.Errorf("Error: cannot define both networks and network_interfaces.") return fmt.Errorf("Cannot specify both network and subnetwork values.")
} } else if networkName != "" {
if networksCount == 0 && networkInterfacesCount == 0 { networkLink, err = getNetworkLink(d, config, prefix+".network")
return fmt.Errorf("Error: Must define at least one network_interface.")
}
var networkInterfaces []*computeBeta.NetworkInterface
if networksCount > 0 {
// TODO: Delete this block when removing network { }
// Build up the list of networkInterfaces
networkInterfaces = make([]*computeBeta.NetworkInterface, 0, networksCount)
for i := 0; i < networksCount; i++ {
prefix := fmt.Sprintf("network.%d", i)
// Load up the name of this network
networkName := d.Get(prefix + ".source").(string)
network, err := config.clientCompute.Networks.Get(
project, networkName).Do()
if err != nil { if err != nil {
return fmt.Errorf( return fmt.Errorf(
"Error loading network '%s': %s", "Error referencing network '%s': %s",
networkName, err) networkName, err)
} }
} else {
// Build the networkInterface subnetworkLink, err = getSubnetworkLink(d, config, prefix+".subnetwork", prefix+".subnetwork_project", "zone")
var iface computeBeta.NetworkInterface if err != nil {
iface.AccessConfigs = []*computeBeta.AccessConfig{ return err
&computeBeta.AccessConfig{
Type: "ONE_TO_ONE_NAT",
NatIP: d.Get(prefix + ".address").(string),
},
} }
iface.Network = network.SelfLink
networkInterfaces = append(networkInterfaces, &iface)
} }
}
if networkInterfacesCount > 0 { // Build the networkInterface
// Build up the list of networkInterfaces var iface computeBeta.NetworkInterface
networkInterfaces = make([]*computeBeta.NetworkInterface, 0, networkInterfacesCount) iface.Network = networkLink
for i := 0; i < networkInterfacesCount; i++ { iface.Subnetwork = subnetworkLink
prefix := fmt.Sprintf("network_interface.%d", i) iface.NetworkIP = address
// Load up the name of this network_interface iface.AliasIpRanges = expandAliasIpRanges(d.Get(prefix + ".alias_ip_range").([]interface{}))
networkName := d.Get(prefix + ".network").(string)
subnetworkName := d.Get(prefix + ".subnetwork").(string)
address := d.Get(prefix + ".address").(string)
var networkLink, subnetworkLink string
if networkName != "" && subnetworkName != "" { // Handle access_config structs
return fmt.Errorf("Cannot specify both network and subnetwork values.") accessConfigsCount := d.Get(prefix + ".access_config.#").(int)
} else if networkName != "" { iface.AccessConfigs = make([]*computeBeta.AccessConfig, accessConfigsCount)
networkLink, err = getNetworkLink(d, config, prefix+".network") for j := 0; j < accessConfigsCount; j++ {
if err != nil { acPrefix := fmt.Sprintf("%s.access_config.%d", prefix, j)
return fmt.Errorf( iface.AccessConfigs[j] = &computeBeta.AccessConfig{
"Error referencing network '%s': %s", Type: "ONE_TO_ONE_NAT",
networkName, err) NatIP: d.Get(acPrefix + ".nat_ip").(string),
}
} else {
subnetworkLink, err = getSubnetworkLink(d, config, prefix+".subnetwork", prefix+".subnetwork_project", "zone")
if err != nil {
return err
}
} }
// Build the networkInterface
var iface computeBeta.NetworkInterface
iface.Network = networkLink
iface.Subnetwork = subnetworkLink
iface.NetworkIP = address
iface.AliasIpRanges = expandAliasIpRanges(d.Get(prefix + ".alias_ip_range").([]interface{}))
// Handle access_config structs
accessConfigsCount := d.Get(prefix + ".access_config.#").(int)
iface.AccessConfigs = make([]*computeBeta.AccessConfig, accessConfigsCount)
for j := 0; j < accessConfigsCount; j++ {
acPrefix := fmt.Sprintf("%s.access_config.%d", prefix, j)
iface.AccessConfigs[j] = &computeBeta.AccessConfig{
Type: "ONE_TO_ONE_NAT",
NatIP: d.Get(acPrefix + ".nat_ip").(string),
}
}
networkInterfaces = append(networkInterfaces, &iface)
} }
networkInterfaces = append(networkInterfaces, &iface)
} }
serviceAccountsCount := d.Get("service_account.#").(int) serviceAccountsCount := d.Get("service_account.#").(int)
@ -992,84 +948,46 @@ func resourceComputeInstanceRead(d *schema.ResourceData, meta interface{}) error
} }
d.Set("service_account", serviceAccounts) d.Set("service_account", serviceAccounts)
networksCount := d.Get("network.#").(int)
networkInterfacesCount := d.Get("network_interface.#").(int)
if networksCount > 0 && networkInterfacesCount > 0 {
return fmt.Errorf("Error: cannot define both networks and network_interfaces.")
}
if networksCount == 0 && networkInterfacesCount == 0 {
return fmt.Errorf("Error: Must define at least one network_interface.")
}
// Set the networks // Set the networks
// Use the first external IP found for the default connection info. // Use the first external IP found for the default connection info.
externalIP := "" externalIP := ""
internalIP := "" internalIP := ""
networks := make([]map[string]interface{}, 0, 1)
if networksCount > 0 {
// TODO: Remove this when realizing deprecation of .network
for i, iface := range instance.NetworkInterfaces {
var natIP string
for _, config := range iface.AccessConfigs {
if config.Type == "ONE_TO_ONE_NAT" {
natIP = config.NatIP
break
}
}
if externalIP == "" && natIP != "" {
externalIP = natIP
}
network := make(map[string]interface{})
network["name"] = iface.Name
network["external_address"] = natIP
network["internal_address"] = iface.NetworkIP
network["source"] = d.Get(fmt.Sprintf("network.%d.source", i))
networks = append(networks, network)
}
}
d.Set("network", networks)
networkInterfaces := make([]map[string]interface{}, 0, 1) networkInterfaces := make([]map[string]interface{}, 0, 1)
if networkInterfacesCount > 0 { for i, iface := range instance.NetworkInterfaces {
for i, iface := range instance.NetworkInterfaces { // The first non-empty ip is left in natIP
// The first non-empty ip is left in natIP var natIP string
var natIP string accessConfigs := make(
accessConfigs := make( []map[string]interface{}, 0, len(iface.AccessConfigs))
[]map[string]interface{}, 0, len(iface.AccessConfigs)) for j, config := range iface.AccessConfigs {
for j, config := range iface.AccessConfigs { accessConfigs = append(accessConfigs, map[string]interface{}{
accessConfigs = append(accessConfigs, map[string]interface{}{ "nat_ip": d.Get(fmt.Sprintf("network_interface.%d.access_config.%d.nat_ip", i, j)),
"nat_ip": d.Get(fmt.Sprintf("network_interface.%d.access_config.%d.nat_ip", i, j)), "assigned_nat_ip": config.NatIP,
"assigned_nat_ip": config.NatIP,
})
if natIP == "" {
natIP = config.NatIP
}
}
if externalIP == "" {
externalIP = natIP
}
if internalIP == "" {
internalIP = iface.NetworkIP
}
networkInterfaces = append(networkInterfaces, map[string]interface{}{
"name": iface.Name,
"address": iface.NetworkIP,
"network": iface.Network,
"subnetwork": iface.Subnetwork,
"subnetwork_project": getProjectFromSubnetworkLink(iface.Subnetwork),
"access_config": accessConfigs,
"alias_ip_range": flattenAliasIpRange(iface.AliasIpRanges),
}) })
if natIP == "" {
natIP = config.NatIP
}
} }
if externalIP == "" {
externalIP = natIP
}
if internalIP == "" {
internalIP = iface.NetworkIP
}
networkInterfaces = append(networkInterfaces, map[string]interface{}{
"name": iface.Name,
"address": iface.NetworkIP,
"network": iface.Network,
"subnetwork": iface.Subnetwork,
"subnetwork_project": getProjectFromSubnetworkLink(iface.Subnetwork),
"access_config": accessConfigs,
"alias_ip_range": flattenAliasIpRange(iface.AliasIpRanges),
})
} }
d.Set("network_interface", networkInterfaces)
// Fall back on internal ip if there is no external ip. This makes sense in the situation where // Fall back on internal ip if there is no external ip. This makes sense in the situation where
// terraform is being used on a cloud instance and can therefore access the instances it creates // terraform is being used on a cloud instance and can therefore access the instances it creates
@ -1315,61 +1233,59 @@ func resourceComputeInstanceUpdate(d *schema.ResourceData, meta interface{}) err
} }
networkInterfacesCount := d.Get("network_interface.#").(int) networkInterfacesCount := d.Get("network_interface.#").(int)
if networkInterfacesCount > 0 { // Sanity check
// Sanity check if networkInterfacesCount != len(instance.NetworkInterfaces) {
if networkInterfacesCount != len(instance.NetworkInterfaces) { return fmt.Errorf("Instance had unexpected number of network interfaces: %d", len(instance.NetworkInterfaces))
return fmt.Errorf("Instance had unexpected number of network interfaces: %d", len(instance.NetworkInterfaces)) }
} for i := 0; i < networkInterfacesCount; i++ {
for i := 0; i < networkInterfacesCount; i++ { prefix := fmt.Sprintf("network_interface.%d", i)
prefix := fmt.Sprintf("network_interface.%d", i) instNetworkInterface := instance.NetworkInterfaces[i]
instNetworkInterface := instance.NetworkInterfaces[i] networkName := d.Get(prefix + ".name").(string)
networkName := d.Get(prefix + ".name").(string)
// TODO: This sanity check is broken by #929, disabled for now (by forcing the equality) // TODO: This sanity check is broken by #929, disabled for now (by forcing the equality)
networkName = instNetworkInterface.Name networkName = instNetworkInterface.Name
// Sanity check // Sanity check
if networkName != instNetworkInterface.Name { if networkName != instNetworkInterface.Name {
return fmt.Errorf("Instance networkInterface had unexpected name: %s", instNetworkInterface.Name) return fmt.Errorf("Instance networkInterface had unexpected name: %s", instNetworkInterface.Name)
}
if d.HasChange(prefix + ".access_config") {
// TODO: This code deletes then recreates accessConfigs. This is bad because it may
// leave the machine inaccessible from either ip if the creation part fails (network
// timeout etc). However right now there is a GCE limit of 1 accessConfig so it is
// the only way to do it. In future this should be revised to only change what is
// necessary, and also add before removing.
// Delete any accessConfig that currently exists in instNetworkInterface
for _, ac := range instNetworkInterface.AccessConfigs {
op, err := config.clientCompute.Instances.DeleteAccessConfig(
project, zone, d.Id(), ac.Name, networkName).Do()
if err != nil {
return fmt.Errorf("Error deleting old access_config: %s", err)
}
opErr := computeOperationWait(config, op, project, "old access_config to delete")
if opErr != nil {
return opErr
}
} }
if d.HasChange(prefix + ".access_config") { // Create new ones
accessConfigsCount := d.Get(prefix + ".access_config.#").(int)
// TODO: This code deletes then recreates accessConfigs. This is bad because it may for j := 0; j < accessConfigsCount; j++ {
// leave the machine inaccessible from either ip if the creation part fails (network acPrefix := fmt.Sprintf("%s.access_config.%d", prefix, j)
// timeout etc). However right now there is a GCE limit of 1 accessConfig so it is ac := &compute.AccessConfig{
// the only way to do it. In future this should be revised to only change what is Type: "ONE_TO_ONE_NAT",
// necessary, and also add before removing. NatIP: d.Get(acPrefix + ".nat_ip").(string),
// Delete any accessConfig that currently exists in instNetworkInterface
for _, ac := range instNetworkInterface.AccessConfigs {
op, err := config.clientCompute.Instances.DeleteAccessConfig(
project, zone, d.Id(), ac.Name, networkName).Do()
if err != nil {
return fmt.Errorf("Error deleting old access_config: %s", err)
}
opErr := computeOperationWait(config, op, project, "old access_config to delete")
if opErr != nil {
return opErr
}
} }
op, err := config.clientCompute.Instances.AddAccessConfig(
// Create new ones project, zone, d.Id(), networkName, ac).Do()
accessConfigsCount := d.Get(prefix + ".access_config.#").(int) if err != nil {
for j := 0; j < accessConfigsCount; j++ { return fmt.Errorf("Error adding new access_config: %s", err)
acPrefix := fmt.Sprintf("%s.access_config.%d", prefix, j) }
ac := &compute.AccessConfig{ opErr := computeOperationWait(config, op, project, "new access_config to add")
Type: "ONE_TO_ONE_NAT", if opErr != nil {
NatIP: d.Get(acPrefix + ".nat_ip").(string), return opErr
}
op, err := config.clientCompute.Instances.AddAccessConfig(
project, zone, d.Id(), networkName, ac).Do()
if err != nil {
return fmt.Errorf("Error adding new access_config: %s", err)
}
opErr := computeOperationWait(config, op, project, "new access_config to add")
if opErr != nil {
return opErr
}
} }
} }
} }

View File

@ -25,14 +25,10 @@ func resourceComputeNetwork() *schema.Resource {
}, },
"auto_create_subnetworks": &schema.Schema{ "auto_create_subnetworks": &schema.Schema{
Type: schema.TypeBool, Type: schema.TypeBool,
Optional: true, Optional: true,
ForceNew: true, ForceNew: true,
/* Ideally this would default to true as per the API, but that would cause Default: true,
existing Terraform configs which have not been updated to report this as
a change. Perhaps we can bump this for a minor release bump rather than
a point release.
Default: false, */
ConflictsWith: []string{"ipv4_range"}, ConflictsWith: []string{"ipv4_range"},
}, },
@ -48,10 +44,10 @@ func resourceComputeNetwork() *schema.Resource {
}, },
"ipv4_range": &schema.Schema{ "ipv4_range": &schema.Schema{
Type: schema.TypeString, Type: schema.TypeString,
Optional: true, Optional: true,
ForceNew: true, ForceNew: true,
Deprecated: "Please use google_compute_subnetwork resources instead.", Removed: "Please use google_compute_subnetwork resources instead.",
}, },
"project": &schema.Schema{ "project": &schema.Schema{
@ -76,32 +72,15 @@ func resourceComputeNetworkCreate(d *schema.ResourceData, meta interface{}) erro
return err return err
} }
//
// Possible modes:
// - 1 Legacy mode - Create a network in the legacy mode. ipv4_range is set. auto_create_subnetworks must not be
// set (enforced by ConflictsWith schema attribute)
// - 2 Distributed Mode - Create a new generation network that supports subnetworks:
// - 2.a - Auto subnet mode - auto_create_subnetworks = true, Google will generate 1 subnetwork per region
// - 2.b - Custom subnet mode - auto_create_subnetworks = false & ipv4_range not set,
//
autoCreateSubnetworks := d.Get("auto_create_subnetworks").(bool)
// Build the network parameter // Build the network parameter
network := &compute.Network{ network := &compute.Network{
Name: d.Get("name").(string), Name: d.Get("name").(string),
AutoCreateSubnetworks: autoCreateSubnetworks, AutoCreateSubnetworks: d.Get("auto_create_subnetworks").(bool),
Description: d.Get("description").(string), Description: d.Get("description").(string),
} }
if v, ok := d.GetOk("ipv4_range"); ok { // make sure AutoCreateSubnetworks field is included in request
log.Printf("[DEBUG] Setting IPv4Range (%#v) for legacy network mode", v.(string)) network.ForceSendFields = []string{"AutoCreateSubnetworks"}
network.IPv4Range = v.(string)
} else {
// custom subnet mode, so make sure AutoCreateSubnetworks field is included in request otherwise
// google will create a network in legacy mode.
network.ForceSendFields = []string{"AutoCreateSubnetworks"}
}
log.Printf("[DEBUG] Network insert request: %#v", network) log.Printf("[DEBUG] Network insert request: %#v", network)
op, err := config.clientCompute.Networks.Insert( op, err := config.clientCompute.Networks.Insert(
project, network).Do() project, network).Do()
@ -136,7 +115,6 @@ func resourceComputeNetworkRead(d *schema.ResourceData, meta interface{}) error
d.Set("gateway_ipv4", network.GatewayIPv4) d.Set("gateway_ipv4", network.GatewayIPv4)
d.Set("self_link", network.SelfLink) d.Set("self_link", network.SelfLink)
d.Set("ipv4_range", network.IPv4Range)
d.Set("name", network.Name) d.Set("name", network.Name)
d.Set("auto_create_subnetworks", network.AutoCreateSubnetworks) d.Set("auto_create_subnetworks", network.AutoCreateSubnetworks)

View File

@ -244,11 +244,11 @@ func resourceContainerCluster() *schema.Resource {
Elem: &schema.Resource{ Elem: &schema.Resource{
Schema: map[string]*schema.Schema{ Schema: map[string]*schema.Schema{
"initial_node_count": { "initial_node_count": {
Type: schema.TypeInt, Type: schema.TypeInt,
Optional: true, Optional: true,
ForceNew: true, ForceNew: true,
Computed: true, Computed: true,
Deprecated: "Use node_count instead", Removed: "Use node_count instead",
}, },
"node_count": { "node_count": {
@ -391,16 +391,7 @@ func resourceContainerClusterCreate(d *schema.ResourceData, meta interface{}) er
for i := 0; i < nodePoolsCount; i++ { for i := 0; i < nodePoolsCount; i++ {
prefix := fmt.Sprintf("node_pool.%d", i) prefix := fmt.Sprintf("node_pool.%d", i)
nodeCount := 0 nodeCount := d.GetOk(prefix + ".node_count")
if initialNodeCount, ok := d.GetOk(prefix + ".initial_node_count"); ok {
nodeCount = initialNodeCount.(int)
}
if nc, ok := d.GetOk(prefix + ".node_count"); ok {
if nodeCount != 0 {
return fmt.Errorf("Cannot set both initial_node_count and node_count on node pool %d", i)
}
nodeCount = nc.(int)
}
if nodeCount == 0 { if nodeCount == 0 {
return fmt.Errorf("Node pool %d cannot be set with 0 node count", i) return fmt.Errorf("Node pool %d cannot be set with 0 node count", i)
} }
@ -757,11 +748,10 @@ func flattenClusterNodePools(d *schema.ResourceData, config *Config, c []*contai
size += int(igm.TargetSize) size += int(igm.TargetSize)
} }
nodePool := map[string]interface{}{ nodePool := map[string]interface{}{
"name": np.Name, "name": np.Name,
"name_prefix": d.Get(fmt.Sprintf("node_pool.%d.name_prefix", i)), "name_prefix": d.Get(fmt.Sprintf("node_pool.%d.name_prefix", i)),
"initial_node_count": np.InitialNodeCount, "node_count": size / len(np.InstanceGroupUrls),
"node_count": size / len(np.InstanceGroupUrls), "node_config": flattenNodeConfig(np.Config),
"node_config": flattenNodeConfig(np.Config),
} }
nodePools = append(nodePools, nodePool) nodePools = append(nodePools, nodePool)
} }

View File

@ -50,10 +50,10 @@ func resourceStorageBucket() *schema.Resource {
}, },
"predefined_acl": &schema.Schema{ "predefined_acl": &schema.Schema{
Type: schema.TypeString, Type: schema.TypeString,
Deprecated: "Please use resource \"storage_bucket_acl.predefined_acl\" instead.", Removed: "Please use resource \"storage_bucket_acl.predefined_acl\" instead.",
Optional: true, Optional: true,
ForceNew: true, ForceNew: true,
}, },
"project": &schema.Schema{ "project": &schema.Schema{
@ -264,12 +264,7 @@ func resourceStorageBucketCreate(d *schema.ResourceData, meta interface{}) error
var res *storage.Bucket var res *storage.Bucket
err = resource.Retry(1*time.Minute, func() *resource.RetryError { err = resource.Retry(1*time.Minute, func() *resource.RetryError {
call := config.clientStorage.Buckets.Insert(project, sb) res, err := config.clientStorage.Buckets.Insert(project, sb).Do()
if v, ok := d.GetOk("predefined_acl"); ok {
call = call.PredefinedAcl(v.(string))
}
res, err = call.Do()
if err == nil { if err == nil {
return nil return nil
} }

View File

@ -81,10 +81,10 @@ func resourceStorageBucketObject() *schema.Resource {
}, },
"predefined_acl": &schema.Schema{ "predefined_acl": &schema.Schema{
Type: schema.TypeString, Type: schema.TypeString,
Deprecated: "Please use resource \"storage_object_acl.predefined_acl\" instead.", Removed: "Please use resource \"storage_object_acl.predefined_acl\" instead.",
Optional: true, Optional: true,
ForceNew: true, ForceNew: true,
}, },
"source": &schema.Schema{ "source": &schema.Schema{
@ -157,9 +157,6 @@ func resourceStorageBucketObjectCreate(d *schema.ResourceData, meta interface{})
insertCall := objectsService.Insert(bucket, object) insertCall := objectsService.Insert(bucket, object)
insertCall.Name(name) insertCall.Name(name)
insertCall.Media(media) insertCall.Media(media)
if v, ok := d.GetOk("predefined_acl"); ok {
insertCall.PredefinedAcl(v.(string))
}
_, err := insertCall.Do() _, err := insertCall.Do()