package card_apple_order

import (
	"context"

	"kami/internal/consts"
	"kami/internal/dao"
	"kami/internal/model"
	"kami/internal/model/do"
	"kami/internal/model/entity"
	"kami/utility/config"
	"kami/utility/utils"

	"github.com/gogf/gf/v2/database/gdb"
	"github.com/gogf/gf/v2/errors/gcode"
	"github.com/gogf/gf/v2/errors/gerror"
	"github.com/gogf/gf/v2/frame/g"
	"github.com/gogf/gf/v2/os/glog"
)

// AddHistory 添加一条充值历史记录
func (h *sAppleOrder) AddHistory(ctx context.Context, input *model.AppleCardRechargeHistoryInput, tx gdb.TX) (err error) {
	m := dao.V1CardAppleHistoryInfo.Ctx(ctx).DB(config.GetDatabaseV1())
	if tx != nil {
		m = m.TX(tx)
	}
	_, err = m.Insert(do.V1CardAppleHistoryInfo{
		AccountId:   input.AccountID,
		AccountName: input.AccountName,
		RechargeId:  input.RechargeId,
		OrderNo:     input.OrderNo,
		Operation:   input.Operation,
		Remark:      input.Remark,
	})
	return
}

func (h *sAppleOrder) QueryDuplicatedCardPass(ctx context.Context, cardPass string) (bool, string) {
	var data []struct {
		Status int `json:"status" orm:"status"`
		Count  int `json:"count" orm:"count"`
	}
	if err := dao.V1CardAppleRechargeInfo.Ctx(ctx).DB(config.GetDatabaseV1()).
		Where(dao.V1CardAppleRechargeInfo.Columns().CardPass, cardPass).Scan(&data); err != nil {
		glog.Error(ctx, "query duplicated card pass error", err)
		return false, "程序内部错误，请联系管理员"
	}
	if len(data) == 0 {
		return false, ""
	}
	mapData := g.MapIntInt{}
	for _, v := range data {
		mapData[v.Status] = v.Count
	}
	if v, ok := mapData[int(consts.AppleRechargeOrderFail)]; ok && v > 0 {
		return true, "卡密无效或已经兑换，请不要重复提交卡密"
	}
	if v, ok := mapData[int(consts.AppleRechargeOrderSuccess)]; ok && v > 0 {
		return true, "卡密已使用，请不要重复提交卡密~"
	}
	if v, ok := mapData[int(consts.AppleRechargeOrderProcessing)]; ok && v > 0 {
		return true, "卡密已有提交记录，请不要重复提交"
	}
	// 只需要一次拉单，只要存在订单，不允许重复
	for _, statusCount := range mapData {
		if statusCount >= 0 {
			return true, "卡密已有提交记录，请不要重复提交"
		}
	}
	return true, "卡密重复，请勿重复提交~"
}

/*
QueryDuplicatedCardPassV2 判断当前卡密是否重复，如果重复，返回True

卡密重复的规则有个例外情况，就是提交卡密为金额异议的情况，这个时候允许卡密重复，并只允许重复一次重复
*/
func (h *sAppleOrder) QueryDuplicatedCardPassV2(ctx context.Context, cardPass string) (bool, string) {
	var data []struct {
		Status int `json:"status" orm:"status"`
		Count  int `json:"count" orm:"count"`
	}
	_ = dao.V1CardAppleRechargeInfo.Ctx(ctx).DB(config.GetDatabaseV1()).
		Fields(dao.V1CardAppleRechargeInfo.Columns().Status).
		FieldCount(dao.V1CardAppleRechargeInfo.Columns().Status, "count").
		Where(dao.V1CardAppleRechargeInfo.Columns().CardPass, cardPass).
		Group(dao.V1CardAppleAccountInfo.Columns().Status).Scan(&data)
	if len(data) == 0 {
		return false, ""
	}
	mapData := g.MapIntInt{}
	for _, v := range data {
		mapData[v.Status] = v.Count
	}
	// 需要二次拉单的
	// 有需要二次传值，已经传值的，不允许重复
	if mapData[int(consts.AppleRechargeOrderAmountDifferent)] > 0 {
		count := 0
		for statusCode, statusCount := range mapData {
			// 二次拉单的，第二次拉单处理失败的，允许再次拉单
			if statusCode != int(consts.AppleRechargeOrderAmountDifferent) &&
				statusCode != int(consts.AppleRechargeOrderFail) {
				count += statusCount
			}
		}
		if count > 0 {
			return true, "卡密已使用，请不要重复提交卡密~"
		} else {
			return false, ""
		}
	}
	if v, ok := mapData[int(consts.AppleRechargeOrderFail)]; ok && v > 0 {
		return true, "卡密无效或已经兑换，请不要重复提交卡密~"
	}
	if v, ok := mapData[int(consts.AppleRechargeOrderSuccess)]; ok && v > 0 {
		return true, "卡密已使用，请不要重复提交卡密~"
	}
	if v, ok := mapData[int(consts.AppleRechargeOrderProcessing)]; ok && v > 0 {
		return true, "卡密已有提交记录，请不要重复提交"
	}
	// 只需要一次拉单，只要存在订单，不允许重复
	for _, statusCount := range mapData {
		if statusCount > 0 {
			return true, "卡密已有提交记录，请不要重复提交"
		}
	}
	return true, "未知状态"
}

// QueryOneByCardPass 通过卡密查询订单
func (h *sAppleOrder) QueryOneByCardPass(ctx context.Context, cardPass string, status *consts.AppleRechargeOrderStatus) (data entity.V1CardAppleRechargeInfo, err error) {
	data = entity.V1CardAppleRechargeInfo{}
	m := dao.V1CardAppleRechargeInfo.Ctx(ctx).DB(config.GetDatabaseV1()).
		Where(dao.V1CardAppleRechargeInfo.Columns().CardPass, cardPass)
	if status != nil {
		m = m.Where(dao.V1CardAppleRechargeInfo.Columns().Status, status)
	}
	err = m.Scan(&data)
	err = utils.HandleNoRowsError(err)
	return
}

// GetRechargeDetails 获取充值操作记录
func (h *sAppleOrder) GetRechargeDetails(ctx context.Context, orderNo string) (total int, data []entity.V1CardAppleHistoryInfo, err error) {
	m := dao.V1CardAppleHistoryInfo.Ctx(ctx).DB(config.GetDatabaseV1())
	err = m.Where(dao.V1CardAppleHistoryInfo.Columns().OrderNo, orderNo).
		OrderDesc(dao.V1CardAppleHistoryInfo.Columns().CreatedAt).
		ScanAndCount(&data, &total, false)
	if err != nil {
		err = gerror.WrapCode(gcode.CodeDbOperationError, err, "获取充值操作记录失败")
	}
	return
}
