# #region SupersetDashboardsListMixin [C:3] [TYPE Module] [SEMANTICS superset, dashboard, list, search, filter]
# @LAYER Infrastructure
# @BRIEF Dashboard listing mixin for SupersetClient — paginated list, summary projection.
# @RELATION DEPENDS_ON -> [SupersetClientBase]
# @RELATION DEPENDS_ON -> [SupersetUserProjectionMixin]
import json
from typing import Any, cast

from ..logger import belief_scope, logger as app_logger

app_logger = cast(Any, app_logger)
# #region SupersetDashboardsListMixin [C:3] [TYPE Class]
# @BRIEF Mixin providing dashboard listing and summary projection operations.
# @RELATION DEPENDS_ON -> [SupersetClientBase]
# @RELATION DEPENDS_ON -> [SupersetUserProjectionMixin]
class SupersetDashboardsListMixin:
    # #region SupersetClientGetDashboards [TYPE Function] [C:3]
    # @PURPOSE: Получает полный список дашбордов, автоматически обрабатывая пагинацию.
    # @RELATION CALLS -> [SupersetClientFetchAllPages]
    def get_dashboards(self, query: dict | None = None) -> tuple[int, list[dict]]:
        with belief_scope("get_dashboards"):
            app_logger.info("[get_dashboards][Enter] Fetching dashboards.")
            validated_query = self._validate_query_params(query or {})
            if "columns" not in validated_query:
                validated_query["columns"] = [
                    "slug", "id", "url", "changed_on_utc", "dashboard_title",
                    "published", "created_by", "changed_by", "changed_by_name", "owners",
                ]
            paginated_data = self._fetch_all_pages(
                endpoint="/dashboard/",
                pagination_options={
                    "base_query": validated_query,
                    "results_field": "result",
                },
            )
            total_count = len(paginated_data)
            app_logger.reflect(f"Found {total_count} dashboards.", extra={"src": "get_dashboards"})
            return total_count, paginated_data
    # #endregion SupersetClientGetDashboards
    # #region SupersetClientGetDashboardsPage [TYPE Function] [C:3]
    # @PURPOSE: Fetches a single dashboards page from Superset without iterating all pages.
    # @RELATION CALLS -> [APIClient]
    def get_dashboards_page(
        self, query: dict | None = None
    ) -> tuple[int, list[dict]]:
        with belief_scope("get_dashboards_page"):
            validated_query = self._validate_query_params(query or {})
            if "columns" not in validated_query:
                validated_query["columns"] = [
                    "slug", "id", "url", "changed_on_utc", "dashboard_title",
                    "published", "created_by", "changed_by", "changed_by_name", "owners",
                ]
            response_json = cast(
                dict[str, Any],
                self.network.request(
                    method="GET",
                    endpoint="/dashboard/",
                    params={"q": json.dumps(validated_query)},
                ),
            )
            result = response_json.get("result", [])
            total_count = response_json.get("count", len(result))
            return total_count, result
    # #endregion SupersetClientGetDashboardsPage
    # #region SupersetClientGetDashboardsSummary [TYPE Function] [C:3]
    # @PURPOSE: Fetches dashboard metadata optimized for the grid.
    # @RELATION CALLS -> [SupersetClientGetDashboards]
    def get_dashboards_summary(self, require_slug: bool = False) -> list[dict]:
        with belief_scope("SupersetClient.get_dashboards_summary"):
            query: dict[str, Any] = {}
            if require_slug:
                query["filters"] = [{"col": "slug", "opr": "neq", "value": ""}]
            _, dashboards = self.get_dashboards(query=query)
            result = []
            max_debug_samples = 12
            for index, dash in enumerate(dashboards):
                raw_owners = dash.get("owners")
                raw_created_by = dash.get("created_by")
                raw_changed_by = dash.get("changed_by")
                raw_changed_by_name = dash.get("changed_by_name")
                owners = self._extract_owner_labels(raw_owners)
                if not owners:
                    owners = self._extract_owner_labels([raw_created_by, raw_changed_by])
                projected_created_by = self._extract_user_display(None, raw_created_by)
                projected_modified_by = self._extract_user_display(
                    raw_changed_by_name, raw_changed_by,
                )
                raw_owner_usernames: list[str] = []
                if isinstance(raw_owners, list):
                    for owner_payload in raw_owners:
                        if isinstance(owner_payload, dict):
                            owner_username = self._sanitize_user_text(
                                owner_payload.get("username")
                            )
                            if owner_username:
                                raw_owner_usernames.append(owner_username)
                result.append({
                    "id": dash.get("id"),
                    "slug": dash.get("slug"),
                    "title": dash.get("dashboard_title"),
                    "url": dash.get("url"),
                    "last_modified": dash.get("changed_on_utc"),
                    "status": "published" if dash.get("published") else "draft",
                    "created_by": projected_created_by,
                    "modified_by": projected_modified_by,
                    "owners": owners,
                })
                if index < max_debug_samples:
                    app_logger.reflect(
                        "Dashboard actor projection sample",
                        extra={"src": "get_dashboards_summary", "payload": {"env": getattr(self.env, 'id', None), "dashboard_id": dash.get('id'), "raw_owners": raw_owners, "raw_owner_usernames": raw_owner_usernames, "raw_created_by": raw_created_by, "raw_changed_by": raw_changed_by, "raw_changed_by_name": raw_changed_by_name, "projected_owners": owners, "projected_created_by": projected_created_by, "projected_modified_by": projected_modified_by}},
                    )
            app_logger.reflect(
                "Dashboard actor projection summary",
                extra={"src": "get_dashboards_summary", "payload": {"env": getattr(self.env, 'id', None), "dashboards": len(result), "sampled": min(len(result), max_debug_samples)}},
            )
            return result
    # #endregion SupersetClientGetDashboardsSummary
    # #region SupersetClientGetDashboardsSummaryPage [TYPE Function] [C:3]
    # @PURPOSE: Fetches one page of dashboard metadata optimized for the grid.
    # @RELATION CALLS -> [SupersetClientGetDashboardsPage]
    def get_dashboards_summary_page(
        self,
        page: int,
        page_size: int,
        search: str | None = None,
        require_slug: bool = False,
    ) -> tuple[int, list[dict]]:
        with belief_scope("SupersetClient.get_dashboards_summary_page"):
            query: dict[str, Any] = {
                "page": max(page - 1, 0),
                "page_size": page_size,
            }
            filters: list[dict[str, Any]] = []
            if require_slug:
                filters.append({"col": "slug", "opr": "neq", "value": ""})
            normalized_search = (search or "").strip()
            if normalized_search:
                filters.append({
                    "col": "dashboard_title", "opr": "ct", "value": normalized_search,
                })
            if filters:
                query["filters"] = filters
            total_count, dashboards = self.get_dashboards_page(query=query)
            result = []
            for dash in dashboards:
                owners = self._extract_owner_labels(dash.get("owners"))
                if not owners:
                    owners = self._extract_owner_labels(
                        [dash.get("created_by"), dash.get("changed_by")],
                    )
                result.append({
                    "id": dash.get("id"),
                    "slug": dash.get("slug"),
                    "title": dash.get("dashboard_title"),
                    "url": dash.get("url"),
                    "last_modified": dash.get("changed_on_utc"),
                    "status": "published" if dash.get("published") else "draft",
                    "created_by": self._extract_user_display(
                        None, dash.get("created_by"),
                    ),
                    "modified_by": self._extract_user_display(
                        dash.get("changed_by_name"), dash.get("changed_by"),
                    ),
                    "owners": owners,
                })
            return total_count, result
    # #endregion SupersetClientGetDashboardsSummaryPage
# #endregion SupersetDashboardsListMixin
# #endregion SupersetDashboardsListMixin
