package com.sz.admin.monitor.service.impl;

import com.mybatisflex.core.query.QueryWrapper;
import com.sz.admin.monitor.mapper.CameraMapper;
import com.sz.admin.monitor.mapper.NvrMapper;
import com.sz.admin.monitor.mapper.RegionMapper;
import com.sz.admin.monitor.mapper.SubstationMapper;

import com.sz.admin.monitor.pojo.po.Camera;
import com.sz.admin.monitor.pojo.po.Nvr;
import com.sz.admin.monitor.pojo.po.Region;
import com.sz.admin.monitor.pojo.po.Substation;
import com.sz.admin.monitor.pojo.vo.tree.CameraNodeVO;
import com.sz.admin.monitor.pojo.vo.tree.NvrNodeVO;
import com.sz.admin.monitor.pojo.vo.tree.TreeNodeVO;
import com.sz.admin.monitor.service.TreeService;
import jakarta.annotation.Resource;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.stereotype.Service;

import java.util.ArrayList;
import java.util.List;

/**
 * ClassName: TreeServiceImpl
 * Package: com.sz.admin.monitor.service.impl
 * Description:
 */
@Service
public class TreeServiceImpl implements TreeService {
    private static final Logger log = LoggerFactory.getLogger(TreeServiceImpl.class);
    @Resource
    private RegionMapper regionMapper;
    @Resource
    private SubstationMapper substationMapper;
    @Resource
    private NvrMapper nvrMapper;
    @Resource
    private CameraMapper cameraMapper;

    @Override
    public List<TreeNodeVO> buildTree() {
        QueryWrapper rootRegionWrapper = new QueryWrapper();
        rootRegionWrapper.eq("parent_id", 0);
        List<Region> rootRegions = regionMapper.selectListByQuery(rootRegionWrapper);
        List<TreeNodeVO> treeRoots = new ArrayList<>();
        for (Region rootRegion : rootRegions) {
            TreeNodeVO rootNode = new TreeNodeVO(rootRegion.getId(), rootRegion.getName(), 0, null);
            List<TreeNodeVO> childrenOfRoot = loadChildrenForRegion(rootRegion.getId());
            rootNode.setChildren(childrenOfRoot);
            treeRoots.add(rootNode);
        }
        return treeRoots;
    }

    @Override
    public List<TreeNodeVO> buildTreePreview() {
        // 查询出所有的边电站
        List<Substation> substationList = substationMapper.selectAll();
        List<TreeNodeVO> treeRootList = new ArrayList<>();
        for (Substation substation : substationList) {
            TreeNodeVO rootNode = new TreeNodeVO(substation.getId(), substation.getName(), 1, null);
            List<TreeNodeVO> nvrChildren = loadChildrenForNvrByPreview(substation.getId());
            rootNode.setChildren(nvrChildren);
            treeRootList.add(rootNode);
        }
        return treeRootList;
    }

    private List<TreeNodeVO> loadChildrenForRegion(Long id) {
        QueryWrapper childRegionQuery  = new QueryWrapper();
        childRegionQuery.eq("parent_id", id);
        List<Region> childRegions  = regionMapper.selectListByQuery(childRegionQuery);
        List<TreeNodeVO> children  = new ArrayList<>();
        for (Region childRegion : childRegions) {
            TreeNodeVO childRegionNode  = new TreeNodeVO(childRegion.getId(), childRegion.getName(), 0, null);
            List<TreeNodeVO> substationChildren  = loadChildrenForSubstation(childRegion.getId());
            childRegionNode.setChildren(substationChildren );
            children.add(childRegionNode);
        }
        QueryWrapper specialSubstationQuery = new QueryWrapper();
        specialSubstationQuery.eq("region_id", id).eq("type", 2); // Assuming type 2 is 超高压
        List<Substation> specialSubstations = substationMapper.selectListByQuery(specialSubstationQuery);

        for (Substation specialSubstation : specialSubstations) {
            TreeNodeVO specialSubstationNode = new TreeNodeVO(specialSubstation.getId(), specialSubstation.getName(), 1, null);
            List<TreeNodeVO> nvrChildren = loadChildrenForNvr(specialSubstation.getId());
            specialSubstationNode.setChildren(nvrChildren);
            children.add(specialSubstationNode);
        }
        return children;
    }
    private List<TreeNodeVO> loadChildrenForSubstation(Long id) {
        QueryWrapper substationQuery = new QueryWrapper();
        substationQuery.eq("region_id", id);
        List<Substation> substations = substationMapper.selectListByQuery(substationQuery);
        List<TreeNodeVO> children = new ArrayList<>();
        for (Substation substation : substations) {
            TreeNodeVO substationNode = new TreeNodeVO(substation.getId(), substation.getName(), 1, null);
            List<TreeNodeVO> nvrChildren = loadChildrenForNvr(substation.getId());
            substationNode.setChildren(nvrChildren);
            children.add(substationNode);
        }
        return children;
    }

    private List<TreeNodeVO> loadChildrenForNvrByPreview(Long id) {
        QueryWrapper nvrQuery = new QueryWrapper();
        nvrQuery.eq("station_id", id);
        List<Nvr> nvrList = nvrMapper.selectListByQuery(nvrQuery);
        List<TreeNodeVO> children = new ArrayList<>();
        for (Nvr nvr : nvrList) {
            NvrNodeVO nvrNode = new NvrNodeVO(nvr.getId(),
                    nvr.getName(),
                    nvr.getIp(),
                    nvr.getPort(),
                    nvr.getDriver(),
                    nvr.getStatus());
            List<TreeNodeVO> cameraChildren = loadChildrenForCamera(nvr.getId());
            nvrNode.setChildren(cameraChildren);
            children.add(nvrNode);
        }
        return children;
    }
    private List<TreeNodeVO> loadChildrenForNvr(Long id) {
        QueryWrapper nvrQuery = new QueryWrapper();
        nvrQuery.eq("station_id", id);
        List<Nvr> nvrList = nvrMapper.selectListByQuery(nvrQuery);
        List<TreeNodeVO> children = new ArrayList<>();
        for (Nvr nvr : nvrList) {
            NvrNodeVO nvrNode = new NvrNodeVO(nvr.getId(),
                nvr.getName(),
                nvr.getIp(),
                nvr.getPort(),
                nvr.getDriver(),
                nvr.getStatus());
            children.add(nvrNode);
        }
        return children;
    }

    private List<TreeNodeVO> loadChildrenForCamera(Long nvrId) {
        QueryWrapper wrapper = QueryWrapper.create()
                .select()
                .from(Camera.class)
                .eq(Camera::getNvrId, nvrId);
        List<Camera> cameraList = cameraMapper.selectListByQuery(wrapper);
        List<TreeNodeVO> children = new ArrayList<>();
        for (Camera camera : cameraList) {
            CameraNodeVO cameraNodeVO = new CameraNodeVO();
            cameraNodeVO.setStatus(camera.getStatus());
            cameraNodeVO.setId(camera.getId());
            cameraNodeVO.setName(camera.getName());
            cameraNodeVO.setType(3);
            children.add(cameraNodeVO);
        }
        return children;
    }
}
