Skip to content

Proposal: Child attribute validators for Objects #274

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

Open
1 task done
gdavison opened this issue Mar 12, 2025 · 0 comments
Open
1 task done

Proposal: Child attribute validators for Objects #274

gdavison opened this issue Mar 12, 2025 · 0 comments
Labels
enhancement New feature or request

Comments

@gdavison
Copy link

Terraform CLI and Framework Versions

All

Use Cases or Problem Statement

Currently, there isn't a standard method for cleanly validating the child members of an Object. For example, to require exactly one of a set of attributes we need add an ExactlyOneOf validator on one of the child attributes, as below. Until #118 is resolved, we also have to add path.MatchRelative() as a self-reference.

func (r *resourceBucketLifecycleConfiguration) Schema(ctx context.Context, request resource.SchemaRequest, response *resource.SchemaResponse) {
	response.Schema = schema.Schema{
		Version: 1,
		Attributes: map[string]schema.Attribute{
			// ...
		},
		Blocks: map[string]schema.Block{
			names.AttrRule: schema.ListNestedBlock{
				CustomType: fwtypes.NewListNestedObjectTypeOf[lifecycleRuleModel](ctx),
				Validators: []validator.List{
					listvalidator.SizeAtLeast(1),
				},
				NestedObject: schema.NestedBlockObject{
					Attributes: map[string]schema.Attribute{
						// ...
					},
					Blocks: map[string]schema.Block{
						// ...
						"expiration": schema.ListNestedBlock{
							CustomType: fwtypes.NewListNestedObjectTypeOf[lifecycleExpirationModel](ctx),
							Validators: []validator.List{
								listvalidator.SizeAtMost(1),
							},
							NestedObject: schema.NestedBlockObject{
								Attributes: map[string]schema.Attribute{
									"date": schema.StringAttribute{
										CustomType: timetypes.RFC3339Type{},
										Optional:   true,
									},
									"days": schema.Int32Attribute{
										Optional: true,
										Validators: []validator.Int32{
											int32validator.AtLeast(1),
										},
									},
									"expired_object_delete_marker": schema.BoolAttribute{
										Optional: true,
										Validators: []validator.Bool{
                      boolvalidator.ExactlyOneOf(
                        path.MatchRelative(), // Required until #118 is addressed
                        path.MatchRelative().AtParent().AtName("date"),
                        path.MatchRelative().AtParent().AtName("days"),
                      ),
										},
									},
								},
							},
						},
						// ...
					},
				},
			},
		},
	}
}

However, the error message displayed is

No attribute specified when one (and only one) of
[rule[0].expiration[0].expired_object_delete_marker,rule[0].expiration[0].expired_object_delete_marker.<.date,rule[0].expiration[0].expired_object_delete_marker.<.days]

which is hard to read, especially the references to the attributes with the AtParent relationship, such as rule[0].expiration[0].expired_object_delete_marker.<.days. I would also recommend adding a space after the , and possibly demarcate the individual attributes with some form of quotation marks.

Using objectvalidator.ExactlyOneOf on the Object includes the object itself in the count, so cannot be used.

Proposal

Add validators such as objectvalidator.ExactlyOneOfChildren which would act like the non-Children version but not count itself. For example, in the case above, the following validator would be set on the Object

objectvalidator.ExactlyOneOfChildren(
    path.MatchRelative().AtName("date"),
    path.MatchRelative().AtName("days"),
    path.MatchRelative().AtName("expired_object_delete_marker"),
)

Additional Information

No response

Code of Conduct

  • I agree to follow this project's Code of Conduct
@gdavison gdavison added the enhancement New feature or request label Mar 12, 2025
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
enhancement New feature or request
Projects
None yet
Development

No branches or pull requests

1 participant