import os import base64 import time from dotenv import load_dotenv from openai import OpenAI import httpx load_dotenv() # Наш финальный список "выживших" MODELS_TO_TEST = [ "openai/claude-opus-4-6", "openai/gpt-4o", "openai/gpt-5-pro" ] client = OpenAI( api_key=os.getenv("LAOZHANG_API_KEY"), base_url=os.getenv("LAOZHANG_BASE_URL"), http_client=httpx.Client(timeout=httpx.Timeout(600.0, connect=30.0)) ) def encode_image(image_path): with open(image_path, "rb") as img: return base64.b64encode(img.read()).decode('utf-8') def get_instructions(criteria_file): with open("SKILL.md", "r", encoding="utf-8") as f: skill = f.read() c_path = os.path.join("references", criteria_file) with open(c_path, "r", encoding="utf-8") as f: criteria = f.read() return f"{skill}\n\n{criteria}" def run_mass_check(base_dir="photo", criteria_file="russian-essay-criteria.md"): # 1. Находим все папки учеников students = [d for d in os.listdir( base_dir) if os.path.isdir(os.path.join(base_dir, d))] if not students: print("[!] В папке photo пусто. Создай там папки с именами учеников.") return print(f"=== ЗАПУСК МАССОВОЙ ПРОВЕРКИ: {len(students)} учеников ===") instructions = get_instructions(criteria_file) for student in students: student_path = os.path.join(base_dir, student) photos = sorted([f for f in os.listdir(student_path) if f.lower().endswith(('.jpg', '.jpeg', '.png'))]) if not photos: print(f"[SKIP] У {student} нет фото.") continue print(f"\n>>> РАБОТАЕМ С: {student.upper()} ({len(photos)} листа)") # Подготовка контента ОДИН РАЗ для всех моделей (экономим время) message_content = [ {"type": "text", "text": "Распознай рукописный текст и проверь сочинение строго по критериям ФИПИ."}] for p in photos: b64 = encode_image(os.path.join(student_path, p)) message_content.append({ "type": "image_url", "image_url": {"url": f"data:image/jpeg;base64,{b64}"} }) for model_id in MODELS_TO_TEST: safe_name = model_id.replace("/", "_") output_file = f"REPORT_{student}_{safe_name}.md" # Проверка: если файл уже есть — пропускаем if os.path.exists(output_file): print(f" [-] {model_id}: Уже проверено.") continue print(f" [!] Запуск {model_id}...") start_time = time.time() try: response = client.chat.completions.create( model=model_id, messages=[ {"role": "system", "content": instructions}, {"role": "user", "content": message_content} ], temperature=0.0 ) res_text = response.choices[0].message.content duration = round(time.time() - start_time, 1) with open(output_file, "w", encoding="utf-8") as f: header = f"--- \n**Ученик:** {student}\n**Модель:** {model_id}\n**Время:** {duration} сек.\n---\n\n" f.write(header + res_text) print(f" [OK] Готово! ({duration} сек.)") time.sleep(12) # Безопасная пауза для лимитов except Exception as e: print(f" [ERR] Ошибка у {model_id}: {str(e)}") if __name__ == "__main__": run_mass_check() print("\n=== ВСЕ ПРОВЕРКИ ВЫПОЛНЕНЫ ===")