/*
 *      Copyright (c) 2018-2028, Chill Zhuang All rights reserved.
 *
 *  Redistribution and use in source and binary forms, with or without
 *  modification, are permitted provided that the following conditions are met:
 *
 *  Redistributions of source code must retain the above copyright notice,
 *  this list of conditions and the following disclaimer.
 *  Redistributions in binary form must reproduce the above copyright
 *  notice, this list of conditions and the following disclaimer in the
 *  documentation and/or other materials provided with the distribution.
 *  Neither the name of the dreamlu.net developer nor the names of its
 *  contributors may be used to endorse or promote products derived from
 *  this software without specific prior written permission.
 *  Author: Chill 庄骞 (smallchill@163.com)
 */
package org.springblade.modules.api.controller;

import cn.hutool.core.io.FileUtil;
import cn.hutool.core.util.NumberUtil;
import cn.hutool.extra.qrcode.QrCodeUtil;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import com.github.xiaoymin.knife4j.annotations.ApiOperationSupport;
import com.ijpay.core.kit.PayKit;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;
import io.swagger.annotations.ApiParam;
import lombok.AllArgsConstructor;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springblade.common.constant.CommonConstant;
import org.springblade.common.utils.CommonUtil;
import org.springblade.core.boot.ctrl.BladeController;
import org.springblade.core.log.exception.ServiceException;
import org.springblade.core.log.logger.BladeLogger;
import org.springblade.core.redis.cache.BladeRedis;
import org.springblade.core.sms.model.SmsCode;
import org.springblade.core.tool.api.R;
import org.springblade.core.tool.utils.StringUtil;
import org.springblade.modules.finance.service.IOrderService;
import org.springblade.modules.platform.wrapper.UserAppWrapper;
import org.springblade.modules.resource.utils.SmsUtil;
import org.springblade.modules.shopping.service.IConsignService;
import org.springblade.modules.system.entity.User;
import org.springblade.modules.system.entity.UserApp;
import org.springblade.modules.system.service.IUserService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.web.bind.annotation.*;

import java.time.Duration;
import java.util.Map;

import static org.springblade.modules.resource.utils.SmsUtil.PARAM_KEY;

/**
 * 控制器
 *
 * @author xuwei
 * @since 2022-02-12
 */
@RestController
@AllArgsConstructor
@RequestMapping(CommonConstant.API_URL + "/test")
@Api(value = "接口测试", tags = "99.接口测试")
public class TestController extends BladeController {
	private static final Logger log = LoggerFactory.getLogger(TestController.class);

	private final IOrderService orderService;
	private final IUserService userService;
	private final IConsignService consignService;
	private final BladeRedis bladeRedis;
	@Autowired
	private BladeLogger logger;

	@GetMapping("/test001")
	@ApiOperationSupport(order = 1)
	@ApiOperation(value = "测试001-生成二维码", notes = "生成二维码")
	public R test001(@RequestParam String name) {
		QrCodeUtil.generate("https://wine.gzzzyd.com/login.html?code=" + name, 300, 300,  FileUtil.file("d:/qrcode.jpg"));
		return R.data(name);
	}

	@GetMapping("/test002")
	@ApiOperationSupport(order = 2)
	@ApiOperation(value = "测试002-获取用户信息", notes = "获取用户信息")
	public R test002(@RequestParam String name) {
		return R.data(getUser());
	}


	@PostMapping("/test003")
	@ApiOperationSupport(order = 3)
	@ApiOperation(value = "测试003-模拟支付成功回调， 待支付变为待发货", notes = "模拟支付成功回调， 待支付变为待发货")
	public R test003(@ApiParam(value = "订单号", required = true) @RequestParam String outOrderNo) {
		//orderService.payCommonSuccess(outOrderNo, "test")
		return R.status(false);
	}

	@PostMapping("/test005")
	@ApiOperationSupport(order = 4)
	@ApiOperation(value = "测试004-待收货变为已完成", notes = "待收货变为已完成")
	public R test005(@ApiParam(value = "订单ID", required = true) @RequestParam Long orderId,
					 @ApiParam(value = "用户id", required = true) @RequestParam(required = false) Long userId) {
		return R.status(orderService.orderEnd(orderId,userId));
	}

	@PostMapping("/test006")
	@ApiOperationSupport(order = 5)
	@ApiOperation(value = "测试006-酒票充值", notes = "传入用户ID")
	public R test006(@ApiParam(value = "用户id", required = true) @RequestParam Long userId,
					 @ApiParam(value = "充值酒票数", required = true) @RequestParam Double ticket) {
		UserApp userApp = new UserApp();
		UserApp query = userApp.selectOne(Wrappers.<UserApp>lambdaQuery().eq(UserApp::getUserId, userId));
		if(query == null){
			return R.fail("用户不存在！");
		}
		userApp.setId(query.getId());
		userApp.setTicket(NumberUtil.add(query.getTicket(), ticket));
		bladeRedis.del(String.valueOf(userId));
		return R.status(userApp.updateById());
	}

	@PostMapping("/test007")
	@ApiOperationSupport(order = 6)
	@ApiOperation(value = "测试007-返回", notes = "返回")
	public R test007(@ApiParam(value = "用户id", required = true) @RequestParam(required = false) Integer type) {
		if (type == 0){
			return R.fail("错误");
		}
		if (type == 1){
			return R.status(true);
		}
		if (type == 2){
			return R.status(false);
		}
		if (type == 3){
			return R.data("获取数据");
		}
		if (type == 4){
			throw new ServiceException("异常");
		}
		for (int i = 0; i < 10; i++) {
			System.out.println(CommonUtil.genTimeID());
			System.out.println(PayKit.getSnowflake(1,1).nextId());
		}
		return R.success("成功");
	}

	@PostMapping("/test008")
	@ApiOperationSupport(order = 6)
	@ApiOperation(value = "测试008-返回", notes = "返回")
	@Transactional(rollbackFor = ServiceException.class)
	public R test008(@ApiParam(value = "用户id", required = true) @RequestParam(required = false) Integer type) {
		throw new ServiceException("异常");
	}

	@PostMapping("/test009")
	@ApiOperationSupport(order = 6)
	@ApiOperation(value = "测试008-日志日志", notes = "返回")
	@Transactional(rollbackFor = ServiceException.class)
	public R test009(@ApiParam(value = "type", required = true) @RequestParam(required = false) Integer type) {
		if(type == 1){
			logger.info("正常", type.toString());
		}else{
			logger.error("正常", type.toString());
		}
		return R.data("测试");
	}

	@PostMapping("/test010")
	@ApiOperationSupport(order = 10)
	@ApiOperation(value = "测试010-聚合验证码", notes = "聚合验证码")
	public R test010(@ApiParam(value = "phone", required = true) @RequestParam(required = false) String phone,
					 @ApiParam(value = "captchaId", required = true) @RequestParam(required = false) String captchaId,
					 @ApiParam(value = "captchaCode", required = true) @RequestParam(required = false) String captchaCode) {
		return R.data(captchaCode(phone, captchaId, captchaCode));
	}

	@PostMapping("/test011")
	@ApiOperationSupport(order = 11)
	@ApiOperation(value = "测试011-聚合发送验证码", notes = "验证码发送")
	public R<SmsCode> test011(@ApiParam(value = "phone", required = true) @RequestParam(required = false) String phone) {
		return R.data(jheSms(phone));
	}


	@PostMapping("/test012")
	@ApiOperationSupport(order = 11)
	@ApiOperation(value = "测试012-获取用户信息", notes = "验证码发送")
	public R<UserApp> test012(@ApiParam(value = "phone", required = true) @RequestParam(required = false) String phone) {
		User user = userService.getOne(Wrappers.<User>lambdaQuery().eq(User::getPhone, phone));
		UserApp userApp = new UserApp();
		UserApp param = userApp.selectOne(Wrappers.<UserApp>lambdaQuery().eq(UserApp::getUserId, user.getId()));
		log.info("userApp === " + param.getEnableAuth());
		return R.data(param);
	}

	@PostMapping("/test013")
	@ApiOperationSupport(order = 13)
	@ApiOperation(value = "测试013-进货扣除积分", notes = "进货扣除积分")
	public R test013(@RequestParam(required = false) String outNo,
					 @RequestParam(required = false) String payCode) {
		//orderService.payCommonSuccess(outNo, payCode);
		return R.success("");
	}

	@PostMapping("/test014")
	@ApiOperationSupport(order = 13)
	@ApiOperation(value = "测试014-积分", notes = "进货扣除积分")
	public R test013(@RequestParam(required = false) Double creditScore) {
		double k = creditScore / 100; //可抢次数
		int scoreCount = NumberUtil.roundDown(k, 2).intValue();
		return R.data(scoreCount);
	}

	@PostMapping("/test015")
	@ApiOperationSupport(order = 13)
	@ApiOperation(value = "测试015-积分", notes = "判断绿色积分")
	public R test015(@RequestParam(required = false) Double ticket,
					 @RequestParam(required = false) Double price) {
		boolean flg = UserAppWrapper.build().isTicket(ticket, price);
		return R.data(flg);
	}


	private SmsCode jheSms(String phone){
		SmsCode smsCode = new SmsCode();
		Map<String, String> params = SmsUtil.getValidateParams();
		String id = StringUtil.randomUUID();
		String key = this.cacheKey(phone, id);
		String val = bladeRedis.get(key);
		log.info(" code === " + params.get(PARAM_KEY));
		if (StringUtil.isBlank(val)){
			bladeRedis.setEx(key, params.get(PARAM_KEY), Duration.ofMinutes(30L));
			smsCode.setId(id);
			smsCode.setValue(params.get(PARAM_KEY));
			smsCode.setSuccess(Boolean.TRUE);
		}else{
			smsCode.setSuccess(Boolean.FALSE);
		}
		return smsCode;
	}

	String cacheKey(String phone, String id) {
		return "blade:sms::captcha:" + phone + ":" + id;
	}

	private boolean captchaCode(String phone, String captchaId, String captchaCode){
		String key = "blade:sms::captcha:" + phone + ":" + captchaId;
		String cache = bladeRedis.get(key);
		if (captchaCode.equals(cache)){
			return true;
		}
		return false;
	}

}
