mirror of
https://github.com/aykhans/dodo.git
synced 2025-09-08 03:50:46 +00:00
add 'Validate' method to the 'Config'
This commit is contained in:
@@ -63,6 +63,52 @@ func (e FieldParseErrors) Error() string {
|
||||
return errorString
|
||||
}
|
||||
|
||||
type FieldValidationError struct {
|
||||
Field string
|
||||
Value string
|
||||
Err error
|
||||
}
|
||||
|
||||
func NewFieldValidationError(field string, value string, err error) FieldValidationError {
|
||||
if err == nil {
|
||||
err = ErrNoError
|
||||
}
|
||||
return FieldValidationError{field, value, err}
|
||||
}
|
||||
|
||||
func (e FieldValidationError) Error() string {
|
||||
return fmt.Sprintf("Field '%s' validation failed: %v", e.Field, e.Err)
|
||||
}
|
||||
|
||||
func (e FieldValidationError) Unwrap() error {
|
||||
return e.Err
|
||||
}
|
||||
|
||||
type FieldValidationErrors struct {
|
||||
Errors []FieldValidationError
|
||||
}
|
||||
|
||||
func NewFieldValidationErrors(fieldValidationErrors []FieldValidationError) FieldValidationErrors {
|
||||
return FieldValidationErrors{fieldValidationErrors}
|
||||
}
|
||||
|
||||
func (e FieldValidationErrors) Error() string {
|
||||
if len(e.Errors) == 0 {
|
||||
return "No field validation errors"
|
||||
}
|
||||
if len(e.Errors) == 1 {
|
||||
return e.Errors[0].Error()
|
||||
}
|
||||
|
||||
errorString := ""
|
||||
for _, err := range e.Errors {
|
||||
errorString += err.Error() + "\n"
|
||||
}
|
||||
errorString, _ = strings.CutSuffix(errorString, "\n")
|
||||
|
||||
return errorString
|
||||
}
|
||||
|
||||
type UnmarshalError struct {
|
||||
error error
|
||||
}
|
||||
|
@@ -252,6 +252,118 @@ func TestNewUnmarshalError(t *testing.T) {
|
||||
})
|
||||
}
|
||||
|
||||
func TestFieldValidationError_Error(t *testing.T) {
|
||||
t.Run("Error returns formatted message", func(t *testing.T) {
|
||||
originalErr := errors.New("invalid value")
|
||||
fieldErr := NewFieldValidationError("username", "testuser", originalErr)
|
||||
|
||||
expected := "Field 'username' validation failed: invalid value"
|
||||
assert.Equal(t, expected, fieldErr.Error())
|
||||
})
|
||||
|
||||
t.Run("Error with empty field name", func(t *testing.T) {
|
||||
originalErr := errors.New("test error")
|
||||
fieldErr := NewFieldValidationError("", "somevalue", originalErr)
|
||||
|
||||
expected := "Field '' validation failed: test error"
|
||||
assert.Equal(t, expected, fieldErr.Error())
|
||||
})
|
||||
|
||||
t.Run("Error with nil underlying error", func(t *testing.T) {
|
||||
fieldErr := NewFieldValidationError("field", "value123", nil)
|
||||
|
||||
expected := "Field 'field' validation failed: no error (internal)"
|
||||
assert.Equal(t, expected, fieldErr.Error())
|
||||
})
|
||||
}
|
||||
|
||||
func TestFieldValidationError_Unwrap(t *testing.T) {
|
||||
t.Run("Unwrap returns original error", func(t *testing.T) {
|
||||
originalErr := errors.New("original error")
|
||||
fieldErr := NewFieldValidationError("field", "value", originalErr)
|
||||
|
||||
assert.Equal(t, originalErr, fieldErr.Unwrap())
|
||||
})
|
||||
|
||||
t.Run("Unwrap with nil error", func(t *testing.T) {
|
||||
fieldErr := NewFieldValidationError("field", "value", nil)
|
||||
|
||||
assert.Equal(t, ErrNoError, fieldErr.Unwrap())
|
||||
})
|
||||
}
|
||||
|
||||
func TestNewFieldValidationError(t *testing.T) {
|
||||
t.Run("Creates FieldValidationError with correct values", func(t *testing.T) {
|
||||
originalErr := errors.New("test error")
|
||||
fieldErr := NewFieldValidationError("testField", "testValue", originalErr)
|
||||
|
||||
assert.Equal(t, "testField", fieldErr.Field)
|
||||
assert.Equal(t, "testValue", fieldErr.Value)
|
||||
assert.Equal(t, originalErr, fieldErr.Err)
|
||||
})
|
||||
|
||||
t.Run("Creates FieldValidationError with ErrNoError when nil passed", func(t *testing.T) {
|
||||
fieldErr := NewFieldValidationError("testField", "testValue", nil)
|
||||
|
||||
assert.Equal(t, "testField", fieldErr.Field)
|
||||
assert.Equal(t, "testValue", fieldErr.Value)
|
||||
assert.Equal(t, ErrNoError, fieldErr.Err)
|
||||
})
|
||||
}
|
||||
|
||||
func TestFieldValidationErrors_Error(t *testing.T) {
|
||||
t.Run("Error with no errors returns default message", func(t *testing.T) {
|
||||
fieldErrors := NewFieldValidationErrors([]FieldValidationError{})
|
||||
|
||||
assert.Equal(t, "No field validation errors", fieldErrors.Error())
|
||||
})
|
||||
|
||||
t.Run("Error with single error returns single error message", func(t *testing.T) {
|
||||
fieldErr := NewFieldValidationError("field1", "value1", errors.New("error1"))
|
||||
fieldErrors := NewFieldValidationErrors([]FieldValidationError{fieldErr})
|
||||
|
||||
expected := "Field 'field1' validation failed: error1"
|
||||
assert.Equal(t, expected, fieldErrors.Error())
|
||||
})
|
||||
|
||||
t.Run("Error with multiple errors returns concatenated messages", func(t *testing.T) {
|
||||
fieldErr1 := NewFieldValidationError("field1", "value1", errors.New("error1"))
|
||||
fieldErr2 := NewFieldValidationError("field2", "value2", errors.New("error2"))
|
||||
fieldErr3 := NewFieldValidationError("field3", "value3", errors.New("error3"))
|
||||
fieldErrors := NewFieldValidationErrors([]FieldValidationError{fieldErr1, fieldErr2, fieldErr3})
|
||||
|
||||
expected := "Field 'field1' validation failed: error1\nField 'field2' validation failed: error2\nField 'field3' validation failed: error3"
|
||||
assert.Equal(t, expected, fieldErrors.Error())
|
||||
})
|
||||
|
||||
t.Run("Error with two errors", func(t *testing.T) {
|
||||
fieldErr1 := NewFieldValidationError("username", "john", errors.New("too short"))
|
||||
fieldErr2 := NewFieldValidationError("email", "invalid", errors.New("invalid format"))
|
||||
fieldErrors := NewFieldValidationErrors([]FieldValidationError{fieldErr1, fieldErr2})
|
||||
|
||||
expected := "Field 'username' validation failed: too short\nField 'email' validation failed: invalid format"
|
||||
assert.Equal(t, expected, fieldErrors.Error())
|
||||
})
|
||||
}
|
||||
|
||||
func TestNewFieldValidationErrors(t *testing.T) {
|
||||
t.Run("Creates FieldValidationErrors with correct values", func(t *testing.T) {
|
||||
fieldErr1 := NewFieldValidationError("field1", "value1", errors.New("error1"))
|
||||
fieldErr2 := NewFieldValidationError("field2", "value2", errors.New("error2"))
|
||||
fieldErrors := NewFieldValidationErrors([]FieldValidationError{fieldErr1, fieldErr2})
|
||||
|
||||
assert.Len(t, fieldErrors.Errors, 2)
|
||||
assert.Equal(t, fieldErr1, fieldErrors.Errors[0])
|
||||
assert.Equal(t, fieldErr2, fieldErrors.Errors[1])
|
||||
})
|
||||
|
||||
t.Run("Creates FieldValidationErrors with empty slice", func(t *testing.T) {
|
||||
fieldErrors := NewFieldValidationErrors([]FieldValidationError{})
|
||||
|
||||
assert.Empty(t, fieldErrors.Errors)
|
||||
})
|
||||
}
|
||||
|
||||
func TestErrorImplementsErrorInterface(t *testing.T) {
|
||||
t.Run("FieldParseError implements error interface", func(t *testing.T) {
|
||||
var err error = NewFieldParseError("field", "value", errors.New("test"))
|
||||
@@ -277,4 +389,14 @@ func TestErrorImplementsErrorInterface(t *testing.T) {
|
||||
var err error = NewUnmarshalError(errors.New("test"))
|
||||
assert.Error(t, err)
|
||||
})
|
||||
|
||||
t.Run("FieldValidationError implements error interface", func(t *testing.T) {
|
||||
var err error = NewFieldValidationError("field", "value", errors.New("test"))
|
||||
assert.Error(t, err)
|
||||
})
|
||||
|
||||
t.Run("FieldValidationErrors implements error interface", func(t *testing.T) {
|
||||
var err error = NewFieldValidationErrors([]FieldValidationError{})
|
||||
assert.Error(t, err)
|
||||
})
|
||||
}
|
||||
|
Reference in New Issue
Block a user