Golang learning journal — (1) go run ., go build . and packages

Shelly
4 min readSep 18, 2022

--

Photo by Leone Venter on Unsplash

Introduction

Hi there! I am Shelly, a non-CS background developer since 2020. This article belongs to my Golang learning journal series. For all the related articles, you can find the links in the table of contents at the very first article of this series.

Why go run main.go shows errors sometimes?

You can use

go run .

to start the go program. However, at your very first time, you may like to try something like this:

go run main.go

and discovered that the program runs with error like this: undefined: xxx.

This is because you may have more than 1 file with package main at the first line of the file. The go run . actually runs “all” the files with package main written on it. Hence, the correct way to start the go program is

go run .# equals to 
go run *.go
# equals to
go run another_file_with_package_main_on_it.go main.go

This brings us to the next question. You may now want to add package main just on top of every file, but you will soon discover that you can’t do that if you put those other files in another folder. This has something to do with how Go manages packages.

By the way, same problem could also happen to go build , if we only specify to build main.go: go build main.go .

How do we use packages?

Packages have hierarchies

You can’t have the same package name in 2 different directories. Hence, writing package main in different files right under the project root folder is correct. e.g.

# write `package main` at:
./main.go
./xx.go
./yy.go

But the following example will be wrong.

# write `package main` at:
./main.go
./folder_x/xx.go
./folder_y/yy.go

Now read again the official document:

A package is a collection of source files in the same directory

Do you notice the word “same directory”? This is in an official document, but you perhaps need some “experience” to really notice these 2 words.
This is also why I say, if it’s your first time, reading pure official documents may not give you the “right” feeling regarding where to focus.

Can use functions directly from another file within the same package

Furthermore, files that have the same package name can use the function defined at each file, without using the “import” keyword. (e.g. if you have functionX defined at ./xx.go, you can access/use functionX directly at ./main.go without import xx .

Can import other packages using an alias or using the default name

Let’s say you have a folder structure like this:

------ main.go
------ hello/hello.go
------ go.mod

Inside main.go :

package mainfunc main() {...}

Inside go.mod :

module cardsgo 1.19

Inside hello/hello.go :

package helloimport "fmt"func Hello() {   fmt.Printf("Hello!")
}
func callName() {...}

Now you can import hellopackage atmain.go by importing cards/hello like below:

# at main.gopackage main
import (
# notice that "cards" is the module name defined at go.mod
"cards/hello"
)
func main() {
hello.Hello()
}

Notice that we can call Hello() using hello.Hell() , because Go automatically takes the package name defined at go.mod(not the folder name, although oftentimes it's the same name) as default. If we have named the package name as package hola , then although the file path is ./hello, we will need to call Hello() with hola.Hello() .

Furthermore, if I want to call hello package with a different name, I can also give it an alias when importing it. Like below, I use xxx an alias for thehello package.

# at main.gopackage main
import (
xxx "cards/hello"
)
func main() {
xxx.Hello()
}

If functions are from other packages, it needs to be capitalized

Did you notice that we have named the function inhello.goas Hello() rather than hello()? We capitalize the first letter. In Go, in order to export the function, aka — make the function available by other files that import the package, you need to make the function name’s first character capitalized. For functions that start with a non-capitalized letter, they can’t be exported.

Next article: pointers — when to pass by pointer, when to pass by value?

Thanks for reading till here. If you found the article helpful, feel free to clap multiple times on the article (one person can clap up to 50 times!), or ❤️ give me some tips following the below link ❤️. Thank you in advance :)

You are also welcome to clap for this article through liker land, so I can receive some coins on the blockchain! :)

--

--