Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Formatted errors.New

Tags:

formatting

go

I would like to implement a version of errors.New that accepts the same parameters as fmt.Sprintf To do so I wrote the following function:

func NewError(format string, a ...interface{}) error {
    return errors.New(fmt.Sprintf(format, a))
}

However, a becomes a single array parameter inside NewError() thereby causing Sprintf() to fill out just a single parameter in the format string. How can I force a to be interpreted as a variable number of arguments?

like image 445
Alex G. Avatar asked Nov 16 '14 14:11

Alex G.


People also ask

How do I create a new error in Go?

The easiest way to create custom errors in Golang is to use the New() function which is present in the errors module of Golang.

What does %w mean in Golang?

Use %w instead of %v or %s : As of Go 1.13 (or earlier if you use golang.org/x/xerrors), you can use the %w verb, only for error values, which wraps the error such that it can later be unwrapped with errors. Unwrap , and so that it can be considered with errors.Is and errors.As .

How do you wrap an error in Go?

In Go 1.13, though, Go added support for wrapping and unwrapping errors as part of the standard library by adding the errors. Unwrap function and the %w verb for the fmt. Errorf function. In this section, you'll update your program to use the %w verb to wrap errors with more information, and you'll then use errors.

How do you use FMT Errorf?

To use this function, you must import the fmt package in your file and access the Errorf function within, using the . notation: fmt. Errorf . Here, Errorf is the actual function, while fmt is the Go package that stores the definition of this function.


1 Answers

fmt.Errorf already does what you are trying to do. Looking at its source, you can see what went wrong:

// Errorf formats according to a format specifier and returns the string
// as a value that satisfies error.
func Errorf(format string, a ...interface{}) error {
        return errors.New(Sprintf(format, a...))
}

Note your code is missing the ... after a. From the spec:

Passing arguments to ... parameters

If the final argument is assignable to a slice type []T, it may be passed unchanged as the value for a ...T parameter if the argument is followed by .... In this case no new slice is created.

Given the slice s and call

s := []string{"James", "Jasmine"}
Greeting("goodbye:", s...)

within Greeting, who will have the same value as s with the same underlying array.

like image 51
Tim Cooper Avatar answered Oct 01 '22 16:10

Tim Cooper