ci: add ruff linting and mypy type checking

Add ruff and mypy to dev dependencies with configuration in pyproject.toml.
Add a lint CI job that runs ruff check, ruff format --check, and mypy.
Auto-fix import sorting and formatting across the codebase. Exclude
alembic/versions from linting (auto-generated migrations). Ignore B008
(FastAPI Depends pattern) and RUF001 (unicode in user-facing strings).

21 ruff lint errors and 50 mypy errors remain for manual review.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
This commit is contained in:
Justin Visser 2026-02-26 22:11:41 +01:00
parent 399276ea69
commit bf04c77aa9
137 changed files with 3066 additions and 1900 deletions

View file

@ -8,10 +8,11 @@ Create Date: 2026-02-16 17:10:00.000000
from collections.abc import Sequence
from alembic import op
import sqlalchemy as sa
from sqlalchemy.dialects import postgresql
from alembic import op
# revision identifiers, used by Alembic.
revision: str = "20260216_0001"
down_revision: str | Sequence[str] | None = None

View file

@ -7,9 +7,10 @@ Create Date: 2026-02-16 17:40:00.000000
from collections.abc import Sequence
from alembic import op
import sqlalchemy as sa
from alembic import op
# revision identifiers, used by Alembic.
revision: str = "20260216_0002"
down_revision: str | Sequence[str] | None = "20260216_0001"
@ -31,4 +32,3 @@ def upgrade() -> None:
def downgrade() -> None:
op.drop_column("users", "is_admin")

View file

@ -7,9 +7,10 @@ Create Date: 2026-02-16 23:45:00.000000
from collections.abc import Sequence
from alembic import op
import sqlalchemy as sa
from alembic import op
# revision identifiers, used by Alembic.
revision: str = "20260216_0003"
down_revision: str | Sequence[str] | None = "20260216_0002"

View file

@ -7,9 +7,10 @@ Create Date: 2026-02-17 10:15:00.000000
from collections.abc import Sequence
from alembic import op
import sqlalchemy as sa
from alembic import op
# revision identifiers, used by Alembic.
revision: str = "20260217_0004"
down_revision: str | Sequence[str] | None = "20260216_0003"
@ -22,9 +23,7 @@ def upgrade() -> None:
inspector = sa.inspect(bind)
columns = {column["name"] for column in inspector.get_columns("ingestion_queue_items")}
indexes = {index["name"] for index in inspector.get_indexes("ingestion_queue_items")}
checks = {
constraint["name"] for constraint in inspector.get_check_constraints("ingestion_queue_items")
}
checks = {constraint["name"] for constraint in inspector.get_check_constraints("ingestion_queue_items")}
if "status" not in columns:
op.add_column(
@ -80,9 +79,7 @@ def downgrade() -> None:
inspector = sa.inspect(bind)
columns = {column["name"] for column in inspector.get_columns("ingestion_queue_items")}
indexes = {index["name"] for index in inspector.get_indexes("ingestion_queue_items")}
checks = {
constraint["name"] for constraint in inspector.get_check_constraints("ingestion_queue_items")
}
checks = {constraint["name"] for constraint in inspector.get_check_constraints("ingestion_queue_items")}
if "ix_ingestion_queue_status_next_attempt" in indexes:
op.drop_index("ix_ingestion_queue_status_next_attempt", table_name="ingestion_queue_items")

View file

@ -7,9 +7,10 @@ Create Date: 2026-02-17 16:20:00.000000
from collections.abc import Sequence
from alembic import op
import sqlalchemy as sa
from alembic import op
# revision identifiers, used by Alembic.
revision: str = "20260217_0005"
down_revision: str | Sequence[str] | None = "20260217_0004"
@ -70,9 +71,7 @@ def upgrade() -> None:
"crawl_runs",
["user_id", "idempotency_key"],
unique=True,
postgresql_where=sa.text(
"idempotency_key IS NOT NULL AND trigger_type = 'manual'::run_trigger_type"
),
postgresql_where=sa.text("idempotency_key IS NOT NULL AND trigger_type = 'manual'::run_trigger_type"),
)

View file

@ -7,9 +7,10 @@ Create Date: 2026-02-17 18:30:00.000000
from collections.abc import Sequence
from alembic import op
import sqlalchemy as sa
from alembic import op
# revision identifiers, used by Alembic.
revision: str = "20260217_0006"
down_revision: str | Sequence[str] | None = "20260217_0005"

View file

@ -7,9 +7,10 @@ Create Date: 2026-02-17 18:55:00.000000
from collections.abc import Sequence
from alembic import op
import sqlalchemy as sa
from alembic import op
# revision identifiers, used by Alembic.
revision: str = "20260217_0007"
down_revision: str | Sequence[str] | None = "20260217_0006"

View file

@ -7,10 +7,10 @@ Create Date: 2026-02-19 14:58:00.000000
from collections.abc import Sequence
from alembic import op
import sqlalchemy as sa
from sqlalchemy.dialects import postgresql
from alembic import op
# revision identifiers, used by Alembic.
revision: str = "20260219_0008"
@ -21,7 +21,7 @@ depends_on: str | Sequence[str] | None = None
TABLE_NAME = "user_settings"
DEFAULT_NAV_VISIBLE_PAGES_SQL = (
"'[\"dashboard\",\"scholars\",\"publications\",\"settings\",\"style-guide\",\"runs\",\"users\"]'::jsonb"
'\'["dashboard","scholars","publications","settings","style-guide","runs","users"]\'::jsonb'
)

View file

@ -7,10 +7,10 @@ Create Date: 2026-02-19 21:20:00.000000
from collections.abc import Sequence
from alembic import op
import sqlalchemy as sa
from sqlalchemy.dialects import postgresql
from alembic import op
# revision identifiers, used by Alembic.
revision: str = "20260219_0009"

View file

@ -7,10 +7,10 @@ Create Date: 2026-02-19 22:20:00.000000
from collections.abc import Sequence
from alembic import op
import sqlalchemy as sa
from sqlalchemy.dialects import postgresql
from alembic import op
# revision identifiers, used by Alembic.
revision: str = "20260219_0010"

View file

@ -7,9 +7,9 @@ Create Date: 2026-02-20 13:35:00.000000
from collections.abc import Sequence
from alembic import op
import sqlalchemy as sa
from alembic import op
revision: str = "20260220_0011"
down_revision: str | Sequence[str] | None = "20260219_0010"

View file

@ -7,10 +7,10 @@ Create Date: 2026-02-20 23:35:00.000000
from collections.abc import Sequence
from alembic import op
import sqlalchemy as sa
from sqlalchemy.dialects import postgresql
from alembic import op
revision: str = "20260220_0012"
down_revision: str | Sequence[str] | None = "20260220_0011"

View file

@ -7,9 +7,9 @@ Create Date: 2026-02-21 12:25:00.000000
from collections.abc import Sequence
from alembic import op
import sqlalchemy as sa
from alembic import op
revision: str = "20260221_0013"
down_revision: str | Sequence[str] | None = "20260220_0012"

View file

@ -7,9 +7,9 @@ Create Date: 2026-02-21 14:35:00
from __future__ import annotations
from alembic import op
import sqlalchemy as sa
from alembic import op
# revision identifiers, used by Alembic.
revision = "20260221_0014"

View file

@ -9,9 +9,9 @@ from __future__ import annotations
from collections.abc import Sequence
from alembic import op
import sqlalchemy as sa
from alembic import op
# revision identifiers, used by Alembic.
revision: str = "20260221_0015"
@ -30,11 +30,7 @@ LEGACY_CHECK_NAME_MIN_2 = "ck_user_settings_request_delay_seconds_min_2"
def _check_constraints() -> set[str]:
bind = op.get_bind()
inspector = sa.inspect(bind)
return {
str(item.get("name"))
for item in inspector.get_check_constraints(TABLE_NAME)
if item.get("name")
}
return {str(item.get("name")) for item in inspector.get_check_constraints(TABLE_NAME) if item.get("name")}
def _drop_check_if_exists(name: str) -> None:
@ -48,12 +44,7 @@ def _drop_check_if_exists(name: str) -> None:
def upgrade() -> None:
op.execute(
sa.text(
"UPDATE user_settings SET request_delay_seconds = 2 "
"WHERE request_delay_seconds < 2"
)
)
op.execute(sa.text("UPDATE user_settings SET request_delay_seconds = 2 WHERE request_delay_seconds < 2"))
_drop_check_if_exists(CHECK_NAME_MIN_1)
_drop_check_if_exists(LEGACY_CHECK_NAME_MIN_1)

View file

@ -7,9 +7,9 @@ Create Date: 2026-02-22 12:45:00.000000
from collections.abc import Sequence
from alembic import op
import sqlalchemy as sa
from alembic import op
revision: str = "20260222_0016"
down_revision: str | Sequence[str] | None = "20260221_0015"

View file

@ -5,26 +5,29 @@ Revises: fa0c5e3262d5
Create Date: 2026-02-24 19:10:00.000000
"""
from collections.abc import Sequence
from alembic import op
import sqlalchemy as sa
from alembic import op
# revision identifiers, used by Alembic.
revision: str = '20260224_0018'
down_revision: str | Sequence[str] | None = 'fa0c5e3262d5'
revision: str = "20260224_0018"
down_revision: str | Sequence[str] | None = "fa0c5e3262d5"
branch_labels: str | Sequence[str] | None = None
depends_on: str | Sequence[str] | None = None
def upgrade() -> None:
# ### commands auto generated by Alembic - please adjust! ###
op.add_column('publications', sa.Column('openalex_enriched', sa.Boolean(), server_default=sa.text('false'), nullable=False))
op.add_column(
"publications", sa.Column("openalex_enriched", sa.Boolean(), server_default=sa.text("false"), nullable=False)
)
# ### end Alembic commands ###
def downgrade() -> None:
# ### commands auto generated by Alembic - please adjust! ###
op.drop_column('publications', 'openalex_enriched')
op.drop_column("publications", "openalex_enriched")
# ### end Alembic commands ###

View file

@ -5,14 +5,14 @@ Revises: 20260224_0018
Create Date: 2026-02-24 22:20:00.000000
"""
from collections.abc import Sequence
from alembic import op
# revision identifiers, used by Alembic.
revision: str = '20260224_0019'
down_revision: str | Sequence[str] | None = '20260224_0018'
revision: str = "20260224_0019"
down_revision: str | Sequence[str] | None = "20260224_0018"
branch_labels: str | Sequence[str] | None = None
depends_on: str | Sequence[str] | None = None

View file

@ -5,22 +5,23 @@ Revises: 20260224_0019
Create Date: 2026-02-24 22:50:00.000000
"""
from collections.abc import Sequence
from alembic import op
import sqlalchemy as sa
from alembic import op
# revision identifiers, used by Alembic.
revision: str = '20260224_0020'
down_revision: str | Sequence[str] | None = '20260224_0019'
revision: str = "20260224_0020"
down_revision: str | Sequence[str] | None = "20260224_0019"
branch_labels: str | Sequence[str] | None = None
depends_on: str | Sequence[str] | None = None
def upgrade() -> None:
op.add_column('publications', sa.Column('openalex_last_attempt_at', sa.DateTime(timezone=True), nullable=True))
op.add_column("publications", sa.Column("openalex_last_attempt_at", sa.DateTime(timezone=True), nullable=True))
def downgrade() -> None:
op.drop_column('publications', 'openalex_last_attempt_at')
op.drop_column("publications", "openalex_last_attempt_at")

View file

@ -7,9 +7,9 @@ Create Date: 2026-02-25 09:10:00.000000
from collections.abc import Sequence
from alembic import op
import sqlalchemy as sa
from alembic import op
# revision identifiers, used by Alembic.
revision: str = "20260225_0021"
@ -56,9 +56,7 @@ def upgrade() -> None:
"crawl_runs",
["user_id"],
unique=True,
postgresql_where=sa.text(
"status IN ('running'::run_status, 'resolving'::run_status)"
),
postgresql_where=sa.text("status IN ('running'::run_status, 'resolving'::run_status)"),
)

View file

@ -7,9 +7,9 @@ Create Date: 2026-02-25 10:00:00.000000
from collections.abc import Sequence
from alembic import op
import sqlalchemy as sa
from alembic import op
# revision identifiers, used by Alembic.
revision: str = "20260225_0022"

View file

@ -7,9 +7,9 @@ Create Date: 2026-02-26 12:40:00.000000
from collections.abc import Sequence
from alembic import op
import sqlalchemy as sa
from alembic import op
# revision identifiers, used by Alembic.
revision: str = "20260226_0023"

View file

@ -7,10 +7,10 @@ Create Date: 2026-02-26 14:20:00.000000
from collections.abc import Sequence
from alembic import op
import sqlalchemy as sa
from sqlalchemy.dialects import postgresql
from alembic import op
# revision identifiers, used by Alembic.
revision: str = "20260226_0024"