springboot集成sse

@Slf4j
@RestController
@RequestMapping("/institution/sse")
public class SseController {

    @Autowired
    private SseEmitters emitters;

    @GetMapping(path = "/paging", produces = MediaType.TEXT_EVENT_STREAM_VALUE)
    @PermitAll
    @TenantIgnore
    public SseEmitter subscribe() {
        log.info("前端订阅成功");
        return emitters.add(new SseEmitter());
    }


}
@Slf4j
@Component
public class SseProducer {

   private String SSE_TOPIC="SSE_TOPIC";
    @Autowired
    private RedissonClient redisson;

    public void publish(SseMessage msg) {
        RTopic topic = redisson.getTopic(SSE_TOPIC);
        System.err.println(topic);
        long clientsReceivedMessage = topic.publish(msg);
        log.info("推送sse信息:{}", clientsReceivedMessage);
    }


}
@Slf4j
@Order(1)
@Component
public class SseListener implements ApplicationRunner {

    @Autowired
    private RedissonClient redisson;

    @Autowired
    private SseEmitters emitters;
    private String SSE_TOPIC="SSE_TOPIC";
    @Override
    public void run(ApplicationArguments args) {
        try {
            RTopic topic = redisson.getTopic(SSE_TOPIC);
            topic.addListener(SseMessage.class, (channel, msg) -> {
                log.info("redisson-sse 监听器收到消息channel:{},msg:{}", channel, msg);
                System.err.println("rinima");
                emitters.send(msg);
            });
        } catch (Exception e) {
            log.error("redisson-sse 监听器消息异常", e);
        }
    }
}

@Slf4j
@Component
public class SseEmitters {

    private final List<SseEmitter> emitters = new CopyOnWriteArrayList<>();

    public SseEmitter add(SseEmitter emitter) {
        this.emitters.add(emitter);
        log.info("添加了新的SseEmitter。发射器总数: {}", this.emitters.size());
        emitter.onCompletion(() -> {
            this.emitters.remove(emitter);
            log.info("SseEmitter已完成。剩余发射器: {}", this.emitters.size());
        });
        emitter.onTimeout(() -> {
            emitter.complete();
            this.emitters.remove(emitter);
            log.info("SseEmitter超时。剩余发射器: {}", this.emitters.size());
        });
        return emitter;
    }

    public void send(Object obj) {
        log.info("当前emitters连接数:{}", this.emitters.size());
        List<SseEmitter> failedEmitters = new ArrayList<>();
        this.emitters.forEach(emitter -> {
            try {
                emitter.send(obj);
                log.info("已向发射器发送消息: {}", emitter);
            } catch (Exception e) {
                log.error("向发射器发送消息时出错: {}", emitter, e);
                emitter.completeWithError(e);
                failedEmitters.add(emitter);
            }
        });
        this.emitters.removeAll(failedEmitters);
        log.info("删除了失败的发射器。剩余发射器: {}", this.emitters.size());
    }
}

initSocket() {
      const eventSource = new EventSource(process.env.VUE_APP_BASE_API + '/admin-api/institution/sse/paging');
      console.log("SSE connection initialized");

      eventSource.onmessage = (event) => {
        console.log('Message from server: ', event.data);

        const data = JSON.parse(event.data);

        this.$notify({
          title: '警告',
          customClass: 'fullscreen-notify', // 添加自定义类名
          dangerouslyUseHTMLString: true,
          message: `<strong>${data.msg}</strong>`,
          duration: 0,
          type: 'warning'
        });

        // 在这里更新数据,将对应的卡片标记为收到呼叫
        const receivedCardId = data.id; 
        this.updateCardStatus(receivedCardId);
        // that.$store.dispatch('GET_ALARM', true)
        that.handleSpeak(this.message);
      };

      eventSource.onopen = (event) => {
        console.log('SSE connection opened');
      };

      eventSource.onerror = (error) => {
        console.error('失败SSE error: ', error);

        if (eventSource.readyState === EventSource.CLOSED) {
          console.log('SSE connection was closed. Reconnecting...');
          this.initSocket(); // 重连
        }
      };
    },

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

立志成为好青年

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值