# HolidayController.java

    package cloud.wconnect.rateshop.controller.rateshop;

    import cloud.wconnect.commonlib.annotation.ApiId;
    import cloud.wconnect.commonlib.component.SessionContext;
    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.exception.ForbiddenException;
    import cloud.wconnect.commonlib.pojo.dto.PropertyDTO;
    import cloud.wconnect.commonlib.redis.PropertyI18nRedisService;
    import cloud.wconnect.commonlib.util.DateTimeUtils;
    import cloud.wconnect.commonlib.util.I18nMessageUtils;
    import cloud.wconnect.commonlib.util.UpdateLogUtil;
    import cloud.wconnect.commonlib.util.UploadUtils;
    import cloud.wconnect.rateshop.entity.rateshop.Holiday;
    import cloud.wconnect.rateshop.pojo.dto.rateshop.holiday.HolidayDTO;
    import cloud.wconnect.rateshop.pojo.query.rateshop.HolidayQuery;
    import cloud.wconnect.rateshop.pojo.vo.rateshop.holiday.CalendarHolidayVO;
    import cloud.wconnect.rateshop.service.rateshop.IHolidayService;
    import com.google.common.collect.Lists;
    import org.springframework.beans.factory.annotation.Autowired;
    import org.springframework.beans.factory.annotation.Value;
    import org.springframework.web.bind.annotation.*;
    import org.springframework.web.multipart.MultipartFile;

    import jakarta.validation.Valid;

    import java.util.Collections;
    import java.util.List;
    import java.util.Map;
    import java.util.Objects;

    /**
     * 节假日控制层
     *
     * @author lichen
     * @date 2023/6/13
     */
    @RestController
    @RequestMapping("/rate-shop/holiday")
    public class HolidayController {

        @Autowired
        private IHolidayService holidayService;
        @Autowired
        private SessionContext sessionContext;
        @Autowired
        private UpdateLogUtil updateLogUtil;
        @Value("${file-max-size.rate-shop}")
        private long fileMaxSize;
        @Autowired
        private PropertyI18nRedisService propertyI18nRedisService;
        @Autowired
        private I18nMessageUtils i18nMessageUtils;

        /**
         * 查询假期信息
         *
         * @param property     资产标识
         * @param holidayQuery 假期查询对象
         * @return void
         * @author lichen
         * @date 2023/6/19
         */
        @ApiId(345)
        @GetMapping
        public List<CalendarHolidayVO> list(String property, @Valid HolidayQuery holidayQuery) {
            int propertyId = sessionContext.getPropertyId(property);
            PropertyDTO propertyDTO = propertyI18nRedisService.get(propertyId);
            //把yyyy-MM-dd的日期转化成时间戳
            long fromTimestamp = DateTimeUtils.dateStrToEpochSecond(holidayQuery.getFromDate(), BaseConstant.DATE_FORMAT_YYYY_MM_DD, propertyDTO.getTimezone());
            long toTimestamp = DateTimeUtils.dateStrToEpochSecond(holidayQuery.getToDate(), BaseConstant.DATE_FORMAT_YYYY_MM_DD, propertyDTO.getTimezone());
            //开始时间不能大于结束时间
            if (fromTimestamp > toTimestamp) {
                throw new BadRequestException(CommonErrorI18nConstant.START_DATE_CANNOT_GREATER_THAN_END_DATE,
                        BaseErrorCodeEnum.DATA_VALIDATION_ERROR.getCode(), "The toDate must be greater than or equal to the fromDate");
            }
            //判断时间间隔必须小于70天
            long diffDay = DateTimeUtils.dateDiffOfDays(fromTimestamp, toTimestamp, propertyDTO.getTimezone());
            if (Math.abs(diffDay) > 70) {
                throw new BadRequestException(CommonErrorI18nConstant.SELECT_DATE_LIMIT,
                        i18nMessageUtils.getErrorParamMapNotNeedTranslate(70),
                        BaseErrorCodeEnum.DATA_VALIDATION_ERROR.getCode(), "The interval between fromDate and toDate must be less than or equal to 70 days");
            }
            //查询节假日信息
            return holidayService.list(propertyDTO, holidayQuery.getFromDate(), holidayQuery.getToDate());
        }

        /**
         * 新增节假日
         *
         * @param property   资产标识
         * @param holidayDTO 节假日对象
         * @return java.util.Map
         * @author lichen
         * @date 2023/6/19
         */
        @ApiId(346)
        @PostMapping
        public Map save(String property, @Valid @RequestBody HolidayDTO holidayDTO) {
            int propertyId = sessionContext.getPropertyId(property);
            PropertyDTO propertyDTO = propertyI18nRedisService.get(propertyId);
            int loginUserId = sessionContext.getLoginUserId();
            //设置资产id
            holidayDTO.setPropertyId(propertyId);
            //设置updateLog日志信息
            holidayDTO.setUpdateLog(updateLogUtil.get(loginUserId));
            //新增节假日
            return holidayService.saveOrUpdate(propertyDTO, holidayDTO);
        }

        /**
         * 修改节假日
         *
         * @param id         节假日id
         * @param property   资产标识
         * @param holidayDTO 节假日对象
         * @return java.util.Map
         * @author lichen
         * @date 2023/6/19
         */
        @ApiId(347)
        @PutMapping("/{id:\\d+}")
        public Map update(@PathVariable Integer id, String property,
                          @Valid @RequestBody HolidayDTO holidayDTO) {
            int propertyId = sessionContext.getPropertyId(property);
            PropertyDTO propertyDTO = propertyI18nRedisService.get(propertyId);
            int loginUserId = sessionContext.getLoginUserId();
            //校验节假日是否存在且是否手动创建
            Holiday holiday = holidayService.checkExistAndIsManualCreate(id);
            //校验节假日是否属于当前资产
            checkBelong(propertyId, holiday);
            //设置资产id
            holidayDTO.setPropertyId(propertyId);
            //设置节假日id
            holidayDTO.setId(id);
            //设置updateLog日志信息
            holidayDTO.setUpdateLog(updateLogUtil.append(holiday.getUpdateLog(), loginUserId));
            //修改节假日
            return holidayService.saveOrUpdate(propertyDTO, holidayDTO);
        }

        /**
         * 删除节假日数据
         *
         * @param id       节假日数据id
         * @param property 资产标识
         * @return void
         * @author lichen
         * @date 2023/6/19
         */
        @ApiId(348)
        @DeleteMapping("/{id:\\d+}")
        public Map delete(@PathVariable Integer id, String property) {
            int propertyId = sessionContext.getPropertyId(property);
            //校验节假日是否存在且是否手动创建
            Holiday holiday = holidayService.checkExistAndIsManualCreate(id);
            //校验节假日是否属于当前资产
            checkBelong(propertyId, holiday);
            //删除节假日
            holidayService.removeById(id);
            return Collections.emptyMap();
        }

        /**
         * 导入假期
         *
         * @param property 资产标识
         * @param file     excel文件
         * @return java.util.Map
         * @author lichen
         * @date 2023/12/20
         */
        @ApiId(1014)
        @PostMapping("/import")
        public Map importExcel(String property, MultipartFile file) {
            if (Objects.isNull(file)) {
                throw new BadRequestException(CommonErrorI18nConstant.CANNOT_EMPTY,
                        i18nMessageUtils.getErrorParamMapNeedTranslate(CommonFieldI18nConstant.FILE),
                        BaseErrorCodeEnum.DATA_VALIDATION_ERROR.getCode(), "The file cannot be null");
            }
            //校验文件
            UploadUtils.checkFileFormat(file, Lists.newArrayList("xls", "xlsx"));
            //校验文件大小
            if (file.getSize() > fileMaxSize) {
                throw new BadRequestException(CommonErrorI18nConstant.FILE_SIZE_ERROR,
                        BaseErrorCodeEnum.DATA_VALIDATION_ERROR.getCode(), "The fileSize max is 20 MB");
            }
            int propertyId = sessionContext.getPropertyId(property);
            PropertyDTO propertyDTO = propertyI18nRedisService.get(propertyId);
            int loginUserId = sessionContext.getLoginUserId();
            //导入
            holidayService.importExcel(propertyDTO, file, loginUserId);
            return Collections.emptyMap();
        }

        /**
         * 校验节假日是否属于当前资产
         *
         * @param propertyId 资产id
         * @param holiday    节假日对象
         * @return void
         * @author lichen
         * @date 2023/6/19
         */
        private void checkBelong(Integer propertyId, Holiday holiday) {
            if (!propertyId.equals(holiday.getPropertyId())) {
                throw new ForbiddenException(BaseErrorCodeEnum.DATA_FORBIDDEN.getI18nCode(),
                        BaseErrorCodeEnum.DATA_FORBIDDEN.getCode(),
                        "The holiday must belong to the current propertyId, current propertyId = "
                                + propertyId + ", holiday propertyId = " + holiday.getPropertyId());
            }
        }

    }