This commit is contained in:
asus
2026-04-22 19:11:24 +03:30
parent 381c5649ea
commit 443961222f
+71 -1
View File
@@ -40,6 +40,46 @@ def _has_cmd(name: str) -> bool:
return shutil.which(name) is not None
def _is_termux() -> bool:
prefix = os.environ.get("PREFIX", "")
return (
"com.termux/files/usr" in prefix
or "com.termux/files/usr" in os.environ.get("PATH", "")
or bool(os.environ.get("TERMUX_VERSION"))
or os.path.exists("/data/data/com.termux/files/usr")
)
def _android_cert_hint() -> str:
return (
"Import the certificate in Android Settings > Security > "
"Encryption & credentials > Install a certificate > CA certificate."
)
def _stage_android_cert(cert_path: str, cert_name: str) -> str | None:
"""
Copy the CA cert to a user-visible location on Android/Termux so the user
can import it through Android's certificate installer UI.
"""
base = cert_name.replace(" ", "_")
candidates = [
os.path.expanduser("~/storage/downloads"),
"/sdcard/Download",
"/storage/emulated/0/Download",
]
for folder in candidates:
if not os.path.isdir(folder):
continue
dest = os.path.join(folder, f"{base}.crt")
try:
shutil.copy2(cert_path, dest)
return dest
except OSError:
continue
return None
# ─────────────────────────────────────────────────────────────────────────────
# Windows
# ─────────────────────────────────────────────────────────────────────────────
@@ -275,6 +315,31 @@ def _is_trusted_linux(cert_path: str) -> bool:
return False
def _install_termux_android(cert_path: str, cert_name: str) -> bool:
"""
Android does not allow a normal user-space process to silently install a CA
into the OS/browser trust store. On Termux we can only stage the file and
guide the user to Android's certificate installer.
"""
staged = _stage_android_cert(cert_path, cert_name)
log.warning("Detected Termux/Android environment.")
log.warning(
"Automatic CA installation into Android's system/browser trust store "
"is not supported from Termux without user interaction."
)
if staged:
log.warning("Certificate copied to: %s", staged)
else:
log.warning(
"Could not copy the certificate to shared storage automatically. "
"Run 'termux-setup-storage' in Termux first, then try again."
)
log.warning("You can also import this file directly: %s", cert_path)
log.warning(_android_cert_hint())
log.warning("After import, fully close and reopen the browser.")
return False
# ─────────────────────────────────────────────────────────────────────────────
# Firefox NSS (cross-platform)
# ─────────────────────────────────────────────────────────────────────────────
@@ -326,6 +391,9 @@ def is_ca_trusted(cert_path: str) -> bool:
"""Return True if the CA cert appears to be already installed."""
system = platform.system()
try:
if _is_termux():
# Android's user/system CA stores are not directly inspectable here.
return False
if system == "Windows":
return _is_trusted_windows(cert_path)
if system == "Darwin":
@@ -349,7 +417,9 @@ def install_ca(cert_path: str, cert_name: str = CERT_NAME) -> bool:
system = platform.system()
log.info("Installing CA certificate on %s", system)
if system == "Windows":
if _is_termux():
ok = _install_termux_android(cert_path, cert_name)
elif system == "Windows":
ok = _install_windows(cert_path, cert_name)
elif system == "Darwin":
ok = _install_macos(cert_path, cert_name)