Go Programming Basics

$GOPATH and $GOROOT

$GOROOT: This is an environment variable which stores the path where your Go installation is present if you have customized it. $GOPATH: The Go universe for your machine. The idea is that all your Go code should reside in a directory tree so the code isn't lying around in random places.

My $GOPATH is /usr/home/suraj/Go, it has the following structure

  • pkg: The libraries which'll be imported in our code, there is a .a file created at the respective path.

  • bin: The binary file of our project will be installed here on calling go install in the project folder

  • src: Will hold the actual code, if you have a github account, then you can create a folder tree inside like

go

  • src

    • github.com

      • thewhitetulip

        • wshare

        • picsort

    • golang.net

    • sourcegraph.com

  • bin (binaries)

    • wshare

    • picsort

  • pkg

Go takes this unique approach so that all the Go code is well organized and not thrown in a haphazard manner. This makes it easy to locate code for humans and software alike.

Packages

Packages are one or more file(s) which contains Go source code. They can be named anything. Each package except the main needs to be a in a distinct folder on the GOPATH. Each Go program starts with the package declaration. As a convention, package names are short and self documenting. The Format package is called fmt since it is short and concise that way.

There can be any number of files in a package directory, but only one file with the main function. While building the code, the compiler starts with the main function in the main package.

Package naming

import "views"

When the Go compiler executes this statement, it'll try to find the library called "views" in $GOROOT/views or $GOPATH/src/views. It'll complain if it doesn't find the library in either of the two paths.

The actual package name is just "views", but for evaluating it, it's the absolute path of the package from the $GOPATH/src directory.

For the Tasks app, it resides in $GOPATH/src/github/thewhitetulip/Tasks, thus, my packages will lie within the Tasks folder. This makes it easy for distributing the libraries.

Note: Bad Workaround.

There is a workaround for this by treating $GOPATH/src itself as your entire project and having libraries directly inside it. This is not the Go way of doing things. Please do not do it.

Internal deployment

We'll follow the standard practice and put our code in $GOPATH/src/github.com/thewhitetulip/Tasks folder. While testing our app, we need a deployment version. I used Tasks while building Tasks, I have made a folder ~/Tasks and here I keep the deployment version of Tasks, which contains the binary version and the static files. Every new build in the src gets pushed in this folder.

Running a server

Webapps are deployed on IP addresses & ports. It is possible to run multiple websites on a single machine on different ports. There are an awfully large number of ports on each computer. Typically we choose a large port number like 8000 so it doesn't affect some other applications. Certain ports are restricted and need sudo access, like 80.

The IP address we bind the server to can be a public or private. Public means using ":8080" or "0.0.0.0:8080". Private means "127.0.0.1:8080"

  • Public IP means that any computer in the same network can access the web app.

  • Private means only your computer will be able to access it.

//Public

log.Fatal(http.ListenAndServe(":8080", nil))

//Private

log.Fatal(http.ListenAndServe("127.0.0.1:8080", nil))

Note: 127.0.0.1

127.0.0.1, called localhost, is a special IP address which is given to every machine to refer to itself. It is called as loopback address. It doesn't matter if you are connected to the network or not, your machine will always have this IP address, so if you are want privacy use 127.0.0.1.

If you do want your web application to be accessible via the network, use 0.0.0.0:8080 or just :8080, when you give just the port number, the Go language assumes the IP address the machine is '0.0.0.0' and not 127.0.0.1.

MVC Pattern

When I started learning building web apps in Django, I first read about the MVC pattern, the models, the views and what not. But that knowledge was to be assumed by me and I had no idea why that decision was made, along with that Django works like magic, one has to adapt to it's quirks. Hence while programming in Go, it'll be immensely benefitial to grow up to the MVC pattern by starting out small. The first app should entirely reside in the main.go file, then slowly, as the app grows, it needs to be structured well, so the all the handlers go into a views package, templates go in a templates folder, database related entities go in another package.

Learning by doing and experimenting is the best way. Challenge the status quo.

-Previous section -Next section

Last updated