Why do type aliases change behaviour (i.e. json.Unmarshal)?

139 views
Skip to first unread message

cpu...@gmail.com

unread,
Mar 15, 2021, 8:48:43 AM3/15/21
to golang-nuts
I've just tried doing something like this in my code:

// Token is an OAuth2 token which includes decoding the expires_in attribute
type Token struct {
oauth2.Token
ExpiresIn int `json:"expires_in"` // expiration time in seconds
}

func (t *Token) UnmarshalJSON(data []byte) error {
...
}

type WrappedToken Token

Only to find out, that unmarshaling a WrappedToken does not call Token.UnmarshalJSON which came as a bit of surprise.

I can only guess it's due to how JSON unmarshaling works, but is this the intended behaviour?

Kind regards,
Andreas

Levieux Michel

unread,
Mar 15, 2021, 9:05:53 AM3/15/21
to cpu...@gmail.com, golang-nuts
This is because per the Go spec: https://golang.org/ref/spec#Type_declarations
You're not creating an alias to Token, but defining a new type from it. If what you are looking for is an alias (meaning to have the "WrappedToken" identifier refer to the exact same type as Token), you need to do:

type WrappedToken = Token

Then all method calls on WrappedToken will be method calls on Token (since both identifier denote the same type).

But maybe that is not what you are looking for, if that's the case, there are other ways around the problem, like type embedding and such.
Hope this helps,

--
You received this message because you are subscribed to the Google Groups "golang-nuts" group.
To unsubscribe from this group and stop receiving emails from it, send an email to golang-nuts...@googlegroups.com.
To view this discussion on the web visit https://groups.google.com/d/msgid/golang-nuts/0ceb1917-af61-4259-8695-55eeb0bd6bffn%40googlegroups.com.

Jan Mercl

unread,
Mar 15, 2021, 9:07:51 AM3/15/21
to cpu...@gmail.com, golang-nuts
On Mon, Mar 15, 2021 at 1:49 PM cpu...@gmail.com <cpu...@gmail.com> wrote:

> type WrappedToken Token

Note that this is not a type alias. WrappedToken is a new type. Even
if its underlying type is Token, WrappedToken does not automatically
have any methods of Token.

> Only to find out, that unmarshaling a WrappedToken does not call Token.UnmarshalJSON which came as a bit of surprise.

To be less surprised, check the language specs that say this is how
the type system works.

cpu...@gmail.com

unread,
Mar 15, 2021, 11:49:28 AM3/15/21
to golang-nuts
Thank you @Michel. Disturbing that I keep making the same mistake again...
Reply all
Reply to author
Forward
0 new messages