I don’t agree with that. The entire premise of RAII in C++ is to ensure the proper management of resources in the context of exceptions. Sure you can write code that doesn’t do that but it would be incorrect (and difficult to debug). But how can you manage that in a library situation? The is no “throws” type declaration, so how can you be certain that the panic is actually raised by your code if you’re calling library routines in the same function? I guess you could wrap every call but that seems tedious - so it seems more “you can’t use panic/recover if you call ANY code not your own” - which also seems difficult to ensure.
You call panic with a value of a type that you define, and you check for that type when you call recover. See encoding/json or text/template.
Wouldn’t it be better (at least safer) to make the standard that you need to use defer to ensure resources are clean as ANY line might panic? or you need to run your app in a “any panic crashes mode” - which again seems problematic for internal library code.
Sure, that is ideal, but it's frankly pointless to expect everybody to write Go code like that. People empirically can't write C++ code like that, and C++ has more support for it than Go does.
Style recommendations need to be achievable.
Ian
Anyway I figure the ship has sailed but this seems an unfortunate gap.
Hmmm. Seems like there shouldn't be a panic and recover in the language then - just always abort - or things are too risky. Or make it a private stdlib localized/internal capability.
There is no problem with recovering your own calls to panic, and that is a useful technique. It is used by, for example, encoding/json.
For that matter recovering a panic to log additional information can also be useful, as long as you don't try to continue executing normally.
Ian
> On Dec 8, 2025, at 6:36 PM, Ian Lance Taylor <[email protected]> wrote:
>
> On Mon, Dec 8, 2025 at 3:23 PM Robert Engels <[email protected]> wrote:
>>
>> Hi Ian. Can you add more detail on “leave data structures and locks in an inconsistent state”. Isn’t that the purpose of defer - especially in the context of code that may panic - to ensure that is not the case?
>
> Yes, defer can indeed be used that way. Still, I believe what I said
> is true: Go code in practice does not attempt to be safe in the
> presence of panics in code that it calls. I will stress "in practice."
>
> Ian
>
>> On Dec 8, 2025, at 1:37 PM, Ian Lance Taylor <[email protected]> wrote:
>>
>> On Mon, Dec 8, 2025 at 11:25 AM Max Claus <[email protected]> wrote:
>>
>>
>> I recently discovered that I had a misconception about how panic recovery works, especially in HTTP handlers. I wrote an article explaining that misunderstanding and suggested using more recover calls for panics in goroutines started from HTTP handler requests (link to article). That seemed like a reasonable approach based on the http package documentation:
>>
>> If ServeHTTP panics, the server (the caller of ServeHTTP) assumes that the effect of the panic was isolated to the active request. It recovers the panic, logs a stack trace to the server error log, and either closes the network connection or sends an HTTP/2 RST_STREAM, depending on the HTTP protocol. (reference)
>>
>>
>> Reading that, I thought it would be a natural pattern to follow the same logic for goroutines started from HTTP requests. However, the feedback I received on Reddit from other engineers suggested that this is considered a bad practice, and that the built-in recovery mechanism in the HTTP server was a historical mistake that the Go team supposedly regrets. (link to reddit thread)
>>
>> I’d like to understand this better. Is it actually considered bad practice? And does the Go team really regret the built-in panic recovery in HTTP handlers? Aside from the Google Go style guide and various opinions from engineers online, I haven’t been able to find any official Go document or article that clearly states this. (link to Google style guide, link to someone commenting about it too).
>>
>>
>> Yes, in general the Go team considers the fact that the net/http
>> server recovers panic to be a historical mistake.
>>
>> Go code in practice does not attempt to be safe in the presence of
>> panics in code that it calls. This means that in practice a panic can
>> leave data structures and locks in an inconsistent state. If the panic
>> is recovered, the future behavior of the program is unpredictable.
>>
>> As a general guideline, only use recover for a panic that you call
>> yourself. If you recover a panic and it's not what you expected, pass
>> the recovered value to a new call to panic. For example, see how the
>> encoding/json or text/template packages handle recovering panics.
>>
>> Ian
>>
>> --
>> You received this message because you are subscribed to the Google Groups "golang-nuts" group.
>> To unsubscribe from this group and stop receiving emails from it, send an email to [email protected].
>> To view this discussion visit https://groups.google.com/d/msgid/golang-nuts/CAOyqgcVLmE9KxnYTC1rbJHE9E1WHpSdGsVwHDT2CH%3DfK_2ZoGQ%40mail.gmail.com.
>>
>>
--
You received this message because you are subscribed to the Google Groups "golang-nuts" group.
To unsubscribe from this group and stop receiving emails from it, send an email to [email protected].
To view this discussion visit https://groups.google.com/d/msgid/golang-nuts/93B21E5B-2FDB-4FC2-8B2F-D5B269078EDD%40me.com.
|