from enum import Enum, auto import time import threading class Spinner: class State(Enum): LOADING = auto() SUCCESS = '✓' FAILURE = '⨯' def __init__(self, text: str): self.text = text self.state = self.State.LOADING def __enter__(self): t = threading.Thread(target = self._thread_fn) t.start() self.thread = t return self def __exit__(self, *_): if self.state == self.State.LOADING: self.state = self.State.SUCCESS if self.thread: self.thread.join() def fail(self): if self.thread: self.state = self.State.FAILURE self.thread.join() self.thread = None def done(self): if self.thread: self.state = self.State.SUCCESS self.thread.join() self.thread = None def _thread_fn(self): interval = 80 spinner = ["⠋", "⠙", "⠹", "⠸", "⠼", "⠴", "⠦", "⠧", "⠇", "⠏"] i = 0 while self.state == self.State.LOADING: i = (i + 1) % len(spinner) print(f"\r{spinner[i]} {self.text}", end=' ') time.sleep(interval / 1000) print(f"\r{self.state.value} {self.text}")