package dao

import (
	"github.com/druidcaesa/gotool"
	"reflect"
	"strings"
	"ulink-admin/modules/system/models/model"
	"ulink-admin/modules/system/models/req"
	"ulink-admin/pkg/base"
	"ulink-admin/pkg/page"
	"ulink-admin/utils"
	"xorm.io/xorm"
)

type SysOperLogDao struct {
}

func (d SysOperLogDao) selectSql(session *xorm.Session) *xorm.Session {
	return session.Table([]string{"sys_oper_log", "o"})
}

// SelectAll 查询所有操作日志记录数据,数据库操作
func (d SysOperLogDao) SelectAll() []*model.SysOperLog {
	session := base.SqlDB.NewSession()
	sysOperLog := make([]*model.SysOperLog, 0)
	err := session.Find(&sysOperLog)
	if err != nil {
		gotool.Logs.ErrorLog().Println(err)
		return nil
	}
	return sysOperLog
}

// Find 查询操作日志记录分页数据
func (d SysOperLogDao) Find(query *req.SysOperLogQuery) (*[]model.SysOperLog, int64) {
	sysOperLog := make([]model.SysOperLog, 0)
	session := base.SqlDB.NewSession().Table(model.SysOperLog{}.TableName())

	if query.Id > 0 {
		session.And("id = ?", query.Id)
	}
	if !gotool.StrUtils.HasEmpty(query.Title) {
		session.And("title = ?", query.Title)
	}
	if query.BusinessType > 0 {
		session.And("business_type = ?", query.BusinessType)
	}
	if !gotool.StrUtils.HasEmpty(query.Method) {
		session.And("method = ?", query.Method)
	}
	if !gotool.StrUtils.HasEmpty(query.RequestMethod) {
		session.And("request_method = ?", query.RequestMethod)
	}
	if query.OperatorType > 0 {
		session.And("operator_type = ?", query.OperatorType)
	}
	if !gotool.StrUtils.HasEmpty(query.OperName) {
		session.And("oper_name = ?", query.OperName)
	}
	if !gotool.StrUtils.HasEmpty(query.DeptName) {
		session.And("dept_name = ?", query.DeptName)
	}
	if !gotool.StrUtils.HasEmpty(query.OperUrl) {
		session.And("oper_url = ?", query.OperUrl)
	}
	if !gotool.StrUtils.HasEmpty(query.OperIp) {
		session.And("oper_ip = ?", query.OperIp)
	}
	if !gotool.StrUtils.HasEmpty(query.OperLocation) {
		session.And("oper_location = ?", query.OperLocation)
	}
	if !gotool.StrUtils.HasEmpty(query.OperParam) {
		session.And("oper_param = ?", query.OperParam)
	}
	if !gotool.StrUtils.HasEmpty(query.JsonResult) {
		session.And("json_result = ?", query.JsonResult)
	}
	if query.Status > 0 {
		session.And("status = ?", query.Status)
	}
	if !gotool.StrUtils.HasEmpty(query.ErrorMsg) {
		session.And("error_msg = ?", query.ErrorMsg)
	}
	if !gotool.StrUtils.HasEmpty(query.BeginTime) {
		session.And("date_format(u.create_time,'%y%m%d') >= date_format(?,'%y%m%d')", query.BeginTime)
	}
	if !gotool.StrUtils.HasEmpty(query.EndTime) {
		session.And("date_format(u.create_time,'%y%m%d') <= date_format(?,'%y%m%d')", query.EndTime)
	}
	session.Desc("id")
	total, err := session.Limit(query.PageSize, page.StartSize(query.PageNum, query.PageSize)).FindAndCount(&sysOperLog)
	if err != nil {
		gotool.Logs.ErrorLog().Println(err)
		return nil, 0
	}
	return &sysOperLog, total
}

// Insert 添加操作日志记录数据
func (d SysOperLogDao) Insert(sysOperLog *model.SysOperLog) int64 {
	session := base.SqlDB.NewSession()
	session.Begin()
	insert, err := session.Insert(sysOperLog)
	if err != nil {
		session.Rollback()
		gotool.Logs.ErrorLog().Println(err)
		return 0
	}
	session.Commit()
	return insert
}

// GetSysOperLogById 根据id查询操作日志记录数据
func (d SysOperLogDao) GetSysOperLogById(sysOperLog model.SysOperLog) *model.SysOperLog {
	_, err := base.SqlDB.NewSession().Where("id= ?", sysOperLog.Id).Get(&sysOperLog)
	if err != nil {
		gotool.Logs.ErrorLog().Println(err)
		return nil
	}
	return &sysOperLog
}

// Delete 批量删除操作日志记录
func (d SysOperLogDao) Delete(sysOperLog []int64) int64 {
	session := base.SqlDB.NewSession()
	session.Begin()
	i, err := session.In("id", sysOperLog).Delete(&model.SysOperLog{})
	if err != nil {
		session.Rollback()
		gotool.Logs.ErrorLog().Println(err)
		return 0
	}
	session.Commit()
	return i
}

// Update 修改操作日志记录数据
func (d SysOperLogDao) Update(sysOperLog *model.SysOperLog) bool {
	session := base.SqlDB.NewSession()
	session.Begin()
	_, err := session.Where("id= ?", sysOperLog.Id).AllCols().Update(sysOperLog)
	if err != nil {
		session.Rollback()
		gotool.Logs.ErrorLog().Println(err)
		return false
	}
	session.Commit()
	return true
}

// CheckUnique 唯一性检查
func (d SysOperLogDao) CheckUnique(sysOperLog *model.SysOperLog, condition []string) int64 {
	session := base.SqlDB.Table(sysOperLog.TableName())
	if sysOperLog.Id > 0 {
		session.And("id != ?", sysOperLog.Id)
	}

	for _, item := range condition {
		fieldValue := reflect.ValueOf(sysOperLog).FieldByName(utils.Ucfirst(item))
		if strings.Contains(fieldValue.Type().String(), "int") {
			session.And(utils.Camel2Case(item)+" = ?", fieldValue.Int())
		} else if strings.Contains(fieldValue.Type().String(), "string") {
			session.And(utils.Camel2Case(item)+" = ?", fieldValue.String())
		} else {
			session.And(utils.Camel2Case(item)+" = ?", fieldValue.String())
		}
	}
	count, err := session.Count()
	if err != nil {
		gotool.Logs.ErrorLog().Println(err)
	}
	return count
}