From 80d00ce4bf8bbcbbdb83e190f697b688c35394ca Mon Sep 17 00:00:00 2001 From: Dave Pearson Date: Wed, 17 May 2023 10:49:46 +0100 Subject: [PATCH] Logging and experimenting for Windows --- src/textual/widgets/_directory_tree.py | 32 +++++++++++++++++--------- 1 file changed, 21 insertions(+), 11 deletions(-) diff --git a/src/textual/widgets/_directory_tree.py b/src/textual/widgets/_directory_tree.py index 437811758..0c615f26e 100644 --- a/src/textual/widgets/_directory_tree.py +++ b/src/textual/widgets/_directory_tree.py @@ -3,6 +3,7 @@ from __future__ import annotations from dataclasses import dataclass from pathlib import Path from queue import Empty, Queue +from threading import RLock from typing import ClassVar, Iterable, Iterator from rich.style import Style @@ -15,6 +16,8 @@ from ..reactive import var from ..worker import Worker, get_current_worker from ._tree import TOGGLE_STYLE, Tree, TreeNode +read_dir = RLock() + @dataclass class DirEntry: @@ -239,6 +242,9 @@ class DirectoryTree(Tree[DirEntry]): """ return paths + def _tlog(self, message: str) -> None: + self.app.call_from_thread(self.log.debug, f"{self.id} - {message}") + def _populate_node(self, node: TreeNode[DirEntry], content: Iterable[Path]) -> None: """Populate the given tree node with the given directory content. @@ -268,6 +274,7 @@ class DirectoryTree(Tree[DirEntry]): if worker.is_cancelled: break yield entry + self._tlog(f"Loaded entry {entry} from {location}") def _load_directory(self, node: TreeNode[DirEntry], worker: Worker) -> None: """Load the directory contents for a given node. @@ -277,14 +284,15 @@ class DirectoryTree(Tree[DirEntry]): """ assert node.data is not None node.data.loaded = True - self.app.call_from_thread( - self._populate_node, - node, - sorted( - self.filter_paths(self._directory_content(node.data.path, worker)), - key=lambda path: (not path.is_dir(), path.name.lower()), - ), - ) + with read_dir: + self.app.call_from_thread( + self._populate_node, + node, + sorted( + self.filter_paths(self._directory_content(node.data.path, worker)), + key=lambda path: (not path.is_dir(), path.name.lower()), + ), + ) _LOADER_INTERVAL: Final[float] = 0.2 """How long the loader should block while waiting for queue content.""" @@ -292,12 +300,14 @@ class DirectoryTree(Tree[DirEntry]): @work(exclusive=True) def _loader(self) -> None: """Background loading queue processor.""" + self._tlog("_loader started") worker = get_current_worker() while not worker.is_cancelled: try: - self._load_directory( - self._to_load.get(timeout=self._LOADER_INTERVAL), worker - ) + next_node = self._to_load.get(timeout=self._LOADER_INTERVAL) + self._tlog(f"Received {next_node} for loading") + self._load_directory(next_node, worker) + self._tlog(f"Loaded {next_node}") except Empty: pass