hashicorp / hashicorp/terraform-plugin-sdk

ResourceData.Set() doesn't set empty List/Set of String when Create/Update resource

Open
#766 1 comment 0 reactions 0 assignees View on GitHub
bug
Dominant language
Go
Stars
485
Forks
244
Avg merge
19h 57m
Merged PRs (30d)
4

Description

### SDK version
```
github.com/hashicorp/terraform-plugin-sdk/v2 v2.6.1
```

### Relevant provider source code

#### provider.go
```go
package example

import (
"github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema"
)

func Provider() *schema.Provider {
return &schema.Provider{
Schema: map[string]*schema.Schema{},
ResourcesMap: map[string]*schema.Resource{
"example_list": resourceList(),
},
}
}

```

#### resource_list.go

```go
package example

import (
"context"
"log"

"github.com/hashicorp/terraform-plugin-sdk/v2/diag"
"github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema"
)

func resourceList() *schema.Resource {
return &schema.Resource{
CreateContext: resourceListCreate,
ReadContext: resourceListRead,
UpdateContext: resourceListUpdate,
DeleteContext: resourceListDelete,
Schema: map[string]*schema.Schema{
"name": {
Type: schema.TypeString,
Required: true,
},
"list": {
Type: schema.TypeList,
Optional: true,
Elem: &schema.Schema{Type: schema.TypeString},
},
"set": {
Type: schema.TypeSet,
Optional: true,
Elem: &schema.Schema{Type: schema.TypeString},
},
"list2": {
Type: schema.TypeList,
Optional: true,
Elem: &schema.Schema{Type: schema.TypeString},
},
"set2": {
Type: schema.TypeSet,
Optional: true,
Elem: &schema.Schema{Type: schema.TypeString},
},
},
}
}

func resourceListCreate(ctx context.Context, d *schema.ResourceData, m interface{}) diag.Diagnostics {
log.Printf("Create")
d.SetId(d.Get("name").(string))

return resourceListRead(ctx, d, m)
}

func resourceListRead(ctx context.Context, d *schema.ResourceData, m interface{}) diag.Diagnostics {
log.Printf("Read")
v := make([]string, 0)
if err := d.Set("list", v); err != nil {
panic(err)
}
if err := d.Set("set", v); err != nil {
panic(err)
}

return nil
}

func resourceListUpdate(ctx context.Context, d *schema.ResourceData, m interface{}) diag.Diagnostics {
log.Printf("Update")
v := make([]string, 0)
if err := d.Set("list2", v); err != nil {
panic(err)
}
if err := d.Set("set2", v); err != nil {
panic(err)
}

return resourceListRead(ctx, d, m)
}

func resourceListDelete(ctx context.Context, d *schema.ResourceData, m interface{}) diag.Diagnostics {
log.Printf("Delete")

return nil
}

```

### Terraform Configuration Files
```hcl
terraform {
required_providers {
example = {
source = "sdk/example"
}
}
}

resource "example_list" "list" {
name = "test"
}
```

### Debug Output
First apply: https://gist.github.com/jeremmfr/8fdf0aef9a9dba35aa7c2a429013a466
Second apply: https://gist.github.com/jeremmfr/ce7fc52349967f60dbb11845b5839e7a

Especially in second apply :
```hcl
Terraform detected the following changes made outside of Terraform since the last "terraform apply":

# example_list.list has been changed
~ resource "example_list" "list" {
id = "test2"
+ list = []
name = "test2"
+ set = []
}

```

### Expected Behavior
`list` and `set` arguments set in state to an empty list on first apply (create).

### Actual Behavior
`list` and `set` arguments set in state to an empty list only when refresh resource.
With new Terraform version (0.15.4), the note `Note: Objects have changed outside of Terraform` appears for the wrong reason.

### Steps to Reproduce
1. `terraform init`
2. `terraform apply -auto-approve`
3. `terraform apply -auto-approve`

### Others errors
If I update `name` argument, `list2` and `set2` not set to an empty list in state when `apply` (update)

Contributor guide

Open the contributing guide

Research direction

Start with the example provider.go and resource_list.go, reproduce the first and second applies, and compare ResourceData.Set behavior during Create, Update, and Read. Trace the SDK handling of empty TypeList and TypeSet values. Done means empty list and set values persist after create and update without an external-change diff, with regression coverage for both paths.

Written by the indexing model from the issue text.

Assessment

Tech stack
go, terraform
Domain
devtools
Issue type
Bug
Difficulty
3/5
Estimated time
1-2 days
Activity status
Stale
Clarity
Mostly clear
Newbie friendliness
42/100

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.