There is a PR which fixes this by saving the mangled name in a pickle. But should pickling private methods be supported at all? They are private for reason – so you cannot simply use it outside of the methods of the same class (this is not perfect, but serves its purpose). Does pickling and copying fall under this use?
Note also that name mangling is an implementation detail. It may not work in other Python implementations or in future CPython versions.
We always can add custom __reduce__() or __getstate__()/__setstate__() methods for objects containing references to its private methods.
Generally I would think that pickling should work in this case fully. Though considering this has been broken for a long time, maybe it’s better to leave it as is and document it as such.
Either way: the language itself should be documented in a way to explicitly say if this should work or not. Then the code can be updated to match.
It’s reasonable to pass a private function around as a callback for example. Of course only the original class has access to the function to pass it around, but once it’s created a reference the function is just a normal callable. You could extend that to “it’s reasonable to send a private function across a network in some distributed multi-processing scheme as a callback”.
Realistically: there seems to be occasional demand for this to work. So I’d be fine with that PR being merged as a fix. (Despite me wishing people would stop using dunder “private” internally-mangled methods entirely)
A pickle should be thought of as code that calls APIs when deserialized because that is in essence what happens. People pickling private things should thus have no expectation that they work for persisted data or communication across language versions just as they shouldn’t between unvetted versions of code explicitly in their test matrix. Use between identical versions should just work.
It could be reasonable to consider this a bugfix and apply it to 3.13 and 3.14. That’d probably help some people using concurrent.futures & multiprocessing where pickles happen?
Well, I see there is a use case for this. But since this never worked, it is a new feature.
The current PR is an incomplete solution. It only handles bound methods. We need to support also classmethods, staticmethods and unbound methods. We should also test how private slots are supported. I am also curious about private nested classes.
If it gets overly complicated to make the code support this i’d lean against doing it and just document the caveat. agreed it is more of a new feature, even if having it would help some code deal with other changes - they’ve got other solutions.