bug: Getting `Bad field type v1.Duration` on v10.15.0+
- [x] I have looked at the documentation here first?
- [x] I have looked at the examples provided that may showcase my question here?
Package version eg. v9, v10:
Error starts occurring on v10.15.0
No errors present on v10.14.1
Issue, Question or Enhancement:
When validating a metav1.Duration struct, we are receiving an error with the validation that we previously never received
[PANICKED] Test Panicked
In [It] at: /Users/joinnis/go/pkg/mod/github.com/go-playground/validator/[email protected]/baked_in.go:2079 @ 08/18/23 00:08:21.25
Bad field type v1.Duration
Full Stack Trace
github.com/go-playground/validator/v10.isGte({0x105ab3970, 0x1400098f680})
/Users/joinnis/go/pkg/mod/github.com/go-playground/validator/[email protected]/baked_in.go:2079 +0x440
github.com/go-playground/validator/v10.hasMinOf({0x105ab3970?, 0x1400098f680?})
/Users/joinnis/go/pkg/mod/github.com/go-playground/validator/[email protected]/baked_in.go:2162 +0x24
github.com/go-playground/validator/v10.wrapFunc.func1({0x1400098f680?, 0x105aba000?}, {0x105ab3970?, 0x1400098f680?})
/Users/joinnis/go/pkg/mod/github.com/go-playground/validator/[email protected]/baked_in.go:43 +0x34
github.com/go-playground/validator/v10.(*validate).traverseField(0x1400098f680, {0x105aafb68, 0x14000190018}, {0x105a726c0?, 0x140001cd680?, 0x14000756868?}, {0x105a7cce0?, 0x140001cd690?, 0x120?}, {0x140000aad00, ...}, ...)
/Users/joinnis/go/pkg/mod/github.com/go-playground/validator/[email protected]/validator.go:180 +0xab4
github.com/go-playground/validator/v10.(*validate).validateStruct(0x1400098f680, {0x105aafb68, 0x14000190018}, {0x105a726c0?, 0x140001cd680?, 0x0?}, {0x105a726c0?, 0x140001cd680?, 0x104c360e8?}, {0x105aba000?, ...}, ...)
/Users/joinnis/go/pkg/mod/github.com/go-playground/validator/[email protected]/validator.go:77 +0x51c
github.com/go-playground/validator/v10.(*Validate).StructCtx(0x140002daa10, {0x105aafb68, 0x14000190018}, {0x105a726c0, 0x140001cd680})
/Users/joinnis/go/pkg/mod/github.com/go-playground/validator/[email protected]/validator_instance.go:389 +0x3cc
github.com/go-playground/validator/v10.(*Validate).Struct(...)
/Users/joinnis/go/pkg/mod/github.com/go-playground/validator/[email protected]/validator_instance.go:362
github.com/aws/karpenter/pkg/apis/settings.Settings.Validate({{0x0, 0x0}, 0x140005a3b48, {0x0, 0x0}, {0x0, 0x0}, {0x0, 0x0}, 0x0, ...})
/Users/joinnis/github/karpenter/pkg/apis/settings/settings.go:110 +0x138
github.com/aws/karpenter/pkg/apis/settings.(*Settings).Inject(0x140005b9dc0, {0x105aafbd8, 0x1400075e060}, 0x14000756e38)
/Users/joinnis/github/karpenter/pkg/apis/settings/settings.go:94 +0x388
github.com/aws/karpenter/pkg/apis/settings_test.glob..func1.9()
/Users/joinnis/github/karpenter/pkg/apis/settings/suite_test.go:203 +0xdc
Code sample, to showcase or reproduce:
package main
type Settings struct {
d *metav1.Duration
}
func (s Settings) Validate() error {
return validator.New().Struct(s)
}
func main() {
s = Settings{d: &metav1.Duration{Duration: time.Second}}
s.Validate()
}
related to #1142
Nested struct validation was not supported in previous version, hence why no error was returned.
However, support extends only to a few tags including the ones that check against zero values such as required and excluded_with. This does not include tags like min.
If you need more complex validation, you must register your own custom tag. Ex.:
func main() {
type Settings struct {
D *metav1.Duration `validate:"metamin=15m"`
}
v := validator.New()
if err := v.RegisterValidation("metamin", func(fl validator.FieldLevel) bool {
duration, ok := fl.Field().Interface().(metav1.Duration)
if !ok {
return false
}
return v.Var(duration.Duration, "min="+fl.Param()) == nil
}); err != nil {
panic(err)
}
// valid
s1 := Settings{&metav1.Duration{time.Minute * 15}}
if err := v.Struct(s1); err != nil {
panic(err)
}
// invalid
s2 := Settings{&metav1.Duration{time.Minute * 14}}
if err := v.Struct(s2); err != nil {
panic(err)
}
}
Also, it's worth noting that struct fields must be exported in order for them to get validated.
Is this the code you're having an issue with? https://github.com/aws/karpenter/blob/a87ed30c8e60d6be25ce10fb058ad66c6174edab/pkg/apis/settings/settings.go#L57
Example doesn't clearly demonstrate an issue.
@jonathan-innis can we consolidate the conversation here :) https://github.com/go-playground/validator/issues/1142