We are currently solving the following issue within our repository. Here is the issue text:
--- BEGIN ISSUE ---
Remove fallback on downloading xz files
It's added in #524 because the current task have xz as artifacts. Once we make a successful deployment, we can switch to zst fully and remove the xz fallback.

--- END ISSUE ---

Below are some code segments, each from a relevant file. One or more of these files may contain bugs.
--- BEGIN FILES ---
Path: `bugbug/db.py`
Content:
```
1 # -*- coding: utf-8 -*-
2 # This Source Code Form is subject to the terms of the Mozilla Public
3 # License, v. 2.0. If a copy of the MPL was not distributed with this file,
4 # You can obtain one at http://mozilla.org/MPL/2.0/.
5 
6 import gzip
7 import io
8 import json
9 import lzma
10 import os
11 import pickle
12 import shutil
13 from contextlib import contextmanager
14 from urllib.parse import urljoin
15 
16 import requests
17 import zstandard
18 
19 from bugbug import utils
20 
21 DATABASES = {}
22 
23 
24 def register(path, url, version, support_files=[]):
25     DATABASES[path] = {"url": url, "version": version, "support_files": support_files}
26 
27     # Create DB parent directory.
28     parent_dir = os.path.dirname(path)
29     if not os.path.exists(parent_dir):
30         os.makedirs(parent_dir, exist_ok=True)
31 
32     if not os.path.exists(f"{path}.version"):
33         with open(f"{path}.version", "w") as f:
34             f.write(str(version))
35 
36 
37 def is_old_version(path):
38     with open(f"{path}.version", "r") as f:
39         prev_version = int(f.read())
40 
41     return DATABASES[path]["version"] > prev_version
42 
43 
44 def extract_file(path):
45     path, compression_type = os.path.splitext(path)
46 
47     with open(path, "wb") as output_f:
48         if compression_type == ".zst":
49             dctx = zstandard.ZstdDecompressor()
50             with open(f"{path}.zst", "rb") as input_f:
51                 dctx.copy_stream(input_f, output_f)
52 
53         elif compression_type == ".xz":
54             with lzma.open(f"{path}.xz") as input_f:
55                 shutil.copyfileobj(input_f, output_f)
56 
57         else:
58             assert False, f"Unexpected compression type: {compression_type}"
59 
60 
61 def download_support_file(path, file_name):
62     try:
63         url = urljoin(DATABASES[path]["url"], file_name)
64         path = os.path.join(os.path.dirname(path), file_name)
65 
66         print(f"Downloading {url} to {path}")
67         utils.download_check_etag(url, path)
68 
69         if path.endswith(".zst") or path.endswith(".xz"):
70             extract_file(path)
71     except requests.exceptions.HTTPError:
72         try:
73             url = f"{os.path.splitext(url)[0]}.xz"
74             path = f"{os.path.splitext(path)[0]}.xz"
75 
76             print(f"Downloading {url} to {path}")
77             utils.download_check_etag(url, path)
78 
79             extract_file(path)
80 
81         except requests.exceptions.HTTPError:
82             print(f"{file_name} is not yet available to download for {path}")
83 
84 
85 def download_version(path):
86     download_support_file(path, f"{os.path.basename(path)}.version")
87 
88 
89 # Download and extract databases.
90 def download(path, force=False, support_files_too=False):
91     if os.path.exists(path) and not force:
92         return
93 
94     zst_path = f"{path}.zst"
95     xz_path = f"{path}.xz"
96 
97     # Only download if the file is not there yet.
98     if (not os.path.exists(zst_path) and not os.path.exists(xz_path)) or force:
99         url = DATABASES[path]["url"]
100         try:
101             path_compressed = zst_path
102             print(f"Downloading {url} to {path_compressed}")
103             utils.download_check_etag(url, path_compressed)
104 
105         except requests.exceptions.HTTPError:
106             try:
107                 url_xz = f"{os.path.splitext(url)[0]}.xz"
108                 path_compressed = xz_path
109                 print(f"Downloading {url_xz} to {path_compressed} instead")
110                 utils.download_check_etag(url_xz, path_compressed)
111 
112             except requests.exceptions.HTTPError:
113                 print(f"{url} is not yet available to download")
114                 raise
115 
116     else:
117         if os.path.exists(zst_path) or not os.path.exists(xz_path):
118             path_compressed = zst_path
119         else:
120             path_compressed = xz_path
121 
122     extract_file(path_compressed)
123 
124     if support_files_too:
125         for support_file in DATABASES[path]["support_files"]:
126             download_support_file(path, support_file)
127 
128 
129 def last_modified(path):
130     url = DATABASES[path]["url"]
131     last_modified = utils.get_last_modified(url)
132 
133     if last_modified is None:
134         base_url = os.path.splitext(url)[0]
135         last_modified = utils.get_last_modified(f"{base_url}.xz")
136 
137     if last_modified is None:
138         raise Exception("Last-Modified is not available")
139 
140     return last_modified
141 
142 
143 class Store:
144     def __init__(self, fh):
145         self.fh = fh
146 
147 
148 class JSONStore(Store):
149     def write(self, elems):
150         for elem in elems:
151             self.fh.write((json.dumps(elem) + "\n").encode("utf-8"))
152 
153     def read(self):
154         for line in io.TextIOWrapper(self.fh, encoding="utf-8"):
155             yield json.loads(line)
156 
157 
158 class PickleStore(Store):
159     def write(self, elems):
160         for elem in elems:
161             self.fh.write(pickle.dumps(elem))
162 
163     def read(self):
164         try:
165             while True:
166                 yield pickle.load(self.fh)
167         except EOFError:
168             pass
169 
170 
171 COMPRESSION_FORMATS = ["gz", "zstd"]
172 SERIALIZATION_FORMATS = {"json": JSONStore, "pickle": PickleStore}
173 
174 
175 @contextmanager
176 def _db_open(path, mode):
177     parts = str(path).split(".")
178     assert len(parts) > 1, "Extension needed to figure out serialization format"
179     if len(parts) == 2:
180         db_format = parts[-1]
181         compression = None
182     else:
183         db_format = parts[-2]
184         compression = parts[-1]
185 
186     assert compression is None or compression in COMPRESSION_FORMATS
187     assert db_format in SERIALIZATION_FORMATS
188 
189     store_constructor = SERIALIZATION_FORMATS[db_format]
190 
191     if compression == "gz":
192         with gzip.GzipFile(path, mode) as f:
193             yield store_constructor(f)
194     elif compression == "zstd":
195         if "w" in mode or "a" in mode:
196             cctx = zstandard.ZstdCompressor()
197             with open(path, mode) as f:
198                 with cctx.stream_writer(f) as writer:
199                     yield store_constructor(writer)
200         else:
201             dctx = zstandard.ZstdDecompressor()
202             with open(path, mode) as f:
203                 with dctx.stream_reader(f) as reader:
204                     yield store_constructor(reader)
205     else:
206         with open(path, mode) as f:
207             yield store_constructor(f)
208 
209 
210 def read(path):
211     assert path in DATABASES
212 
213     if not os.path.exists(path):
214         return ()
215 
216     with _db_open(path, "rb") as store:
217         for elem in store.read():
218             yield elem
219 
220 
221 def write(path, elems):
222     assert path in DATABASES
223 
224     with _db_open(path, "wb") as store:
225         store.write(elems)
226 
227 
228 def append(path, elems):
229     assert path in DATABASES
230 
231     with _db_open(path, "ab") as store:
232         store.write(elems)
233 
234 
235 def delete(path, match):
236     assert path in DATABASES
237 
238     dirname, basename = os.path.split(path)
239     new_path = os.path.join(dirname, f"new_{basename}")
240 
241     def matching_elems(store):
242         for elem in store.read():
243             if not match(elem):
244                 yield elem
245 
246     with _db_open(new_path, "wb") as wstore:
247         with _db_open(path, "rb") as rstore:
248             wstore.write(matching_elems(rstore))
249 
250     os.unlink(path)
251     os.rename(new_path, path)
252
```
--- END FILES ---

Please first localize the bug based on the issue statement, and then generate a patch according to the `git diff` format fenced by three backticks.

Here is an example:

```diff
diff --git a/examples/server_async.py b/examples/server_async.py
--- a/examples/server_async.py
+++ b/examples/server_async.py
@@ -313,4 +313,4 @@
 
 
 if __name__ == "__main__":
-    asyncio.run(run_async_server("."), debug=True)
+    asyncio.run(run_async_server(), debug=True)
diff --git a/examples/server_sync.py b/examples/server_sync.py
--- a/examples/server_sync.py
+++ b/examples/server_sync.py
@@ -313,5 +313,5 @@
 
 
 if __name__ == "__main__":
-    server = run_sync_server(".")
+    server = run_sync_server()
     server.shutdown()

```

diff --git a/bugbug/db.py b/bugbug/db.py
--- a/bugbug/db.py
+++ b/bugbug/db.py
@@ -6,10 +6,8 @@
 import gzip
 import io
 import json
-import lzma
 import os
 import pickle
-import shutil
 from contextlib import contextmanager
 from urllib.parse import urljoin
 
@@ -49,11 +47,6 @@
             dctx = zstandard.ZstdDecompressor()
             with open(f"{path}.zst", "rb") as input_f:
                 dctx.copy_stream(input_f, output_f)
-
-        elif compression_type == ".xz":
-            with lzma.open(f"{path}.xz") as input_f:
-                shutil.copyfileobj(input_f, output_f)
-
         else:
             assert False, f"Unexpected compression type: {compression_type}"
 
@@ -66,20 +59,10 @@
         print(f"Downloading {url} to {path}")
         utils.download_check_etag(url, path)
 
-        if path.endswith(".zst") or path.endswith(".xz"):
+        if path.endswith(".zst"):
             extract_file(path)
     except requests.exceptions.HTTPError:
-        try:
-            url = f"{os.path.splitext(url)[0]}.xz"
-            path = f"{os.path.splitext(path)[0]}.xz"
-
-            print(f"Downloading {url} to {path}")
-            utils.download_check_etag(url, path)
-
-            extract_file(path)
-
-        except requests.exceptions.HTTPError:
-            print(f"{file_name} is not yet available to download for {path}")
+        print(f"{file_name} is not yet available to download for {path}")
 
 
 def download_version(path):
@@ -92,34 +75,19 @@
         return
 
     zst_path = f"{path}.zst"
-    xz_path = f"{path}.xz"
 
     # Only download if the file is not there yet.
-    if (not os.path.exists(zst_path) and not os.path.exists(xz_path)) or force:
+    if not os.path.exists(zst_path) or force:
         url = DATABASES[path]["url"]
         try:
-            path_compressed = zst_path
-            print(f"Downloading {url} to {path_compressed}")
-            utils.download_check_etag(url, path_compressed)
+            print(f"Downloading {url} to {zst_path}")
+            utils.download_check_etag(url, zst_path)
 
         except requests.exceptions.HTTPError:
-            try:
-                url_xz = f"{os.path.splitext(url)[0]}.xz"
-                path_compressed = xz_path
-                print(f"Downloading {url_xz} to {path_compressed} instead")
-                utils.download_check_etag(url_xz, path_compressed)
-
-            except requests.exceptions.HTTPError:
-                print(f"{url} is not yet available to download")
-                raise
+            print(f"{url} is not yet available to download")
+            raise
 
-    else:
-        if os.path.exists(zst_path) or not os.path.exists(xz_path):
-            path_compressed = zst_path
-        else:
-            path_compressed = xz_path
-
-    extract_file(path_compressed)
+    extract_file(zst_path)
 
     if support_files_too:
         for support_file in DATABASES[path]["support_files"]:
@@ -130,10 +98,6 @@
     url = DATABASES[path]["url"]
     last_modified = utils.get_last_modified(url)
 
-    if last_modified is None:
-        base_url = os.path.splitext(url)[0]
-        last_modified = utils.get_last_modified(f"{base_url}.xz")
-
     if last_modified is None:
         raise Exception("Last-Modified is not available")

{"golden_diff": "diff --git a/bugbug/db.py b/bugbug/db.py\n--- a/bugbug/db.py\n+++ b/bugbug/db.py\n@@ -6,10 +6,8 @@\n import gzip\n import io\n import json\n-import lzma\n import os\n import pickle\n-import shutil\n from contextlib import contextmanager\n from urllib.parse import urljoin\n \n@@ -49,11 +47,6 @@\n             dctx = zstandard.ZstdDecompressor()\n             with open(f\"{path}.zst\", \"rb\") as input_f:\n                 dctx.copy_stream(input_f, output_f)\n-\n-        elif compression_type == \".xz\":\n-            with lzma.open(f\"{path}.xz\") as input_f:\n-                shutil.copyfileobj(input_f, output_f)\n-\n         else:\n             assert False, f\"Unexpected compression type: {compression_type}\"\n \n@@ -66,20 +59,10 @@\n         print(f\"Downloading {url} to {path}\")\n         utils.download_check_etag(url, path)\n \n-        if path.endswith(\".zst\") or path.endswith(\".xz\"):\n+        if path.endswith(\".zst\"):\n             extract_file(path)\n     except requests.exceptions.HTTPError:\n-        try:\n-            url = f\"{os.path.splitext(url)[0]}.xz\"\n-            path = f\"{os.path.splitext(path)[0]}.xz\"\n-\n-            print(f\"Downloading {url} to {path}\")\n-            utils.download_check_etag(url, path)\n-\n-            extract_file(path)\n-\n-        except requests.exceptions.HTTPError:\n-            print(f\"{file_name} is not yet available to download for {path}\")\n+        print(f\"{file_name} is not yet available to download for {path}\")\n \n \n def download_version(path):\n@@ -92,34 +75,19 @@\n         return\n \n     zst_path = f\"{path}.zst\"\n-    xz_path = f\"{path}.xz\"\n \n     # Only download if the file is not there yet.\n-    if (not os.path.exists(zst_path) and not os.path.exists(xz_path)) or force:\n+    if not os.path.exists(zst_path) or force:\n         url = DATABASES[path][\"url\"]\n         try:\n-            path_compressed = zst_path\n-            print(f\"Downloading {url} to {path_compressed}\")\n-            utils.download_check_etag(url, path_compressed)\n+            print(f\"Downloading {url} to {zst_path}\")\n+            utils.download_check_etag(url, zst_path)\n \n         except requests.exceptions.HTTPError:\n-            try:\n-                url_xz = f\"{os.path.splitext(url)[0]}.xz\"\n-                path_compressed = xz_path\n-                print(f\"Downloading {url_xz} to {path_compressed} instead\")\n-                utils.download_check_etag(url_xz, path_compressed)\n-\n-            except requests.exceptions.HTTPError:\n-                print(f\"{url} is not yet available to download\")\n-                raise\n+            print(f\"{url} is not yet available to download\")\n+            raise\n \n-    else:\n-        if os.path.exists(zst_path) or not os.path.exists(xz_path):\n-            path_compressed = zst_path\n-        else:\n-            path_compressed = xz_path\n-\n-    extract_file(path_compressed)\n+    extract_file(zst_path)\n \n     if support_files_too:\n         for support_file in DATABASES[path][\"support_files\"]:\n@@ -130,10 +98,6 @@\n     url = DATABASES[path][\"url\"]\n     last_modified = utils.get_last_modified(url)\n \n-    if last_modified is None:\n-        base_url = os.path.splitext(url)[0]\n-        last_modified = utils.get_last_modified(f\"{base_url}.xz\")\n-\n     if last_modified is None:\n         raise Exception(\"Last-Modified is not available\")\n", "issue": "Remove fallback on downloading xz files\nIt's added in #524 because the current task have xz as artifacts. Once we make a successful deployment, we can switch to zst fully and remove the xz fallback.\n", "before_files": [{"content": "# -*- coding: utf-8 -*-\n# This Source Code Form is subject to the terms of the Mozilla Public\n# License, v. 2.0. If a copy of the MPL was not distributed with this file,\n# You can obtain one at http://mozilla.org/MPL/2.0/.\n\nimport gzip\nimport io\nimport json\nimport lzma\nimport os\nimport pickle\nimport shutil\nfrom contextlib import contextmanager\nfrom urllib.parse import urljoin\n\nimport requests\nimport zstandard\n\nfrom bugbug import utils\n\nDATABASES = {}\n\n\ndef register(path, url, version, support_files=[]):\n    DATABASES[path] = {\"url\": url, \"version\": version, \"support_files\": support_files}\n\n    # Create DB parent directory.\n    parent_dir = os.path.dirname(path)\n    if not os.path.exists(parent_dir):\n        os.makedirs(parent_dir, exist_ok=True)\n\n    if not os.path.exists(f\"{path}.version\"):\n        with open(f\"{path}.version\", \"w\") as f:\n            f.write(str(version))\n\n\ndef is_old_version(path):\n    with open(f\"{path}.version\", \"r\") as f:\n        prev_version = int(f.read())\n\n    return DATABASES[path][\"version\"] > prev_version\n\n\ndef extract_file(path):\n    path, compression_type = os.path.splitext(path)\n\n    with open(path, \"wb\") as output_f:\n        if compression_type == \".zst\":\n            dctx = zstandard.ZstdDecompressor()\n            with open(f\"{path}.zst\", \"rb\") as input_f:\n                dctx.copy_stream(input_f, output_f)\n\n        elif compression_type == \".xz\":\n            with lzma.open(f\"{path}.xz\") as input_f:\n                shutil.copyfileobj(input_f, output_f)\n\n        else:\n            assert False, f\"Unexpected compression type: {compression_type}\"\n\n\ndef download_support_file(path, file_name):\n    try:\n        url = urljoin(DATABASES[path][\"url\"], file_name)\n        path = os.path.join(os.path.dirname(path), file_name)\n\n        print(f\"Downloading {url} to {path}\")\n        utils.download_check_etag(url, path)\n\n        if path.endswith(\".zst\") or path.endswith(\".xz\"):\n            extract_file(path)\n    except requests.exceptions.HTTPError:\n        try:\n            url = f\"{os.path.splitext(url)[0]}.xz\"\n            path = f\"{os.path.splitext(path)[0]}.xz\"\n\n            print(f\"Downloading {url} to {path}\")\n            utils.download_check_etag(url, path)\n\n            extract_file(path)\n\n        except requests.exceptions.HTTPError:\n            print(f\"{file_name} is not yet available to download for {path}\")\n\n\ndef download_version(path):\n    download_support_file(path, f\"{os.path.basename(path)}.version\")\n\n\n# Download and extract databases.\ndef download(path, force=False, support_files_too=False):\n    if os.path.exists(path) and not force:\n        return\n\n    zst_path = f\"{path}.zst\"\n    xz_path = f\"{path}.xz\"\n\n    # Only download if the file is not there yet.\n    if (not os.path.exists(zst_path) and not os.path.exists(xz_path)) or force:\n        url = DATABASES[path][\"url\"]\n        try:\n            path_compressed = zst_path\n            print(f\"Downloading {url} to {path_compressed}\")\n            utils.download_check_etag(url, path_compressed)\n\n        except requests.exceptions.HTTPError:\n            try:\n                url_xz = f\"{os.path.splitext(url)[0]}.xz\"\n                path_compressed = xz_path\n                print(f\"Downloading {url_xz} to {path_compressed} instead\")\n                utils.download_check_etag(url_xz, path_compressed)\n\n            except requests.exceptions.HTTPError:\n                print(f\"{url} is not yet available to download\")\n                raise\n\n    else:\n        if os.path.exists(zst_path) or not os.path.exists(xz_path):\n            path_compressed = zst_path\n        else:\n            path_compressed = xz_path\n\n    extract_file(path_compressed)\n\n    if support_files_too:\n        for support_file in DATABASES[path][\"support_files\"]:\n            download_support_file(path, support_file)\n\n\ndef last_modified(path):\n    url = DATABASES[path][\"url\"]\n    last_modified = utils.get_last_modified(url)\n\n    if last_modified is None:\n        base_url = os.path.splitext(url)[0]\n        last_modified = utils.get_last_modified(f\"{base_url}.xz\")\n\n    if last_modified is None:\n        raise Exception(\"Last-Modified is not available\")\n\n    return last_modified\n\n\nclass Store:\n    def __init__(self, fh):\n        self.fh = fh\n\n\nclass JSONStore(Store):\n    def write(self, elems):\n        for elem in elems:\n            self.fh.write((json.dumps(elem) + \"\\n\").encode(\"utf-8\"))\n\n    def read(self):\n        for line in io.TextIOWrapper(self.fh, encoding=\"utf-8\"):\n            yield json.loads(line)\n\n\nclass PickleStore(Store):\n    def write(self, elems):\n        for elem in elems:\n            self.fh.write(pickle.dumps(elem))\n\n    def read(self):\n        try:\n            while True:\n                yield pickle.load(self.fh)\n        except EOFError:\n            pass\n\n\nCOMPRESSION_FORMATS = [\"gz\", \"zstd\"]\nSERIALIZATION_FORMATS = {\"json\": JSONStore, \"pickle\": PickleStore}\n\n\n@contextmanager\ndef _db_open(path, mode):\n    parts = str(path).split(\".\")\n    assert len(parts) > 1, \"Extension needed to figure out serialization format\"\n    if len(parts) == 2:\n        db_format = parts[-1]\n        compression = None\n    else:\n        db_format = parts[-2]\n        compression = parts[-1]\n\n    assert compression is None or compression in COMPRESSION_FORMATS\n    assert db_format in SERIALIZATION_FORMATS\n\n    store_constructor = SERIALIZATION_FORMATS[db_format]\n\n    if compression == \"gz\":\n        with gzip.GzipFile(path, mode) as f:\n            yield store_constructor(f)\n    elif compression == \"zstd\":\n        if \"w\" in mode or \"a\" in mode:\n            cctx = zstandard.ZstdCompressor()\n            with open(path, mode) as f:\n                with cctx.stream_writer(f) as writer:\n                    yield store_constructor(writer)\n        else:\n            dctx = zstandard.ZstdDecompressor()\n            with open(path, mode) as f:\n                with dctx.stream_reader(f) as reader:\n                    yield store_constructor(reader)\n    else:\n        with open(path, mode) as f:\n            yield store_constructor(f)\n\n\ndef read(path):\n    assert path in DATABASES\n\n    if not os.path.exists(path):\n        return ()\n\n    with _db_open(path, \"rb\") as store:\n        for elem in store.read():\n            yield elem\n\n\ndef write(path, elems):\n    assert path in DATABASES\n\n    with _db_open(path, \"wb\") as store:\n        store.write(elems)\n\n\ndef append(path, elems):\n    assert path in DATABASES\n\n    with _db_open(path, \"ab\") as store:\n        store.write(elems)\n\n\ndef delete(path, match):\n    assert path in DATABASES\n\n    dirname, basename = os.path.split(path)\n    new_path = os.path.join(dirname, f\"new_{basename}\")\n\n    def matching_elems(store):\n        for elem in store.read():\n            if not match(elem):\n                yield elem\n\n    with _db_open(new_path, \"wb\") as wstore:\n        with _db_open(path, \"rb\") as rstore:\n            wstore.write(matching_elems(rstore))\n\n    os.unlink(path)\n    os.rename(new_path, path)\n", "path": "bugbug/db.py"}], "after_files": [{"content": "# -*- coding: utf-8 -*-\n# This Source Code Form is subject to the terms of the Mozilla Public\n# License, v. 2.0. If a copy of the MPL was not distributed with this file,\n# You can obtain one at http://mozilla.org/MPL/2.0/.\n\nimport gzip\nimport io\nimport json\nimport os\nimport pickle\nfrom contextlib import contextmanager\nfrom urllib.parse import urljoin\n\nimport requests\nimport zstandard\n\nfrom bugbug import utils\n\nDATABASES = {}\n\n\ndef register(path, url, version, support_files=[]):\n    DATABASES[path] = {\"url\": url, \"version\": version, \"support_files\": support_files}\n\n    # Create DB parent directory.\n    parent_dir = os.path.dirname(path)\n    if not os.path.exists(parent_dir):\n        os.makedirs(parent_dir, exist_ok=True)\n\n    if not os.path.exists(f\"{path}.version\"):\n        with open(f\"{path}.version\", \"w\") as f:\n            f.write(str(version))\n\n\ndef is_old_version(path):\n    with open(f\"{path}.version\", \"r\") as f:\n        prev_version = int(f.read())\n\n    return DATABASES[path][\"version\"] > prev_version\n\n\ndef extract_file(path):\n    path, compression_type = os.path.splitext(path)\n\n    with open(path, \"wb\") as output_f:\n        if compression_type == \".zst\":\n            dctx = zstandard.ZstdDecompressor()\n            with open(f\"{path}.zst\", \"rb\") as input_f:\n                dctx.copy_stream(input_f, output_f)\n        else:\n            assert False, f\"Unexpected compression type: {compression_type}\"\n\n\ndef download_support_file(path, file_name):\n    try:\n        url = urljoin(DATABASES[path][\"url\"], file_name)\n        path = os.path.join(os.path.dirname(path), file_name)\n\n        print(f\"Downloading {url} to {path}\")\n        utils.download_check_etag(url, path)\n\n        if path.endswith(\".zst\"):\n            extract_file(path)\n    except requests.exceptions.HTTPError:\n        print(f\"{file_name} is not yet available to download for {path}\")\n\n\ndef download_version(path):\n    download_support_file(path, f\"{os.path.basename(path)}.version\")\n\n\n# Download and extract databases.\ndef download(path, force=False, support_files_too=False):\n    if os.path.exists(path) and not force:\n        return\n\n    zst_path = f\"{path}.zst\"\n\n    # Only download if the file is not there yet.\n    if not os.path.exists(zst_path) or force:\n        url = DATABASES[path][\"url\"]\n        try:\n            print(f\"Downloading {url} to {zst_path}\")\n            utils.download_check_etag(url, zst_path)\n\n        except requests.exceptions.HTTPError:\n            print(f\"{url} is not yet available to download\")\n            raise\n\n    extract_file(zst_path)\n\n    if support_files_too:\n        for support_file in DATABASES[path][\"support_files\"]:\n            download_support_file(path, support_file)\n\n\ndef last_modified(path):\n    url = DATABASES[path][\"url\"]\n    last_modified = utils.get_last_modified(url)\n\n    if last_modified is None:\n        raise Exception(\"Last-Modified is not available\")\n\n    return last_modified\n\n\nclass Store:\n    def __init__(self, fh):\n        self.fh = fh\n\n\nclass JSONStore(Store):\n    def write(self, elems):\n        for elem in elems:\n            self.fh.write((json.dumps(elem) + \"\\n\").encode(\"utf-8\"))\n\n    def read(self):\n        for line in io.TextIOWrapper(self.fh, encoding=\"utf-8\"):\n            yield json.loads(line)\n\n\nclass PickleStore(Store):\n    def write(self, elems):\n        for elem in elems:\n            self.fh.write(pickle.dumps(elem))\n\n    def read(self):\n        try:\n            while True:\n                yield pickle.load(self.fh)\n        except EOFError:\n            pass\n\n\nCOMPRESSION_FORMATS = [\"gz\", \"zstd\"]\nSERIALIZATION_FORMATS = {\"json\": JSONStore, \"pickle\": PickleStore}\n\n\n@contextmanager\ndef _db_open(path, mode):\n    parts = str(path).split(\".\")\n    assert len(parts) > 1, \"Extension needed to figure out serialization format\"\n    if len(parts) == 2:\n        db_format = parts[-1]\n        compression = None\n    else:\n        db_format = parts[-2]\n        compression = parts[-1]\n\n    assert compression is None or compression in COMPRESSION_FORMATS\n    assert db_format in SERIALIZATION_FORMATS\n\n    store_constructor = SERIALIZATION_FORMATS[db_format]\n\n    if compression == \"gz\":\n        with gzip.GzipFile(path, mode) as f:\n            yield store_constructor(f)\n    elif compression == \"zstd\":\n        if \"w\" in mode or \"a\" in mode:\n            cctx = zstandard.ZstdCompressor()\n            with open(path, mode) as f:\n                with cctx.stream_writer(f) as writer:\n                    yield store_constructor(writer)\n        else:\n            dctx = zstandard.ZstdDecompressor()\n            with open(path, mode) as f:\n                with dctx.stream_reader(f) as reader:\n                    yield store_constructor(reader)\n    else:\n        with open(path, mode) as f:\n            yield store_constructor(f)\n\n\ndef read(path):\n    assert path in DATABASES\n\n    if not os.path.exists(path):\n        return ()\n\n    with _db_open(path, \"rb\") as store:\n        for elem in store.read():\n            yield elem\n\n\ndef write(path, elems):\n    assert path in DATABASES\n\n    with _db_open(path, \"wb\") as store:\n        store.write(elems)\n\n\ndef append(path, elems):\n    assert path in DATABASES\n\n    with _db_open(path, \"ab\") as store:\n        store.write(elems)\n\n\ndef delete(path, match):\n    assert path in DATABASES\n\n    dirname, basename = os.path.split(path)\n    new_path = os.path.join(dirname, f\"new_{basename}\")\n\n    def matching_elems(store):\n        for elem in store.read():\n            if not match(elem):\n                yield elem\n\n    with _db_open(new_path, \"wb\") as wstore:\n        with _db_open(path, \"rb\") as rstore:\n            wstore.write(matching_elems(rstore))\n\n    os.unlink(path)\n    os.rename(new_path, path)\n", "path": "bugbug/db.py"}]}