Skip to content

Commit e9a70da

Browse files
committed
Add support for form files
1 parent ec96099 commit e9a70da

File tree

3 files changed

+47
-13
lines changed

3 files changed

+47
-13
lines changed

create_error.go

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,10 @@ func CreateJsonError(errors map[string]string) error {
1010
return createCustomError(JsonMode, errors)
1111
}
1212

13+
func CreateFormError(errors map[string]string) error {
14+
return createCustomError(FormMode, errors)
15+
}
16+
1317
func createCustomError(mode Mode, errors map[string]string) error {
1418
fieldErrors := []FieldErrors{}
1519
for key, message := range errors {

laravalidate.go

Lines changed: 20 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -35,11 +35,13 @@ func newValidator(ctx context.Context, languages []language.Tag, value reflect.V
3535
type Mode uint8
3636

3737
const (
38-
GoMode Mode = iota
39-
JsonMode
38+
GoMode Mode = iota
39+
JsonMode // Tries to use json struct tags
40+
FormMode // Tries to use form struct tags
4041
)
4142

4243
// JsonValidate should be used to validate a json parsed message, errors returned will have a json paths.
44+
// These look at the `json="xx"` struct tag for hints how to name the error keys.
4345
//
4446
// If an error is returned the type should be of *ValidationError.
4547
//
@@ -49,6 +51,17 @@ func JsonValidate(ctx context.Context, languages []language.Tag, input any) erro
4951
return validate(ctx, languages, input, JsonMode)
5052
}
5153

54+
// FormValidate should be used to validate a form parsed message, errors returned will have a form paths.
55+
// These look at the `form="xx"` struct tag for hints how to name the error keys.
56+
//
57+
// If an error is returned the type should be of *ValidationError.
58+
//
59+
// Ctx can be set to nil, default value will be context.Background().
60+
// Languages can be set to nil, default value will be []language.Tag{language.English}.
61+
func FormValidate(ctx context.Context, languages []language.Tag, input any) error {
62+
return validate(ctx, languages, input, FormMode)
63+
}
64+
5265
// GoValidate should be used to validate something within a go codebase with validation errors that apply to the go codebase.
5366
//
5467
// If an error is returned the type should be of *ValidationError.
@@ -259,10 +272,12 @@ func (v *Validator) Validate(stack Stack, value *reflect.Value, valueType reflec
259272
return
260273
}
261274

262-
goPath, jsonPath := stack.ToPaths()
275+
goPath, jsonPath, formPath := stack.ToPaths()
263276
path := goPath
264277
if v.mode == JsonMode {
265278
path = jsonPath
279+
} else if v.mode == FormMode {
280+
path = formPath
266281
}
267282

268283
v.errors = append(v.errors, FieldErrors{
@@ -295,6 +310,8 @@ outer:
295310
stackElement := stack[len(stack)-1]
296311
if v.mode == JsonMode {
297312
replaceVariable(variable, stackElement.JsonName)
313+
} else if v.mode == FormMode {
314+
replaceVariable(variable, stackElement.FormName)
298315
} else {
299316
replaceVariable(variable, stackElement.GoName)
300317
}

stack.go

Lines changed: 23 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -16,6 +16,7 @@ const (
1616
type StackElement struct {
1717
GoName string
1818
JsonName string
19+
FormName string
1920
Index int // Only for kind == StackKindList
2021
Kind StackKind
2122
Parent *reflect.Value
@@ -24,20 +25,18 @@ type StackElement struct {
2425

2526
type Stack []StackElement
2627

27-
func (s Stack) ToPaths() (golang, json string) {
28-
golang = ""
29-
json = ""
30-
28+
func (s Stack) ToPaths() (golang, json, form string) {
3129
for idx, e := range s {
3230
if idx == 0 {
3331
golang = e.GoName
3432
json = e.JsonName
33+
form = e.FormName
3534
continue
3635
}
3736
golang += "." + e.GoName
3837
json += "." + e.JsonName
38+
form += "." + e.FormName
3939
}
40-
4140
return
4241
}
4342

@@ -46,6 +45,7 @@ func (s Stack) AppendIndex(index int, parent *reflect.Value, parentType reflect.
4645
return append(s, StackElement{
4746
GoName: indexStr,
4847
JsonName: indexStr,
48+
FormName: indexStr,
4949
Index: index,
5050
Kind: StackKindList,
5151
Parent: parent,
@@ -54,17 +54,30 @@ func (s Stack) AppendIndex(index int, parent *reflect.Value, parentType reflect.
5454
}
5555

5656
func (s Stack) AppendField(field reflect.StructField, parent *reflect.Value, parentType reflect.Type) Stack {
57-
jsonTag := field.Tag.Get("json")
58-
jsonTag = strings.Split(jsonTag, ",")[0]
59-
57+
jsonTag, ok := field.Tag.Lookup("json")
6058
jsonName := field.Name
61-
if jsonTag != "" && jsonTag != "-" {
62-
jsonName = jsonTag
59+
if ok {
60+
jsonTag = strings.Split(jsonTag, ",")[0]
61+
62+
if jsonTag != "" && jsonTag != "-" {
63+
jsonName = jsonTag
64+
}
65+
}
66+
67+
formTag, ok := field.Tag.Lookup("form")
68+
formName := field.Name
69+
if ok {
70+
formTag = strings.Split(formTag, ",")[0]
71+
72+
if formTag != "" && formTag != "-" {
73+
formName = formTag
74+
}
6375
}
6476

6577
return append(s, StackElement{
6678
GoName: field.Name,
6779
JsonName: jsonName,
80+
FormName: formName,
6881
Index: -1,
6982
Kind: StackKindObject,
7083
Parent: parent,

0 commit comments

Comments
 (0)