package service

import (
	"context"
	"fmt"
	"log"

	"github.com/cockroachdb/errors"
	"github.com/larksuite/oapi-sdk-go/api"
	"github.com/larksuite/oapi-sdk-go/api/core/request"
	"github.com/larksuite/oapi-sdk-go/core"
	"github.com/pingcap/jira-bot/model"
)

func GetUserInfo(conds ...interface{}) (user *model.User, err error) {
	user, err = model.FindUser(model.GetApp().DB, conds...)
	if err != nil {
		return
	}

	if user.NeedQueryLark() {
		err = QueryUserLarkDataByEmail(user)
		if err != nil {
			return
		}
		err = model.Save(model.GetApp().DB, user)
	}

	return
}

func QueryUserLarkDataByEmail(user *model.User) error {
	coreCtx := core.WrapContext(context.Background())
	params := map[string]interface{}{
		"emails": user.Email,
	}
	ret := make(map[string]interface{})
	req := request.NewRequestWithNative("/open-apis/user/v1/batch_get_id", "GET",
		request.AccessTokenTypeTenant, nil, &ret, request.SetQueryParams(params))
	err := api.Send(coreCtx, model.GetApp().LarkConf, req)
	if err != nil {
		return err
	}

	if users, ok := ret["email_users"]; ok {
		if userdata, ok := users.(map[string]interface{})[user.Email]; ok {
			if ids, ok := userdata.([]interface{})[0].(map[string]interface{}); ok {
				user.FeishuOpenId = ids["open_id"].(string)
				user.FeishuUserId = ids["user_id"].(string)
			}
		}
	}

	userGetReq := model.GetApp().LarkContactService.Users.Get(core.WrapContext(context.Background()))
	userGetReq.SetUserId(user.FeishuUserId)
	userGetReq.SetUserIdType("user_id")
	userResult, err := userGetReq.Do()
	if err != nil {
		return errors.Wrap(err, fmt.Sprintf("QueryUserLarkDataByEmail failed email=%s", user.Email))
	}

	if userResult.User != nil {
		user.FeishuLeaderUserId = userResult.User.LeaderUserId
		leaderUserGetReq := model.GetApp().LarkContactService.Users.Get(core.WrapContext(context.Background()))
		leaderUserGetReq.SetUserId(user.FeishuLeaderUserId)
		leaderUserGetReq.SetUserIdType("user_id")
		leaderUserResult, err := leaderUserGetReq.Do()
		if err != nil {
			return errors.Wrap(err, fmt.Sprintf("QueryUserLarkDataByEmail failed email=%s", user.Email))
		}
		if leaderUserResult.User != nil {
			user.LeaderEmail = leaderUserResult.User.Email
		}
	} else {
		log.Println("QueryUserLarkDataByEmail userResult.User == nil err, ",
			userResult, user)
	}
	return nil
}

func DailyRun() {
	users := model.Users{}
	err := model.GetApp().DB.Find(&users).Error
	if err != nil {
		log.Println("[error] query users failed ", err)
		return
	}

	for i := range users {
		user := &users[i]
		err = QueryUserLarkDataByEmail(user)
		if err != nil {
			continue
		}
	}

	err = model.Save(model.GetApp().DB, users)
	if err != nil {
		log.Println("[error] DailyRun save failed", err)
	}
}
