
How to ship production-grade Go - cpeterso
https://www.oreilly.com/ideas/how-to-ship-production-grade-go
======
tedsuo
Oh god, there is some terrible advice in that article.

1\. Don’t wrap errors, log.

Errors have two purposes - control flow for your application, and information
for the developer and operator. If you are already logging the flow of your
program, there is no need to wrap an error and create a call stack - you
already have the call stack. If you cannot follow the control flow from your
logs, you need to improve your logging, because you will also need to debug
production problems that do not produce a literal error object.

And if you want more causality than you can get out of your logging, consider
upgrading from logging to tracing. I contribute to
[http://opentracing.io](http://opentracing.io) so naturally that’s the tracing
API I would suggest you look at.

2\. Do not do anything with panics except recover from them or exit.

If you have a panic that you cannot recover from (and in general, that should
be all of them), then it means your application is in a unknowable state.
While Go is not as unsafe as C, any and all state in your program could be
bad, and it is completely unclear what is still working and what is not.
Nothing you do at this point is safe. For the love of god, do not hang your
application and prevent it from exiting by trying to send a Slack message.
Your goal should be to restart your program from a fresh clean state as
quickly as possible, not to tie it up on the way out. Let the program exit and
have an external monitoring program, whose state is NOT corrupted because its
in a separate process, do all of the triage and reporting.

~~~
paulddraper
(1) I see this all the time.

An error is logged and propogated, then logged and propogated, then logged and
propogated, then pretty soon your logs are 50x copies of themselves and the
flood of logging sweeps you away.

You either (a) know what you to do about an error and log it or (b) you don't
know what to do and propogate it.

An error should be logged eventually, but it shouldn't be logged 20 times.

~~~
tedsuo
I totally agree, there's no need to log that you bubbled an error. My
recommendation is to have the function that generates the error also log it
internally. That way, you don't need to log any returned errors at all, unless
you are calling a 3rd party library that can't log it's own error.

~~~
twblalock
Error handling, which includes logging the error, should almost always be the
responsibility of the caller. Only the caller knows why the call was made, and
only the caller knows the impact of the error on what the caller is trying to
do.

~~~
paulddraper
Exactly.

You run a process that exits with a non-zero code. Is that an error that
should be logged? Or just informational? (E.g. `diff`.)

You request an HTTP resource that doesn't exist. Loggable error? Or normal
result?

Only the caller knows.

~~~
tedsuo
I recommend separating collection from instrumentation. Always instrument at
the source, so that you can instrument the flow of your entire application. If
the caller decides there is something about the code flow that is worth
recording, it can trigger collection of the entire trace.

------
tyingq
I'd add another, something like "Be Aware of the Ramifications of Partial
HTTP/S Implementations".

Because it's so easy to expose http/https in golang, I see a fair amount of
code that takes the easy path of handling GETS and not doing much else. No
support for HEAD, or compression, proper mime types in Content-type, or
lacking Cache-Control headers, Etags, 304 responses, etc. Go can do all these,
of course, but I see them missing often.

I've seen, for example, blogs, that (probably not on purpose) defeat browser
caching. Not great for performance, or your egress bill.

~~~
niftich
I realize that much of the Go community is hesitant about the sort of third-
party code that intentionally constraints the problem-space by restricting
choice and then calls your code at a few well-defined points; preferring to
call out to libraries instead (vs. the other way around); but what solutions,
if any, are widely utilized to avoid the above situation?

~~~
omginternets
I quite like [http://echo.labstack.com](http://echo.labstack.com)

I quite like it because you can access the net/http constructs
(ResponseWriter, Request, etc) if you really need them, but in most cases it
removes a lot of boilerplate.

------
shusson
> Test more than you think you should

I think this is a dangerous way of thinking. Writing more tests does not
necessarily improve code quality or decrease the risk of defects. A focus on
coverage can lead to bloated tests which end up taking more time to maintain
than the original code.

------
mbrumlow
Here she talks about it on a pod cast if you want to hear her talk about it a
bit.

[https://dev.to/gotime/42-race-detection-firmware-and-
product...](https://dev.to/gotime/42-race-detection-firmware-and-
productiongrade-go-with-kavya-joshi)

------
rebase
The author is actually a fairly junior developer (graduated in 2013), but I
must hand it to them for taking the initiative of getting published by such a
large entity (oreilly media) and locking down speaking engagements (GopherCon)
so early in their career!

They have a bright future even if this article does not contain the most
accurate advice.

~~~
AvenueIngres
Meh. I don't want to take it away from the author, it certainly shows they're
motivated, but I have a hard time this isn't a textbook example of how
publishers/conference organisers are trying hard to get "underrepresented"
token demographics in cover. Even if it is to perform trivial talks (a
glorified "intro to channels in golang"... really!?) or write platitudes like
said article. They're clearly underqualified to distillate advice to anyone,
maybe interns/students could benefit from this though.

------
falcolas
So, the same way you ship any code: robust against errors, well tested, well
instrumented.

Useless, ad ridden article, frankly.

~~~
jasode
_> same way you ship any code_

Well, the article is specifically about Go instead of generalized universal
advice so she put concrete syntax examples using the Go language (vs "any
code" in any language). There are examples to wrap errors, report panics, and
using structured logs. The specificity of real code snippets is useful.

 _> Useless, ad ridden article, frankly._

I'm guessing this is the real root of your complaint. In my view, the ads are
tucked away to the side, not obnoxious, and are simply related to other
O'Reilly offerings.

The actual _programming advice_ in the article looks like it has value and I
think you're being unfairly harsh.

~~~
falcolas
The advice may have Go examples, but is still very generic advice. It's also
not really about shipping Go programs, it's about general hardening of
programs.

And to mirror a sibling comment, on mobile the ads are interspersed every
couple of paragraphs, making it very hard to follow the flow of the article.

Unfairly harsh? Clickbait headline, generic advice (with just enough Go
examples to "justify" the title), aggressive styling to hide ads in the flow
of the rest of the article... I disagree. I'm perhaps not being harsh enough.

~~~
NiceGuy_Ty
I just scrolled through on mobile (materialistic app) and only saw one ad.
Seems to me like you're being hyperbolic.

~~~
falcolas
So you're looking at it on an app that touts its readability mode, and think
that _I_ must be "hyperbolic"?

I can count at least three inline O'Reilly ads, with adblock enabled.

