It is a very long doc, but that also shows that concurrency has so many patterns one might like.
My own pattern is typically
1. Decide level of parallelism ahead of time and start workers (that many `go X()` invocations
2. Setup sync.Waitgroup for the same count
3. Create two channels, one for each direction.
4. Job itself needs some sort of struct to hold details
Most of my jobs don't support mid-work cancelation, so I don't bother with anything else.
Study the generic reader/writer implementations in the io module. (On my system, those sources are in /usr/lib/go/src/io.) The io.Reader and io.Writer interfaces are very simple, but very powerful because of how they allow composition. A shell pipeline like `cat somefile.dat | base64 -d | gzip -d | jq .` can be quite directly translated into chained io.Readers and io.Writers.
Another example of this is how HTTP middlewares chain together, see for example all the middlewares in https://github.com/gorilla/handlers. All of these exhibit one particular quality of idiomatic Go code: a preference for composition over inheritance.
Another quality of idiomatic Go code is that concurrent algorithms prefer channels over locking mechanisms (unless the performance penalty of using channels is too severe). I don't have immediate examples coming to mind on this one though, since the use of channels and mutexes tends to be quite intertwined with the algorithm in question.
This looks like some C++ or Java developer trying to shoehorn OOP concepts into a language that is not OOP-first. Just to pick out one particularly egregious example:
> Registry: Keep track of all subclasses of a given class