add GaoRegistrationEvent status and valid date range

This commit is contained in:
Timi
2026-08-03 11:41:33 +08:00
parent 7370b2fc98
commit d45bf11477
9 changed files with 100 additions and 23 deletions
+1 -1
View File
@@ -173,7 +173,7 @@
<dependency>
<groupId>com.imyeyu.spring</groupId>
<artifactId>timi-spring</artifactId>
<version>0.0.17</version>
<version>0.0.18</version>
</dependency>
<dependency>
<groupId>com.imyeyu.network</groupId>
@@ -23,6 +23,9 @@ public class GaoRegistrationEvent extends UUIDEntity {
/// @since 2026-08-01
public enum Status {
/// 草稿,未发布不可登记
DRAFT,
/// 可登记
ACTIVE,
@@ -55,8 +58,11 @@ public class GaoRegistrationEvent extends UUIDEntity {
/// 每个自然月一次
NATURAL_MONTH,
/// 累计限 N 次
TOTAL_LIMIT
/// 事件总登记次数上限
TOTAL_LIMIT,
/// 单个客户总登记次数上限
CUSTOMER_TOTAL_LIMIT
}
/// 登记事件名称
@@ -71,9 +77,6 @@ public class GaoRegistrationEvent extends UUIDEntity {
/// 状态
private Status status;
/// true 为启用
private Boolean enabled;
/// true 为登记时要求拍照
private Boolean requirePhoto;
@@ -83,6 +86,12 @@ public class GaoRegistrationEvent extends UUIDEntity {
/// 登记限制数值,按限制类型表示小时数或次数
private Integer limitValue;
/// 可登记起始时间戳,毫秒,空为不限制
private Long beginAt;
/// 可登记终止时间戳,毫秒,空为不限制
private Long endAt;
/// 排序值
private Integer sort;
@@ -3,7 +3,6 @@ package com.imyeyu.api.modules.gao.mapper;
import com.imyeyu.api.modules.gao.entity.GaoRegistrationEvent;
import com.imyeyu.spring.mapper.BaseMapper;
import org.apache.ibatis.annotations.Param;
import org.apache.ibatis.annotations.Select;
import java.util.List;
@@ -16,6 +15,5 @@ public interface GaoRegistrationEventMapper extends BaseMapper<GaoRegistrationEv
List<GaoRegistrationEvent> selectByIdList(@Param("idList") List<String> idList);
@Select("SELECT * FROM `gao_registration_event` WHERE `enabled` = TRUE AND (`status` IS NULL OR `status` = 'ACTIVE') AND `deleted_at` IS NULL ORDER BY `sort` ASC, `created_at` ASC")
List<GaoRegistrationEvent> selectEnabledList();
List<GaoRegistrationEvent> selectEnabledList(@Param("now") Long now);
}
@@ -43,6 +43,12 @@ public interface GaoRegistrationEventRecordMapper extends BaseMapper<GaoRegistra
/// @return 登记数
Long countByCustomerIdAndRegistrationEventId(@Param("customerId") String customerId, @Param("registrationEventId") String registrationEventId);
/// 统计登记事件总登记数
///
/// @param registrationEventId 登记事件 ID
/// @return 登记数
Long countByRegistrationEventId(@Param("registrationEventId") String registrationEventId);
/// 按周期统计登记事件记录
///
/// @param registrationEventId 登记事件 ID
@@ -313,21 +313,22 @@ public class GaoRegistrationEventRecordServiceImplement extends AbstractEntitySe
private void checkRegistrationEventPermission(GaoRegistrationEvent registrationEvent) {
List<String> roleCodeList = registrationEventService.listRoleCode(registrationEvent.getId());
if (roleCodeList != null && !roleCodeList.isEmpty()) {
roleChecker.checkAny(ModuleCode.GAO, roleCodeList.toArray(String[]::new));
}
TimiException.requiredTrue(roleCodeList != null && !roleCodeList.isEmpty(), "登记事件未配置可登记角色");
roleChecker.checkAny(ModuleCode.GAO, roleCodeList.toArray(String[]::new));
}
private void checkRegistrationEventCreatable(GaoRegistrationEvent registrationEvent, String customerId, long registeredAt) {
TimiException.requiredTrue(Boolean.TRUE.equals(registrationEvent.getEnabled()), "登记事件未启用");
TimiException.requiredTrue(registrationEvent.getStatus() == null || registrationEvent.getStatus() == GaoRegistrationEvent.Status.ACTIVE, "登记事件不可登记");
TimiException.requiredTrue(registrationEvent.getBeginAt() == null || registrationEvent.getBeginAt() <= registeredAt, "登记事件未到可登记时间");
TimiException.requiredTrue(registrationEvent.getEndAt() == null || registeredAt <= registrationEvent.getEndAt(), "登记事件已过可登记时间");
GaoRegistrationEvent.LimitType limitType = TimiJava.defaultIfNull(registrationEvent.getLimitType(), GaoRegistrationEvent.LimitType.NONE);
switch (limitType) {
case DAILY_HALF_DAY -> checkRegistrationLimitRange(customerId, registrationEvent.getId(), getHalfDayBegin(registeredAt), getHalfDayEnd(registeredAt), "该客户当前半日已登记该事件");
case NATURAL_DAY -> checkRegistrationLimitRange(customerId, registrationEvent.getId(), getDayBegin(registeredAt), getDayEnd(registeredAt), "该客户当日已登记该事件");
case INTERVAL_HOUR -> checkIntervalHourRegistrationLimit(registrationEvent, customerId, registeredAt);
case NATURAL_MONTH -> checkRegistrationLimitRange(customerId, registrationEvent.getId(), getMonthBegin(registeredAt), getMonthEnd(registeredAt), "该客户当月已登记该事件");
case TOTAL_LIMIT -> checkTotalRegistrationLimit(registrationEvent, customerId);
case TOTAL_LIMIT -> checkTotalRegistrationLimit(registrationEvent);
case CUSTOMER_TOTAL_LIMIT -> checkCustomerTotalRegistrationLimit(registrationEvent, customerId);
default -> {
}
}
@@ -345,13 +346,20 @@ public class GaoRegistrationEventRecordServiceImplement extends AbstractEntitySe
checkRegistrationLimitRange(customerId, registrationEvent.getId(), beginRegisteredAt, registeredAt, "该客户登记该事件间隔不足");
}
private void checkTotalRegistrationLimit(GaoRegistrationEvent registrationEvent, String customerId) {
private void checkCustomerTotalRegistrationLimit(GaoRegistrationEvent registrationEvent, String customerId) {
Integer limitValue = registrationEvent.getLimitValue();
TimiException.requiredTrue(limitValue != null && 0 < limitValue, "登记事件累计次数配置错误");
TimiException.requiredTrue(limitValue != null && 0 < limitValue, "登记事件单客户总次数配置错误");
Long count = mapper.countByCustomerIdAndRegistrationEventId(customerId, registrationEvent.getId());
TimiException.requiredTrue(TimiJava.defaultIfNull(count, 0L) < limitValue, "该客户登记该事件次数已达上限");
}
private void checkTotalRegistrationLimit(GaoRegistrationEvent registrationEvent) {
Integer limitValue = registrationEvent.getLimitValue();
TimiException.requiredTrue(limitValue != null && 0 < limitValue, "登记事件总次数配置错误");
Long count = mapper.countByRegistrationEventId(registrationEvent.getId());
TimiException.requiredTrue(TimiJava.defaultIfNull(count, 0L) < limitValue, "登记事件总次数已达上限");
}
private long getDayBegin(long registeredAt) {
ZoneId zoneId = ZoneId.systemDefault();
return Instant.ofEpochMilli(registeredAt).atZone(zoneId).toLocalDate().atStartOfDay(zoneId).toInstant().toEpochMilli();
@@ -6,11 +6,13 @@ import com.imyeyu.api.modules.gao.entity.GaoRegistrationEvent;
import com.imyeyu.api.modules.gao.mapper.GaoRegistrationEventRoleRelationMapper;
import com.imyeyu.api.modules.gao.mapper.GaoRegistrationEventMapper;
import com.imyeyu.api.modules.gao.service.GaoRegistrationEventService;
import com.imyeyu.java.TimiJava;
import com.imyeyu.java.bean.timi.TimiException;
import com.imyeyu.spring.bean.Page;
import com.imyeyu.spring.bean.PageResult;
import com.imyeyu.spring.mapper.BaseMapper;
import com.imyeyu.spring.service.AbstractEntityService;
import com.imyeyu.utils.Time;
import lombok.RequiredArgsConstructor;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
@@ -61,7 +63,18 @@ public class GaoRegistrationEventServiceImplement extends AbstractEntityService<
@Override
public void update(GaoRegistrationEvent entity) {
checkEntity(entity, true);
super.update(entity);
GaoRegistrationEvent current = get(entity.getId());
current.setName(entity.getName());
current.setDescription(entity.getDescription());
current.setColor(entity.getColor());
current.setStatus(entity.getStatus());
current.setRequirePhoto(entity.getRequirePhoto());
current.setLimitType(entity.getLimitType());
current.setLimitValue(entity.getLimitValue());
current.setBeginAt(entity.getBeginAt());
current.setEndAt(entity.getEndAt());
current.setSort(entity.getSort());
mapper.update(current);
saveRoleRelation(entity.getId(), entity.getRoleCodeList());
}
@@ -70,7 +83,6 @@ public class GaoRegistrationEventServiceImplement extends AbstractEntityService<
public void delete(String id) {
GaoRegistrationEvent entity = get(id);
entity.setStatus(GaoRegistrationEvent.Status.DELETED);
entity.setEnabled(false);
super.update(entity);
}
@@ -83,8 +95,11 @@ public class GaoRegistrationEventServiceImplement extends AbstractEntityService<
@Override
public List<GaoRegistrationEvent> listEnabled() {
List<GaoRegistrationEvent> list = mapper.selectEnabledList();
List<GaoRegistrationEvent> list = mapper.selectEnabledList(Time.now());
loadRegistrationEventLimit(list);
list = list.stream()
.filter(item -> !TimiJava.isEmpty(item.getRoleCodeList()))
.toList();
return list;
}
@@ -102,16 +117,18 @@ public class GaoRegistrationEventServiceImplement extends AbstractEntityService<
if (entity.getStatus() == null) {
entity.setStatus(GaoRegistrationEvent.Status.ACTIVE);
}
if (entity.getEnabled() == null) {
entity.setEnabled(true);
}
if (entity.getRequirePhoto() == null) {
entity.setRequirePhoto(false);
}
if (entity.getLimitType() == null) {
entity.setLimitType(GaoRegistrationEvent.LimitType.NONE);
}
TimiException.requiredTrue(
entity.getRoleCodeList() != null && entity.getRoleCodeList().stream().anyMatch(item -> item != null && !item.isBlank()),
"not found registrationEvent.roleCodeList"
);
checkRegistrationLimit(entity);
checkRegisterablePeriod(entity);
if (entity.getColor() != null) {
entity.setColor(entity.getColor().trim());
}
@@ -122,7 +139,8 @@ public class GaoRegistrationEventServiceImplement extends AbstractEntityService<
private void checkRegistrationLimit(GaoRegistrationEvent entity) {
if (entity.getLimitType() == GaoRegistrationEvent.LimitType.INTERVAL_HOUR
|| entity.getLimitType() == GaoRegistrationEvent.LimitType.TOTAL_LIMIT) {
|| entity.getLimitType() == GaoRegistrationEvent.LimitType.TOTAL_LIMIT
|| entity.getLimitType() == GaoRegistrationEvent.LimitType.CUSTOMER_TOTAL_LIMIT) {
TimiException.required(entity.getLimitValue(), "not found registrationEvent.limitValue");
TimiException.requiredTrue(0 < entity.getLimitValue(), "registrationEvent.limitValue lte 0");
return;
@@ -130,6 +148,16 @@ public class GaoRegistrationEventServiceImplement extends AbstractEntityService<
entity.setLimitValue(null);
}
private void checkRegisterablePeriod(GaoRegistrationEvent entity) {
if (entity.getBeginAt() == null && entity.getEndAt() == null) {
return;
}
TimiException.requiredTrue(
entity.getBeginAt() == null || entity.getEndAt() == null || entity.getBeginAt() <= entity.getEndAt(),
"registrationEvent.beginAt gt registrationEvent.endAt"
);
}
private void saveRoleRelation(String registrationEventId, List<String> roleCodeList) {
roleRelationMapper.deleteByRegistrationEventId(registrationEventId);
if (roleCodeList == null || roleCodeList.isEmpty()) {
@@ -0,0 +1,7 @@
ALTER TABLE `gao_registration_event`
DROP KEY `idx_gao_registration_event_status`,
DROP COLUMN `enabled`,
MODIFY COLUMN `status` VARCHAR(32) NOT NULL DEFAULT 'ACTIVE' COMMENT '状态,DRAFT 草稿,ACTIVE 可登记,INACTIVE 不可登记,DELETED 已删除',
ADD COLUMN `begin_at` BIGINT NULL COMMENT '可登记起始时间戳,毫秒,空为不限制' AFTER `limit_value`,
ADD COLUMN `end_at` BIGINT NULL COMMENT '可登记终止时间戳,毫秒,空为不限制' AFTER `begin_at`,
ADD KEY `idx_gao_registration_event_status` (`status`, `deleted_at`, `sort`, `created_at`);
@@ -18,4 +18,16 @@
</if>
AND `deleted_at` IS NULL
</select>
<select id="selectEnabledList" resultType="com.imyeyu.api.modules.gao.entity.GaoRegistrationEvent">
SELECT
*
FROM `gao_registration_event`
WHERE
(`status` IS NULL OR `status` = 'ACTIVE')
AND (`begin_at` IS NULL OR `begin_at` &lt;= #{now})
AND (`end_at` IS NULL OR #{now} &lt;= `end_at`)
AND `deleted_at` IS NULL
ORDER BY `sort` ASC, `created_at` ASC
</select>
</mapper>
@@ -42,6 +42,15 @@
AND `deleted_at` IS NULL
</select>
<select id="countByRegistrationEventId" resultType="java.lang.Long">
SELECT
COUNT(1)
FROM `gao_registration_event_record`
WHERE
`registration_event_id` = #{registrationEventId}
AND `deleted_at` IS NULL
</select>
<select id="statByRegistrationEventAndPeriodType" resultType="com.imyeyu.api.modules.gao.vo.GaoRegistrationEventPeriodStatView">
SELECT
`registration_event_id` AS `registrationEventId`,