I was testing go's type visibility and received unexpected behavior when I exposed a private type through a public function:
package pak
type foo struct { // shoudn't be visible to any other package than pak
Bar string
}
func NewFoo(str string) *foo {
return &foo{str}
}
// ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
package main
import (
"fmt"
"pak"
)
func main() {
// these lines should be equivalent...
var f = pak.NewFoo("Hello, World!") // this works fine...
var f *pak.foo = pak.NewFoo("Hello, World!") // ERROR: cannot refer to unexported name pak.foo
fmt.Printf("%T\n", f)
fmt.Printf("%s\n", f.Bar) // how does it know about .Bar, if it can't see pak.foo?
}
Without explicitly declaring the type of f
, it prints:
*pak.foo
Hello, World!
but with *pak.foo
it fails to compile.
Why doesn't it fail in both cases?
(this question is sort of related, but it does not answer this question)