总结优化
This commit is contained in:
@@ -2,42 +2,54 @@ import subprocess
|
||||
import time
|
||||
import markdown
|
||||
from pathlib import Path
|
||||
|
||||
import psutil
|
||||
from playwright.async_api import async_playwright
|
||||
import os
|
||||
import asyncio
|
||||
from loguru import logger
|
||||
|
||||
|
||||
async def safe_close_browser(browser, timeout: float = 5.0) -> None:
|
||||
async def safe_close_browser(browser, timeout: float = 4.0) -> None:
|
||||
if not browser:
|
||||
return
|
||||
|
||||
# Close contexts first to reduce hanging risk.
|
||||
try:
|
||||
for ctx in browser.contexts:
|
||||
# 1. 先尝试关闭所有 page(最重要)
|
||||
for context in browser.contexts[:]: # 复制列表防止修改中迭代
|
||||
for page in context.pages[:]:
|
||||
try:
|
||||
await asyncio.wait_for(ctx.close(), timeout=timeout)
|
||||
except Exception:
|
||||
await asyncio.wait_for(page.close(), timeout=1.5)
|
||||
except:
|
||||
pass
|
||||
except Exception:
|
||||
pass
|
||||
try:
|
||||
await asyncio.wait_for(context.close(), timeout=timeout)
|
||||
except:
|
||||
pass
|
||||
|
||||
# Then close browser with timeout.
|
||||
# 2. 尝试优雅关闭 browser
|
||||
try:
|
||||
await asyncio.wait_for(browser.close(), timeout=timeout)
|
||||
logger.debug("browser closed gracefully")
|
||||
return
|
||||
except asyncio.TimeoutError:
|
||||
logger.warning("Browser close timed out, killing process")
|
||||
except Exception as e:
|
||||
logger.warning(f"Browser close failed, killing process: {e}")
|
||||
except (asyncio.TimeoutError, Exception) as e:
|
||||
logger.warning(f"browser.close failed: {e}")
|
||||
|
||||
# Final fallback: kill underlying process.
|
||||
try:
|
||||
proc = browser.process
|
||||
if proc:
|
||||
proc.kill()
|
||||
except Exception:
|
||||
pass
|
||||
# 3. 强制杀进程树(最关键一步)
|
||||
if browser.process and browser.process.pid:
|
||||
try:
|
||||
parent = psutil.Process(browser.process.pid)
|
||||
children = parent.children(recursive=True)
|
||||
for child in children:
|
||||
try:
|
||||
child.kill()
|
||||
except psutil.NoSuchProcess:
|
||||
pass
|
||||
parent.kill()
|
||||
# 可选:等待一小会儿确认退出
|
||||
psutil.wait_procs([parent] + children, timeout=3)
|
||||
logger.debug("process tree killed")
|
||||
except (psutil.NoSuchProcess, Exception) as e:
|
||||
logger.warning(f"force kill failed: {e}")
|
||||
|
||||
|
||||
# ================= 样式与 HTML 处理 =================
|
||||
|
||||
Reference in New Issue
Block a user