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

website: Create concept-specific configuration validation pages #501

Merged
merged 1 commit into from Sep 30, 2022
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.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
29 changes: 23 additions & 6 deletions website/data/plugin-framework-nav-data.json
Expand Up @@ -16,7 +16,16 @@
},
{
"title": "Providers",
"path": "providers"
"routes": [
{
"title": "Overview",
"path": "providers"
},
{
"title": "Validate Configuration",
"path": "providers/validate-configuration"
}
]
},
{
"title": "Resources",
Expand All @@ -30,19 +39,23 @@
"path": "resources/configure"
},
{
"title": "Import",
"path": "resources/import"
"title": "Validate Configuration",
"path": "resources/validate-configuration"
},
{
"title": "Plan Modification",
"title": "Modify Plan",
"path": "resources/plan-modification"
},
{
"title": "State Upgrade",
"title": "Import State",
"path": "resources/import"
},
{
"title": "Upgrade State",
"path": "resources/state-upgrade"
},
{
"title": "Private State Management",
"title": "Manage Private State",
"path": "resources/private-state"
},
{
Expand All @@ -62,6 +75,10 @@
"title": "Configure Clients",
"path": "data-sources/configure"
},
{
"title": "Validate Configuration",
"path": "data-sources/validate-configuration"
},
{
"title": "Timeouts",
"path": "data-sources/timeouts"
Expand Down
2 changes: 1 addition & 1 deletion website/docs/plugin/framework/data-sources/index.mdx
Expand Up @@ -14,7 +14,7 @@ description: >-
This page describes the basic implementation details required for supporting a data source within the provider. Further documentation is available for deeper data source concepts:

- [Configure](/plugin/framework/data-sources/configure) data sources with provider-level data types or clients.
- [Validate](/plugin/framework/validation) practitioner configuration against acceptable values.
- [Validate](/plugin/framework/data-sources/validate-configuration) practitioner configuration against acceptable values.
- [Timeouts](/plugin/framework/data-sources/timeouts) in practitioner configuration for use in a data source read function.

## Define Data Source Type
Expand Down
@@ -0,0 +1,81 @@
---
page_title: 'Plugin Development - Framework: Validate Data Source Configurations'
description: >-
How to validate data source configurations with the provider development framework.
---

# Validate Configuration

-> Note: The Plugin Framework is in beta.

[Data sources](/plugin/framework/data-sources) support validating an entire practitioner configuration in either declarative or imperative logic. Feedback, such as required syntax or acceptable combinations of values, is returned via [diagnostics](/plugin/framework/diagnostics).

This page describes implementation details for validating entire data source configurations, typically referencing multiple attributes. Further documentation is available for other configuration validation concepts:

- [Single attribute validation](/plugin/framework/validation#attribute-validation) is a schema-based mechanism for implementing attribute-specific validation logic.
- [Type validation](/plugin/framework/validation#type-validation) is a schema-based mechanism for implementing reusable validation logic for any attribute using the type.

## ConfigValidators Method

The [`datasource.DataSourceWithConfigValidators` interface](https://pkg.go.dev/github.com/hashicorp/terraform-plugin-framework/datasource#DataSourceWithConfigValidators) follows a similar pattern to attribute validation and allows for a more declarative approach. This enables consistent validation logic across multiple data sources. Each validator intended for this interface must implement the [`datasource.ConfigValidator` interface](https://pkg.go.dev/github.com/hashicorp/terraform-plugin-framework/datasource#ConfigValidator).

The [`terraform-plugin-framework-validators` Go module](https://pkg.go.dev/github.com/hashicorp/terraform-plugin-framework-validators) has a collection of common use case data source configuration validators in the [`datasourcevalidator` package](https://pkg.go.dev/github.com/hashicorp/terraform-plugin-framework-validators/datasourcevalidator). These use [path expressions](/plugin/framework/path-expressions) for matching attributes.

This example will raise an error if a practitioner attempts to configure both `attribute_one` and `attribute_two`:

```go
// Other methods to implement the datasource.DataSource interface are omitted for brevity
type ThingDataSource struct {}

func (d ThingDataSource) ConfigValidators(ctx context.Context) []datasource.ConfigValidator {
return []datasource.ConfigValidator{
datasourcevalidator.Conflicting(
path.MatchRoot("attribute_one"),
path.MatchRoot("attribute_two"),
),
}
}
```

## ValidateConfig Method

The [`datasource.DataSourceWithValidateConfig` interface](https://pkg.go.dev/github.com/hashicorp/terraform-plugin-framework/datasource#DataSourceWithValidateConfig) is more imperative in design and is useful for validating unique functionality across multiple attributes that typically applies to a single data source.

This example will raise a warning if a practitioner attempts to configure `attribute_one`, but not `attribute_two`:

```go
// Other methods to implement the datasource.DataSource interface are omitted for brevity
type ThingDataSource struct {}

type ThingDataSourceModel struct {
AttributeOne types.String `tfsdk:"attribute_one"`
AttributeTwo types.String `tfsdk:"attribute_two"`
}

func (d ThingDataSource) ValidateConfig(ctx context.Context, req datasource.ValidateConfigRequest, resp *datasource.ValidateConfigResponse) {
var data ThingDataSourceModel

resp.Diagnostics.Append(req.Config.Get(ctx, &data)...)

if resp.Diagnostics.HasError() {
return
}

// If attribute_one is not configured, return without warning.
if data.AttributeOne.IsNull() || data.AttributeOne.IsUnknown() {
return
}

// If attribute_two is not null, return without warning.
if !data.AttributeTwo.IsNull() {
return
}

resp.Diagnostics.AddAttributeWarning(
path.Root("attribute_two"),
"Missing Attribute Configuration",
"Expected attribute_two to be configured with attribute_one. "+
"The data source may return unexpected results.",
)
}
```
Expand Up @@ -16,7 +16,7 @@ This page describes the basic implementation details required for defining a pro

- [Configure data sources](/plugin/framework/data-sources/configure) with provider-level data types or clients.
- [Configure resources](/plugin/framework/resources/configure) with provider-level data types or clients.
- [Validate](/plugin/framework/validation) practitioner configuration against acceptable values.
- [Validate](/plugin/framework/providers/validate-configuration) practitioner configuration against acceptable values.

## Define Provider Type

Expand Down
@@ -0,0 +1,81 @@
---
page_title: 'Plugin Development - Framework: Validate Provider Configurations'
description: >-
How to validate provider configurations with the provider development framework.
---

# Validate Configuration

-> Note: The Plugin Framework is in beta.

[Providers](/plugin/framework/providers) support validating an entire practitioner configuration in either declarative or imperative logic. Feedback, such as required syntax or acceptable combinations of values, is returned via [diagnostics](/plugin/framework/diagnostics).

This page describes implementation details for validating entire provider configurations, typically referencing multiple attributes. Further documentation is available for other configuration validation concepts:

- [Single attribute validation](/plugin/framework/validation#attribute-validation) is a schema-based mechanism for implementing attribute-specific validation logic.
- [Type validation](/plugin/framework/validation#type-validation) is a schema-based mechanism for implementing reusable validation logic for any attribute using the type.

## ConfigValidators Method

The [`provider.ProviderWithConfigValidators` interface](https://pkg.go.dev/github.com/hashicorp/terraform-plugin-framework/provider#ProviderWithConfigValidators) follows a similar pattern to attribute validation and allows for a more declarative approach. This enables consistent validation logic across multiple providers. Each validator intended for this interface must implement the [`provider.ConfigValidator` interface](https://pkg.go.dev/github.com/hashicorp/terraform-plugin-framework/provider#ConfigValidator).

The [`terraform-plugin-framework-validators` Go module](https://pkg.go.dev/github.com/hashicorp/terraform-plugin-framework-validators) has a collection of common use case provider configuration validators in the [`providervalidator` package](https://pkg.go.dev/github.com/hashicorp/terraform-plugin-framework-validators/providervalidator). These use [path expressions](/plugin/framework/path-expressions) for matching attributes.

This example will raise an error if a practitioner attempts to configure both `attribute_one` and `attribute_two`:

```go
// Other methods to implement the provider.Provider interface are omitted for brevity
type ExampleCloudProvider struct {}

func (p ExampleCloudProvider) ConfigValidators(ctx context.Context) []provider.ConfigValidator {
return []provider.ConfigValidator{
providervalidator.Conflicting(
path.MatchRoot("attribute_one"),
path.MatchRoot("attribute_two"),
),
}
}
```

## ValidateConfig Method

The [`provider.ProviderWithValidateConfig` interface](https://pkg.go.dev/github.com/hashicorp/terraform-plugin-framework/provider#ProviderWithValidateConfig) is more imperative in design and is useful for validating unique functionality across multiple attributes that typically applies to a single provider.

This example will raise a warning if a practitioner attempts to configure `attribute_one`, but not `attribute_two`:

```go
// Other methods to implement the provider.Provider interface are omitted for brevity
type ExampleCloudProvider struct {}

type ExampleCloudProviderModel struct {
AttributeOne types.String `tfsdk:"attribute_one"`
AttributeTwo types.String `tfsdk:"attribute_two"`
}

func (p ExampleCloudProvider) ValidateConfig(ctx context.Context, req provider.ValidateConfigRequest, resp *provider.ValidateConfigResponse) {
var data ExampleCloudProviderModel

resp.Diagnostics.Append(req.Config.Get(ctx, &data)...)

if resp.Diagnostics.HasError() {
return
}

// If attribute_one is not configured, return without warning.
if data.AttributeOne.IsNull() || data.AttributeOne.IsUnknown() {
return
}

// If attribute_two is not null, return without warning.
if !data.AttributeTwo.IsNull() {
return
}

resp.Diagnostics.AddAttributeWarning(
path.Root("attribute_two"),
"Missing Attribute Configuration",
"Expected attribute_two to be configured with attribute_one. "+
"The provider may return unexpected results.",
)
}
```
2 changes: 1 addition & 1 deletion website/docs/plugin/framework/resources/index.mdx
Expand Up @@ -22,7 +22,7 @@ This page describes the basic implementation details required for supporting a r
- [Manage private state](/plugin/framework/resources/private-state) to store additional data in resource state that is not shown in plans.
- [Modify plans](/plugin/framework/resources/plan-modification) to enrich the output for expected resource behaviors during changes, such as including default values for missing configurations or marking a resource for replacement if an in-place update cannot occur.
- [Upgrade state](/plugin/framework/resources/state-upgrade) to transparently update state data outside plans.
- [Validate](/plugin/framework/validation) practitioner configuration against acceptable values.
- [Validate](/plugin/framework/resources/validate-configuration) practitioner configuration against acceptable values.
- [Timeouts](/plugin/framework/resources/timeouts) in practitioner configuration for use in resource create, read, update and delete functions.

## Define Resource Type
Expand Down
@@ -0,0 +1,81 @@
---
page_title: 'Plugin Development - Framework: Validate Resource Configurations'
description: >-
How to validate resource configurations with the provider development framework.
---

# Validate Configuration

-> Note: The Plugin Framework is in beta.

[Resources](/plugin/framework/resources) support validating an entire practitioner configuration in either declarative or imperative logic. Feedback, such as required syntax or acceptable combinations of values, is returned via [diagnostics](/plugin/framework/diagnostics).

This page describes implementation details for validating entire resource configurations, typically referencing multiple attributes. Further documentation is available for other configuration validation concepts:

- [Single attribute validation](/plugin/framework/validation#attribute-validation) is a schema-based mechanism for implementing attribute-specific validation logic.
- [Type validation](/plugin/framework/validation#type-validation) is a schema-based mechanism for implementing reusable validation logic for any attribute using the type.

## ConfigValidators Method

The [`resource.ResourceWithConfigValidators` interface](https://pkg.go.dev/github.com/hashicorp/terraform-plugin-framework/resource#ResourceWithConfigValidators) follows a similar pattern to attribute validation and allows for a more declarative approach. This enables consistent validation logic across multiple resources. Each validator intended for this interface must implement the [`resource.ConfigValidator` interface](https://pkg.go.dev/github.com/hashicorp/terraform-plugin-framework/resource#ConfigValidator).

The [`terraform-plugin-framework-validators` Go module](https://pkg.go.dev/github.com/hashicorp/terraform-plugin-framework-validators) has a collection of common use case resource configuration validators in the [`resourcevalidator` package](https://pkg.go.dev/github.com/hashicorp/terraform-plugin-framework-validators/resourcevalidator). These use [path expressions](/plugin/framework/path-expressions) for matching attributes.

This example will raise an error if a practitioner attempts to configure both `attribute_one` and `attribute_two`:

```go
// Other methods to implement the resource.Resource interface are omitted for brevity
type ThingResource struct {}

func (r ThingResource) ConfigValidators(ctx context.Context) []resource.ConfigValidator {
return []resource.ConfigValidator{
resourcevalidator.Conflicting(
path.MatchRoot("attribute_one"),
path.MatchRoot("attribute_two"),
),
}
}
```

## ValidateConfig Method

The [`resource.ResourceWithValidateConfig` interface](https://pkg.go.dev/github.com/hashicorp/terraform-plugin-framework/resource#ResourceWithValidateConfig) is more imperative in design and is useful for validating unique functionality across multiple attributes that typically applies to a single resource.

This example will raise a warning if a practitioner attempts to configure `attribute_one`, but not `attribute_two`:

```go
// Other methods to implement the resource.Resource interface are omitted for brevity
type ThingResource struct {}

type ThingResourceModel struct {
AttributeOne types.String `tfsdk:"attribute_one"`
AttributeTwo types.String `tfsdk:"attribute_two"`
}

func (r ThingResource) ValidateConfig(ctx context.Context, req resource.ValidateConfigRequest, resp *resource.ValidateConfigResponse) {
var data ThingResourceModel

resp.Diagnostics.Append(req.Config.Get(ctx, &data)...)

if resp.Diagnostics.HasError() {
return
}

// If attribute_one is not configured, return without warning.
if data.AttributeOne.IsNull() || data.AttributeOne.IsUnknown() {
return
}

// If attribute_two is not null, return without warning.
if !data.AttributeTwo.IsNull() {
return
}

resp.Diagnostics.AddAttributeWarning(
path.Root("attribute_two"),
"Missing Attribute Configuration",
"Expected attribute_two to be configured with attribute_one. "+
"The resource may return unexpected results.",
)
}
```