pythonmultithreadingtkinter

tkinter auto joining thread


I am writing a tkinter app and is using threads for performance (computing-intensive tasks)

Threads need to be joined, but I am lazy.

I don't really like the idea of constantly checking if a thread is alive.

I created a class to handle join automatically when the job is done. However, it still has the risk of having race conditions (that's what GPT said)

class RunInThreadHandler(ctk.CTkFrame):
    def __init__(self, master: ctk.CTkBaseClass,
                 target: Callable,
                 args: tuple = (),
                 func_end_callback: Optional[Callable] = None,
                 kwargs: Optional[dict[str, Any]] = None):
        super().__init__(master)
        self._func: Callable = target
        self._args: tuple = args
        self._kwargs: dict[str, Any] = kwargs if kwargs is not None else {}
        self._func_end_callback: Optional[Callable] = func_end_callback
        self._thread: Optional[Thread] = Thread(target=self._thread_func)
        self._thread.start()

    def _thread_func(self):
        try:
            self._func(*self._args, **self._kwargs)
        except BaseException as exc:
            print(exc)
        self.after(1000, self._thread.join)
        if self._func_end_callback is not None:
            self.after(1000, self._func_end_callback)

Usage:

RunInThreadHandler(self, target=foo)  # runs foo in thread on the spot

Q: Any better ways?


Solution

  • Typically, the purpose of calling join() is for the creator of the thread to verify that the thread execution has completed or in cases, non-termination, to force terminate the thread and performs the necessary cleanups.

    So, if the user of RunInThreadHandler is not interested in waiting for the thread to complete for the reasons above, then I don't see any point in calling join(). Moreover, as you have pointed out yourself, the way you write the code will cause the code to join itself, which will cause your thread to never terminate.