package com.qqchen.deploy.backend.deploy.service.impl;

import com.qqchen.deploy.backend.deploy.converter.JenkinsViewConverter;
import com.qqchen.deploy.backend.deploy.dto.JenkinsSyncHistoryDTO;
import com.qqchen.deploy.backend.deploy.entity.ExternalSystem;
import com.qqchen.deploy.backend.deploy.entity.JenkinsView;
import com.qqchen.deploy.backend.deploy.dto.JenkinsViewDTO;
import com.qqchen.deploy.backend.deploy.enums.ExternalSystemSyncStatus;
import com.qqchen.deploy.backend.deploy.enums.JenkinsSyncType;
import com.qqchen.deploy.backend.deploy.query.JenkinsViewQuery;
import com.qqchen.deploy.backend.deploy.integration.IJenkinsServiceIntegration;
import com.qqchen.deploy.backend.deploy.integration.response.JenkinsViewResponse;
import com.qqchen.deploy.backend.deploy.repository.IExternalSystemRepository;
import com.qqchen.deploy.backend.deploy.repository.IJenkinsSyncHistoryRepository;
import com.qqchen.deploy.backend.deploy.repository.IJenkinsViewRepository;
import com.qqchen.deploy.backend.deploy.service.IJenkinsSyncHistoryService;
import com.qqchen.deploy.backend.deploy.service.IJenkinsViewService;
import com.qqchen.deploy.backend.framework.enums.ResponseCode;
import com.qqchen.deploy.backend.framework.exception.BusinessException;
import com.qqchen.deploy.backend.framework.service.impl.BaseServiceImpl;
import jakarta.annotation.Resource;
import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

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

/**
 * Jenkins视图 Service实现
 */
@Slf4j
@Service
public class JenkinsViewServiceImpl extends BaseServiceImpl<JenkinsView, JenkinsViewDTO, JenkinsViewQuery, Long>
    implements IJenkinsViewService {

    @Resource
    private IExternalSystemRepository externalSystemRepository;

    @Resource
    private IJenkinsViewRepository jenkinsViewRepository;

    @Resource
    private IJenkinsServiceIntegration jenkinsServiceIntegration;

    @Resource
    private JenkinsViewConverter jenkinsViewConverter;

    @Resource
    private IJenkinsSyncHistoryRepository jenkinsSyncHistoryRepository;

    @Resource
    private IJenkinsSyncHistoryService jenkinsSyncHistoryService;

    /**
     * 同步Jenkins视图
     *
     * @param externalSystemId 外部系统ID
     * @return 同步的视图数量
     */
    @Override
    @Transactional(rollbackFor = Exception.class)
    public Integer syncViews(Long externalSystemId) {
        // 1. 创建同步历史记录
        JenkinsSyncHistoryDTO syncHistory = new JenkinsSyncHistoryDTO();
        syncHistory.setExternalSystemId(externalSystemId);
        syncHistory.setSyncType(JenkinsSyncType.VIEW);
        syncHistory.setStatus(ExternalSystemSyncStatus.RUNNING);
        jenkinsSyncHistoryService.saveOrUpdateHistory(syncHistory);

        try {
            // 2. 查询外部系统
            ExternalSystem externalSystem = externalSystemRepository.findById(externalSystemId).orElseThrow(() -> new BusinessException(ResponseCode.EXTERNAL_SYSTEM_NOT_FOUND));

            // 3. 调用Jenkins API获取视图列表
            List<JenkinsViewResponse> viewResponses = jenkinsServiceIntegration.listViews(externalSystem);
            if (viewResponses.isEmpty()) {
                log.info("No views found in Jenkins system: {}", externalSystemId);
                // 更新同步历史为成功
                syncHistory.setStatus(ExternalSystemSyncStatus.SUCCESS);
                jenkinsSyncHistoryService.saveOrUpdateHistory(syncHistory);
                return 0;
            }

            // 4. 转换并保存/更新视图数据
            List<JenkinsView> jenkinsViews = new ArrayList<>();
            for (JenkinsViewResponse viewResponse : viewResponses) {
                // 查找是否存在相同的视图
                Optional<JenkinsView> existingView = jenkinsViewRepository
                    .findByExternalSystemIdAndViewName(externalSystemId, viewResponse.getName());

                JenkinsView jenkinsView;
                if (existingView.isPresent()) {
                    // 更新已存在的视图
                    jenkinsView = existingView.get();
                    updateViewFromResponse(jenkinsView, viewResponse);
                    log.debug("Updating existing Jenkins view: {}", jenkinsView.getViewName());
                } else {
                    // 创建新的视图
                    jenkinsView = new JenkinsView();
                    jenkinsView.setExternalSystemId(externalSystemId);
                    jenkinsView.setViewName(viewResponse.getName());
                    updateViewFromResponse(jenkinsView, viewResponse);
                    log.debug("Creating new Jenkins view: {}", jenkinsView.getViewName());
                }
                jenkinsViews.add(jenkinsView);
            }

            // 5. 批量保存或更新
            jenkinsViewRepository.saveAll(jenkinsViews);
            log.info("Successfully synchronized {} Jenkins views for external system: {}", jenkinsViews.size(), externalSystemId);

            // 6. 更新同步历史为成功
            syncHistory.setStatus(ExternalSystemSyncStatus.SUCCESS);
            jenkinsSyncHistoryService.saveOrUpdateHistory(syncHistory);

            return jenkinsViews.size();
        } catch (Exception e) {
            log.error("Failed to sync Jenkins views for external system: {}", externalSystemId, e);
            syncHistory.setStatus(ExternalSystemSyncStatus.FAILED);
            syncHistory.setErrorMessage(e.getMessage());
            jenkinsSyncHistoryService.saveOrUpdateHistory(syncHistory);
            throw e;
        }
    }

    /**
     * 从API响应更新视图信息
     */
    private void updateViewFromResponse(JenkinsView jenkinsView, JenkinsViewResponse response) {
        jenkinsView.setDescription(response.getDescription());
        jenkinsView.setViewUrl(response.getUrl());
    }

    @Override
    public List<JenkinsViewDTO> findByExternalSystemId(Long externalSystemId) {
        JenkinsViewQuery query = new JenkinsViewQuery();
        query.setExternalSystemId(externalSystemId);
        return super.findAll(query);
    }
}