107

I am studying a sample Go application that stores data in mongodb. The code at this line (https://github.com/zeebo/gostbook/blob/master/context.go#L36) seems to access a user ID stored in a gorilla session:

if uid, ok := sess.Values["user"].(bson.ObjectId); ok {
  ...
}

Would someone please explain to me the syntax here? I understand that sess.Values["user"] gets a value from the session, but what is the part that follows? Why is the expression after the dot in parentheses? Is this a function invocation?

starball
  • 20,030
  • 7
  • 43
  • 238
akonsu
  • 28,824
  • 33
  • 119
  • 194

1 Answers1

145

sess.Values["user"] is an interface{}, and what is between parenthesis is called a type assertion. It checks that the value of sess.Values["user"] is of type bson.ObjectId. If it is, then ok will be true. Otherwise, it will be false.

For instance:

var i interface{}
i = int(42)

a, ok := i.(int)
// a == 42 and ok == true

b, ok := i.(string)
// b == "" (default value) and ok == false
julienc
  • 19,087
  • 17
  • 82
  • 82
  • 12
    @akonsu, It worth mentioning that the idiom used for type assertion is known as "comma ok" (`if value, ok := try_to_obtain_value(); ok { ...`), and is explained, for instance, in ["Effective Go"](http://golang.org/doc/effective_go.html) -- see the section called "Maps". I should add that this whole document is a must read for any wannabe gopher. – kostix Jun 30 '14 at 15:54
  • 12
    also worth mentioning that while `b, ok := i.(string)` works like _TryAssert_, `b := i.(string)` immediately panics if assertion is invalid. – stratovarius Mar 23 '18 at 08:16
  • thanks, what about this `sess.Values["user"].(type)` it returns the type, right? – tim Sep 10 '20 at 21:34
  • To be honest, this is a somewhat useful answer, and the comment by @kostix about `comma ok` is helpful. But it doesn't develop the interface aspect as fully as the user's example does. I'll soon have the ability to do that myself but since this question is closed I'll leave it there. – Oliver Williams Jul 08 '21 at 01:26