59 lines
1.8 KiB
Python
59 lines
1.8 KiB
Python
"""
|
||
模拟超时跳过逻辑
|
||
文件列表:file_A 正常(2s),file_B 超时(20s),file_C 正常(2s)
|
||
期望结果:B 超时后直接跳到 C,总耗时约 TIMEOUT+2s 而不是 20+2+2s
|
||
"""
|
||
|
||
import time
|
||
import threading
|
||
import concurrent.futures
|
||
from concurrent.futures import ThreadPoolExecutor
|
||
|
||
EXTRACT_TIMEOUT = 5 # 测试用 5 秒超时
|
||
|
||
|
||
def fake_extract(file_name, cancel_event):
|
||
"""模拟抽取:file_B 故意睡 20 秒"""
|
||
sleep_time = 20 if file_name == "file_B" else 2
|
||
print(f" [{file_name}] 开始抽取,预计耗时 {sleep_time}s")
|
||
for _ in range(sleep_time * 10):
|
||
time.sleep(0.1)
|
||
if cancel_event.is_set():
|
||
print(f" [{file_name}] 收到取消信号,退出不写 JSON")
|
||
return {"file": file_name, "status": "timeout"}
|
||
print(f" [{file_name}] 抽取完成,写 JSON")
|
||
return {"file": file_name, "status": "ok"}
|
||
|
||
|
||
def run():
|
||
files = ["file_A", "file_B", "file_C"]
|
||
results = []
|
||
t_start = time.time()
|
||
|
||
with ThreadPoolExecutor(max_workers=2) as pool:
|
||
future_meta = []
|
||
for f in files:
|
||
evt = threading.Event()
|
||
fut = pool.submit(fake_extract, f, evt)
|
||
future_meta.append((fut, f, evt))
|
||
|
||
for fut, f, evt in future_meta:
|
||
try:
|
||
result = fut.result(timeout=EXTRACT_TIMEOUT)
|
||
results.append(result)
|
||
except concurrent.futures.TimeoutError:
|
||
evt.set()
|
||
print(f" [{f}] 超时,跳过,记录 fault 文件")
|
||
results.append({"file": f, "status": "timeout"})
|
||
|
||
total = time.time() - t_start
|
||
print(f"\n总耗时: {total:.1f}s")
|
||
print("结果汇总:")
|
||
for r in results:
|
||
print(f" {r}")
|
||
|
||
|
||
if __name__ == "__main__":
|
||
run()
|
||
|