I don’t understand why people try to unit test handlers. Use integration tests for this and the real services you depend on, use unit tests to test functions and business logic, not glue code like handlers. If you build a vast complex web of mocks attempting to reproduce behaviour you’ll only test the happy path and failures you can think of. It’s lots of work for no benefit.
This is interesting, but seems a little unnecessarily complex in places. Not sure they need to stray so far from Go. You can pretty much do exactly the same thing in golang just with a check(err) function which panics instead (tried to paste this into this comment as code but the formatting wasn't so good (no newlines)).
Not sure how profitable comparisons of languages like this are, but it is a choice we all face. Go mostly leaves things out (except perhaps a better concurrency story than python), so in a feature by feature comparison, it's going to look less impressive at first.
It's certainly less easy to get up to speed in if you're learning programming for the first time, and in different domains it has completely different strengths (for example python has far more mature science and data analysis libraries, because lots of people are using it for that).
The biggest problem I had was getting my head around pointers vs method receivers and which to use (I ended up using pointers for almost everything). Also was tripped up by map key iteration order changing. Otherwise it's been pretty plain sailing learning go compared to some other languages.
A somewhat click-baity title, but definitely worth a read. It does make a good point that though channels are the thing everyone has heard of Go using, the simpler mutex can be very useful. The docs for the sync package don't make it sound very friendly, but it is actually easier to understand for many simple use cases of just protecting access to a struct or map across goroutines. They make it sound in the go docs like you should never be using a mutex:
Package sync provides basic synchronization primitives such as mutual exclusion locks. Other than the Once and WaitGroup types, most are intended for use by low-level library routines. Higher-level synchronization is better done via channels and communication.