From 8c8b833d32c02d3ae6f43b04bb1e45968796b402 Mon Sep 17 00:00:00 2001 From: varunkasyap Date: Thu, 19 Feb 2026 14:17:27 +0530 Subject: Fixed #36919 -- Allowed Task and TaskResult to be pickled. --- django/tasks/base.py | 19 ++++++++++++++++++- 1 file changed, 18 insertions(+), 1 deletion(-) (limited to 'django') diff --git a/django/tasks/base.py b/django/tasks/base.py index 94eb29f2ea..b5c960a7cf 100644 --- a/django/tasks/base.py +++ b/django/tasks/base.py @@ -1,5 +1,5 @@ from collections.abc import Callable -from dataclasses import dataclass, field, replace +from dataclasses import dataclass, field, fields, replace from datetime import datetime from inspect import isclass, iscoroutinefunction from typing import Any @@ -55,6 +55,23 @@ class Task: def __post_init__(self): self.get_backend().validate_task(self) + @classmethod + def _reconstruct(cls, kwargs): + func_path = kwargs["func"] + try: + func = import_string(func_path) + kwargs["func"] = func.func + except (ImportError, AttributeError) as e: + msg = f"Expected {func_path!r} to point to a Task instance." + raise ValueError(msg) from e + return cls(**kwargs) + + def __reduce__(self): + kwargs = {f.name: getattr(self, f.name) for f in fields(self)} + kwargs["func"] = self.module_path + + return (self.__class__._reconstruct, (kwargs,)) + @property def name(self): return self.func.__name__ -- cgit v1.3