# -*- coding: utf-8; -*-
################################################################################
#
#  WuttaFarm --Web app to integrate with and extend farmOS
#  Copyright © 2026 Lance Edgar
#
#  This file is part of WuttaFarm.
#
#  WuttaFarm is free software: you can redistribute it and/or modify it under
#  the terms of the GNU General Public License as published by the Free Software
#  Foundation, either version 3 of the License, or (at your option) any later
#  version.
#
#  WuttaFarm is distributed in the hope that it will be useful, but WITHOUT ANY
#  WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR
#  A PARTICULAR PURPOSE.  See the GNU General Public License for more details.
#
#  You should have received a copy of the GNU General Public License along with
#  WuttaFarm.  If not, see <http://www.gnu.org/licenses/>.
#
################################################################################
"""
Base views for Logs
"""

from collections import OrderedDict

import colander

from wuttaweb.forms.schema import WuttaDictEnum
from wuttaweb.db import Session
from wuttaweb.forms.widgets import WuttaDateTimeWidget

from wuttafarm.web.views import WuttaFarmMasterView
from wuttafarm.db.model import LogType, Log
from wuttafarm.web.forms.schema import LogAssetRefs


def get_log_type_enum(config):
    app = config.get_app()
    model = app.model
    session = Session()
    log_types = OrderedDict()
    query = session.query(model.LogType).order_by(model.LogType.name)
    for log_type in query:
        log_types[log_type.drupal_id] = log_type.name
    return log_types


class LogTypeView(WuttaFarmMasterView):
    """
    Master view for Log Types
    """

    model_class = LogType
    route_prefix = "log_types"
    url_prefix = "/log-types"

    grid_columns = [
        "name",
        "description",
    ]

    sort_defaults = "name"

    filter_defaults = {
        "name": {"active": True, "verb": "contains"},
    }

    form_fields = [
        "name",
        "description",
        "farmos_uuid",
        "drupal_id",
    ]

    def configure_grid(self, grid):
        g = grid
        super().configure_grid(g)

        # name
        g.set_link("name")

    def get_xref_buttons(self, log_type):
        buttons = super().get_xref_buttons(log_type)

        if log_type.farmos_uuid:
            buttons.append(
                self.make_button(
                    "View farmOS record",
                    primary=True,
                    url=self.request.route_url(
                        "farmos_log_types.view", uuid=log_type.farmos_uuid
                    ),
                    icon_left="eye",
                )
            )

        return buttons


class LogView(WuttaFarmMasterView):
    """
    Master view for All Logs
    """

    model_class = Log
    route_prefix = "log"
    url_prefix = "/logs"

    farmos_refurl_path = "/logs"

    viewable = False
    creatable = False
    editable = False
    deletable = False
    model_is_versioned = False

    labels = {
        "message": "Log Name",
    }

    grid_columns = [
        "status",
        "drupal_id",
        "timestamp",
        "message",
        "log_type",
        "assets",
        "location",
        "quantity",
        "groups",
        "is_group_assignment",
    ]

    sort_defaults = ("timestamp", "desc")

    filter_defaults = {
        "message": {"active": True, "verb": "contains"},
    }

    def configure_grid(self, grid):
        g = grid
        super().configure_grid(g)

        # drupal_id
        g.set_label("drupal_id", "ID", column_only=True)

        # timestamp
        g.set_renderer("timestamp", "date")
        g.set_link("timestamp")

        # message
        g.set_link("message")

        # log_type
        g.set_enum("log_type", get_log_type_enum(self.config))

        # assets
        g.set_renderer("assets", self.render_assets_for_grid)

        # view action links to final log record
        def log_url(log, i):
            return self.request.route_url(f"logs_{log.log_type}.view", uuid=log.uuid)

        g.add_action("view", icon="eye", url=log_url)

    def render_assets_for_grid(self, log, field, value):
        assets = [str(a.asset) for a in log._assets]
        return ", ".join(assets)


class LogMasterView(WuttaFarmMasterView):
    """
    Base class for Asset master views
    """

    labels = {
        "message": "Log Name",
        "owners": "Owner",
    }

    grid_columns = [
        "status",
        "drupal_id",
        "timestamp",
        "message",
        "assets",
        # "location",
        "quantity",
        "is_group_assignment",
        "owners",
    ]

    sort_defaults = ("timestamp", "desc")

    filter_defaults = {
        "message": {"active": True, "verb": "contains"},
    }

    form_fields = [
        "message",
        "timestamp",
        "assets",
        "location",
        "quantity",
        "notes",
        "status",
        "log_type",
        "owners",
        "is_group_assignment",
        "farmos_uuid",
        "drupal_id",
    ]

    def get_query(self, session=None):
        """ """
        model = self.app.model
        model_class = self.get_model_class()
        session = session or self.Session()
        return session.query(model_class).join(model.Log)

    def configure_grid(self, grid):
        g = grid
        super().configure_grid(g)
        model = self.app.model

        # status
        g.set_sorter("status", model.Log.status)
        g.set_filter("status", model.Log.status)

        # drupal_id
        g.set_label("drupal_id", "ID", column_only=True)
        g.set_sorter("drupal_id", model.Log.drupal_id)
        g.set_filter("drupal_id", model.Log.drupal_id)

        # timestamp
        g.set_renderer("timestamp", "date")
        g.set_link("timestamp")
        g.set_sorter("timestamp", model.Log.timestamp)
        g.set_filter("timestamp", model.Log.timestamp)

        # message
        g.set_link("message")
        g.set_sorter("message", model.Log.message)
        g.set_filter("message", model.Log.message)

        # assets
        g.set_renderer("assets", self.render_assets_for_grid)

    def render_assets_for_grid(self, log, field, value):
        return ", ".join([a.asset.asset_name for a in log.log._assets])

    def configure_form(self, form):
        f = form
        super().configure_form(f)
        enum = self.app.enum
        log = f.model_instance

        # timestamp
        # TODO: the widget should be automatic (assn proxy field)
        f.set_widget("timestamp", WuttaDateTimeWidget(self.request))
        if self.creating:
            f.set_default("timestamp", self.app.make_utc())

        # assets
        if self.creating or self.editing:
            f.remove("assets")  # TODO: need to support this
        else:
            f.set_node("assets", LogAssetRefs(self.request))
            f.set_default("assets", [a.asset_uuid for a in log.log._assets])

        # location
        if self.creating or self.editing:
            f.remove("location")  # TODO: need to support this

        # log_type
        if self.creating:
            f.remove("log_type")
        else:
            f.set_node(
                "log_type",
                WuttaDictEnum(self.request, get_log_type_enum(self.config)),
            )
            f.set_readonly("log_type")

        # quantity
        if self.creating or self.editing:
            f.remove("quantity")  # TODO: need to support this

        # notes
        f.set_widget("notes", "notes")

        # owners
        if self.creating or self.editing:
            f.remove("owners")  # TODO: need to support this

        # status
        f.set_node("status", WuttaDictEnum(self.request, enum.LOG_STATUS))

        # is_group_assignment
        f.set_node("is_group_assignment", colander.Boolean())

    def objectify(self, form):
        log = super().objectify(form)

        if self.creating:
            model_class = self.get_model_class()
            log.log_type = self.get_farmos_log_type()

        return log

    def get_farmos_url(self, log):
        return self.app.get_farmos_url(f"/log/{log.drupal_id}")

    def get_farmos_log_type(self):
        return self.model_class.__wutta_hint__["farmos_log_type"]

    def get_xref_buttons(self, log):
        buttons = super().get_xref_buttons(log)

        if log.farmos_uuid:
            log_type = self.get_farmos_log_type()
            route = f"farmos_logs_{log_type}.view"
            buttons.append(
                self.make_button(
                    "View farmOS record",
                    primary=True,
                    url=self.request.route_url(route, uuid=log.farmos_uuid),
                    icon_left="eye",
                )
            )

        return buttons


def defaults(config, **kwargs):
    base = globals()

    LogTypeView = kwargs.get("LogTypeView", base["LogTypeView"])
    LogTypeView.defaults(config)

    LogView = kwargs.get("LogView", base["LogView"])
    LogView.defaults(config)


def includeme(config):
    defaults(config)
