package dingtalk

import (
	"ai_scheduler/internal/data/constants"
	"ai_scheduler/internal/data/impl"
	"ai_scheduler/internal/data/model"
	"ai_scheduler/internal/entitys"
	"ai_scheduler/internal/pkg"
	"ai_scheduler/internal/pkg/l_request"
	"context"
	"database/sql"
	"encoding/json"
	"errors"
	"fmt"
	"net/http"
	"strings"
	"time"
)

type User struct {
	dingUserImpl  *impl.BotUserImpl
	botConfigImpl *impl.BotConfigImpl
	auth          *Auth
	dept          *Dept
}

func NewUser(
	dingUserImpl *impl.BotUserImpl,
	auth *Auth,
	dept *Dept,
) *User {
	return &User{
		dingUserImpl: dingUserImpl,
		auth:         auth,
		dept:         dept,
	}
}

func (u *User) GetUserInfoFromBot(ctx context.Context, staffId string, botOption ...BotOption) (userInfo *entitys.DingTalkUserInfo, err error) {
	if len(staffId) == 0 {
		return
	}
	user, err := u.dingUserImpl.GetByStaffId(staffId)
	if err != nil {
		if !errors.Is(err, sql.ErrNoRows) {
			return
		}
	}
	//待优化
	authInfo, err := u.auth.GetTokenFromBotOption(ctx, botOption...)
	if err != nil || authInfo == nil {
		return
	}
	//如果没有找到，则新增
	if user == nil {

		DingUserInfo, _err := u.getUserInfoFromDingTalk(ctx, authInfo.AccessToken, staffId)
		if _err != nil {
			return nil, _err
		}
		user = &model.AiBotUser{
			StaffID: DingUserInfo.Userid,
			Name:    DingUserInfo.Name,
			Title:   DingUserInfo.Title,
			//Extension:  DingUserInfo.Extension,
			DeptIDList: strings.Join(pkg.SliceIntToString(DingUserInfo.DeptIdList), ","),
			IsBoss:     int32(pkg.Ter(DingUserInfo.Boss, constants.IsBossTrue, constants.IsBossFalse)),
			IsSenior:   int32(pkg.Ter(DingUserInfo.Senior, constants.IsSeniorTrue, constants.IsSeniorFalse)),
			HiredDate:  time.UnixMilli(DingUserInfo.HiredDate),
		}

		_, err = u.dingUserImpl.Add(user)
		if err != nil {
			return
		}
	}
	userInfo = &entitys.DingTalkUserInfo{
		UserId:    int(user.UserID),
		StaffId:   user.StaffID,
		Name:      user.Name,
		IsBoss:    constants.IsBoss(user.IsBoss),
		IsSenior:  constants.IsSenior(user.IsSenior),
		HiredDate: user.HiredDate,
		Extension: user.Extension,
	}
	if len(user.DeptIDList) > 0 {
		deptIdList := pkg.SliceStringToInt(strings.Split(user.DeptIDList, ","))
		depts, _err := u.dept.GetDeptInfoByDeptIds(ctx, deptIdList, authInfo)
		if _err != nil {
			return nil, err
		}
		for _, dept := range depts {
			userInfo.Dept = append(userInfo.Dept, dept)
		}
	}

	return userInfo, nil
}

func (u *User) getUserInfoFromDingTalk(ctx context.Context, token string, staffId string) (user UserInfoResResult, err error) {
	if token == "" && staffId == "" {
		err = errors.New("获取钉钉用户信息的必要参数不足")
		return
	}

	req := l_request.Request{
		Method: http.MethodPost,
		Url: constants.GetDingTalkRequestUrl(constants.RequestUrlGetUserGet, map[string]string{
			"access_token": token,
		}),
		Data: map[string]string{
			"userid": staffId,
		},
	}
	res, err := req.Send()
	if err != nil {
		return
	}
	var userInfoRes UserInfoRes
	err = json.Unmarshal(res.Content, &userInfoRes)
	if err != nil {
		return
	}
	if userInfoRes.Errcode != 0 {
		fmt.Errorf("钉钉请求报错:%s", userInfoRes.Errmsg)
	}
	return userInfoRes.Result, err
}
