Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

support tags for rds instance resource #607

Merged
merged 1 commit into from
Oct 27, 2020
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
45 changes: 21 additions & 24 deletions docs/resources/rds_instance.md
Original file line number Diff line number Diff line change
Expand Up @@ -142,6 +142,10 @@ The following arguments are supported:
Specifies the security group which the RDS DB instance belongs to.
Changing this parameter will create a new resource.

* `vpc_id` -
(Required)
Specifies the VPC ID. Changing this parameter will create a new resource.

* `subnet_id` -
(Required)
Specifies the network id of a subnet. Changing this parameter will create a new resource.
Expand All @@ -150,10 +154,6 @@ The following arguments are supported:
(Required)
Specifies the volume information. Structure is documented below.

* `vpc_id` -
(Required)
Specifies the VPC ID. Changing this parameter will create a new resource.

* `backup_strategy` -
(Optional)
Specifies the advanced backup policy. Structure is documented below.
Expand All @@ -173,7 +173,10 @@ The following arguments are supported:

* `enterprise_project_id` -
(Optional)
The enterprise project id of the RDS. Changing this creates a new RDS.
The enterprise project id of the RDS instance. Changing this creates a new RDS instance.

* `tags` - (Optional) A mapping of tags to assign to the RDS instance.
Each tag is represented by one key-value pair.

The `db` block supports:

Expand Down Expand Up @@ -254,39 +257,33 @@ The `backup_strategy` block supports:

In addition to the arguments listed above, the following computed attributes are exported:

* `created` -
Indicates the creation time.
* `status` - Indicates the DB instance status.

* `nodes` -
Indicates the instance nodes information. Structure is documented below.
* `created` - Indicates the creation time.

* `private_ips` -
Indicates the private IP address list. It is a blank string until an
ECS is created.
* `nodes` - Indicates the instance nodes information. Structure is documented below.

* `public_ips` -
Indicates the public IP address list.
* `private_ips` - Indicates the private IP address list.
It is a blank string until an ECS is created.

* `public_ips` - Indicates the public IP address list.

* `db` - See Argument Reference above. The db block also contains:

* `user_name` - Indicates the default user name of database.

The `nodes` block contains:

* `availability_zone` -
Indicates the AZ.
* `availability_zone` - Indicates the AZ.

* `id` -
Indicates the node ID.
* `id` - Indicates the node ID.

* `name` -
Indicates the node name.
* `name` - Indicates the node name.

* `role` -
Indicates the node type. The value can be master or slave, indicating the primary node or standby node respectively.
* `role` - Indicates the node type. The value can be master or slave,
indicating the primary node or standby node respectively.

* `status` -
Indicates the node status.
* `status` - Indicates the node status.

## Timeouts

Expand Down
98 changes: 83 additions & 15 deletions huaweicloud/resource_huaweicloud_rds_instance_v3.go
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,7 @@ import (
"github.com/hashicorp/terraform-plugin-sdk/helper/resource"
"github.com/hashicorp/terraform-plugin-sdk/helper/schema"
"github.com/huaweicloud/golangsdk"
"github.com/huaweicloud/golangsdk/openstack/common/tags"
"github.com/huaweicloud/golangsdk/openstack/rds/v1/datastores"
"github.com/huaweicloud/golangsdk/openstack/rds/v1/flavors"
"github.com/huaweicloud/golangsdk/openstack/rds/v1/instances"
Expand Down Expand Up @@ -186,17 +187,14 @@ func resourceRdsInstanceV3() *schema.Resource {
ForceNew: true,
},

"tags": tagsSchema(),

"param_group_id": {
Type: schema.TypeString,
Optional: true,
ForceNew: true,
},

"created": {
Type: schema.TypeString,
Computed: true,
},

"nodes": {
Type: schema.TypeList,
Computed: true,
Expand Down Expand Up @@ -241,6 +239,15 @@ func resourceRdsInstanceV3() *schema.Resource {
Type: schema.TypeString,
},
},

"status": {
Type: schema.TypeString,
Computed: true,
},
"created": {
Type: schema.TypeString,
Computed: true,
},
},
}
}
Expand Down Expand Up @@ -297,7 +304,17 @@ func resourceRdsInstanceV3Create(d *schema.ResourceData, meta interface{}) error
if err != nil {
return fmt.Errorf("Error constructing id, err=%s", err)
}
d.SetId(id.(string))
instanceID := id.(string)
d.SetId(instanceID)

//set tags
tagRaw := d.Get("tags").(map[string]interface{})
if len(tagRaw) > 0 {
taglist := expandResourceTags(tagRaw)
if tagErr := tags.Create(client, "instances", instanceID, taglist).ExtractErr(); tagErr != nil {
return fmt.Errorf("Error setting tags of RDS instance %s: %s", instanceID, tagErr)
}
}

return resourceRdsInstanceV3Read(d, meta)
}
Expand Down Expand Up @@ -333,6 +350,10 @@ func resourceRdsInstanceV3Update(d *schema.ResourceData, meta interface{}) error
if err != nil {
return err
}
if v == nil {
return fmt.Errorf("RDS instance: %s was not found", d.Id())
}

res["list"] = v
opts := resourceRdsInstanceV3UserInputParams(d)
v, _ = opts["nodes"]
Expand Down Expand Up @@ -462,6 +483,13 @@ func resourceRdsInstanceV3Update(d *schema.ResourceData, meta interface{}) error
log.Printf("[DEBUG] Successfully updated instance %s volume: %+v", node_id, volume)
}

if d.HasChange("tags") {
tagErr := UpdateResourceTags(rdsClient, d, "instances", d.Id())
if tagErr != nil {
return fmt.Errorf("Error updating tags of RDS instance:%s, err:%s", d.Id(), tagErr)
}
}

return resourceRdsInstanceV3Read(d, meta)
}

Expand All @@ -478,8 +506,13 @@ func resourceRdsInstanceV3Read(d *schema.ResourceData, meta interface{}) error {
if err != nil {
return err
}
res["list"] = v
if v == nil {
log.Printf("[WARN] RDS instance: %s was not found", d.Id())
d.SetId("")
return nil
}

res["list"] = v
err = setRdsInstanceV3Properties(d, res)
if err != nil {
return err
Expand Down Expand Up @@ -519,14 +552,14 @@ func resourceRdsInstanceV3Delete(d *schema.ResourceData, meta interface{}) error
_, err = waitToFinish(
[]string{"Done"}, []string{"Pending"},
d.Timeout(schema.TimeoutCreate),
1*time.Second,
5*time.Second,
func() (interface{}, string, error) {
_, err := fetchRdsInstanceV3ByList(d, client)
v, err := fetchRdsInstanceV3ByList(d, client)
if err != nil {
if strings.Index(err.Error(), "Error finding the resource by list api") != -1 {
return true, "Done", nil
}
return nil, "", nil
return nil, "Failed", err
}
if v == nil {
return true, "Done", nil
}
return true, "Pending", nil
},
Expand Down Expand Up @@ -880,7 +913,7 @@ func asyncWaitRdsInstanceV3Create(d *schema.ResourceData, config *Config, result
return waitToFinish(
[]string{"Completed"},
[]string{"Running"},
timeout, 1*time.Second,
timeout, 5*time.Second,
func() (interface{}, string, error) {
r := golangsdk.Result{}
_, r.Err = client.Get(url, &r.Body, &golangsdk.RequestOpts{
Expand Down Expand Up @@ -932,7 +965,7 @@ func findRdsInstanceV3ByList(client *golangsdk.ServiceClient, link string, ident
}
}

return nil, fmt.Errorf("Error finding the resource by list api")
return nil, nil
}

func sendRdsInstanceV3ListRequest(client *golangsdk.ServiceClient, url string) (interface{}, error) {
Expand Down Expand Up @@ -981,6 +1014,14 @@ func setRdsInstanceV3Properties(d *schema.ResourceData, response map[string]inte
return fmt.Errorf("Error setting Instance:created, err: %s", err)
}

v, err = navigateValue(response, []string{"list", "status"}, nil)
if err != nil {
return fmt.Errorf("Error reading Instance:status, err: %s", err)
}
if err = d.Set("status", v); err != nil {
return fmt.Errorf("Error setting Instance:status, err: %s", err)
}

v, err = navigateValue(response, []string{"list", "enterprise_project_id"}, nil)
if err != nil {
return fmt.Errorf("Error reading Instance:enterprise_project_id, err: %s", err)
Expand Down Expand Up @@ -1081,6 +1122,14 @@ func setRdsInstanceV3Properties(d *schema.ResourceData, response map[string]inte
return fmt.Errorf("Error setting Instance:vpc_id, err: %s", err)
}

v, err = flattenRdsInstanceTags(response)
if err != nil {
return fmt.Errorf("Error reading Instance:tags, err: %s", err)
}
if err = d.Set("tags", v); err != nil {
return fmt.Errorf("Error setting Instance:tags, err: %s", err)
}

return nil
}

Expand Down Expand Up @@ -1270,3 +1319,22 @@ func flattenRdsInstanceV3Volume(d interface{}, arrayIndex map[string]int, curren

return result, nil
}

func flattenRdsInstanceTags(d interface{}) (map[string]interface{}, error) {
result := make(map[string]interface{})

tagsRaw, err := navigateValue(d, []string{"list", "tags"}, nil)
if err != nil {
return nil, fmt.Errorf("Error reading Instance tags, err: %s", err)
}

for _, item := range tagsRaw.([]interface{}) {
val := item.(map[string]interface{})
if key, ok := val["key"].(string); ok {
result[key] = val["value"]
}
}

log.Printf("[DEBUG] reading RDS Instance tags: %#v", result)
return result, nil
}
Loading