Shifting from JavaScript to Go, I’ve encountered a few “whaaat?!” moments that eventually became “haaa, ok!” moments. To put it more eloquently, if you’re a JavaScript/TypeScript developer and thinking about trying Go, this article is for you.
Working at Orbs, a blockchain for consumer apps, I’ve taken part in contributing to the reference implementation in TypeScript — I’ve implemented a consensus algorithm from scratch. Recently, we’ve started working on the reference implementation in Go language. My task is to port the consensus algorithm to Go — you can see the converted code in progress here.
for
loops and if
statements. I’d say that Go is something between C and JavaScriptThere are many other differences in addition to the following list, but I have found that these are the most interesting for developers that come from JavaScript background.
Go is using pointers. Yes! Pointers. BUT WAIT! Don’t stop reading.In order to be able to do GC properly and avoid reading/writing out of memory, Go pointers do not allow any arithmetics on pointers. You can’t do p++ on a pointer to move it to the next item in an array, like you would do in C. But you do have all the other benefits of pointers (References)
One key thing you should understand is that Go is very opinionated. For example regarding syntax, in Go you MUST put the {
in your if
statement at the same line. Not doing so will result in a compilation error!
Go is structured in a way that classes, inheritance, and polymorphism are not possible (or at least very difficult). What started as “I don’t like that!” became “Hmmm, maybe that’s even better!” when I understood that Go is pushing you to use composition instead of inheritance.
In Go, there are many shortcuts. It almost feels as though anything that can be written in Go with fewer characters.
// The long wayvar age Int = 42
// The short wayage := 42
This makes your learning curve steeper, but if you stick with Go, you’ll (probably) eventually like it.
Go is typed, but no generics. This means that you don’t have the lodash-like map/reduce functions. This “Whaaat” did not end with “haa ok”…It is planned for future versions of Go.
When I first installed Go and wanted to create a project, I thought that I’d create a folder and put all my code there, build it, and run…nope. This is not how Go usually operates. All your projects should be under the same global src
folder, under a folder unique to your project, usually your Github path (for example: ~/go/src/github.com/gilamran/PBFT-Typescript
)
There are many issues with this approach like the dependencies of your project being under the same src
folder and versions becoming a big issue.
Golang does support vendor
folder (Similar to node_modules
in JavaScript), but it will fetch the master
branch…
There are many attempts to solve this, but know that currently dependencies in Go can be painful.
Golang loves tests, so much so that when the compiler detects test files (by file name _test.go), it will automatically exclude the test code when you build.
Before you dive in, let me give you a short preview of how we do things:
,
after the value.
var arr = [3]int{1,2,3,}
{
of if
is at the same line
var ThisIsPublic = "You can access this variable from outside"var privateValue = "Accessible only inside the current package"
// common typesvar num int = 5var pi float32 = 3.14var name string = "Gil"var isActive bool = true
// without initialisationvar num int // value is 0var pi float32 // value is 0var name string // value is ""var isActive bool // value is falsevar person Person // value is nil
// one linervar one, two, three boolvar a, b, c = true, "Hi", 0.5 // you got the point
// short version with inferencenum := 5 // `var` is omitted, and type is inffered
// you should be familiar with thisfor i := 0; i < 100; i++ {sum += i}
// whilefor sum < 1000 {sum += sum}
// infinite loopfor {}
/// yep, no parenthesisif age < 18 {return true} else {return false}
// switch no need to add `break`switch state {case "ACTIVE" :deactivate()case "INACTIVE":activate()default:fmt.Printf("Unknown state")}
// simple functionfunc add(a int, b int) int {return a + b}
// multiple return valuesfunc swap(a, b int) (int, int) {return b, a}
// named return valuesfunc namedResult(input int) (output int) {output = 0...output = 42...return}
Of course, this is the just tip of the iceberg. There are many other advanced things like channels, structs, and interfaces, but I’ll leave those for a future post.
Go is very interesting, very fast, and has an amazing GC. It really shines when talking about concurrency and it is very opinionated about how you write code. On the down side, the package management is not spectacular, and the lack of Generics is a bit annoying.
So, if you want to do something for the server, and you want it to work very fast, Go is a good choice.
Like what you read? Check out our GitHub projects and join the community:
orbs-network/orbs-network-go_Orbs platform reference implementation in Go. Contribute to orbs-network/orbs-network-go development by creating an…_github.com
orbs-network/orbs-spec_Orbs platform protocol and service specifications. Contribute to orbs-network/orbs-spec development by creating an…_github.com
orbs-network/orbs-network-typescript_Monorepo for Orbs platform reference implementation — orbs-network/orbs-network-typescript_github.com
orbs-network/lean-helix-go_Go implementation of Lean Helix consensus algorithm - orbs-network/lean-helix-go_github.com
Join the Orbs community: