package com.inspect.metadata.mqtt.utils;

import com.inspect.metadata.mqtt.domain.HrNest;
import com.inspect.metadata.mqtt.mapper.HrNestMapper;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import javax.annotation.PostConstruct;
import javax.annotation.PreDestroy;
import java.util.ArrayList;
import java.util.List;
import java.util.concurrent.Executors;
import java.util.concurrent.ScheduledExecutorService;
import java.util.concurrent.TimeUnit;

@Service
public class HrMqttBatchProcessingService {
    private final static Logger log = LoggerFactory.getLogger(HrMqttBatchProcessingService.class);

    @Autowired
    private HrNestMapper hrNestMapper;

    private final List<HrNest> buffer = new ArrayList<>();
    private final Object lock = new Object();

    private int batchSize = 20;

    private long flushInterval = 20;

    @PostConstruct
    public void init() {
        // 启动定时刷新线程
        ScheduledExecutorService scheduler = Executors.newSingleThreadScheduledExecutor();
        scheduler.scheduleAtFixedRate(this::flushBuffer, flushInterval, flushInterval, TimeUnit.SECONDS);
    }

    public void addNest(HrNest nest) {
        synchronized (lock) {
            buffer.add(nest);
            if (buffer.size() >= batchSize) {
                flushBuffer();
            }
        }
    }

    private void flushBuffer() {
        if (buffer.isEmpty()) {
            return;
        }

        List<HrNest> batchToSave;
        synchronized (lock) {
            batchToSave = new ArrayList<>(buffer);
            buffer.clear();
        }

        try {
            int affectedRows = hrNestMapper.batchInsert(batchToSave);
            log.debug("批量插入 {} 条数据，成功 {} 条", batchToSave.size(), affectedRows);
            System.out.println("批量插入" + affectedRows + "条数据");
        } catch (Exception e) {
            log.error("批量插入数据失败，将数据重新放回缓冲区", e);
            // 失败时重新加入缓冲区（可根据业务需求调整重试策略）
            synchronized (lock) {
                buffer.addAll(0, batchToSave);
            }
        }
    }

    @PreDestroy
    public void destroy() {
        // 应用关闭前强制刷新缓冲区
        flushBuffer();
    }
}
