Skip to content

Instantly share code, notes, and snippets.

Embed
What would you like to do?

A problem runtime error due to lack of Generics

Introduction

This document is written my experience and thinking about Go.
Go is simple. And it is good that performance in runtime. But in Go I had to write code that is unsafe in some cases.I think that it is caused by lack of Generics.
I will write about them.

Case of json.Unmarshal

I was writing a common code with json.Unmarshal.
It’s written as follows.

jsonText := `
{
    "foo":"bar"
}
`
var fooBar FooBar

//error in runtime
//json: Unmarshal(non-pointer main.FooBar)foo:
if err := json.Unmarshal([]byte(jsonText), fooBar); err != nil {
    fmt.Printf(err.Error())
}

//output is "foo:"
fmt.Println("foo:" + fooBar.Foo)

This code is wrong. The json.Unmarshal's result is error. Because the argument of fooBar is not pointer.
The correct code as follows.  

jsonText := `
{
    "foo":"bar"
}
`
var fooBar FooBar

//err is nil
//Because argument of fooBar is pointer.
if err := json.Unmarshal([]byte(jsonText), &fooBar); err != nil {
    fmt.Printf(err.Error())
}

//output is "foo:bar"
fmt.Println("foo:" + fooBar.Foo)

Case of gorm

I got another error when I was writing code with gorm at work.
I refrain from writing detailed code due from company intention.
Describing only the necessary parts as follows.

type FooBar struct {
	Foo string
}

type FooBar2 struct {
	ID  uint
	Foo string
}

func main() {
	db, _ := gorm.Open("mysql", dbArgs)
	db.Create(&FooBar{Foo: "test1"}) //Succeed
	db.Create(FooBar{Foo: "test2"})  //Succeed
	db.Create(&FooBar2{Foo: "test3"})//Succeed
    db.Create(FooBar2{Foo: "test4"}) //An error will occur (using unaddressable value)
    
    /*
        It seems to struct with numeric ID will be auto incriment and primary key by default in gorm.
        So, the FooBar2's variable should be written ID from gorm and addressable.
    */
}

Then, I wrote code at work as follows.

if /* Rarely become true */ {
    db.Create(FooBar2{Foo: "test4"})
}

This code is Later there will be serious runtime probrems. This only has to write a test code and take countermeasures. But The majority of other statically typed language make such code a compile error with Generics.

Conclusion

  • These problem can be compile error. but An runtime error occur in go.
  • Need type constraint (eg: Generics, or other type system.)
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
You can’t perform that action at this time.