diff options
Diffstat (limited to 'alot/buffers/search.py')
-rw-r--r-- | alot/buffers/search.py | 66 |
1 files changed, 44 insertions, 22 deletions
diff --git a/alot/buffers/search.py b/alot/buffers/search.py index 8cd76a87..c1650db4 100644 --- a/alot/buffers/search.py +++ b/alot/buffers/search.py @@ -1,6 +1,9 @@ # Copyright (C) 2011-2018 Patrick Totzke <patricktotzke@gmail.com> # This file is released under the GNU GPL, version 3 or a later revision. # For further details see the COPYING file + +import asyncio + import urwid from notmuch2 import NotmuchError @@ -93,8 +96,8 @@ class SearchBuffer(Buffer): modename = 'search' - _result_count_val = None - _thread_count_val = None + _message_count = None + _thread_count = None def __init__(self, ui, initialquery='', sort_order=None): self.dbman = ui.dbman @@ -107,27 +110,46 @@ class SearchBuffer(Buffer): super().__init__() def __str__(self): - formatstring = '[search] for "%s" (%d message%s in %d thread%s)' - return formatstring % (self.querystring, - self._result_count, 's' if self._result_count > 1 else '', - self._thread_count, 's' if self._thread_count > 1 else '') + ret = '[search] for "%s"' % self.querystring - @property - def _result_count(self): - if self._result_count_val is None: - self._result_count_val = self.dbman.count_messages(self.querystring) - return self._result_count_val - @property - def _thread_count(self): - if self._thread_count_val is None: - self._thread_count_val = self.dbman.count_threads(self.querystring) - return self._thread_count_val + if self._thread_count is not None: + threadstr = ' in %d thread%s' % (self._thread_count, '' if self._thread_count == 1 else 's') + else: + threadstr = '' + + if self._message_count is not None: + ret += ' (%d message%s%s)' % (self._message_count, '' if self._message_count == 1 else 's', + threadstr) + + return ret + + async def _calc_result_count(self): + """ + Asynchronously compute message/thread counts. + Cache and return them. + """ + # instance variables can get reset if rebuild() gets called + # while we are waiting, hence this code + message_count = self._message_count + thread_count = self._thread_count + + if message_count is None or thread_count is None: + tasks = [self.ui._loop.run_in_executor(None, f, self.querystring) + for f in (self.dbman.count_messages, self.dbman.count_threads)] + message_count, thread_count = await asyncio.gather(*tasks) + + self._message_count = message_count + self._thread_count = thread_count + + return message_count, thread_count + + async def get_info(self): + message_count, thread_count = await self._calc_result_count() - def get_info(self): info = {} - info['querystring'] = self.querystring - info['result_count'] = self._result_count - info['thread_count'] = self._thread_count + info['querystring'] = self.querystring + info['result_count'] = message_count + info['thread_count'] = thread_count info['result_count_positive'] = 's' if info['result_count'] > 1 else '' return info @@ -138,8 +160,8 @@ class SearchBuffer(Buffer): else: exclude_tags = frozenset() - self._result_count_val = None - self._thread_count_val = None + self._result_count = None + self._thread_count = None try: threads = self.dbman.get_threads(self.querystring, self.sort_order, |