github.com/haraldrudell/parl@v0.4.176/ensure-error.go (about)

     1  /*
     2  © 2020–present Harald Rudell <harald.rudell@gmail.com> (https://haraldrudell.github.io/haraldrudell/)
     3  ISC License
     4  */
     5  
     6  package parl
     7  
     8  import (
     9  	"fmt"
    10  
    11  	"github.com/haraldrudell/parl/perrors"
    12  )
    13  
    14  const (
    15  	// counts the stack frame of [parl.ensureError]
    16  	parlEnsureErrorFrames = 1
    17  	// counts the stack frame of [parl.EnsureError]
    18  	parlEnsureErrorFrames0 = 1
    19  )
    20  
    21  // ensureError interprets a panic values as an error
    22  //   - returned value is either nil or an error value with stack trace
    23  //   - the error is ensured to have stack trace
    24  func EnsureError(panicValue any) (err error) {
    25  	return ensureError(panicValue, parlEnsureErrorFrames0)
    26  }
    27  
    28  // ensureError returns an error from a panic value that is any
    29  //   - returned value is either nil or an error value with stack trace
    30  //   - frames is used to select the stack frame from where the stack trace begins
    31  //   - frames 0 is he caller of ensure Error
    32  func ensureError(panicValue any, frames int) (err error) {
    33  
    34  	// no panic is no-op
    35  	if panicValue == nil {
    36  		return // no panic return
    37  	}
    38  
    39  	// ensure value to be error
    40  	var ok bool
    41  	if err, ok = panicValue.(error); !ok {
    42  		err = fmt.Errorf("non-error value: %T %+[1]v", panicValue)
    43  	}
    44  
    45  	// ensure stack trace
    46  	if !perrors.HasStack(err) {
    47  		if frames < 0 {
    48  			frames = 0
    49  		}
    50  		err = perrors.Stackn(err, frames+parlEnsureErrorFrames)
    51  	}
    52  
    53  	return
    54  }