/*
 * 自定义查询
 */

using System;
using System.Web;
using System.Collections.Generic;
using System.Diagnostics;
using System.Linq;
using System.Threading.Tasks;
using Microsoft.AspNetCore.Mvc;
using Microsoft.AspNetCore.Http;
using Microsoft.Extensions.Logging;
using Microsoft.Extensions.Options;
using MySystem.Models;
using Library;
using LitJson;
using MySystemLib;
using System.Text.RegularExpressions;
using System.Data;

namespace MySystem.Areas.Admin.Controllers
{
    [Area("Admin")]
    [Route("Admin/[controller]/[action]")]
    public class CustomQueryController : BaseController
    {
        public CustomQueryController(IHttpContextAccessor accessor, ILogger<BaseController> logger, IOptions<Setting> setting) : base(accessor, logger, setting)
        {
            OtherMySqlConn.connstr = ConfigurationManager.AppSettings["SqlConnStr"].ToString();
        }

        #region 自定义查询列表

        /// <summary>
        /// 根据条件查询自定义查询列表
        /// </summary>
        /// <returns></returns>
        public IActionResult Index(CustomQuery data, string right)
        {
            ViewBag.RightInfo = RightInfo;
            ViewBag.right = right;


            return View();
        }

        #endregion

        #region 根据条件查询自定义查询列表

        /// <summary>
        /// 自定义查询列表
        /// </summary>
        /// <returns></returns>
        public JsonResult IndexData(CustomQuery data, int page = 1, int limit = 30)
        {

            Dictionary<string, string> Fields = new Dictionary<string, string>();

            string condition = " and Status>-1";
            if(SysUserName != "admin")
            {
                condition += " and CONCAT(',', AdminNames,',') like '%," + SysUserName + ",%'";
            }
            if(!string.IsNullOrEmpty(data.Title))
            {
                condition += " and Title like '%" + data.Title + "%'";
            }

            Dictionary<string, object> obj = new AdminContentOther(_accessor.HttpContext, PublicFunction.MainTables).IndexData("CustomQuery", Fields, "Id desc", "0", page, limit, condition);
            List<Dictionary<string, object>> diclist = obj["data"] as List<Dictionary<string, object>>;
            foreach (Dictionary<string, object> dic in diclist)
            {

            }
            return Json(obj);
        }

        #endregion

        #region 增加自定义查询

        /// <summary>
        /// 增加或修改自定义查询信息
        /// </summary>
        /// <returns></returns>
        public IActionResult Add(string right)
        {
            ViewBag.RightInfo = RightInfo;
            ViewBag.right = right;


            return View();
        }

        #endregion

        #region 增加自定义查询

        /// <summary>
        /// 增加或修改自定义查询信息
        /// </summary>
        /// <returns></returns>
        [HttpPost]
        public string Add(CustomQuery data)
        {
            Dictionary<string, object> Fields = new Dictionary<string, object>();

            Fields.Add("SqlContent", data.SqlContent); //sql语句
            Fields.Add("Title", data.Title); //标题
            Fields.Add("AdminNames", data.AdminNames); //后台账号
            Fields.Add("ExcuteFlag", data.ExcuteFlag); //是否执行
            Fields.Add("DatabaseConnect", data.DatabaseConnect); //数据库

            Fields.Add("SeoTitle", data.SeoTitle);
            Fields.Add("SeoKeyword", data.SeoKeyword);
            Fields.Add("SeoDescription", data.SeoDescription);
            int Id = new AdminContentOther(_accessor.HttpContext, PublicFunction.MainTables).Add("CustomQuery", Fields, 0);
            AddSysLog(data.Id.ToString(), "CustomQuery", "add");
            db.SaveChanges();

            return "success";
        }

        #endregion

        #region 修改自定义查询

        /// <summary>
        /// 增加或修改自定义查询信息
        /// </summary>
        /// <returns></returns>
        public IActionResult Edit(string right, int Id = 0)
        {
            ViewBag.RightInfo = RightInfo;
            ViewBag.right = right;


            CustomQuery editData = db.CustomQuery.FirstOrDefault(m => m.Id == Id) ?? new CustomQuery();
            ViewBag.data = editData;
            return View();
        }

        #endregion

        #region 修改自定义查询

        /// <summary>
        /// 增加或修改自定义查询信息
        /// </summary>
        /// <returns></returns>
        [HttpPost]
        public string Edit(CustomQuery data)
        {
            Dictionary<string, object> Fields = new Dictionary<string, object>();

            Fields.Add("SqlContent", data.SqlContent); //sql语句
            Fields.Add("Title", data.Title); //标题
            Fields.Add("AdminNames", data.AdminNames); //后台账号
            Fields.Add("ExcuteFlag", data.ExcuteFlag); //是否执行
            Fields.Add("DatabaseConnect", data.DatabaseConnect); //数据库

            Fields.Add("SeoTitle", data.SeoTitle);
            Fields.Add("SeoKeyword", data.SeoKeyword);
            Fields.Add("SeoDescription", data.SeoDescription);
            new AdminContentOther(_accessor.HttpContext, PublicFunction.MainTables).Edit("CustomQuery", Fields, data.Id);
            AddSysLog(data.Id.ToString(), "CustomQuery", "update");
            db.SaveChanges();

            return "success";
        }

        #endregion

        #region 删除自定义查询信息

        /// <summary>
        /// 删除自定义查询信息
        /// </summary>
        /// <returns></returns>
        public string Delete(string Id)
        {
            string[] idlist = Id.Split(new char[] { ',' });
            AddSysLog(Id, "CustomQuery", "del");
            foreach (string subid in idlist)
            {
                int id = int.Parse(subid);
                Dictionary<string, object> Fields = new Dictionary<string, object>();
                Fields.Add("Status", -1);
                new AdminContentOther(_accessor.HttpContext, PublicFunction.MainTables).Edit("CustomQuery", Fields, id);
            }
            db.SaveChanges();

            return "success";
        }

        #endregion

        #region 开启

        /// <summary>
        /// 开启
        /// </summary>
        /// <returns></returns>
        public string Open(string Id)
        {
            string[] idlist = Id.Split(new char[] { ',' });
            AddSysLog(Id, "CustomQuery", "open");
            foreach (string subid in idlist)
            {
                int id = int.Parse(subid);
                Dictionary<string, object> Fields = new Dictionary<string, object>();
                Fields.Add("Status", 1);
                new AdminContentOther(_accessor.HttpContext, PublicFunction.MainTables).Edit("CustomQuery", Fields, id);
            }
            db.SaveChanges();
            return "success";
        }

        #endregion

        #region 关闭

        /// <summary>
        /// 关闭
        /// </summary>
        /// <returns></returns>
        public string Close(string Id)
        {
            string[] idlist = Id.Split(new char[] { ',' });
            AddSysLog(Id, "CustomQuery", "close");
            foreach (string subid in idlist)
            {
                int id = int.Parse(subid);
                Dictionary<string, object> Fields = new Dictionary<string, object>();
                Fields.Add("Status", 0);
                new AdminContentOther(_accessor.HttpContext, PublicFunction.MainTables).Edit("CustomQuery", Fields, id);
            }
            db.SaveChanges();
            return "success";
        }

        #endregion

        #region 排序
        /// <summary>
        /// 排序
        /// </summary>
        /// <param name="Id"></param>
        public string Sort(int Id, int Sort)
        {
            new AdminContentOther(_accessor.HttpContext, PublicFunction.MainTables).Sort("CustomQuery", Sort, Id);

            AddSysLog(Id.ToString(), "CustomQuery", "sort");
            return "success";
        }
        #endregion

        #region 导入数据
        /// <summary>
        /// 导入数据
        /// </summary>
        /// <param name="ExcelData"></param>
        public string Import(string ExcelData)
        {
            ExcelData = HttpUtility.UrlDecode(ExcelData);
            JsonData list = JsonMapper.ToObject(ExcelData);
            for (int i = 1; i < list.Count; i++)
            {
                JsonData dr = list[i];

                db.CustomQuery.Add(new CustomQuery()
                {
                    CreateDate = DateTime.Now,
                    UpdateDate = DateTime.Now,

                });
                db.SaveChanges();
            }
            AddSysLog("0", "CustomQuery", "Import");
            return "success";
        }
        #endregion

        #region 导出Excel

        /// <summary>
        /// 导出Excel
        /// </summary>
        /// <returns></returns>
        public JsonResult ExportExcel(CustomQuery data)
        {
            Dictionary<string, string> Fields = new Dictionary<string, string>();
            Fields.Add("Title", "1"); //标题


            string condition = " and Status>-1";


            Dictionary<string, object> obj = new AdminContentOther(_accessor.HttpContext, PublicFunction.MainTables).IndexData("CustomQuery", Fields, "Id desc", "0", 1, 20000, condition, "", false);
            List<Dictionary<string, object>> diclist = obj["data"] as List<Dictionary<string, object>>;
            foreach (Dictionary<string, object> dic in diclist)
            {

            }

            Dictionary<string, object> result = new Dictionary<string, object>();
            result.Add("Status", "1");
            result.Add("Info", "Excel报表-" + DateTime.Now.ToString("yyyy-MM-ddTHH:mm:ss") + ".xlsx");
            result.Add("Obj", diclist);
            Dictionary<string, object> ReturnFields = new Dictionary<string, object>();

            result.Add("Fields", ReturnFields);
            AddSysLog("0", "CustomQuery", "ExportExcel");
            return Json(result);
        }

        #endregion



        
        #region 自定义提交

        /// <summary>
        /// 自定义提交
        /// </summary>
        /// <returns></returns>
        public IActionResult Confirm(string right, int Id)
        {
            ViewBag.RightInfo = RightInfo;
            ViewBag.right = right;
            ViewBag.Id = Id.ToString();

            CustomQuery item = db.CustomQuery.FirstOrDefault(m => m.Id == Id) ?? new CustomQuery();
            if(SysUserName != "admin")
            {
                string checkString = "," + item.AdminNames + ",";
                if(!checkString.Contains("," + SysUserName + ","))
                {
                    return Content("无权限");
                }
            }
            Dictionary<string, string> query = new Dictionary<string, string>();
            string sql = item.SqlContent;
            MatchCollection mc = Regex.Matches(sql, @"\$\{.*?\}\$");
            foreach(Match m in mc)
            {
                string[] fieldData = m.Value.Replace("${", "").Replace("}$", "").Split('|');
                string fieldName = fieldData[0];
                string Title = fieldData[1];
                if(!query.ContainsKey(fieldName))
                {
                    query.Add(fieldName, Title);
                }
            }
            List<CustomQuerySub> subItems = db.CustomQuerySub.Where(m => m.ParentId == Id).ToList();
            foreach(CustomQuerySub sub in subItems)
            {
                sql = sub.SqlContent;
                mc = Regex.Matches(sql, @"\$\{.*?\}\$");
                foreach(Match m in mc)
                {
                    string[] fieldData = m.Value.Replace("${", "").Replace("}$", "").Split('|');
                    string fieldName = fieldData[0];
                    string Title = fieldData[1];
                    if(!query.ContainsKey(fieldName))
                    {
                        query.Add(fieldName, Title);
                    }
                }
            }
            ViewBag.query = query;

            return View();
        }

        #endregion

        #region 自定义提交

        /// <summary>
        /// 自定义提交
        /// </summary>
        /// <returns></returns>
        [HttpPost]
        public string Confirm(int Id)
        {
            var sysAdmin = bsdb.SysAdmin.FirstOrDefault(m => m.AdminName == SysUserName && m.Status > -1);
            CustomQuery item = db.CustomQuery.FirstOrDefault(m => m.Id == Id) ?? new CustomQuery();
            string ConnectStr = "";
            Dictionary<string, string> dicVals = new Dictionary<string, string>();
            List<CustomQuerySub> subItems = db.CustomQuerySub.Where(m => m.ParentId == Id).ToList();
            foreach(CustomQuerySub sub in subItems)
            {
                ConnectStr = sub.DatabaseConnect;
                if(!string.IsNullOrEmpty(ConnectStr))
                {
                    ConnectStr = GetConnectStr(sub.DatabaseConnect);
                }
                else
                {
                    if(item.ExcuteFlag == 2)
                    {
                        ConnectStr = MysqlConn.RedisConnStr;
                    }
                    else
                    {
                        ConnectStr = MysqlConn.ReadSqlConnStr;
                    }
                }

                string sqlstr = sub.SqlContent;
                MatchCollection mcsub = Regex.Matches(sqlstr, @"\$\{.*?\}\$");
                foreach(Match m in mcsub)
                {
                    string[] fieldData = m.Value.Replace("${", "").Replace("}$", "").Split('|');
                    string fieldName = fieldData[0];
                    sqlstr = sqlstr.Replace(m.Value, Request.Query[fieldName].ToString());
                }

                mcsub = Regex.Matches(sqlstr, @"\#\{.*?\}\#");
                foreach(Match m in mcsub)
                {
                    string fieldName = m.Value.Replace("#{", "").Replace("}#", "");
                    if(dicVals.ContainsKey(fieldName))
                    {
                        sqlstr = sqlstr.Replace(m.Value, dicVals[fieldName]);
                    }
                }

                DataTable dtsub = CustomerSqlConn.dtable(sqlstr, ConnectStr);
                if(dtsub.Rows.Count > 0)
                {
                    if(dtsub.Rows.Count > 1)
                    {
                        string val = "";
                        foreach(DataRow dr in dtsub.Rows)
                        {
                            val += dr[0].ToString() + ",";
                        }
                        val = val.TrimEnd(',');
                        dicVals.Add(sub.Alias + "." + dtsub.Columns[0].ColumnName, val);
                    }
                    else
                    {
                        DataRow dr = dtsub.Rows[0];
                        foreach(DataColumn dc in dtsub.Columns)
                        {
                            dicVals.Add(sub.Alias + "." + dc.ColumnName, dr[dc.ColumnName].ToString());
                        }
                    }
                }
            }
            ConnectStr = item.DatabaseConnect;
            if(!string.IsNullOrEmpty(ConnectStr))
            {
                ConnectStr = GetConnectStr(item.DatabaseConnect);
            }
            else
            {
                if(item.ExcuteFlag == 2)
                {
                    ConnectStr = MysqlConn.RedisConnStr;
                }
                else
                {
                    ConnectStr = MysqlConn.ReadSqlConnStr;
                }
            }
            string sql = item.SqlContent;
            MatchCollection mc = Regex.Matches(sql, @"\$\{.*?\}\$");
            foreach(Match m in mc)
            {
                string[] fieldData = m.Value.Replace("${", "").Replace("}$", "").Split('|');
                string fieldName = fieldData[0];
                sql = sql.Replace(m.Value, Request.Form[fieldName].ToString());
            }
            mc = Regex.Matches(sql, @"\$\replace{.*?\}\$");
            foreach(Match m in mc)
            {
                string[] fieldData = m.Value.Replace("$replace{", "").Replace("}$", "").Split('|');
                string str = fieldData[0];
                string oldStr = fieldData[1];
                string newStr = fieldData[2];
                str = str.Replace(oldStr, newStr);
                sql = sql.Replace(m.Value, str);
            }
            if(item.ExcuteFlag == 1)
            {
                string SendData = "{\"Operater\":\"" + sysAdmin.Id + "\",\"SqlString\":\"" + sql + "\",\"FileName\":\"执行\",\"MaxCount\":\"50\",\"ConnectStr\":\"" + ConnectStr + "\"}";
                RedisDbconn.Instance.AddList("ExportQueue", SendData);
            }
            else if(item.ExcuteFlag == 3)
            {
                string redisCommand = sql;
                string[] redisCommandList = redisCommand.Split(' ');
                string kind = redisCommandList[0];
                string key = redisCommandList[1];
                string val = redisCommandList[2];
                if(kind == "lpush")
                {
                    new CustomRedisDbconn(ConnectStr).AddList(key, val);
                }
                else if(kind == "set")
                {
                    new CustomRedisDbconn(ConnectStr).Set(key, val);
                }
                else if(kind == "addint")
                {
                    new CustomRedisDbconn(ConnectStr).AddInt(key, int.Parse(val));
                }
                else if(kind == "addnum")
                {
                    new CustomRedisDbconn(ConnectStr).AddNumber(key, decimal.Parse(val));
                }
            }
            return "success";
        }

        #endregion

        #region 获取链接数据库字符串

        public string GetConnectStr(string key)
        {
            return Library.ConfigurationManager.AppSettings[key].ToString();
        }

        #endregion

    }
}
