package me.zhengjie.modules.front.service.impl;

import cn.hutool.core.util.ObjectUtil;
import cn.hutool.core.util.StrUtil;
import com.alibaba.fastjson2.JSONObject;
import me.zhengjie.config.properties.FileProperties;
import me.zhengjie.exception.BadRequestException;
import me.zhengjie.modules.front.domain.dto.LoginVo;
import me.zhengjie.modules.front.domain.dto.WeChatMiniAuthorizeVo;
import me.zhengjie.modules.front.service.WeChatService;
import me.zhengjie.modules.security.config.SecurityProperties;
import me.zhengjie.modules.security.security.TokenProvider;
import me.zhengjie.modules.security.service.OnlineUserService;
import me.zhengjie.modules.security.service.dto.JwtUserDto;
import me.zhengjie.modules.system.domain.BusUser;
import me.zhengjie.modules.system.mapper.BusUserMapper;
import me.zhengjie.modules.system.service.BusUserService;
import me.zhengjie.utils.*;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Service;
import org.springframework.web.multipart.MultipartFile;

import javax.servlet.http.HttpServletRequest;
import java.io.File;
import java.time.LocalDateTime;
import java.time.format.DateTimeFormatter;
import java.util.Random;

@Service
public class WeChatServiceImpl implements WeChatService {

    private final Logger logger = LoggerFactory.getLogger(WeChatServiceImpl.class);

    @Value("${weChat.appId}")
    private String appId;

    @Value("${weChat.secret}")
    private String secret;

    @Autowired private QrCodeUtil qrCodeUtil;
    @Autowired private BusUserMapper BusUserMapper;
    @Autowired private RestTemplateUtils restTemplateUtil;
    @Autowired private TokenProvider tokenProvider;
    @Autowired private SecurityProperties properties;
    @Autowired private FileProperties fileProperties;
    @Autowired private OnlineUserService onlineUserService;
    @Autowired private BusUserService busUserService;
    private static final String DEFAULT_AVATAR = "/avatar/avatar.png";
    private static final String WECHAT_MINI_SNS_AUTH_CODE2SESSION_URL = "https://api.weixin.qq.com/sns/jscode2session?appid={}&secret={}&js_code={}&grant_type=authorization_code";

    @Override
    public String getQrCode(Long deviceId, String code) {
        MultipartFile multipartFile = qrCodeUtil.getQrCode(code, code);
        String suffix = FileUtil.getExtensionName(multipartFile.getOriginalFilename());
        String type = FileUtil.getFileType(suffix);
        File file = FileUtil.upload(multipartFile, fileProperties.getPath().getPath() + type +  File.separator);
        if(ObjectUtil.isNull(file)){
            throw new BadRequestException("上传失败");
        }
        return file.getName();
    }

    @Override
    public LoginVo authorizeLogin(String code, HttpServletRequest request) {
        LoginVo loginVo = new LoginVo();
        WeChatMiniAuthorizeVo response = new WeChatMiniAuthorizeVo(); //miniAuthCode(code);
        response.setOpenId("123456");
        String openId = response.getOpenId();
        String type = "login";
        BusUser BusUser = BusUserMapper.getUserByOpenId(openId);
        if (ObjectUtil.isNotNull(BusUser)) {
            if (BusUser.getStatus().equals(0)) { throw new BadRequestException("当前账户已禁用，请联系管理员！"); }
        } else {
            BusUser add = new BusUser();
            add.setSex(0);
            add.setRealName(DateUtil.localDateTimeFormat(LocalDateTime.now(), DateTimeFormatter.ofPattern("yyyyMMddHHmmssSSS")));
            add.setNickname("用户_" + new Random().nextInt(900000) + 100000);
            add.setToken(openId);
            add.setAvatar(DEFAULT_AVATAR);
            BusUserMapper.insert(add);
            BusUser = add;
            type = "register";
        }
        loginVo.setType(type);
        loginVo.setUid(BusUser.getId());
        loginVo.setNikeName(BusUser.getNickname());
        loginVo.setPhone(BusUser.getPhone());
        loginVo.setAvatar(BusUser.getAvatar());
        // 生成令牌
        JwtUserDto jwtUserDto = busUserService.addUserCache(BusUser);
        String token = tokenProvider.createToken(jwtUserDto);
        loginVo.setToken(properties.getTokenStartWith() + token);
        // 保存在线信息
        onlineUserService.save(jwtUserDto, token, request);
        return loginVo;
    }

    private WeChatMiniAuthorizeVo miniAuthCode(String code) {
        String url = StrUtil.format(WECHAT_MINI_SNS_AUTH_CODE2SESSION_URL, appId, secret, code);
        JSONObject data = restTemplateUtil.getData(url);
        if (ObjectUtil.isNull(data)) {
            throw new BadRequestException("微信平台接口异常，没任何数据返回！");
        }
        if (data.containsKey("errcode") && !"0".equals(data.getString("errcode"))) {
            if (data.containsKey("errmsg")) {
                throw new BadRequestException("微信接口调用失败：" + data.getString("errcode") + data.getString("errmsg"));
            }
        }
        return JSONObject.parseObject(data.toJSONString(), WeChatMiniAuthorizeVo.class);
    }

}
