mirror of
https://github.com/dcs-liberation/dcs_liberation.git
synced 2025-11-10 14:22:26 +00:00
This is the first step toward bundling all assets related to a save game into a single item. That makes it easier to avoid clobbering "temporary" assets from other games like the state.json, but also makes it easier for players to file bug reports, since there's only a single asset to upload. This is only the first step because so far it only includes the various save files: start of turn, end of last turn before results processing, and "latest" (the game saved explicitly by the player).
35 lines
1.4 KiB
Python
35 lines
1.4 KiB
Python
import shutil
|
|
from pathlib import Path
|
|
from tempfile import TemporaryDirectory
|
|
from zipfile import ZipFile
|
|
|
|
|
|
class ZipFileExt:
|
|
@staticmethod
|
|
def remove_member(path: Path, name: str, missing_ok: bool = False) -> None:
|
|
"""Replaces the archive with a copy that excludes one member.
|
|
|
|
This is needed to workaround Python's lack of a ZipFile.remove() or a way to
|
|
overwrite existing members. Attempting to update a member in a zipfile will
|
|
write a duplicate entry: https://github.com/python/cpython/issues/51067.
|
|
"""
|
|
with ZipFile(path, "r") as zip_file:
|
|
if name not in zip_file.namelist():
|
|
if missing_ok:
|
|
return
|
|
raise ValueError(f"Cannot override {name} as it does not exist")
|
|
|
|
# Doing this by extracting all the files to a temporary directory is faster than
|
|
# reading and writing a file at a time (1-5 seconds vs 0.5 seconds for a save
|
|
# bundle).
|
|
with TemporaryDirectory() as temp_dir_str:
|
|
temp_dir = Path(temp_dir_str)
|
|
shutil.unpack_archive(path, temp_dir)
|
|
(temp_dir / name).unlink()
|
|
shutil.make_archive(
|
|
# shutil.make_archive automatically adds the extension
|
|
str(path.with_suffix("")),
|
|
"zip",
|
|
root_dir=temp_dir_str,
|
|
)
|