diff --git a/ruoyi-system-cron/src/main/java/com/ruoyi/cron/api/CronTaskApi.java b/ruoyi-system-cron/src/main/java/com/ruoyi/cron/api/CronTaskApi.java index 16bdc34..6a8bec2 100644 --- a/ruoyi-system-cron/src/main/java/com/ruoyi/cron/api/CronTaskApi.java +++ b/ruoyi-system-cron/src/main/java/com/ruoyi/cron/api/CronTaskApi.java @@ -22,20 +22,26 @@ import com.ruoyi.cron.document.CronTask; import com.ruoyi.cron.document.CronTaskLog; import com.ruoyi.cron.event.CronTaskChangeEvent; import com.ruoyi.cron.event.CronTaskEvent; +import com.ruoyi.cron.event.CronTaskLogEvent; import com.ruoyi.cron.query.CronTaskLogQuery; import com.ruoyi.cron.runner.CronBeanPostProcessor; import com.ruoyi.cron.runner.CronRunner; import com.ruoyi.cron.task.CronTaskTestTask; import com.ruoyi.cron.vo.CronTaskVo; +import lombok.Getter; import lombok.RequiredArgsConstructor; +import org.springframework.context.event.EventListener; import org.springframework.data.mongodb.core.MongoTemplate; +import org.springframework.scheduling.annotation.Async; import org.springframework.validation.annotation.Validated; import org.springframework.web.bind.annotation.*; +import org.springframework.web.servlet.mvc.method.annotation.SseEmitter; import javax.validation.constraints.NotEmpty; import java.util.List; import java.util.TreeSet; +import java.util.concurrent.CopyOnWriteArrayList; import java.util.stream.Collectors; import static com.ruoyi.common.utils.MongoUtil.*; @@ -93,6 +99,62 @@ public class CronTaskApi { return runner.getCurrentLogs().stream().filter(l -> l.getGroupId() == group).collect(Collectors.toList()); } + + private final static List emitters = new CopyOnWriteArrayList<>(); + + public static class MySseEmitter extends SseEmitter { + @Getter + private Integer id; + + public MySseEmitter(long timeout, Integer id) { + super(timeout); + this.id = id; + } + } + + /** + * 订阅某台机器人的信息 + * + * @param id 0:表示订阅所有设备数据,负数表示非机器的订阅 + * @return + */ + @GetMapping("/sse-{id}") + @SaIgnore + public SseEmitter subscribe(@PathVariable Integer id) { + if (id == null) { + id = 0; + } + MySseEmitter emitter = new MySseEmitter(Long.MAX_VALUE, id); + emitters.add(emitter); + emitter.onTimeout(() -> { + emitters.remove(emitter); + }); + emitter.onCompletion(() -> { + emitters.remove(emitter); + }); + emitter.onError(e -> { + emitters.remove(emitter); + }); + return emitter; + } + + @EventListener + @Async + public void listenter(CronTaskLogEvent event) { + List es = ListUtil.list(true); + for (MySseEmitter e : emitters) { + if (!event.getGroupId().equals(e.getId())) { + continue; + } + try { + e.send(event); + } catch (Exception e1) { + es.add(e); + } + } + emitters.removeAll(es); + } + @PostMapping @SaCheckPermission("sys:cron:add") @Log(title = "定时任务", businessType = BusinessType.INSERT) diff --git a/ruoyi-system-cron/src/main/java/com/ruoyi/cron/event/CronTaskLogEvent.java b/ruoyi-system-cron/src/main/java/com/ruoyi/cron/event/CronTaskLogEvent.java new file mode 100644 index 0000000..ff68e7a --- /dev/null +++ b/ruoyi-system-cron/src/main/java/com/ruoyi/cron/event/CronTaskLogEvent.java @@ -0,0 +1,27 @@ +package com.ruoyi.cron.event; + +import lombok.Getter; +import org.springframework.context.ApplicationEvent; + +import java.time.Clock; + +@Getter +public class CronTaskLogEvent extends ApplicationEvent { + + private String taskId; + private Integer groupId; + private String ex; + + + public CronTaskLogEvent(String taskId, Integer groupId, String ex) { + super(groupId); + this.taskId = taskId; + this.groupId = groupId; + this.ex = ex; + } + + @Override + public Integer getSource() { + return (Integer) super.getSource(); + } +} diff --git a/ruoyi-system-cron/src/main/java/com/ruoyi/cron/runner/TaskLogImpl.java b/ruoyi-system-cron/src/main/java/com/ruoyi/cron/runner/TaskLogImpl.java index 404b549..985003b 100644 --- a/ruoyi-system-cron/src/main/java/com/ruoyi/cron/runner/TaskLogImpl.java +++ b/ruoyi-system-cron/src/main/java/com/ruoyi/cron/runner/TaskLogImpl.java @@ -2,8 +2,10 @@ package com.ruoyi.cron.runner; import cn.hutool.core.date.DateUtil; import cn.hutool.core.util.StrUtil; +import com.ruoyi.common.utils.spring.SpringUtils; import com.ruoyi.cron.TaskLog; import com.ruoyi.cron.document.CronTaskLog; +import com.ruoyi.cron.event.CronTaskLogEvent; import org.springframework.stereotype.Component; import java.util.Date; @@ -18,10 +20,12 @@ public class TaskLogImpl implements TaskLog { if (logHolder.get() == null) { return; } + String ex = DateUtil.format(new Date(), "HH:mm:ss.SSS ")+ Thread.currentThread().getName()+ "\t : " + msg; if (StrUtil.isBlank(logHolder.get().getEx())) { - logHolder.get().setEx(DateUtil.format(new Date(), "HH:mm:ss.SSS ")+ Thread.currentThread().getName()+ "\t : " + msg); + logHolder.get().setEx(ex); } else { - logHolder.get().setEx(logHolder.get().getEx() + DateUtil.format(new Date(), "\nHH:mm:ss.SSS ")+ Thread.currentThread().getName()+ "\t : " + msg); + logHolder.get().setEx(logHolder.get().getEx() + "\n" + ex); } + SpringUtils.publishEvent(new CronTaskLogEvent(logHolder.get().getTaskId(),logHolder.get().getGroupId(),ex)); } }