|
- // Copyright (C) MongoDB, Inc. 2017-present.
- //
- // Licensed under the Apache License, Version 2.0 (the "License"); you may
- // not use this file except in compliance with the License. You may obtain
- // a copy of the License at http://www.apache.org/licenses/LICENSE-2.0
-
- package internal
-
- import (
- "fmt"
- )
-
- // WrappedError represents an error that contains another error.
- type WrappedError interface {
- // Message gets the basic message of the error.
- Message() string
- // Inner gets the inner error if one exists.
- Inner() error
- }
-
- // RolledUpErrorMessage gets a flattened error message.
- func RolledUpErrorMessage(err error) string {
- if wrappedErr, ok := err.(WrappedError); ok {
- inner := wrappedErr.Inner()
- if inner != nil {
- return fmt.Sprintf("%s: %s", wrappedErr.Message(), RolledUpErrorMessage(inner))
- }
-
- return wrappedErr.Message()
- }
-
- return err.Error()
- }
-
- //UnwrapError attempts to unwrap the error down to its root cause.
- func UnwrapError(err error) error {
-
- switch tErr := err.(type) {
- case WrappedError:
- return UnwrapError(tErr.Inner())
- case *multiError:
- return UnwrapError(tErr.errors[0])
- }
-
- return err
- }
-
- // WrapError wraps an error with a message.
- func WrapError(inner error, message string) error {
- return &wrappedError{message, inner}
- }
-
- // WrapErrorf wraps an error with a message.
- func WrapErrorf(inner error, format string, args ...interface{}) error {
- return &wrappedError{fmt.Sprintf(format, args...), inner}
- }
-
- // MultiError combines multiple errors into a single error. If there are no errors,
- // nil is returned. If there is 1 error, it is returned. Otherwise, they are combined.
- func MultiError(errors ...error) error {
-
- // remove nils from the error list
- var nonNils []error
- for _, e := range errors {
- if e != nil {
- nonNils = append(nonNils, e)
- }
- }
-
- switch len(nonNils) {
- case 0:
- return nil
- case 1:
- return nonNils[0]
- default:
- return &multiError{
- message: "multiple errors encountered",
- errors: nonNils,
- }
- }
- }
-
- type multiError struct {
- message string
- errors []error
- }
-
- func (e *multiError) Message() string {
- return e.message
- }
-
- func (e *multiError) Error() string {
- result := e.message
- for _, e := range e.errors {
- result += fmt.Sprintf("\n %s", e)
- }
- return result
- }
-
- func (e *multiError) Errors() []error {
- return e.errors
- }
-
- type wrappedError struct {
- message string
- inner error
- }
-
- func (e *wrappedError) Message() string {
- return e.message
- }
-
- func (e *wrappedError) Error() string {
- return RolledUpErrorMessage(e)
- }
-
- func (e *wrappedError) Inner() error {
- return e.inner
- }
|