package com.yeejoin.amos.boot.module.tzs.biz.controller;

import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.yeejoin.amos.boot.biz.common.controller.BaseController;
import com.yeejoin.amos.boot.biz.common.utils.RedisUtils;
import com.yeejoin.amos.boot.module.tzs.api.dto.WechatAccessDto;
import com.yeejoin.amos.boot.module.tzs.api.entity.WechatRelation;
import com.yeejoin.amos.boot.module.tzs.api.service.IDispatchTaskService;
import com.yeejoin.amos.boot.module.tzs.api.service.IWechatService;
import com.yeejoin.amos.boot.module.tzs.biz.service.impl.WechatRelationServiceImpl;
import com.yeejoin.amos.component.feign.model.FeignClientResult;
import com.yeejoin.amos.feign.systemctl.Systemctl;
import com.yeejoin.amos.feign.systemctl.model.SmsRecordModel;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiModelProperty;
import io.swagger.annotations.ApiOperation;
import io.swagger.annotations.ApiParam;
import org.apache.commons.codec.digest.DigestUtils;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.RestController;
import org.typroject.tyboot.core.foundation.enumeration.UserType;
import org.typroject.tyboot.core.foundation.utils.ValidationUtil;
import org.typroject.tyboot.core.restful.doc.TycloudOperation;
import org.typroject.tyboot.core.restful.exception.instance.BadRequest;
import org.typroject.tyboot.core.restful.utils.ResponseHelper;
import org.typroject.tyboot.core.restful.utils.ResponseModel;
import org.w3c.dom.Node;
import org.w3c.dom.NodeList;

import javax.servlet.http.HttpServletResponse;
import javax.xml.parsers.DocumentBuilder;
import javax.xml.parsers.DocumentBuilderFactory;
import java.io.ByteArrayInputStream;
import java.io.InputStream;
import java.util.ArrayList;
import java.util.Collections;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.Random;

/**
 * 微信公众号controller
 */
@RestController
@Api(tags = "微信公众号Api")
@RequestMapping(value = "/wechatBack")
public class WechatController extends BaseController {

	private long time = 600l;

	private final String token = "yeejoin_2021";

	@Autowired
	RedisUtils redisUtils;

	@Autowired
	private IWechatService wechatService;

	@Autowired
	WechatRelationServiceImpl wechatRelationServiceImpl;

	@Autowired
	IDispatchTaskService dispatchTaskService;



	/**
	 * 获取微信回调信息返回验证是否通过
	 * @param signature
	 * @param timestamp
	 * @param nonce
	 * @param echostr
	 * @return
	 */
	@TycloudOperation(ApiLevel = UserType.ANONYMOUS , needAuth = false)
	@GetMapping(value = "/getInfo")
	@ApiOperation(httpMethod = "GET", value = "获取微信传回的get信息", notes = "获取微信传回的get信息")
	public String getWechatInfo(@RequestParam String signature,@RequestParam String timestamp,@RequestParam String nonce,@RequestParam String echostr) {
		List<String> params = new ArrayList<String>();
		params.add(token);
		params.add(timestamp);
		params.add(nonce);
		Collections.sort(params);
		String tokenStr = StringUtils.join(params,"");
		tokenStr = DigestUtils.sha1Hex(tokenStr);
		if(tokenStr.equals(signature)) {
			return echostr;
		} else {
			return "";
		}
	}

	/**
	 * 获取微信推送的操作通知
	 * @param xml
	 * @param resp
	 * @return
	 */
	@TycloudOperation(ApiLevel = UserType.ANONYMOUS , needAuth = false)
	@PostMapping(value = "/getInfo")
	@ApiOperation(httpMethod = "POST", value = "获取微信传回的post信息", notes = "获取微信传回的post信息")
	public String getWechatInfoPost(@RequestBody String xml, HttpServletResponse resp) {
		Map<String, String> requtstMap = xmlToMap(xml);
		return "1";
	}


	/**
	 * XML格式字符串转换为Map
	 *
	 * @param xml XML字符串
	 * @return XML数据转换后的Map
	 * @throws Exception
	 */
	public static Map<String, String> xmlToMap(String xml) {
		try {
			Map<String, String> data = new HashMap<>();
			DocumentBuilderFactory documentBuilderFactory = DocumentBuilderFactory.newInstance();
			DocumentBuilder documentBuilder = documentBuilderFactory.newDocumentBuilder();
			InputStream stream = new ByteArrayInputStream(xml.getBytes("UTF-8"));
			org.w3c.dom.Document doc = documentBuilder.parse(stream);
			doc.getDocumentElement().normalize();
			NodeList nodeList = doc.getDocumentElement().getChildNodes();
			for (int idx = 0; idx < nodeList.getLength(); ++idx) {
				Node node = nodeList.item(idx);
				if (node.getNodeType() == Node.ELEMENT_NODE) {
					org.w3c.dom.Element element = (org.w3c.dom.Element) node;
					data.put(element.getNodeName(), element.getTextContent());
				}
			}
			stream.close();
			return data;
		} catch (Exception e) {
			e.printStackTrace();
			return null;
		}
	}

	/**
	 * 获取wechatToken信息
	 *
	 * @return
	 */
	@TycloudOperation(ApiLevel = UserType.AGENCY, needAuth = false)
	@GetMapping(value = "/getAccessToken")
	@ApiOperation(httpMethod = "GET", value = "获取token信息", notes = "获取token信息")
	public ResponseModel<String> getAccessToken() {
		String token = wechatService.getAccessToken();
		return ResponseHelper.buildResponse(token);
	}

	/**
	 * 根据手机号发送短信验证码
	 * @param tel
	 * @return
	 */
	@TycloudOperation(ApiLevel = UserType.AGENCY, needAuth = false)
	@GetMapping(value = "/sendSms/{tel}")
	@ApiOperation(httpMethod = "GET", value = "根据手机号发送短信验证码", notes = "根据手机号发送短信验证码")
	public ResponseModel<Boolean> sendSmsCode(@PathVariable String tel) {
		Boolean flag = false;
		String code = getrandom();
		HashMap<String, String>  params = new HashMap<>();
		params.put("smsCode","SMS_TZS_0001");
		params.put("mobile",tel);
		params.put("code",code);
		FeignClientResult<SmsRecordModel> result = Systemctl.smsClient.sendCommonSms(params);
		if(result.getStatus() == 200) {
			flag = true;
			// code 保存在redis中 设置10分钟过期时间
			redisUtils.set("tel_code_" + tel, code,time);
		}
		return ResponseHelper.buildResponse(flag);
	}


	/**
	 * 根据微信code获取openId和手机号接口
	 *
	 * @return
	 */
	@TycloudOperation(ApiLevel = UserType.AGENCY, needAuth = false)
	@GetMapping(value = "/getOpenIdTel/{code}")
	@ApiOperation(httpMethod = "GET", value = "根据微信code获取openId和手机号接口", notes = "根据微信code获取openId和手机号接口")
	public ResponseModel<WechatAccessDto> getOpenIdTel(@PathVariable String code) {
		WechatAccessDto wechatAccessDto = new WechatAccessDto();
		String openId = wechatService.getOpenId(code);
		if(StringUtils.isNotEmpty(openId)) {
			wechatAccessDto.setOpenId(openId);
			WechatRelation temp = wechatRelationServiceImpl.getOne(new LambdaQueryWrapper<WechatRelation>().eq(WechatRelation::getOpenId,openId));
			if(temp != null ) {
				wechatAccessDto.setTel(temp.getPhone());
			}
		}
		return ResponseHelper.buildResponse(wechatAccessDto);
	}

	/**
	 * 根据任务id 经纬度 返回现在距离任务距离
	 *
	 * @return
	 */
	@TycloudOperation(ApiLevel = UserType.AGENCY, needAuth = false)
	@PostMapping(value = "/returnDistance")
	@ApiOperation(httpMethod = "POST", value = "根据任务id 经纬度 返回现在距离任务距离", notes = "根据任务id 经纬度 返回现在距离任务距离")
	public ResponseModel<String> returnDistance(@ApiParam(value = "任务id", required = true) @RequestParam(name = "taskId") Long taskId,
														 @ApiParam(value = "经度", required = true)  @RequestParam(name = "longitude")  String longitude,
														 @ApiParam(value = "纬度", required = true)  @RequestParam(name = "latitude")  String latitude) {
		if (ValidationUtil.isEmpty(taskId)
				|| ValidationUtil.isEmpty(longitude)
				|| ValidationUtil.isEmpty(latitude)){
			throw new BadRequest("参数校验失败.");
		}
		String distance = dispatchTaskService.returnDistanceByTaskId(taskId,longitude,latitude);
		return ResponseHelper.buildResponse(distance);
	}



	/**
	 * 创建验证码
	 * @return
	 */
	public static String getrandom(){
		String code = "";
		Random random = new Random();
		for (int i = 0; i < 6; i++) {
			int r = random.nextInt(10); //每次随机出一个数字（0-9）
			code = code + r;  //把每次随机出的数字拼在一起
		}
		return code;

	}

}
