package com.njzscloud.common.sichen.util;

import com.njzscloud.common.core.thread.DefaultThreadFactory;
import lombok.extern.slf4j.Slf4j;

import java.util.concurrent.Executors;
import java.util.concurrent.ScheduledExecutorService;
import java.util.concurrent.ScheduledFuture;
import java.util.concurrent.TimeUnit;

@Slf4j
public class TimerUtil {
    private static ScheduledExecutorService scheduler;

    public static void init(boolean virtual, String poolName, int corePoolSize) {
        scheduler = Executors.newScheduledThreadPool(virtual ? 0 : corePoolSize, new DefaultThreadFactory(virtual, poolName));
        log.info("定时器初始化成功");
    }

    public static void shutdown() {
        if (scheduler != null) {
            scheduler.shutdown();
            scheduler = null;
        }
        log.info("定时器已关闭");
    }

    /**
     * 提交周期任务
     *
     * @param period 周期（毫秒，以任务开始时间为准）
     * @param task   任务
     */
    public static ScheduledFuture<?> setInterval(long period, Runnable task) {
        return setInterval(true, 0, period, task);
    }

    /**
     * 提交周期任务
     *
     * @param delay  延迟（毫秒，首次执行）
     * @param period 周期（毫秒，以任务开始时间为准）
     * @param task   任务
     */
    public static ScheduledFuture<?> setInterval(long delay, long period, Runnable task) {
        return setInterval(true, delay, period, task);
    }

    /**
     * 提交周期任务
     *
     * @param absolute 绝对周期，false-->以任务结束时间为准、true-->以任务开始时间为准
     * @param period   周期（毫秒）
     * @param task     任务
     */
    public static ScheduledFuture<?> setInterval(boolean absolute, long period, Runnable task) {
        return setInterval(absolute, 0, period, task);
    }

    /**
     * 提交周期任务
     *
     * @param absolute 绝对周期，false-->以任务结束时间为准、true-->以任务开始时间为准
     * @param delay    延迟（毫秒，首次执行）
     * @param period   周期（毫秒）
     * @param task     任务
     */
    public static ScheduledFuture<?> setInterval(boolean absolute, long delay, long period, Runnable task) {
        if (absolute) {
            return scheduler.scheduleAtFixedRate(task, delay, period, TimeUnit.MILLISECONDS);
        } else {
            return scheduler.scheduleWithFixedDelay(task, delay, period, TimeUnit.MILLISECONDS);
        }
    }

    /**
     * 提交延迟任务
     *
     * @param delay 延迟（毫秒）
     * @param task  任务
     */
    public static ScheduledFuture<?> setTimeout(long delay, Runnable task) {
        return scheduler.schedule(task, delay, TimeUnit.MILLISECONDS);
    }
}
