# DbManualHandleDbHfService.java

    package cloud.wconnect.workperformance.service.database.historyforecast;

    import cloud.wconnect.commonlib.cons.BaseConstant;
    import cloud.wconnect.commonlib.cons.BaseErrorCodeEnum;
    import cloud.wconnect.commonlib.cons.CommonErrorI18nConstant;
    import cloud.wconnect.commonlib.cons.CommonFieldI18nConstant;
    import cloud.wconnect.commonlib.exception.BadRequestException;
    import cloud.wconnect.commonlib.pojo.dto.PropertyDTO;
    import cloud.wconnect.commonlib.util.DateTimeUtils;
    import cloud.wconnect.commonlib.util.I18nMessageUtils;
    import cloud.wconnect.commonlib.util.InternationalizationUtils;
    import cloud.wconnect.workperformance.cons.database.DbPmsReportTypeEnum;
    import cloud.wconnect.workperformance.entity.database.DbReportImportLog;
    import cloud.wconnect.workperformance.pojo.dto.database.report.DbImportReportDTO;
    import cloud.wconnect.workperformance.service.database.IDbManualHandleReportService;
    import com.baomidou.dynamic.datasource.annotation.DS;
    import jakarta.annotation.Resource;
    import org.springframework.context.ApplicationContext;
    import org.springframework.stereotype.Component;
    import org.springframework.web.multipart.MultipartFile;

    import java.time.LocalDate;
    import java.util.Collection;

    /**
     * 手动解决 History and Forecast/Service 报告
     *
     * @author zc
     * @date 2026/1/5
     */
    @Component
    @DS("database")
    public class DbManualHandleDbHfService implements IDbManualHandleReportService {

        @Resource
        private ApplicationContext applicationContext;
        @Resource
        private I18nMessageUtils i18nMessageUtils;

        /**
         * 根据判断是否支持此报告类型
         *
         * @param reportType 报告分类
         * @return boolean
         * @author zc
         * @date 2026/1/5
         */
        @Override
        public boolean supports(int reportType) {
            return reportType == DbPmsReportTypeEnum.HISTORY_AND_FORECAST.getType();
        }

        /**
         * 校验文件内容是否合法
         *
         * @param propertyDTO 资产
         * @param file        文件
         * @author zc
         * @date 2026/1/5
         */
        @Override
        public void checkFile(PropertyDTO propertyDTO, String source, MultipartFile file) {
            Collection<IDbPmsHfParseService> parserList =
                    applicationContext.getBeansOfType(IDbPmsHfParseService.class).values();
            for (IDbPmsHfParseService parser : parserList) {
                if (parser.supports(source)) {
                    parser.checkFile(propertyDTO, file);
                    return;
                }
            }
        }

        /**
         * 校验日期参数
         *
         * @param propertyDTO 资产
         * @param reportDTO   报告
         * @author zc
         * @date 2026/1/5
         */
        @Override
        public void checkDate(PropertyDTO propertyDTO, String source, DbImportReportDTO reportDTO) {
            LocalDate startLocalDate = DateTimeUtils.strToLocalDate(reportDTO.getStartDate().toString(),
                    BaseConstant.DATE_FORMAT_YYYYMMDD);
            LocalDate endLocalDate = DateTimeUtils.strToLocalDate(reportDTO.getEndDate().toString(),
                    BaseConstant.DATE_FORMAT_YYYYMMDD);
            LocalDate businessLocalDate = DateTimeUtils.strToLocalDate(reportDTO.getBusinessDate().toString(),
                    BaseConstant.DATE_FORMAT_YYYYMMDD);

            // StartDate 与 EndDate 间隔不超过 367
            if (DateTimeUtils.numberOfDays(startLocalDate, endLocalDate) > 367) {
                throw new BadRequestException(CommonErrorI18nConstant.SELECT_DATE_LIMIT,
                        i18nMessageUtils.getErrorParamMapNotNeedTranslate(367),
                        BaseErrorCodeEnum.DATA_VALIDATION_ERROR.getCode(),
                        "The time span cannot exceed 367 days");
            }

            // EndDate <= BusinessDate + 365
            LocalDate maxEndDate = businessLocalDate.plusDays(365);
            if (endLocalDate.isAfter(maxEndDate)) {
                String maxEndDateStr = InternationalizationUtils.formatLocalDate(maxEndDate,
                        propertyDTO.getInternationalization().getDateTime().getShortDate(),
                        propertyDTO.getLanguage());
                throw new BadRequestException(CommonErrorI18nConstant.CANNOT_GREATER_THAN,
                        i18nMessageUtils.getErrorParamMapNotNeedTranslate(CommonFieldI18nConstant.END_DATE,
                                maxEndDateStr),
                        BaseErrorCodeEnum.DATA_VALIDATION_ERROR.getCode(),
                        "The endDate must be less than " + maxEndDateStr);
            }
        }

        /**
         * 处理数据
         *
         * @param propertyDTO 资产
         * @param file        文件
         * @param operatorId  操作人 id
         * @param source      来源
         * @author zc
         * @date 2026/1/5
         */
        @Override
        public void handleData(PropertyDTO propertyDTO, MultipartFile file, DbReportImportLog importLog, int operatorId, String source) {
            Collection<IDbPmsHfParseService> parserList =
                    applicationContext.getBeansOfType(IDbPmsHfParseService.class).values();
            for (IDbPmsHfParseService parser : parserList) {
                if (parser.supports(source)) {
                    parser.handleData(propertyDTO, file, importLog, operatorId);
                    return;
                }
            }
        }
    }