package com.sqx.modules.job.service.impl;

import cn.hutool.core.map.MapProxy;
import cn.hutool.core.util.StrUtil;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.github.pagehelper.PageHelper;
import com.github.pagehelper.PageInfo;
import com.sqx.common.utils.Constant;
import com.sqx.common.utils.PageUtils;
import com.sqx.modules.job.dao.ScheduleJobDao;
import com.sqx.modules.job.entity.ScheduleJobEntity;
import com.sqx.modules.job.service.ScheduleJobService;
import org.apache.commons.lang.StringUtils;
import org.springframework.context.ApplicationContext;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.lang.reflect.Method;
import java.util.*;

@Service("scheduleJobService")
public class ScheduleJobServiceImpl extends ServiceImpl<ScheduleJobDao, ScheduleJobEntity> implements ScheduleJobService {

	private final ApplicationContext applicationContext;

    public ScheduleJobServiceImpl(ApplicationContext applicationContext) {
        this.applicationContext = applicationContext;
    }

    /**
	 * 项目启动时，初始化定时器
	 */


	@Override
	public PageUtils queryPage(Map<String, Object> params) {
		String beanName = (String)params.get("beanName");

		MapProxy proxy = MapProxy.create(params);
		long pageNum = proxy.getLong(Constant.PAGE, 1L);
		long pageSize = proxy.getLong(Constant.LIMIT, 10L);
		PageHelper.startPage((int) pageNum, (int) pageSize);
		return PageUtils.page(new PageInfo<>(this.list(new QueryWrapper <ScheduleJobEntity>().like(StringUtils.isNotBlank(beanName),"bean_name", beanName))));
	}


	@Override
	@Transactional(rollbackFor = Exception.class)
	public void saveJob(ScheduleJobEntity scheduleJob) {
		scheduleJob.setCreateTime(new Date());
		scheduleJob.setStatus(Constant.ScheduleStatus.NORMAL.getValue());
        this.save(scheduleJob);
    }

	@Override
	@Transactional(rollbackFor = Exception.class)
	public void update(ScheduleJobEntity scheduleJob) {

        this.updateById(scheduleJob);
    }

	@Override
	@Transactional(rollbackFor = Exception.class)
    public void deleteBatch(Long[] jobIds) {
    	//删除数据
    	this.removeByIds(Arrays.asList(jobIds));
	}

	@Override
    public int updateBatch(Long[] jobIds, int status){
    	Map<String, Object> map = new HashMap<>(2);
    	map.put("list", jobIds);
    	map.put("status", status);
    	return baseMapper.updateBatch(map);
    }


	@Override
	public Object run(Long[] jobIds) throws Exception {
		ArrayList<Object> result = new ArrayList<>();
		for(Long jobId : jobIds){
			ScheduleJobEntity jobEntity = baseMapper.selectById(jobId);
			if (jobEntity == null) {
				throw new RuntimeException("任务不存在");
			}

			// 从Spring容器获取类的实例
			Object classInstance = applicationContext.getBean(StrUtil.lowerFirst(jobEntity.getBeanName()));
			if (!"com.sqx.modules.job.task".equals(classInstance.getClass().getPackage().getName())) {
				throw new RuntimeException("非法调用");
			}

//		if (jobDTO.getArgs() != null && !jobDTO.getArgs().isEmpty()) {
//			Class<?>[] argTypes = new Class<?>[jobDTO.getArgs().size()];
//			for (int i = 0; i < jobDTO.getArgs().size(); i++) {
//				argTypes[i] = jobDTO.getArgs().get(i).getClass();
//			}
//			// 获取指定的Method对象
//			Method method = classInstance.getClass().getDeclaredMethod(jobDTO.getMethodName(), argTypes);
//
//			// 调用方法并返回结果
//            return method.invoke(classInstance, jobDTO.getArgs().toArray());
//		}
			// 获取指定的Method对象
			Method method = classInstance.getClass().getDeclaredMethod("run", String.class);

			// 调用方法并返回结果
			Object invoke = method.invoke(classInstance, jobEntity.getParams());
			if (invoke  != null) {
				result.add(invoke);
			}
		}

		return result;
	}

	//	@Override
//	@Transactional(rollbackFor = Exception.class)
//    public void run(Long[] jobIds) {
//    	for(Long jobId : jobIds){
//    		ScheduleUtils.run(scheduler, this.getById(jobId));
//    	}
//    }
//
//	@Override
//	@Transactional(rollbackFor = Exception.class)
//    public void pause(Long[] jobIds) {
//        for(Long jobId : jobIds){
//    		ScheduleUtils.pauseJob(scheduler, jobId);
//    	}
//
//    	updateBatch(jobIds, Constant.ScheduleStatus.PAUSE.getValue());
//    }
//
//	@Override
//	@Transactional(rollbackFor = Exception.class)
//    public void resume(Long[] jobIds) {
//    	for(Long jobId : jobIds){
//    		ScheduleUtils.resumeJob(scheduler, jobId);
//    	}
//
//    	updateBatch(jobIds, Constant.ScheduleStatus.NORMAL.getValue());
//    }

}
