diff --git a/config.yaml.example b/config.yaml.example index 47b9dde..d42ae5c 100644 --- a/config.yaml.example +++ b/config.yaml.example @@ -4,6 +4,11 @@ # 如果没有设置项目级apikey 就用全局 API Key access_key: "YOUR_ACCESS_KEY_HERE" +# 是否显示详细日志(控制台输出 + 写入日志文件) +# true: 显示所有执行过程(默认) +# false: 秒回复成功,仅在脚本不存在时返回错误 +show_log: true + # 项目配置 projects: xsinfo: diff --git a/webhook_server.py b/webhook_server.py index 8e6fe27..89ed812 100644 --- a/webhook_server.py +++ b/webhook_server.py @@ -111,6 +111,7 @@ class WebhookHandler(BaseHTTPRequestHandler): config = load_config() global_key = config.get("access_key", "") + show_log = config.get("show_log", True) # 优先项目级 key,否则用全局 key proj = get_project_config(config, param_val) if param_val else None @@ -129,25 +130,26 @@ class WebhookHandler(BaseHTTPRequestHandler): referer = self.headers.get("Referer", "N/A") # 执行脚本 - result, status_code = self._execute_script(proj, param_val, client_ip, user_agent, referer) + result, status_code = self._execute_script(show_log, proj, param_val, client_ip, user_agent, referer) script_res = result.get("script", {}) - log_event( - "script_executed", - { - "param": param_val, - "project": param_val or "unknown", - "ip": client_ip, - "ua": user_agent, - "referer": referer, - "executed": script_res.get("executed", False), - "status": script_res.get("status", "unknown"), - "exit_code": script_res.get("exit_code"), - }, - status=script_res.get("status", "unknown"), - ) + if show_log: + log_event( + "script_executed", + { + "param": param_val, + "project": param_val or "unknown", + "ip": client_ip, + "ua": user_agent, + "referer": referer, + "executed": script_res.get("executed", False), + "status": script_res.get("status", "unknown"), + "exit_code": script_res.get("exit_code"), + }, + status=script_res.get("status", "unknown"), + ) self.send_json(status_code, {"ok": status_code == 200, "param": param_val, **result}) - def _execute_script(self, proj: dict, param: str, client_ip: str, user_agent: str, referer: str) -> tuple[dict, int]: + def _execute_script(self, show_log: bool, proj: dict, param: str, client_ip: str, user_agent: str, referer: str) -> tuple[dict, int]: """执行脚本,key 对了就执行,不管什么请求""" print(f"\n{'='*60}") print(f"🚀 执行脚本 | param={param}") @@ -166,6 +168,11 @@ class WebhookHandler(BaseHTTPRequestHandler): script_path = os.path.expanduser(proj["script"]) script_cwd = os.path.dirname(os.path.abspath(__file__)) if os.path.exists(script_path): + if not show_log: + # 秒回复模式:不等待执行,不记录日志,直接返回成功 + self._quick_run(script_path, script_cwd) + return {"script": {"executed": False, "status": "background", "exit_code": None, "stdout": None, "stderr": None, "error": None}}, 200 + os.chmod(script_path, 0o755) try: result = subprocess.run( @@ -196,6 +203,7 @@ class WebhookHandler(BaseHTTPRequestHandler): script_result["error"] = str(e) print(f"⚠️ 执行失败 - {e}") else: + # 文件不存在时即使 show_log=False 也返回错误 script_result["executed"] = True script_result["status"] = "not_found" script_result["error"] = f"script not found: {script_path}" @@ -218,6 +226,14 @@ class WebhookHandler(BaseHTTPRequestHandler): return {"script": script_result}, status_code + def _quick_run(self, script_path: str, script_cwd: str): + """后台静默执行脚本,不等待,不记录日志。""" + import threading + def _run(): + os.chmod(script_path, 0o755) + subprocess.run([script_path], cwd=script_cwd, capture_output=True, text=True) + threading.Thread(target=_run, daemon=True).start() + def main(): # 启动前检查配置文件