Files
anti-plagiarism/services/worker-gpu/app/models/base.py
jze9 2daaa8c8a4 chore(lint): ruff-гейт в CI + фиксы (0 находок) — блокирует кривой деплой
Второй CI-гейт после тестов: ruff как статический анализатор всего Python-кода
(services + scripts). Раньше ни линта, ни проверки типов в CI не было вовсе.

Конфиг ruff.toml: правила E/F/W/I/UP/B/SIM/C4, line-length 100. Осознанно
выключены E501 (длину держит форматтер; длинные RU-комментарии — норма),
B008 (Depends()/Query() в дефолтах — идиома FastAPI, не баг) и UP042
((str, Enum)→StrEnum меняет __str__/сериализацию — не трогаем).

Починено под ноль находок:
- B904 (11): raise ... from exc / from None — читаемые цепочки исключений в
  Celery-ретраях и HTTPException, ошибки обработки не маскируют исходные.
- SIM105 (5): try/except/pass → contextlib.suppress (faiss remove_ids, lsh.remove,
  сброс кэша, ws-disconnect, парс года).
- C416/SIM108/B905/F841/UP035/UP017/F401/I001: dict(rows), тернарник, zip strict,
  мёртвая переменная, устаревшие импорты, timezone.utc→UTC, чистка/сортировка.

Обвязка: scripts/run_lint.sh (ruff в изолированном python:3.11-slim), шаг «Линт»
в job test перед юнит-тестами (падаем раньше). make lint / make lint-fix.
Все 41 юнит-тест по-прежнему зелёные, изменённые файлы компилируются.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-08-11 17:20:24 +05:00

67 lines
2.9 KiB
Python
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
"""Базовые модели данных для GPU воркера (минимальный набор для работы с БД)."""
from datetime import datetime
from sqlalchemy import JSON, ForeignKey, Integer, String, Text, func
from sqlalchemy.orm import DeclarativeBase, Mapped, mapped_column
class Base(DeclarativeBase):
"""Базовый класс SQLAlchemy моделей."""
pass
class User(Base):
"""Минимальная модель пользователя для GPU воркера."""
__tablename__ = "users"
id: Mapped[int] = mapped_column(Integer, primary_key=True)
email: Mapped[str] = mapped_column(String(255))
name: Mapped[str] = mapped_column(String(255))
plan: Mapped[str] = mapped_column(String(20), default="free")
is_verified: Mapped[bool] = mapped_column(default=False)
created_at: Mapped[datetime] = mapped_column(server_default=func.now())
class Task(Base):
"""Модель задачи."""
__tablename__ = "tasks"
id: Mapped[str] = mapped_column(String(36), primary_key=True)
user_id: Mapped[int] = mapped_column(ForeignKey("users.id"))
type: Mapped[str] = mapped_column(String(20))
status: Mapped[str] = mapped_column(String(20), default="queued")
celery_task_id: Mapped[str | None] = mapped_column(String(255), nullable=True)
input_data: Mapped[dict] = mapped_column(JSON, default=dict)
result: Mapped[dict | None] = mapped_column(JSON, nullable=True)
error: Mapped[str | None] = mapped_column(Text, nullable=True)
queue_position: Mapped[int | None] = mapped_column(nullable=True)
created_at: Mapped[datetime] = mapped_column(server_default=func.now())
updated_at: Mapped[datetime | None] = mapped_column(nullable=True)
class Document(Base):
"""Модель документа в базе знаний."""
__tablename__ = "documents"
id: Mapped[int] = mapped_column(Integer, primary_key=True)
source: Mapped[str] = mapped_column(String(50))
ext_id: Mapped[str] = mapped_column(String(255))
doi: Mapped[str | None] = mapped_column(String(255), nullable=True)
title: Mapped[str] = mapped_column(Text)
authors: Mapped[list] = mapped_column(JSON, default=list)
year: Mapped[int | None] = mapped_column(nullable=True)
lang: Mapped[str | None] = mapped_column(String(10), nullable=True)
journal: Mapped[str | None] = mapped_column(Text, nullable=True)
volume: Mapped[str | None] = mapped_column(String(50), nullable=True)
issue: Mapped[str | None] = mapped_column(String(50), nullable=True)
pages: Mapped[str | None] = mapped_column(String(50), nullable=True)
abstract: Mapped[str | None] = mapped_column(Text, nullable=True)
url: Mapped[str | None] = mapped_column(Text, nullable=True)
minio_key: Mapped[str | None] = mapped_column(Text, nullable=True)
faiss_id: Mapped[int | None] = mapped_column(nullable=True)
indexed_at: Mapped[datetime] = mapped_column(server_default=func.now())