Store Service — Phase 4
Что сделано
StoreServiceApplication.java
Добавлен @EnableScheduling — без него @Scheduled методы молча не выполняются (баг был в OrderServiceApplication в Phase 1 Kafka outbox).
ZalTableRepository.findExpiredReservations
@Query("""
SELECT t FROM ZalTable t
WHERE t.status = 'reserved'
AND t.reservedUntil IS NOT NULL
AND t.reservedUntil < :now
AND t.deletedAt IS NULL
""")
List<ZalTable> findExpiredReservations(@Param("now") LocalDateTime now);NEW worker/ReservationExpiryScheduler.java
@Component
public class ReservationExpiryScheduler {
@Scheduled(fixedDelay = 60_000) // раз в минуту
public void releaseExpiredReservations() {
List<ZalTable> expired = repo.findExpiredReservations(LocalDateTime.now());
for (ZalTable t : expired) {
try {
service.cancelReservation(t.getId());
log.info("Auto-released table {} ...", t.getNumber());
} catch (Exception e) {
log.warn("Failed to auto-release ...", e);
}
}
}
}Note: использует cancelReservation (не release). cancelReservation проверяет status='reserved' — если стол стал occupied (бронь сменилась на заказ) или вернулся в free (кто-то снял вручную), no-op.
Файлы
src/main/java/com/erp/store/StoreServiceApplication.java—@EnableSchedulingsrc/main/java/com/erp/store/repository/ZalTableRepository.java— findExpiredReservationssrc/main/java/com/erp/store/worker/ReservationExpiryScheduler.java(NEW)
Smoke
# Создать стол с истекшей бронью
docker exec erp-postgres psql -U erp -d store_db -c "
INSERT INTO zal_tables (id, store_id, franchise_id, number, capacity, position_x, position_y, status, reserved_until, reserved_note, created_at, updated_at)
VALUES (gen_random_uuid(), '<store>', '<franchise>', 99, 4, 100, 100, 'reserved',
NOW() - INTERVAL '5 minutes', 'Test expired', NOW(), NOW());
"
# Подождать минуту
sleep 65
# Проверить
docker exec erp-postgres psql -U erp -d store_db -c "
SELECT number, status, reserved_until FROM zal_tables WHERE number = 99;
"
# Ожидаем: status=free, reserved_until=null
# Логи
docker logs erp-store-service 2>&1 | grep "Auto-released"