from sqlalchemy import select
from sqlalchemy.ext.asyncio import AsyncSession
from sqlalchemy.orm import joinedload

from src.db.models.rf_project_report import RfProjectReport



class RfProjectReportRepository:
    def __init__(self, db: AsyncSession):
        self.db = db

    async def get(
            self, 
            report_id: int | None = None,
            year: int | None = None,
            report_type: str | None = None,
            project_id: int | None = None,
            load_project: bool = False,
    ) -> RfProjectReport | None:
        assert report_id is not None or all((el is not None for el in (year, report_type, project_id)))
        query = select(
            RfProjectReport
        )
        if report_id is not None:
            query = query.where(RfProjectReport.id == report_id)
        else:
            query = query.where(
                RfProjectReport.year == year,
                RfProjectReport.report_type == report_type,
                RfProjectReport.project_id == project_id
            )
        
        if load_project:
            query = query.options(joinedload(RfProjectReport.project))
        query = query.limit(1)
        return (await self.db.execute(query)).scalar_one_or_none()

    async def get_list(
            self, 
            report_id: int | None = None,
            year: int | None = None,
            report_type: str | None = None,
            project_id: int | None = None,
    ) -> list[RfProjectReport]:
        query = select(
            RfProjectReport
        )
        if report_id is not None:
            query = query.where(RfProjectReport.id == report_id)
        if year is not None:
            query = query.where(RfProjectReport.year == year)
        if report_type is not None:
            query = query.where(RfProjectReport.report_type == report_type)
        if project_id is not None:
            query = query.where(RfProjectReport.project_id == project_id)
        
        return (await self.db.execute(query)).scalars().all()
