package com.younike.admin.controller.system.monitor;


import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.younike.common.bean.APIResult;
import com.younike.common.bean.ResultGenerator;
import com.younike.common.core.controller.BaseController;
import com.younike.common.core.page.PageDomain;
import com.younike.common.core.page.PageParam;
import com.younike.common.core.page.TableSupport;
import com.younike.common.quartz.entity.JobEntity;
import com.younike.common.quartz.service.JobService;
import com.younike.common.utils.bean.BeanUtils;
import com.younike.common.utils.string.StringUtils;
import com.younike.service.params.system.QuartzParam;
import com.younike.service.service.ISysQuartzService;

import org.apache.shiro.authz.annotation.RequiresPermissions;
import org.quartz.CronExpression;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.*;

import javax.annotation.Resource;

/**
 * quartz 定时任务Controller
 * 2021-7-27 Another
 */
@RestController
@RequestMapping("/system/quartz")
public class SysQuartzController extends BaseController {

    @Autowired
    private ISysQuartzService sysQuartzService;
    @Resource
    private JobService jobService;


    /**
     * 分页
     * @param quartzParam
     * @return
     */
    @RequiresPermissions("system:quartz:query")
    @GetMapping("/query")
    public Page query(QuartzParam quartzParam) {
        PageDomain pageDomain = TableSupport.buildPageRequest();
        PageParam<QuartzParam> pageParam = new PageParam<>(pageDomain.getPageNum(), pageDomain.getPageSize(), quartzParam);
        return sysQuartzService.getList(pageParam);
    }

    /**
     * 根据 文件全路径 查询
     * @param jobClassName 文件全路径
     * @return
     */
    @RequiresPermissions("system:quartz:see")
    @GetMapping("/findByJobClassName/{jobClassName}")
    public APIResult<QuartzParam> findByJobClassName(@PathVariable String jobClassName) {
        if (StringUtils.isBlank(jobClassName)) {
            return ResultGenerator.getFailResult("请求参数（文件全路径不能为空）");
        }
        return ResultGenerator.getSuccessResult(sysQuartzService.findByJobClassName(jobClassName));
    }

    /**
     * 新增
     * @param quartzParam
     * @return
     */
    @RequiresPermissions("system:quartz:add")
    @PostMapping("/insert")
    public APIResult<Object> insert(@RequestBody QuartzParam quartzParam) {
        if (StringUtils.isBlank(quartzParam.getJobClassName())) {
            return ResultGenerator.getFailResult("文件路径不能为空");
        }
        if (StringUtils.isBlank(quartzParam.getCronExpression())) {
            return ResultGenerator.getFailResult("Cron表达式不能为空");
        }
        if (!CronExpression.isValidExpression(quartzParam.getCronExpression())) {
            return ResultGenerator.getFailResult("Cron表达式格式错误");
        }
        try {
            Class.forName(quartzParam.getJobClassName());
        } catch (ClassNotFoundException e) {
            return ResultGenerator.getFailResult("未找到指定文件，请检查 文件路径 是否填写正确");
        }
        // 验证 用户创建的定时任务是否已存在
        QuartzParam entity = sysQuartzService.findByJobClassName(quartzParam.getJobClassName());
        if (entity != null) {
            return ResultGenerator.getFailResult("定时任务已存在");
        }
        JobEntity jobEntity = new JobEntity(quartzParam.getJobClassName());
        BeanUtils.copyProperties(quartzParam, jobEntity);
        try {
            jobService.createJob(jobEntity);
        } catch (Exception e) {
            e.printStackTrace();
            return ResultGenerator.getFailResult("新增失败");
        }
        return ResultGenerator.getSuccessmsg("新增成功");
    }

    /**
     * 修改
     * @param quartzParam
     * @return
     */
    @RequiresPermissions("system:quartz:add")
    @PutMapping("/update")
    public APIResult<Object> update(@RequestBody QuartzParam quartzParam) {
        if (StringUtils.isBlank(quartzParam.getCronExpression())) {
            return ResultGenerator.getFailResult("Cron表达式不能为空");
        }
        if (!CronExpression.isValidExpression(quartzParam.getCronExpression())) {
            return ResultGenerator.getFailResult("Cron表达式格式错误");
        }
        JobEntity jobEntity = new JobEntity(quartzParam.getJobClassName());
        BeanUtils.copyProperties(quartzParam, jobEntity);
        try {
            jobService.createJob(jobEntity);
        } catch (Exception e) {
            e.printStackTrace();
            return ResultGenerator.getFailResult("修改失败");
        }
        return ResultGenerator.getSuccessmsg("修改成功");
    }

    /**
     * 删除
     * @param jobClassName 文件全路径
     * @return
     */
    @RequiresPermissions("system:quartz:remove")
    @DeleteMapping("/delete/{jobClassName}")
    public APIResult<Object> delete(@PathVariable String jobClassName) {
        JobEntity jobEntity = new JobEntity(jobClassName);
        try {
            jobService.deleteJob(jobEntity);
        } catch (Exception e) {
            e.printStackTrace();
            return ResultGenerator.getFailResult("保存失败");
        }
        return ResultGenerator.getSuccessmsg("保存成功");
    }

    /**
     * 立即 执行一次定时任务
     * @param jobClassName 文件全路径
     * @return
     */
    @PutMapping("/startOnce")
    public APIResult<Object> startOnce(@RequestBody String jobClassName) {
        JobEntity jobEntity = new JobEntity(jobClassName);
        try {
            jobService.startOnce(jobEntity);
        } catch (Exception e) {
            e.printStackTrace();
            return ResultGenerator.getFailResult("执行失败");
        }
        return ResultGenerator.getSuccessmsg("执行成功");
    }

    /**
     * 停止 定时任务
     * @param jobClassName 文件全路径
     * @return
     */
    @PutMapping("/pauseJob")
    public APIResult<Object> pauseJob(@RequestBody String jobClassName) {
        JobEntity jobEntity = new JobEntity(jobClassName);
        try {
            jobService.pauseJob(jobEntity);
        } catch (Exception e) {
            e.printStackTrace();
            return ResultGenerator.getFailResult("停止失败");
        }
        return ResultGenerator.getSuccessmsg("停止成功");
    }

    /**
     * 恢复 定时任务
     * @param jobClassName 文件全路径
     * @return
     */
    @PutMapping("/resumeJob")
    public APIResult<Object> resumeJob(@RequestBody String jobClassName) {
        JobEntity jobEntity = new JobEntity(jobClassName);
        try {
            jobService.resumeJob(jobEntity);
        } catch (Exception e) {
            e.printStackTrace();
            return ResultGenerator.getFailResult("恢复失败");
        }
        return ResultGenerator.getSuccessmsg("恢复成功");
    }

}
