loguru
loguru copied to clipboard
TypeError: __init__() missing 2 required keyword-only arguments: 'request' and 'response'
l got error sometimes, but not 100%
--- Logging error in Loguru Handler #1 ---
Record was: None
Traceback (most recent call last):
File "C:\Users\Ronaldinho\.virtualenvs\xxx-5Vbn2Ffj\lib\site-packages\loguru\_handler.py", line 270, in _queued_writer
message = queue.get()
File "c:\users\ronaldinho\.pyenv\pyenv-win\versions\3.9.6\lib\multiprocessing\queues.py", line 368, in get
return _ForkingPickler.loads(res)
File "C:\Users\Ronaldinho\.virtualenvs\xxx-5Vbn2Ffj\lib\site-packages\loguru\_recattrs.py", line 77, in _from_pickled_value
value = pickle.loads(pickled_value)
TypeError: __init__() missing 2 required keyword-only arguments: 'request' and 'response'
--- End of logging error ---
is it because of my log content is not serializable? but i even don't know this is occur in which line it attempt to log...
This is due to log not being deserializable. The serialization process sending the message to the queue works fine, but at the time it needs to be retrieved and logged from within the thread, it fails. That's why you can see Record was: None. Unfortunately, the logging thread isn't able to retrieve the logged object so it can't display any useful information about its origin.
This is not the first time this problem has been reported (see #329). It's hard to find a solution, but I think I'll have to modify the serialization function, so that it's done in two steps (first file+line which can't fail, then the remaining record data, and print basic info if later fails).
In the meantime, you can identify the failing logging call by temporarily adding a custom sink (it mimics enqueue=True in the main thread so record will be fully displayed on error):
import pickle
def debugging_sink(message):
pickle.loads(pickle.dumps(message))
logger.add(debugging_sink, enqueue=False)
Most of time, the error is due to an Exception subclass (see Cannot unpickle Exception subclass).
Once the origin is identified, you can fix it like that:
try:
faulty_function()
except Exception:
type, _, tb = sys.exc_info()
logger.opt(exception=(type, None, tb)).error("An error occurred")
You can also apply the fix globally as follow:
def patcher(record):
exception = record["exception"]
if exception is not None:
fixed = Exception(str(exception.value))
record["exception"] = exception._replace(value=fixed)
logger.configure(patcher=patcher)
ok i will keep tracking it, thank you