> At Google, we require that Go programmers pass a Context parameter as the first argument to every function on the call path between incoming and outgoing requests.
This pattern demonstrates a fundamental difference between Go and languages that encourage thread-state data. The arguments for thread-state include not requiring all functions to pass such a context variable, since it is (hopefully) already populated in the thread state. The hopefully part is where thread-state becomes unpleasant, because if you want to do concurrent work, you must pass one thread's state to the other. The other thread has no guarantee that it is there, so the programmer must either hope it is or verify it, which is annoying.
The context-passing style doesn't require that kind of hope, but does require each function to pass the context to another. When I was working on a medium-sized go project, I would often need a context deep in the stack, and be forced to add it to many functions up the tree. Hence, having the standard that all functions get the context always seems excellent because it is no longer something to think or worry about and doesn't increase code length by an unreasonable amount.
I heartily agree with this recommendation and will be using it going forward in my go projects.
>Hence, having the standard that all functions get the context always seems excellent because it is no longer something to think or worry about and doesn't increase code length by an unreasonable amount.
how about new paradigm - context-oriented programming :) where, like "this/self" in OOP, ctx is always present. And looking through the posted article Google is somewhat there with context [instance level] kind of inheritance (the context tree)
> how about new paradigm - context-oriented programming :) where, like "this/self" in OOP, ctx is always present.
This is how OOP in C is done though usually its done with the context being an opaque object.
Having functions with multiple arguments that depends on other functions with multiple arguments that depends on yet other functions with multiple arguments will result is very hard to manage function dependencies sooner or later and "context-oriented-programming" solves this problem very nicely.
A function that takes a single argument as a pointer to a struct can be extended indefinitely without breaking the function API.A function that takes its arguments by individual arguments will break everytime it need to be extended by an additional argument.
>The hopefully part is where thread-state becomes unpleasant, because if you want to do concurrent work, you must pass one thread's state to the other. The other thread has no guarantee that it is there, so the programmer must either hope it is or verify it, which is annoying.
Right, so then you are in a situation where you can always rely on it implicitly, until you can't.
Much better to be consistent and force the inclusion everywhere as you mention in your second paragraph.
> At Google, we require that Go programmers pass a Context parameter as the first argument to every function on the call path between incoming and outgoing requests.
This pattern demonstrates a fundamental difference between Go and languages that encourage thread-state data. The arguments for thread-state include not requiring all functions to pass such a context variable, since it is (hopefully) already populated in the thread state. The hopefully part is where thread-state becomes unpleasant, because if you want to do concurrent work, you must pass one thread's state to the other. The other thread has no guarantee that it is there, so the programmer must either hope it is or verify it, which is annoying.
The context-passing style doesn't require that kind of hope, but does require each function to pass the context to another. When I was working on a medium-sized go project, I would often need a context deep in the stack, and be forced to add it to many functions up the tree. Hence, having the standard that all functions get the context always seems excellent because it is no longer something to think or worry about and doesn't increase code length by an unreasonable amount.
I heartily agree with this recommendation and will be using it going forward in my go projects.