diff --git a/accesser/utils/certmanager.py b/accesser/utils/certmanager.py
index f50c709..37df450 100644
--- a/accesser/utils/certmanager.py
+++ b/accesser/utils/certmanager.py
@@ -16,7 +16,7 @@
# You should have received a copy of the GNU General Public License
# along with this program. If not, see .
-import os
+import os, platform
import datetime
from pathlib import Path
@@ -33,14 +33,53 @@
)
from cryptography.x509.oid import ExtendedKeyUsageOID
+from .log import logger
+logger = logger.getChild("certmanager")
from . import setting
from .setting import basepath
-if setting.config["importca"]:
- certpath = os.path.join(basepath, "CERT")
-else:
- certpath = "CERT"
-if not os.path.exists(certpath):
+
+def decide_state_path_legacy():
+ if setting.config["importca"]:
+ return Path(basepath)
+ else:
+ return Path()
+
+
+def decide_state_path_unix_like():
+ if os.geteuid() == 0:
+ logger.warn("Running Accesser as the root user carries certain risks; see pull #245")
+ return Path("/var/lib") / "accesser"
+
+ state_path = os.getenv("XDG_STATE_HOME", None)
+ if state_path is not None:
+ state_path = Path(state_path) / "accesser"
+ else:
+ state_path = Path.home() / ".local/state" / "accesser"
+ return state_path
+
+
+def decide_certpath():
+ certpath = None
+ # 人为指定最优先
+ #if setting.config["state_dir"]:
+ #return Path(setting.config["state_dir"]) / "cert"
+ match platform.system():
+ case 'Linux' | 'FreeBSD':
+ deprecated_path = decide_state_path_legacy() / "CERT"
+ # 暂仅在 *nix 上视为已废弃
+ if deprecated_path.exists():
+ logger.warn("deprecated path, see pull #245")
+ return deprecated_path
+ certpath = decide_state_path_unix_like() / "cert"
+ case _:
+ # windows,mac,android ...
+ certpath = decide_state_path_legacy() / "CERT"
+ return certpath
+
+
+certpath = decide_certpath()
+if not certpath.exists():
os.makedirs(certpath, exist_ok=True)
@@ -92,11 +131,11 @@ def create_root_ca():
.sign(key, hashes.SHA256())
)
- (Path(certpath) / "root.crt").write_bytes(
+ (certpath / "root.crt").write_bytes(
cert.public_bytes(serialization.Encoding.PEM)
)
- (Path(certpath) / "root.key").write_bytes(
+ (certpath / "root.key").write_bytes(
key.private_bytes(
encoding=serialization.Encoding.PEM,
format=serialization.PrivateFormat.PKCS8,
@@ -104,7 +143,7 @@ def create_root_ca():
)
)
- (Path(certpath) / "root.pfx").write_bytes(
+ (certpath / "root.pfx").write_bytes(
serialization.pkcs12.serialize_key_and_certificates(
b"Accesser", key, cert, None, serialization.NoEncryption()
)
@@ -112,8 +151,8 @@ def create_root_ca():
def create_certificate(server_name):
- rootpem = (Path(certpath) / "root.crt").read_bytes()
- rootkey = (Path(certpath) / "root.key").read_bytes()
+ rootpem = (certpath / "root.crt").read_bytes()
+ rootkey = (certpath / "root.key").read_bytes()
ca_cert = x509.load_pem_x509_certificate(rootpem)
pkey = serialization.load_pem_private_key(rootkey, password=None)
@@ -180,7 +219,7 @@ def create_certificate(server_name):
.sign(pkey, hashes.SHA256())
)
- (Path(certpath) / f"{server_name}.crt").write_bytes(
+ (certpath / f"{server_name}.crt").write_bytes(
cert.public_bytes(serialization.Encoding.PEM)
+ pkey.private_bytes(
encoding=serialization.Encoding.PEM,
diff --git a/accesser/utils/importca.py b/accesser/utils/importca.py
index 94a46a6..6b7380c 100644
--- a/accesser/utils/importca.py
+++ b/accesser/utils/importca.py
@@ -17,6 +17,7 @@
# along with this program. If not, see .
import os, sys
+from pathlib import Path
import subprocess
import locale
@@ -25,14 +26,10 @@
from . import setting
from . import certmanager as cm
-from .setting import basepath
from .log import logger
logger = logger.getChild('importca')
-if setting.config['importca']:
- certpath = os.path.join(basepath, 'CERT')
-else:
- certpath = 'CERT'
+certpath = cm.certpath
def logandrun(cmd):
if hasattr(subprocess, 'STARTUPINFO'):
diff --git a/accesser/utils/setting.py b/accesser/utils/setting.py
index 7c9e74e..6b871ff 100644
--- a/accesser/utils/setting.py
+++ b/accesser/utils/setting.py
@@ -71,8 +71,18 @@ def parse_args():
action="store_true",
help="do not import certificate to system automatically",
)
+ parser.add_argument(
+ "--state-dir",
+ type=str,
+ help="where state file store , override notimportca",
+ default=None,
+ )
args = parser.parse_args()
if args.notsetproxy:
config["setproxy"] = False
+ return
+ # FIXME Wrong initialization sequence
+ # see pull #245
if args.notimportca:
config["importca"] = False
+ config["state_dir"] = args.state_dir