First let's consider the following:
func process(body io.Reader) {
fmt.Printf("body == nil ? %+v\n", body == nil)
}
func main() {
var body *bytes.Buffer
fmt.Printf("body == nil ? %+v\n", body == nil)
process(body)
process(nil)
}
And here's the output:
body == nil ? true
body == nil ? false // Did you get this right?
body == nil ? true
Another example:
type Container struct {
Reader io.Reader
}
func processContainer(container Container) {
fmt.Printf("container.Reader == nil ? %+v\n", container.Reader == nil)
}
func main() {
var body *bytes.Buffer
processContainer(Container{Reader: body})
processContainer(Container{Reader: nil})
}
Output:
container.Reader == nil ? false // Did you get this right?
container.Reader == nil ? true
The explanation for this is at https://golang.org/doc/faq#nil_error.
A naive solution is to make the == nil
test just return true if the interface object contains nil
value. But this would violate transitivity of ==
, as it would assert two objects with nil value but different interface types true under ==
.
However, I wonder if there should be an IsNil()
method on all interface types, which would solve this issue?
Another example, this line from Go http client, can catch you unexpectedly:
https://github.com/golang/go/blob/master/src/net/http/client.go#L545
So if you call it like this
var body *bytes.Buffer
http.NewRequest(method, path, body)
You'll get a nil pointer exception, even though, by the look of the source code, this shouldn't happen.
Edit
Sorry I referenced the wrong line of the Go http source, now corrected. But the example still holds.
Edit 2
I've highlighted my question to make it clear what I'm asking.
First read this related question: Hiding nil values, understanding why golang fails here
You can check if the interface value itself is
nil
by comparing it tonil
.If you want to check if the value wrapped inside a non-
nil
interface isnil
, you can use reflection:reflect.Value.IsNil()
.See this modified example:
Output (try it on the Go Playground):
If you want a "unified"
IsNil()
function which tells if either isnil
: