using ClosedXML.Excel;
using CloudBuilder.Core.DependencyInjection.Form;
using CloudBuilder.Core.Report;
using CloudBuilder.Core.Service;
using CloudBuilder.Gui;
using CloudBuilder.Gui.DependencyInjection;
using CloudBuilder.Request.Security;
using CloudBuilder.Security.Data;
using CloudBuilder.Security.Entity;
using CloudBuilder.Security.Linkup;
using CloudBuilder.Security.Policy;
using CloudBuilder.Security.SearchCriteria;
using DocumentFormat.OpenXml.Spreadsheet;
using Krypton.Toolkit;
using Microsoft.AspNetCore.Authorization;
using Microsoft.AspNetCore.Http.Extensions;
using Microsoft.Extensions.DependencyInjection;
using Microsoft.IdentityModel.Tokens;
using Newtonsoft.Json;
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.ComponentModel.DataAnnotations;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Net;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Forms;


namespace CloudBuilder.Security.Gui
{
    public partial class SecurityPermissionEnquiryPage : AbstractPage
    {
        private SecurityPermissionEntity[] securityPermissions = null!;
        private SecurityPermissionSearchCriteria searchCriteria = null!;
        private BindingContextAttributeProvider provider;
        private SecurityPermissionRequest securityPermissionRequest;
        private SecurityMessagePolicy securityMessagePolicy;

        //初始化Page，注入容器内，不要在此做任何事情
        public SecurityPermissionEnquiryPage()
        {
            InitializeComponent();
        }

        /// <summary>
        /// 第一次加载时执行，只执行一次
        /// </summary>
        public override void FunctionLoaded()
        {
            try
            {
                base.FunctionLoaded();
                //初始化容器-------------------------------------
                securityPermissionRequest = ServiceHelper.GetTypeService<SecurityPermissionRequest>();
                securityMessagePolicy = ServiceHelper.GetTypeService<SecurityMessagePolicy>()!;

                //界面初始化
                InitGui();
            }
            catch (ValidatedException ex)
            {
                ShowMessageBox.ShowInfo(ex.Message);
            }
            catch (ServiceErrorException ex)
            {
                ShowMessageBox.ShowError(ex.Message);
            }
            catch (Exception ex)
            {
                ShowMessageBox.ShowError(ex.Message);
            }
        }

        /// <summary>
        /// 每次从别的界面进入时执行，不包括下面的界面切换，发生在FunctionLoaded之后
        /// 这个是有参数传入，常用于查询界面进入到操作界面发生
        /// </summary>
        /// <param name="param"></param>
        public override void FunctionActivated(object param)
        {
            base.FunctionActivated(param);
            permissionNameTxt.Focus();
        }
        /// <summary>
        /// 当Page被选中时执行,用于Tab导航的切换，没有参数变化，跟FunctionActivated有区别
        /// </summary>
        public override void FunctionSelected()
        {
            this.ParentAbstractForm.AcceptButton = this.searchBut;
            if (!IsDialog)
                this.ParentAbstractForm.CancelButton = this.resetBut;
            else
                this.ParentAbstractForm.CancelButton = this.cancelBut;

            permissionNameTxt.Focus();
        }
        /// <summary>
        /// 控件的初始化
        /// </summary>
        private void InitGui()
        {
            //DataGridView初始化不要自动生成列，且允许重排列名操作
            dataGv.InitColumn(true, true);
            //初始化绑定设置
            InitBindingContext();
            //设置显示模式
            SetDisplayMode(true);

            InitGridViewPagination();
        }
        /// <summary>
        /// DataGridView分页控件初始化
        /// </summary>
        private void InitGridViewPagination()
        {
            searchCriteria = new SecurityPermissionSearchCriteria();
            gridViewPagination.SetLimit(searchCriteria.limit);
            gridViewPagination.OnPaginationChanged += Search;
            gridViewPagination.OnPrint += Print;
        }

        /// <summary>
        /// 打印当前查询结果
        /// </summary>
        private void Print()
        {
            //設置查詢條件
            List<string> searCriteria = new List<string>();
            if (!string.IsNullOrEmpty(permissionNameTxt.Text))
                searCriteria.Add(searchPermissionNameLabel.Text + permissionNameTxt.Text);

            //設置每列的格式
            TemplateHeader[] headers = dataGv.GetTemplateHeaders();

            //打印Excel
            new DataToExcelHelper<SecurityPermissionEntity>(null).PrintExcel(this.Parent.Text, this.Parent.Text, searCriteria, headers, securityPermissions);
        }

        /// <summary>
        /// 有特殊要求的UI控件初始化设置，使用guiOperateHelper管理
        /// </summary>
        private void InitBindingContext()
        {
            InitPermission();

            guiOperateHelper = new GuiOperateHelper();
        }

        private void InitPermission()
        {
            viewBut.Set(SecurityPermissionPolicy.SecurityPermission, Operate.Find);
            createBut.Set(SecurityPermissionPolicy.SecurityPermission, Operate.Insert);
            amendBut.Set(SecurityPermissionPolicy.SecurityPermission, Operate.Update);
            deleteBut.Set(SecurityPermissionPolicy.SecurityPermission, Operate.Delete);
        }

        private void SetDisplayMode(bool enable)
        {
            guiOperateHelper.EnableControls(true, this.searchPanel, this.bottomPanel);
            guiOperateHelper.EnableControls(false, dataGv);

            if (securityPermissions != null)
                guiOperateHelper.EnableControls(enable, viewBut, amendBut, deleteBut);
            else
                guiOperateHelper.EnableControls(false, viewBut, amendBut, deleteBut);

            //如果是弹出的窗口，不显示
            createBut.Visible = !IsDialog;
            dialogPanel.Visible = IsDialog;
            operationPanel.Visible = !IsDialog;

            this.permissionNameTxt.Focus();
        }

        private void searchBut_Click(object sender, EventArgs e)
        {
            try
            {
                Search();
            }
            catch (ValidatedException ex)
            {
                ShowMessageBox.ShowInfo(ex.Message);
            }
            catch (ServiceErrorException ex)
            {
                ShowMessageBox.ShowError(ex.Message);
            }
            catch (Exception ex)
            {
                ShowMessageBox.ShowError(ex.Message);
            }
        }

        /// <summary>
        /// 与Web同步写法
        /// </summary>
        /// <returns></returns>
        private SecurityPermissionSearchCriteria PackSearchCriteria()
        {
            searchCriteria = new SecurityPermissionSearchCriteria();
            searchCriteria.limit = gridViewPagination.Limit;
            searchCriteria.page = gridViewPagination.CurrentPage;

            List<SearchFilter> filters = new List<SearchFilter>();

            SearchFilter filter = new SearchFilter();
            filter.Column = SecurityPermissionEntity.DB_PERMISSION_NAME;
            filter.Type = SearchFilterTypePolicy.TEXT;
            filter.Operator = SearchFilterOperatorPolicy.CONTAIN;
            filter.Value = permissionNameTxt.GetValue();
            filters.Add(filter);

            searchCriteria.Filter = filters.ToArray();

            return searchCriteria;
        }

        private void Search()
        {
            try
            {
                var data = securityPermissionRequest.FindBySearchCriteria(PackSearchCriteria());

                if (data != null) securityPermissions = data.Permissions;

                gridViewPagination.SetTotal(data.Total);

                if (securityPermissions == null || securityPermissions.Length == 0)
                {
                    ShowMessageBox.ShowInfo(securityMessagePolicy.ComposeMessage(SecurityMessagePolicy.GUI_WS_RECORD_NOT_FOUND));
                    guiOperateHelper.ResetControls(this.dataGv);
                    return;
                }

                dataGv.SetDataSource(securityPermissions);

                SetDisplayMode(true);
            }
            catch (ValidatedException ex)
            {
                ShowMessageBox.ShowInfo(ex.Message);
            }
            catch (ServiceErrorException ex)
            {
                ShowMessageBox.ShowError(ex.Message);
            }
            catch (Exception ex)
            {
                ShowMessageBox.ShowError(ex.Message);
            }
        }

        private void resetBut_Click(object sender, EventArgs e)
        {
            guiOperateHelper.ResetControls(this.mainPanel);
            //Reset时默认会设置limit为AbstractSearchCriteria.limit，如果不同时，需要重新设置
            gridViewPagination.SetLimit(searchCriteria.limit);
            SetDisplayMode(false);
        }

        private void createBut_Click(object sender, EventArgs e)
        {
            DisplayPage(GuiDisplayMode.Create, null);
        }

        private void DisplayPage(GuiDisplayMode mode, string permissionName)
        {
            SecurityPermissionOperationLinkup linkupData = new SecurityPermissionOperationLinkup();
            linkupData.DisplayMode = Convert.ToInt32(mode);
            linkupData.PermissionName = permissionName;

            this.DisplayAbstractPage(typeof(SecurityPermissionOperationPage).Name, linkupData);
        }


        private void viewBut_Click(object sender, EventArgs e)
        {
            if (dataGv.RowCount <= 0 || dataGv.SelectedCells.Count <= 0)
            {
                ShowMessageBox.ShowInfo(securityMessagePolicy.ComposeMessage(SecurityMessagePolicy.GUI_WS_RECORD_NOT_FOUND));
                return;
            }

            SecurityPermissionEntity data = dataGv.GetRowData<SecurityPermissionEntity>(dataGv.SelectedCells[0].RowIndex);

            DisplayPage(GuiDisplayMode.View, data.PermissionName);
        }

        private void amendBut_Click(object sender, EventArgs e)
        {
            if (dataGv.RowCount <= 0 || dataGv.SelectedCells.Count <= 0)
            {
                ShowMessageBox.ShowInfo(securityMessagePolicy.ComposeMessage(SecurityMessagePolicy.GUI_WS_RECORD_NOT_FOUND));
                return;
            }

            SecurityPermissionEntity data = dataGv.GetRowData<SecurityPermissionEntity>(dataGv.SelectedCells[0].RowIndex);

            DisplayPage(GuiDisplayMode.Amend, data.PermissionName);
        }

        private void deleteBut_Click(object sender, EventArgs e)
        {
            try
            {
                Delete();
            }
            catch (ValidatedException ex)
            {
                ShowMessageBox.ShowInfo(ex.Message);
            }
            catch (ServiceErrorException ex)
            {
                ShowMessageBox.ShowError(ex.Message);
            }
            catch (Exception ex)
            {
                ShowMessageBox.ShowError(ex.Message);
            }
        }

        private void Delete()
        {
            if (dataGv.RowCount <= 0 || dataGv.SelectedCells.Count <= 0)
            {
                ShowMessageBox.ShowInfo(securityMessagePolicy.ComposeMessage(SecurityMessagePolicy.GUI_WS_RECORD_NOT_FOUND));
                return;
            }

            if (DialogResult.Yes != ShowMessageBox.ShowOption(securityMessagePolicy.ComposeMessage(SecurityMessagePolicy.GUI_CONFIRM_DEL_NULL), securityMessagePolicy.ComposeMessage(SecurityMessagePolicy.GUI_DELETE))) return;

            SecurityPermissionEntity[] datas = dataGv.GetSelectedCellsData<SecurityPermissionEntity>();

            securityPermissionRequest.Deletes(datas.Select(x => x.PermissionName).ToArray());

            ShowMessageBox.ShowInfo(securityMessagePolicy.ComposeMessage(SecurityMessagePolicy.GUI_SUCCEED_DELETED_NULL));

            Search();
        }

        private void okBut_Click(object sender, EventArgs e)
        {
            try
            {
                if (dataGv.RowCount <= 0 || dataGv.SelectedCells.Count <= 0) return;
                //SecurityPermissionEntity data = dataGv.GetRowData<SecurityPermissionEntity>(dataGv.SelectedCells[0].RowIndex);
                SecurityPermissionEntity[] datas = dataGv.GetSelectedCellsData<SecurityPermissionEntity>();

                this.ParentAbstractForm.OutputData = datas;
                this.ParentAbstractForm.DialogResult = DialogResult.OK;
                this.ParentAbstractForm.Close();
            }
            catch (ValidatedException ex)
            {
                ShowMessageBox.ShowInfo(ex.Message);
            }
            catch (ServiceErrorException ex)
            {
                ShowMessageBox.ShowError(ex.Message);
            }
            catch (Exception ex)
            {
                ShowMessageBox.ShowError(ex.Message);
            }
        }

        private void cancelBut_Click(object sender, EventArgs e)
        {
            try
            {
                this.ParentAbstractForm.DialogResult = DialogResult.Cancel;
                this.ParentAbstractForm.Close();
            }
            catch (ValidatedException ex)
            {
                ShowMessageBox.ShowInfo(ex.Message);
            }
            catch (ServiceErrorException ex)
            {
                ShowMessageBox.ShowError(ex.Message);
            }
            catch (Exception ex)
            {
                ShowMessageBox.ShowError(ex.Message);
            }
        }

        private void dataGv_CellDoubleClick(object sender, DataGridViewCellEventArgs e)
        {
            try
            {
                if (IsDialog)
                    okBut_Click(null, null);
                else
                    viewBut_Click(null, null);
            }
            catch (ValidatedException ex)
            {
                ShowMessageBox.ShowInfo(ex.Message);
            }
            catch (ServiceErrorException ex)
            {
                ShowMessageBox.ShowError(ex.Message);
            }
            catch (Exception ex)
            {
                ShowMessageBox.ShowError(ex.Message);
            }
        }
    }
}
