Skip to content

Commit

Permalink
tfsdk: Document and clarify GetAttribute and SetAttribute further (#534)
Browse files Browse the repository at this point in the history
Reference: #66
Reference: #186

Documenting existing intentions and behaviors with `tfsdk.Config`, `tfsdk.Plan`, and `tfsdk.State` type `GetAttribute()` and `SetAttribute()` methods.
  • Loading branch information
bflad committed Nov 10, 2022
1 parent f427696 commit 0eb939e
Show file tree
Hide file tree
Showing 5 changed files with 35 additions and 10 deletions.
9 changes: 7 additions & 2 deletions tfsdk/config.go
Expand Up @@ -20,8 +20,13 @@ func (c Config) Get(ctx context.Context, target interface{}) diag.Diagnostics {
return c.data().Get(ctx, target)
}

// GetAttribute retrieves the attribute found at `path` and populates the
// `target` with the value.
// GetAttribute retrieves the attribute or block found at `path` and populates
// the `target` with the value. This method is intended for top level schema
// attributes or blocks. Use `types` package methods or custom types to step
// into collections.
//
// Attributes or elements under null or unknown collections return null
// values, however this behavior is not protected by compatibility promises.
func (c Config) GetAttribute(ctx context.Context, path path.Path, target interface{}) diag.Diagnostics {
return c.data().GetAtPath(ctx, path, target)
}
Expand Down
13 changes: 11 additions & 2 deletions tfsdk/plan.go
Expand Up @@ -20,8 +20,13 @@ func (p Plan) Get(ctx context.Context, target interface{}) diag.Diagnostics {
return p.data().Get(ctx, target)
}

// GetAttribute retrieves the attribute found at `path` and populates the
// `target` with the value.
// GetAttribute retrieves the attribute or block found at `path` and populates
// the `target` with the value. This method is intended for top level schema
// attributes or blocks. Use `types` package methods or custom types to step
// into collections.
//
// Attributes or elements under null or unknown collections return null
// values, however this behavior is not protected by compatibility promises.
func (p Plan) GetAttribute(ctx context.Context, path path.Path, target interface{}) diag.Diagnostics {
return p.data().GetAtPath(ctx, path, target)
}
Expand Down Expand Up @@ -58,6 +63,10 @@ func (p *Plan) Set(ctx context.Context, val interface{}) diag.Diagnostics {
// path does not have a value, it will be added, including any parent attribute
// paths as necessary.
//
// The value must not be an untyped nil. Use a typed nil or types package null
// value function instead. For example with a types.StringType attribute,
// use (*string)(nil) or types.StringNull().
//
// Lists can only have the next element added according to the current length.
func (p *Plan) SetAttribute(ctx context.Context, path path.Path, val interface{}) diag.Diagnostics {
data := p.data()
Expand Down
13 changes: 11 additions & 2 deletions tfsdk/state.go
Expand Up @@ -21,8 +21,13 @@ func (s State) Get(ctx context.Context, target interface{}) diag.Diagnostics {
return s.data().Get(ctx, target)
}

// GetAttribute retrieves the attribute found at `path` and populates the
// `target` with the value.
// GetAttribute retrieves the attribute or block found at `path` and populates
// the `target` with the value. This method is intended for top level schema
// attributes or blocks. Use `types` package methods or custom types to step
// into collections.
//
// Attributes or elements under null or unknown collections return null
// values, however this behavior is not protected by compatibility promises.
func (s State) GetAttribute(ctx context.Context, path path.Path, target interface{}) diag.Diagnostics {
return s.data().GetAtPath(ctx, path, target)
}
Expand Down Expand Up @@ -69,6 +74,10 @@ func (s *State) Set(ctx context.Context, val interface{}) diag.Diagnostics {
// path does not have a value, it will be added, including any parent attribute
// paths as necessary.
//
// The value must not be an untyped nil. Use a typed nil or types package null
// value function instead. For example with a types.StringType attribute,
// use (*string)(nil) or types.StringNull().
//
// Lists can only have the next element added according to the current length.
func (s *State) SetAttribute(ctx context.Context, path path.Path, val interface{}) diag.Diagnostics {
data := s.data()
Expand Down
4 changes: 2 additions & 2 deletions website/docs/plugin/framework/accessing-values.mdx
Expand Up @@ -67,9 +67,9 @@ explanation on how objects can be converted into Go types.

To descend into deeper nested data structures, the `types.List`, `types.Map`, and `types.Set` types each have an `ElementsAs()` method. The `types.Object` type has an `As()` method.

## Get a Single Attribute's Value
## Get a Single Attribute or Block Value

Use the `GetAttribute` method to retrieve a single attribute value from the configuration, plan, and state.
Use the `GetAttribute` method to retrieve a top level attribute or block value from the configuration, plan, and state.

```go
func (r ThingResource) Read(ctx context.Context,
Expand Down
6 changes: 4 additions & 2 deletions website/docs/plugin/framework/writing-state.mdx
Expand Up @@ -64,9 +64,11 @@ The state information is represented as an object, and gets persisted like an
object. Refer to the [conversion rules](#conversion-rules) for an explanation on how
objects get persisted and what Go types are valid for persisting as an object.

## Set a Single Attribute's Value
## Set a Single Attribute or Block Value

Use the `SetAttribute` method to set an individual attribute value.
Use the `SetAttribute` method to set an individual attribute or block value.

-> The value must not be an untyped `nil`. Use a typed `nil` or `types` package null value function instead. For example with a `types.StringType` attribute, use `(*string)(nil)` or `types.StringNull()`.

```go
func (r ThingResource) Read(ctx context.Context,
Expand Down

0 comments on commit 0eb939e

Please sign in to comment.