forked from mirror/gin
46 lines
1013 B
Go
46 lines
1013 B
Go
|
package gin
|
||
|
|
||
|
import (
|
||
|
"errors"
|
||
|
"reflect"
|
||
|
"strings"
|
||
|
)
|
||
|
|
||
|
func Validate(c *Context, obj interface{}) error {
|
||
|
|
||
|
var err error
|
||
|
typ := reflect.TypeOf(obj)
|
||
|
val := reflect.ValueOf(obj)
|
||
|
|
||
|
if typ.Kind() == reflect.Ptr {
|
||
|
typ = typ.Elem()
|
||
|
val = val.Elem()
|
||
|
}
|
||
|
|
||
|
for i := 0; i < typ.NumField(); i++ {
|
||
|
field := typ.Field(i)
|
||
|
fieldValue := val.Field(i).Interface()
|
||
|
zero := reflect.Zero(field.Type).Interface()
|
||
|
|
||
|
// Validate nested and embedded structs (if pointer, only do so if not nil)
|
||
|
if field.Type.Kind() == reflect.Struct ||
|
||
|
(field.Type.Kind() == reflect.Ptr && !reflect.DeepEqual(zero, fieldValue)) {
|
||
|
err = Validate(c, fieldValue)
|
||
|
}
|
||
|
|
||
|
if strings.Index(field.Tag.Get("binding"), "required") > -1 {
|
||
|
if reflect.DeepEqual(zero, fieldValue) {
|
||
|
name := field.Name
|
||
|
if j := field.Tag.Get("json"); j != "" {
|
||
|
name = j
|
||
|
} else if f := field.Tag.Get("form"); f != "" {
|
||
|
name = f
|
||
|
}
|
||
|
err = errors.New("Required " + name)
|
||
|
c.Error(err, "json validation")
|
||
|
}
|
||
|
}
|
||
|
}
|
||
|
return err
|
||
|
}
|