from pathlib import Path

from qgis.core import (
    NULL,
    Qgis,
    QgsApplication,
    QgsProviderConnectionException,
    QgsProviderRegistry,
)
from qgis.PyQt import uic
from qgis.PyQt.QtCore import QDateTime
from qgis.PyQt.QtGui import QIcon
from qgis.PyQt.QtWidgets import QWidget

from plui_versionning.toolbelt import PlgLogger, PlgOptionsManager


class ProcedureDetailsWidget(QWidget):
    def __init__(self, parent: QWidget = None):
        """
        QWidget Afficher/Modifier les détails d'une procédure

        Args:
            parent: parent QWidget
        """
        super().__init__(parent)
        self.log = PlgLogger().log
        self.plg_settings = PlgOptionsManager()

        # DB connection
        self.db_connection_uri = self.plg_settings.get_plg_settings().db_connection_uri
        self.db_schema_name = self.plg_settings.get_plg_settings().db_schema_name

        uic.loadUi(Path(__file__).parent / f"{Path(__file__).stem}.ui", self)

        self.procedure = None
        self.read_mode = True
        self.edit_icon = QIcon(QgsApplication.iconPath("mActionToggleEditing.svg"))
        self.save_icon = QIcon(QgsApplication.iconPath("mActionSaveAllEdits.svg"))
        self.edit_tooltip = "Editer les détails d'un projet"
        self.save_tooltip = "Sauvegarder les changements"
        self.btn_edit.setIcon(self.edit_icon)
        self.btn_edit.setToolTip(self.edit_tooltip)
        self.btn_edit.clicked.connect(self.editer_details)
        self.set_read_only_widgets(self.read_mode)

    def set_read_only_widgets(self, read_only: bool):
        """Set read only mode and enable/disable widgets

        Args:
            read_only (boolean): Parameter to set/unset read only mode and enable/disable widget
        """
        self.edit_intitule.setReadOnly(read_only)
        self.edit_commentaires.setReadOnly(read_only)
        self.edit_intitule.setEnabled(not read_only)
        self.edit_commentaires.setEnabled(not read_only)
        self.btn_edit.setIcon(self.edit_icon if read_only else self.save_icon)
        self.btn_edit.setToolTip(self.edit_tooltip if read_only else self.save_tooltip)
        self.btn_edit.setDown(not read_only)

    def set_procedure(self, id_procedure: int):
        """
        Query to the database regarding procedure to get all attributes
        """
        self.procedure = id_procedure
        sql = """
            select pluiv_p.id, intitule, procedure_plui, code_proc, lib_nomproc as type, datefin_proc, num_phase, commentaires
            from "{}".v_pluiv_procedures pluiv_p
            join "{}".procedureurbatype on code_proc = nomproc
            where pluiv_p.id = {}
        """.format(
            self.db_schema_name, self.db_schema_name, id_procedure
        )
        md = QgsProviderRegistry.instance().providerMetadata("postgres")
        conn = md.createConnection(self.db_connection_uri, {})
        try:
            result = conn.executeSql(sql)[0]
            self.lbl_procedure_value.setText(result[2])
            self.edit_intitule.setText(result[1])
            self.lbl_code_value.setText(result[3])
            self.lbl_type_value.setText(result[4])
            self.lbl_date_fin_proc_value.setText(
                QDateTime(result[5]).toPyDateTime().strftime("%d/%m/%Y")
                if result[5] != NULL
                else ""
            )
            self.lbl_phase_value.setText(str(result[6]))
            self.edit_commentaires.setText(result[7] if result[7] != NULL else "")
        except QgsProviderConnectionException as e:
            self.log(message=e, log_level=Qgis.Critical, push=True)
        # Read only quand on change de projet
        self.read_mode = True
        self.set_read_only_widgets(self.read_mode)

    def editer_details(self):
        """Editer les détails d'une procédure"""
        self.read_mode = not self.read_mode

        # Enregistrement des nouvelles données quand on retourne en read only
        if self.read_mode:
            self.maj_details()
            # Set procedure pour actualiser les détails
            self.set_procedure(self.procedure)
        else:
            # Gestion de l'interface
            self.set_read_only_widgets(self.read_mode)

    def maj_details(self):
        """Enregistrement en base des nouveaux détails de procédure"""
        intitule = self.edit_intitule.text()
        commentaires = self.edit_commentaires.toPlainText()

        query = """
        update \"{}\".pluiv_procedures
            set intitule = '{}',
                commentaires = '{}'
        where id = {}
        """.format(
            self.db_schema_name,
            str.replace(intitule, "'", "''"),
            str.replace(commentaires, "'", "''"),
            self.procedure,
        )
        md = QgsProviderRegistry.instance().providerMetadata("postgres")
        conn = md.createConnection(self.db_connection_uri, {})
        try:
            conn.executeSql(query)
            self.log(
                message=f"Les détails de la procédure {intitule} ont été mis à jour",
                log_level=Qgis.Success,
                push=True,
            )
        except QgsProviderConnectionException as e:
            self.log(message=e, log_level=Qgis.Critical, push=True)
