In most Go programs I have seen, even those that have just one package, the names of types are written with a capital letter, which makes them exported.
Is this just a convention to make clear that they are types or is there a need for all types to be exported?
Initially I was going to put examples here of exported types, but looking around some popular Go projects I only found exported types so far. So any example of an unexported type in a reasonably large Go project would be welcome.
After all, many nouns and verbs are small (e.g., dog, go), but these words must still be capitalized. The small words we are referring to in this case essentially include articles, conjunctions, and prepositions, which should not be capitalized (again, unless they are the first word of a title).
Go uses capitalization to determine identifier visibility. Those that start with a lower case letter are package-private, and those that start with a capital are package-public.
Capitalized Identifiers are exported. The capital letter indicates that this is an exported identifier and is available outside the package.
There are no proper nouns in the example above. Words like democracy, government and authority refer to general concepts and categories rather than specific names. Specific periods and named events in history are proper nouns and thus capitalized. Centuries, however, stay in lowercase.
The type starting with an uppercase letter are exported to other packages. Those starting with a lowercase letter can be used only inside the package. Important note: it is possible to export an interface without exporting the struct that implements it.
It is not a convention to export types. Only export them if you allow them to be used outside the package. In the example you provided, there was no need to export the Server
type, because it has no exported field or methods.
Export only the types that are part of the contract with the client. Exporting types that are only used internally is a mistake and is confusing in the documentation.
Edit:
A little clarification about the Server
type. It implements the http.Handler
interface (must define ServeHTTP(http.ResponseWriter, *http.Request)
), so it is possible to make it not exported and use the interface as the return type of NewServer
function.
Types can be private.
Having a public function returning a private type however does not work. As long as the type is only used package internally, I keep it private.
EDIT: In your example, Server has to be public because it is returned by public functions and thus used outside the package. The function NewServer returns *Server.
EDIT for new example:
In the new example this is the main package. It can't be imported anyway.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With