hashicorp / hashicorp/terraform-plugin-sdk

Custom DiffSuppress method can cause .Get method to return empty results

Open
#120 0 comments 0 reactions 0 assignees View on GitHub
bug terraform-plugin-framework
Dominant language
Go
Stars
485
Forks
244
Avg merge
19h 57m
Merged PRs (30d)
4

Description

It looks like there is some unexpected behavior with nested properties when using a custom DiffSuppress method. When creating a new resource there is some custom logic to determine whether a property has changed or not inside of nested objects. However when an address part way down the path returns True from the diffSuppress and then a call to `.Get` is made to that address it will return an empty state (in this case a empty slice of interfaces).

I've tried to strip down my config / code to the most relevant details below:

### Terraform Version
The terraform core is vendored at:
```
v github.com/hashicorp/terraform/helper/config v0.11.2 v0.11.2
```
I fetched the latest and was still able to reproduce the issue.

### Terraform Configuration Files

example resource:
```hcl
resource "google_compute_disk" "default" {
name = "test-disk"
image = "debian-9"

disk_encryption_key {
raw_key = "some key"
}

source_image_encryption_key {
raw_key = "some other key"
}
}
```

### Example code
I added the same diff suppress method to both the `disk_encryption_key` and the `source_image_encryption_key` which share the same structure/properties, ([details can be seen here](https://www.terraform.io/docs/providers/google/r/compute_disk.html#raw_key-2)) but made it so that 1 of the two would be suppressed:

```
func fakeDiffSuppress(k, old, new string, d *schema.ResourceData) bool {
if k == "disk_encryption_key.#" {
log.Println("supressing top level disk_encryption_key diff")
return true
}
return false
}

func resourceComputeDiskCreate(d *schema.ResourceData, meta interface{}) error {
config := meta.(*Config)
log.Println("disk_encryption_key is ", d.Get("disk_encryption_key"))
log.Println("nested disk_encryption_key is ", d.Get("disk_encryption_key.0"))

log.Println("source_image_encryption_key is ", d.Get("source_image_encryption_key"))
log.Println("nested source_image_encryption_key is ", d.Get("source_image_encryption_key.0"))

```

### Debug Output
...
2018-10-08T17:15:11.619-0700 [DEBUG] plugin.terraform-provider-google: 2018/10/08 17:15:11 supressing top level disk_encryption_key diff
2018-10-08T17:15:11.620-0700 [DEBUG] plugin.terraform-provider-google: 2018/10/08 17:15:11 supressing top level disk_encryption_key diff
google_compute_disk.default: Creating...
2018/10/08 17:15:11 [DEBUG] apply: google_compute_disk.default: executing Apply
2018-10-08T17:15:11.622-0700 [DEBUG] plugin.terraform-provider-google: 2018/10/08 17:15:11 disk_encryption_key is []
2018-10-08T17:15:11.622-0700 [DEBUG] plugin.terraform-provider-google: 2018/10/08 17:15:11 nested disk_encryption_key is map[kms_key_name: raw_key:some key sha256:]
2018-10-08T17:15:11.622-0700 [DEBUG] plugin.terraform-provider-google: 2018/10/08 17:15:11 source_image_encryption_key is [map[kms_key_name: raw_key:some other key sha256:]]
2018-10-08T17:15:11.622-0700 [DEBUG] plugin.terraform-provider-google: 2018/10/08 17:15:11 nested source_image_encryption_key is map[kms_key_name: raw_key:some other key sha256:]

### Expected Behavior
I would expect that regardless of the diff suppress behavior when trying to retrieve a property on a resource from config it would return that property if set.

### Actual Behavior
As see in the debug output, when trying to retrieve the property with `d.Get("disk_encryption_key")` an empty slice is returned. Trying to get details of properties nested even deeper is still possible though.

Contributor guide

Open the contributing guide

Research direction

Start with fakeDiffSuppress and resourceComputeDiskCreate, reproducing the nested disk_encryption_key and source_image_encryption_key d.Get calls shown in the report. Trace how DiffSuppress affects nested values and verify that d.Get("disk_encryption_key") preserves configured data while deeper lookups continue to work.

Written by the indexing model from the issue text.

Assessment

Tech stack
go, terraform
Domain
tooling
Issue type
Bug
Difficulty
4/5
Estimated time
3-5 days
Activity status
Stale
Clarity
Mostly clear
Newbie friendliness
45/100

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.