This is work in progress…

https://golang.org/doc/effective_go.html

https://willowtreeapps.com/ideas/the-pros-and-cons-of-programming-in-go

https://grpc.io/blog/grpc_on_http2/

https://github.com/golang/go/wiki/Projects

The most important lesson

Use GoLand as your IDE….

Remember its native!

At the first hurdle I messed up. If you are on windows 64 bit then download the amd64 windows zip, otherwise delve (the debugger) won’t understand your architecture.

Go notes

Just cribbed notes as I set it up for the first time.

Env setup

Use the windows zip - 64 bit image please. Set GOPATH and add to the PATH.

BUT, see below, because I found it easier to use git bash actually. Visual Code refused to behave on Windows with go get unless I started from git session.

set GOROOT=c:\tools\go
set GOPATH=c:\tools\go-work
set PATH=%GOROOT%\bin;%GOPATH%\bin;%PATH%
#Proxy environment variable
set http_proxy=http://user:password@host:port/
set https_proxy=http://user:password@host:port/

See comment on GOPATH below.

Then start up VisualCode with the %GOPATH% folder, and create a src/hello folder. Then create the hello.go as per the starter guide and install the go extension for Visual Studio Code when it prompts you.

In visual code, open File->Preferences->Extensions->go and click to set go.goroot in settings.json.

{
  "go.goroot": "c:\tools\go"
}

First commands:

# Build the compiled package in the local build cache, for use as a library.
go build
# Installs it into the %GOPATH%/bin dir, which should be in your path
go install github.com/PendraRed/hello
go clean -i

or

# Build the compiled package in the local build cache, for use as a library.
go build
cd github.com/PendraRed/hello
# Installs it into the %GOPATH%/bin dir, which should be in your path
go install

Visual code

Visual Code had problems, so I set up git bash with a .bashrc in my home dir, which read like:

export GOROOT=/c/tools/go
export GOPATH=/c/all_dev/go-work
export PATH=$GOROOT/bin:$GOPATH/bin:$PATH
alias vcode='"C:\\Program Files\Microsoft VS Code\Code.exe"'

cd $GOPATH/src/
echo "Type vcode to open Visual Code"

Then you can run all the stuff below within visual code, ie open Git Bash on windows and type vcode - the alias I set up above.

Note that there are configs in Visual Code to set this up too, but the googling I did failed to find in fast enough, and I’m in a hurry. Some example commands Visual Code wants to run:

go get -v github.com/sqs/goreturns
go.exe get -u -v github.com/mdempsky/gocode
go get -v github.com/rogpeppe/godef

A warning triangle appears saying - Go analysis tools missing, click on it and install them. These are the ones:

Installing 9 tools at C:/all_dev/go-work\bin
  gopkgs
  go-outline
  go-symbols
  guru
  gorename
  dlv
  gocode-gomod
  godef
  golint

A note on architecture

Note, if dlv fails to install its probably because you downloaded the 32 bit rather than the 64 bit zip file when you installed go. The helpful error is: ‘disasm.go:12:14: undefined: archInst’

Which should read ‘please install 64 bit go for delve to run’, so the zip to install from is: go1.12.5.windows-amd64.zip (or whatever version you are now on)

GoLand

Googling found the JetBrains go IDE, which is simply better and worth the money. So, I ditched Visual Code.

Also, set a User Env variable, ie search for ‘env’ in the windows search box, and open up user envs. Set GOARCH to amd64. You will need it to be this rather the 32 bit intel value of 386. (everyone is 64 bit surely?)

GOPATH

Sadly most of Go is simply not in modules yet. So the link below is basically wrong: https://blog.jetbrains.com/go/2019/01/22/working-with-go-modules/

Instead, set up two standard directories - one for fresh downloads, one for standard packages you like and then finally use a path for the project you are working on. i.e. follow what he says here: https://dmitri.shuralyov.com/blog/18

The tutorial - locally

From the tutorial:

go get golang.org/x/tour
tour

Coding

All code is in GOPATH, each git root is under the %GOPATH%/src directory.

%GOPATH%/
  bin/
  src/
    github.com/PendraRed/hello

Executable commands must always use

package main

Project structure

There is more to it than first meets the eye.

https://www.ardanlabs.com/blog/2017/02/package-oriented-design.html

Exported functions

All start with a capital letter, otherwise you cannot call them.

testing

Files end in _test.go and functions are called Testxxxx.

Debugging

Well, I presumed it would be like adb hell. But it isn’t, once Visual Code had delve installed, then the Debug menu appears, and you can set breakpoints, step through the code, view variables and so on. Its all fine.

BUT, I wrote this before moving to GoLand and paying money. Forget Visual Code.

repositories

Go can use go get to download packages from remote repos. If you are on windows and dont have admin then you need to edit the git config to use a writeable dev dir.

Or, just use git bash to get remote stuff.

IDE

So, Visual Code was going to be my IDE. But what about debugging?
https://github.com/Microsoft/vscode-go/wiki/Debugging-Go-code-using-VS-Code

Hmm. looks clunky. So GoLand from Jetbrains seems perfect.

Code Format

gofmt –help

It really does like linux. So, in cygwin it works because it has a diff command. c:/tools/go/bin/gofmt -d xxx.go

gotests

Handy code to generate tests for files or packages, nicely integrated with GoLand.

https://github.com/cweill/gotests#installation

go get -u github.com/cweill/gotests/…

However, in my new mantra of DO NOT USE FRAMEWORKS, I ditched it soon after. My Go now imports very little unless its core or REALLY REALLY useful.

Random notes

.len gives lengths of strings and arrays. .cap gives the capacity. A slice is a descriptor for a contiguous segment of an underlying array. Uninitialised value is nil.

Structs have fields, which may be named explicitly or be implicite EmbeddedField.

type Locker interface { Lock() Unlock() }

Labels are used to break, continue and goto.

functions are not associated with a type. Methods are associated with a type, by defining them with a receiving type. Don’t mix pointer receivers with value receivers. Value receivers are on copies so you can’t edit values, so, well, I’m just using pointer receivers now, avoids issues.

Go statements will execute the goroutine independently and its results will be discarded ( its a simpler threading model, and you chat to the goroutine using a channel).

Selects will process channels with available input - it will process any one of them in a pseudo random selection.

defer will cause the deferred function to execute when the enclosing function ends. However, the parameters are executed at the time the function is deferred. Defered functions are placed on a lifo stack.

Panic will roll up the stack and terminate the goroutine. However, when exiting a stack frame any defered functions can call recover, and then return normally to stop the panic from rolling further up the stack. The deferred functions may themselves invoke another panic after calling recover to continue the failure.

Slices

The Go tutorial is great. Extracting this tho: The make function allocates a zeroed array and returns a slice that refers to that array.

a := make([]int, 0, 5) // len(a)=0, cap(a)=5

read this: https://blog.golang.org/go-slices-usage-and-internals

ie use slices and not arrays.

Pointer receivers and interfaces

Being an OOP OOD etc person who was coding when C++ was new, I really got into polymorphism. In Go, when doing microservices try to unlearn all that. Keep your code as simple as possible. Avoid class hierarchies.

Remember Foo is public, and foo is not. Keep your interfaces clean through caps (public Cap(), private lowerCase()). So far, this has been enough.

However, if you have an interface you can do switches on types and also check type using:

https://tour.golang.org/methods/15

https://tour.golang.org/methods/16