Pickling a subclass that adds a new attribute doesn’t seem to include the new attribute. For example:
import requests
import pickle
class MySession(requests.Session):
def __init__(self, *args, **kwargs):
super().__init__(*args, **kwargs)
self.details = False
data = MySession()
file = "/tmp/pickle"
with open(file, "wb") as f:
from pprint import pprint
print(f"Saving session {data} to {file} with {data.details}")
pprint(data.__dict__)
pickle.dump(data, f)
print("Validating")
with open(file, "rb") as f:
newdata = pickle.load(f)
pprint(newdata.__dict__)
print(data.details)
print(newdata.details)
produces the following exception:
Saving session <__main__.MySession object at 0x7f0976cb9400> to /tmp/pickle with False
{'adapters': OrderedDict([('https://',
<requests.adapters.HTTPAdapter object at 0x7f0975dca4e0>),
('http://',
<requests.adapters.HTTPAdapter object at 0x7f0976be9ca0>)]),
'auth': None,
'cert': None,
'cookies': <RequestsCookieJar[]>,
'details': False,
'headers': {'User-Agent': 'python-requests/2.32.3', 'Accept-Encoding': 'gzip, deflate, br', 'Accept': '*/*', 'Connection': 'keep-alive'},
'hooks': {'response': []},
'max_redirects': 30,
'params': {},
'proxies': {},
'stream': False,
'trust_env': True,
'verify': True}
Validating
{'adapters': OrderedDict([('https://',
<requests.adapters.HTTPAdapter object at 0x7f09759c1010>),
('http://',
<requests.adapters.HTTPAdapter object at 0x7f0975a4e960>)]),
'auth': None,
'cert': None,
'cookies': <RequestsCookieJar[]>,
'headers': {'User-Agent': 'python-requests/2.32.3', 'Accept-Encoding': 'gzip, deflate, br', 'Accept': '*/*', 'Connection': 'keep-alive'},
'hooks': {'response': []},
'max_redirects': 30,
'params': {},
'proxies': {},
'stream': False,
'trust_env': True,
'verify': True}
False
Traceback (most recent call last):
File "/tmp/repro.py", line 22, in <module>
print(newdata.details)
^^^^^^^^^^^^^^^
AttributeError: 'MySession' object has no attribute 'details'
The details
attribute of MySession
didn’t get saved in the pickle file. But why?
Disregard below this line:
Now I am just going to ramble because SO thinks my post contains too much code and not enough details, but when a picture is worth a thousand words, why do we need to add 10,000 words to a pretty self explanatory picture?