Skip to content
Snippets Groups Projects
Verified Commit f2e29d79 authored by Nik | Klampfradler's avatar Nik | Klampfradler
Browse files

Rework progress API to be more coherent with upstream and DRY

parent 0d35f974
No related branches found
No related tags found
2 merge requests!494Refactor ProgressRecorder for non-optional Celery usage and add doc strings,!491Resolve "Make Celery non-optional"
from decimal import Decimal
from functools import wraps
from typing import Callable, Union
from numbers import Number
from typing import Callable, Optional
from django.contrib import messages
from celery_progress.backend import PROGRESS_STATE, AbstractProgressRecorder
......@@ -26,11 +28,11 @@ class ProgressRecorder(AbstractProgressRecorder):
@recorded_task
def do_something(foo, bar, recorder, baz=None):
# ...
recorder.total = len(list_with_data)
recorder.set_progress(total=len(list_with_data))
for i, item in enumerate(list_with_data):
# ...
recorder.set_progress(i + 1)
recorder.set_progress(i+1)
# ...
recorder.add_message(messages.SUCCESS, "All data were imported successfully.")
......@@ -61,42 +63,57 @@ class ProgressRecorder(AbstractProgressRecorder):
def __init__(self, task):
self.task = task
self.messages = []
self.total = 100
self.current = 0
def set_progress(self, current: Union[int, float], **kwargs):
self._messages = []
self._current = 0
self._total = 100
def set_progress(
self,
current: Optional[Number] = None,
total: Optional[Number] = None,
description: Optional[str] = None,
level: int = messages.INFO,
):
"""Set the current progress in the frontend.
The progress percentage is automatically calculated in relation to self.total.
:param current: The absolute number of processed items
:param current: The number of processed items; relative to total, default unchanged
:param total: The total number of items (or 100 if using a percentage), default unchanged
:param description: A textual description, routed to the frontend as an INFO message
"""
self.current = current
if current is not None:
self._current = current
if total is not None:
self._total = total
percent = 0
if self.total > 0:
percent = (Decimal(current) / Decimal(self.total)) * Decimal(100)
percent = float(round(percent, 2))
if self._total > 0:
percent = self._current / self._total
if description is not None:
self._messages.append((level, description))
self.task.update_state(
state=PROGRESS_STATE,
meta={
"current": current,
"total": self.total,
"current": self._current,
"total": self._total,
"percent": percent,
"messages": self.messages,
"messages": self._messages,
},
)
def add_message(self, level: int, message: str):
def add_message(self, level: int, message: str) -> None:
"""Show a message in the progress frontend.
This method is a shortcut for set_progress with no new progress arguments,
passing only the message and level as description.
:param level: The message level (default levels from django.contrib.messages)
:param message: The actual message (should be translated)
"""
self.messages.append((level, message))
self.set_progress(self.current)
self.set_progress(description=message, level=level)
def recorded_task(orig: Callable, *args, **kwargs) -> app.Task:
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment