nps: bundle pkg2zip binary and run it via Wine
pkg2zip's prebuilt releases are Windows-only, so ship pkg2zip.exe in data/bin/ (MIT, mmozeiko) and invoke it through Wine on Linux. find_pkg2zip prefers the bundled binary, then a configured path, then a native pkg2zip on PATH. Adds data/bin/ATTRIBUTION.md and README credit.
This commit is contained in:
+23
-3
@@ -9,6 +9,7 @@ folder.
|
||||
from __future__ import annotations
|
||||
|
||||
import logging
|
||||
import os
|
||||
import shutil
|
||||
import subprocess
|
||||
import urllib.parse
|
||||
@@ -142,14 +143,30 @@ def fetch_items(content_type: str, url: str = "", timeout: int = 60) -> List[dic
|
||||
|
||||
|
||||
def find_pkg2zip(configured_path: str = "") -> Optional[Path]:
|
||||
"""Locate the pkg2zip binary (configured path, else PATH)."""
|
||||
"""Locate pkg2zip: configured path, then the bundled binary, then PATH."""
|
||||
if configured_path:
|
||||
p = Path(configured_path)
|
||||
return p if p.is_file() else None
|
||||
bundled = config.DATA_DIR / "bin" / "pkg2zip.exe"
|
||||
if bundled.is_file():
|
||||
return bundled
|
||||
found = shutil.which("pkg2zip")
|
||||
return Path(found) if found else None
|
||||
|
||||
|
||||
def _pkg2zip_cmd(pkg2zip: Path) -> List[str]:
|
||||
"""Command prefix for pkg2zip, wrapping the bundled .exe in Wine on Linux."""
|
||||
if pkg2zip.suffix.lower() == ".exe" and os.name != "nt":
|
||||
wine = shutil.which("wine") or shutil.which("wine64")
|
||||
if not wine:
|
||||
raise RuntimeError(
|
||||
"The bundled pkg2zip is a Windows binary and Wine is not installed — "
|
||||
"install Wine (or point Settings → Store at a native pkg2zip)."
|
||||
)
|
||||
return [wine, str(pkg2zip)]
|
||||
return [str(pkg2zip)]
|
||||
|
||||
|
||||
def _safe_folder(value: str) -> str:
|
||||
import re
|
||||
cleaned = re.sub(r"[^A-Za-z0-9]", "", value or "").upper()
|
||||
@@ -180,10 +197,13 @@ def extract_pkg(pkg_path, title_id: str, dest_dir, pkg2zip: Path,
|
||||
if progress_cb is not None:
|
||||
progress_cb("Extracting", 0.0, "")
|
||||
try:
|
||||
cmd = _pkg2zip_cmd(pkg2zip) + ["-x", str(pkg_path)]
|
||||
env = dict(os.environ)
|
||||
env["WINEDEBUG"] = "-all" # silence Wine's console chatter
|
||||
proc = subprocess.Popen(
|
||||
[str(pkg2zip), "-x", str(pkg_path)],
|
||||
cmd,
|
||||
cwd=str(tmp), stdout=subprocess.PIPE, stderr=subprocess.STDOUT,
|
||||
text=True, bufsize=1,
|
||||
text=True, bufsize=1, env=env,
|
||||
)
|
||||
assert proc.stdout is not None
|
||||
for _line in proc.stdout:
|
||||
|
||||
Reference in New Issue
Block a user