[PATCH v2] nmbug: write tags out to a temporary file, not 'nmbug.index'

Subject: [PATCH v2] nmbug: write tags out to a temporary file, not 'nmbug.index'

Date: Sun, 13 Feb 2022 09:54:08 -0700

To: notmuch@notmuchmail.org

Cc: Sean Whitton

From: Sean Whitton


If more than nmbug process is running at once, then each will try to
read and write the same file.  The particular failure I've seen is
that the process which finishes first deletes nmbug.index, and then
the other process dies with a FileNotFoundError.  So use a distinct
temporary file per process.
---
 devel/nmbug/nmbug | 44 ++++++++++++++++++++++----------------------
 1 file changed, 22 insertions(+), 22 deletions(-)

Here is a second attempt, though I'm afraid I have little idea whether it is
idiomatic Python.

diff --git a/devel/nmbug/nmbug b/devel/nmbug/nmbug
index 043c1863..396098d0 100755
--- a/devel/nmbug/nmbug
+++ b/devel/nmbug/nmbug
@@ -586,37 +586,38 @@ def get_status():
         'deleted': {},
         'missing': {},
         }
-    index = _index_tags()
-    maybe_deleted = _diff_index(index=index, filter='D')
-    for id, tags in maybe_deleted.items():
-        (_, stdout, stderr) = _spawn(
-            args=['notmuch', 'search', '--output=files', 'id:{0}'.format(id)],
-            stdout=_subprocess.PIPE,
-            wait=True)
-        if stdout:
-            status['deleted'][id] = tags
-        else:
-            status['missing'][id] = tags
-    status['added'] = _diff_index(index=index, filter='A')
-    _os.remove(index)
-    return status
-
-
-def _index_tags():
-    "Write notmuch tags to the nmbug.index."
-    path = _os.path.join(NMBGIT, 'nmbug.index')
+    (_, index) = _tempfile.mkstemp()
+    try:
+        _index_tags(index)
+        maybe_deleted = _diff_index(index=index, filter='D')
+        for id, tags in maybe_deleted.items():
+            (_, stdout, stderr) = _spawn(
+                args=['notmuch', 'search', '--output=files', 'id:{0}'.format(id)],
+                stdout=_subprocess.PIPE,
+                wait=True)
+            if stdout:
+                status['deleted'][id] = tags
+            else:
+                status['missing'][id] = tags
+                status['added'] = _diff_index(index=index, filter='A')
+                return status
+    finally:
+        _os.remove(index)
+
+def _index_tags(index):
+    "Write notmuch tags to a file."
     query = ' '.join('tag:"{tag}"'.format(tag=tag) for tag in get_tags())
     prefix = '+{0}'.format(_ENCODED_TAG_PREFIX)
     _git(
         args=['read-tree', '--empty'],
-        additional_env={'GIT_INDEX_FILE': path}, wait=True)
+        additional_env={'GIT_INDEX_FILE': index}, wait=True)
     with _spawn(
             args=['notmuch', 'dump', '--format=batch-tag', '--', query],
             stdout=_subprocess.PIPE) as notmuch:
         with _git(
                 args=['update-index', '--index-info'],
                 stdin=_subprocess.PIPE,
-                additional_env={'GIT_INDEX_FILE': path}) as git:
+                additional_env={'GIT_INDEX_FILE': index}) as git:
             for line in notmuch.stdout:
                 if line.strip().startswith('#'):
                     continue
@@ -629,7 +630,6 @@ def _index_tags():
                 for line in _index_tags_for_message(
                         id=id, status='A', tags=tags):
                     git.stdin.write(line)
-    return path
 
 
 def _index_tags_for_message(id, status, tags):
-- 
2.30.2

_______________________________________________
notmuch mailing list -- notmuch@notmuchmail.org
To unsubscribe send an email to notmuch-leave@notmuchmail.org

Thread: