diff --git a/launcher.py b/launcher.py index 8ee5188..ed173e0 100644 --- a/launcher.py +++ b/launcher.py @@ -1,16 +1,19 @@ +import io import json import mimetypes +import os +import shutil +import subprocess +import threading from pathlib import Path from shutil import rmtree -from subprocess import CREATE_NO_WINDOW, PIPE, STDOUT, Popen +from subprocess import CREATE_NO_WINDOW, Popen import requests import webview from launcher import config from log import logger -import shutil -import os mimetypes.add_type("text/html", ".html") mimetypes.add_type("text/css", ".css") @@ -33,6 +36,7 @@ def custom_event(data): mirror_list = { "pypi": "https://pypi.org/simple", + "aliyun": "https://mirrors.aliyun.com/pypi/simple/", "tuna": "https://mirrors.tuna.tsinghua.edu.cn/pypi/web/simple", "sjtu": "https://mirror.sjtu.edu.cn/pypi/web/simple", @@ -41,16 +45,27 @@ mirror_list = { command_list = { "lfs": "git\\bin\\git lfs install", "ensurepip": "python\\python -m ensurepip --default-pip", - "clone": "git\\bin\\git clone https://git.zhaozuohong.vip/mower-ng/mower-ng.git --branch slow", - "fetch": lambda: f"..\\git\\bin\\git fetch origin {config.conf.branch}", - "switch": lambda: f"..\\git\\bin\\git switch -f {config.conf.branch}", - "reset": lambda: f"..\\git\\bin\\git reset --hard origin/{config.conf.branch}", + "clone": "git\\bin\\git -c lfs.concurrenttransfers=100 clone https://git.zhaozuohong.vip/mower-ng/mower-ng.git --branch slow", + "fetch": lambda: f"..\\git\\bin\\git fetch origin {config.conf.branch} --progress", + "switch": lambda: f"..\\git\\bin\\git -c lfs.concurrenttransfers=100 switch -f {config.conf.branch} --progress", + "reset": lambda: f"..\\git\\bin\\git -c lfs.concurrenttransfers=200 reset --hard origin/{config.conf.branch}", "pip_install": lambda: f"..\\python\\Scripts\\pip install --no-cache-dir -i {mirror_list[config.conf.mirror]} -r requirements.txt --no-warn-script-location", "webview": "start ..\\python\\pythonw webview_ui.py", "manager": "start ..\\python\\pythonw manager.py", } +def read_stream(stream, log_func): + text_io = io.TextIOWrapper(stream, encoding='utf-8', errors='replace') + try: + for line in iter(text_io.readline, ''): + text = line.rstrip('\n') + log_func(f"log: {text}") + custom_event(text.strip() + "\n") + finally: + text_io.close() + + class Api: def load_config(self): @@ -121,19 +136,26 @@ class Api: if callable(command): command = command() custom_event(command + "\n") + logger.info(f"cwd {cwd}") + logger.info(f"command {command}") try: - with Popen( - command, stdout=PIPE, stderr=STDOUT, shell=True, cwd=cwd, bufsize=0 + with subprocess.Popen( + command, stdout=subprocess.PIPE, stderr=subprocess.PIPE, shell=True, cwd=cwd, bufsize=0, + universal_newlines=False ) as p: - for data in p.stdout: - try: - text = data.decode("utf-8") - except Exception: - text = data.decode("gbk") - custom_event(text) + stdout_thread = threading.Thread(target=read_stream, args=(p.stdout, logger.info)) + stderr_thread = threading.Thread(target=read_stream, args=(p.stderr, logger.error)) + + stdout_thread.start() + stderr_thread.start() + + stdout_thread.join() + stderr_thread.join() if p.returncode == 0: return "success" except Exception as e: + logger.error(f"command {command} 执行异常{e}") + logger.exception(e) custom_event(str(e)) return "failed"