github.com/blend/go-sdk@v1.20220411.3/validate/validation_error.go (about)

     1  /*
     2  
     3  Copyright (c) 2022 - Present. Blend Labs, Inc. All rights reserved
     4  Use of this source code is governed by a MIT license that can be found in the LICENSE file.
     5  
     6  */
     7  
     8  package validate
     9  
    10  import (
    11  	"fmt"
    12  
    13  	"github.com/blend/go-sdk/ex"
    14  )
    15  
    16  // The root error, all validation errors inherit from this type.
    17  const (
    18  	ErrValidation ex.Class = "validation error"
    19  )
    20  
    21  var (
    22  	_ ex.ClassProvider = (*ValidationError)(nil)
    23  )
    24  
    25  // ValidationError is the inner error for validation exceptions.
    26  type ValidationError struct {
    27  	// Cause is the error class that connotes the type of failure.
    28  	Cause error
    29  	// Message is variable or contextaul data to add meaning to the cause.
    30  	Message string
    31  	// Value is the offending value, it can be unset, and is meant to be a common piece of context.
    32  	Value interface{}
    33  }
    34  
    35  // Class implements
    36  func (ve ValidationError) Class() error {
    37  	return ve.Cause
    38  }
    39  
    40  // Error implements error.
    41  func (ve ValidationError) Error() string {
    42  	if ve.Value != nil && ve.Message != "" {
    43  		return fmt.Sprintf("%v; %v; %v", ve.Cause, ve.Message, ve.Value)
    44  	}
    45  	if ve.Value != nil {
    46  		return fmt.Sprintf("%v; %v", ve.Cause, ve.Value)
    47  	}
    48  	if ve.Message != "" {
    49  		return fmt.Sprintf("%v; %v", ve.Cause, ve.Message)
    50  	}
    51  	return ve.Cause.Error()
    52  }
    53  
    54  // ErrInner returns the inner validation error if it's present on
    55  // the outer error.
    56  func ErrInner(err error) *ValidationError {
    57  	inner := ex.ErrInner(err)
    58  	if inner == nil {
    59  		return nil
    60  	}
    61  	if typed, ok := inner.(*ValidationError); ok {
    62  		return typed
    63  	}
    64  	return nil
    65  }
    66  
    67  // ErrCause returns the underlying validation failure for an error.
    68  // If the error is not a validation error, it returns the error class.
    69  func ErrCause(err error) error {
    70  	if exClass := ex.ErrClass(err); exClass != ErrValidation {
    71  		return exClass
    72  	}
    73  	if inner := ErrInner(err); inner != nil {
    74  		return inner.Cause
    75  	}
    76  	return nil
    77  }
    78  
    79  // ErrMessage returns the underlying validation error message.
    80  func ErrMessage(err error) string {
    81  	if inner := ErrInner(err); inner != nil {
    82  		return inner.Message
    83  	}
    84  	return ""
    85  }
    86  
    87  // ErrValue returns the validation error value.
    88  func ErrValue(err error) interface{} {
    89  	if inner := ErrInner(err); inner != nil {
    90  		return inner.Value
    91  	}
    92  	return nil
    93  }
    94  
    95  // ErrFormat formats an error.
    96  func ErrFormat(err error) string {
    97  	if err == nil {
    98  		return "ok!"
    99  	}
   100  	return ErrInner(err).Error()
   101  }
   102  
   103  // Is returns if an error is a validation error.
   104  func Is(err error) bool {
   105  	return ex.Is(err, ErrValidation)
   106  }