Skip to content

Commit

Permalink
Merge pull request #208 from ku-ring/develop
Browse files Browse the repository at this point in the history
version 2.8.1
  • Loading branch information
zbqmgldjfh authored Aug 5, 2024
2 parents b65837d + ebfa8cf commit b588b51
Show file tree
Hide file tree
Showing 7 changed files with 68 additions and 78 deletions.
Original file line number Diff line number Diff line change
@@ -1,12 +1,12 @@
package com.kustacks.kuring.admin.adapter.in.web;

import com.google.firebase.database.annotations.NotNull;
import com.kustacks.kuring.admin.adapter.in.web.dto.AdminAlertCreateRequest;
import com.kustacks.kuring.admin.adapter.in.web.dto.RealNotificationRequest;
import com.kustacks.kuring.admin.adapter.in.web.dto.TestNotificationRequest;
import com.kustacks.kuring.admin.application.port.in.AdminCommandUseCase;
import com.kustacks.kuring.admin.application.port.in.dto.RealNotificationCommand;
import com.kustacks.kuring.admin.domain.AdminRole;
import com.kustacks.kuring.alert.adapter.in.web.dto.AlertCreateRequest;
import com.kustacks.kuring.alert.application.port.in.dto.AlertCreateCommand;
import com.kustacks.kuring.auth.authorization.AuthenticationPrincipal;
import com.kustacks.kuring.auth.context.Authentication;
Expand Down Expand Up @@ -61,12 +61,12 @@ public ResponseEntity<BaseResponse<String>> createRealNotice(
return ResponseEntity.ok().body(new BaseResponse<>(ADMIN_REAL_NOTICE_CREATE_SUCCESS, null));
}

@Operation(summary = "예약 알림 등록", description = "서버에 예약 알림을 등록한다")
@Operation(summary = "예약 알림 등록", description = "서버에 알림 시간을 yyyy-MM-dd HH:mm:ss 형태로 요청시 예약 알림을 등록한다")
@SecurityRequirement(name = "JWT")
@Secured(AdminRole.ROLE_ROOT)
@PostMapping("/alerts")
public ResponseEntity<BaseResponse<String>> createAlert(
@RequestBody AlertCreateRequest request
@RequestBody AdminAlertCreateRequest request
) {
AlertCreateCommand command = new AlertCreateCommand(
request.title(), request.content(),
Expand Down
Original file line number Diff line number Diff line change
@@ -1,8 +1,8 @@
package com.kustacks.kuring.alert.adapter.in.web.dto;
package com.kustacks.kuring.admin.adapter.in.web.dto;

import jakarta.validation.constraints.NotEmpty;

public record AlertCreateRequest(
public record AdminAlertCreateRequest(
@NotEmpty(message = "제목은 필수입니다")
String title,
String content,
Expand Down

This file was deleted.

Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,7 @@
import org.springframework.context.event.EventListener;
import org.springframework.scheduling.TaskScheduler;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.transaction.support.TransactionTemplate;

import java.time.Clock;
import java.time.Instant;
Expand All @@ -31,6 +32,7 @@
public class AlertService implements AlertCommandUseCase {

private final ConcurrentMap<Long, ScheduledFuture<?>> taskList = new ConcurrentHashMap<>();
private final TransactionTemplate transactionTemplate;
private final AlertCommandPort alertCommandPort;
private final AlertQueryPort alertQueryPort;
private final MessageEventPort messageEventPort;
Expand Down Expand Up @@ -69,22 +71,25 @@ public void cancelAlertSchedule(Long id) {
}
}

private static void cancle(Long id, Alert entryAlert) {
entryAlert.changeCanceled();
log.info("[EntryAlert 취소] entryAlertId: {}", id);
}

@Override
public void sendAlert(Long id) {
alertQueryPort.findByIdAndStatusForUpdate(id, AlertStatus.PENDING)
.ifPresent(entryAlert -> send(id, entryAlert));
Alert findAlert = alertQueryPort.findByIdAndStatusForUpdate(id, AlertStatus.PENDING)
.orElseThrow(() -> new IllegalArgumentException("해당 알림이 존재하지 않습니다."));

send(id, findAlert.getTitle(), findAlert.getContent());

findAlert.changeCompleted();
taskList.remove(id);
}

private void send(Long id, Alert entryAlert) {
private void cancle(Long id, Alert entryAlert) {
entryAlert.changeCanceled();
log.info("[EntryAlert 취소] entryAlertId: {}", id);
}

private void send(Long id, String title, String content) {
log.info("[EntryAlert 전송 시작] entryAlertId: {}", id);
messageEventPort.sendMessageEvent(entryAlert.getTitle(), entryAlert.getContent());
entryAlert.changeCompleted();
taskList.remove(id);
messageEventPort.sendMessageEvent(title, content);
}

private List<AlertDto> findAllPending() {
Expand All @@ -98,7 +103,15 @@ private void addSchedule(AlertDto alertDto) {
Long alertId = alertDto.getId();
Instant alertTime = toInstant(alertDto.getAlertTime());
log.info("Alert 스케쥴링 추가. alertId: {}, alertTime: {}", alertId, alertTime);
ScheduledFuture<?> scheduled = taskScheduler.schedule(() -> this.sendAlert(alertId), alertTime);

ScheduledFuture<?> scheduled = taskScheduler.schedule(
() -> transactionTemplate.execute(status -> {
sendAlert(alertId);
return null; // 트랜잭션 템플릿의 반환값, 필요에 따라 null 또는 다른 값을 반환
}),
alertTime
);

taskList.put(alertId, scheduled);
}

Expand Down
Original file line number Diff line number Diff line change
@@ -1,8 +1,8 @@
package com.kustacks.kuring.acceptance;

import com.kustacks.kuring.admin.adapter.in.web.dto.AdminAlertCreateRequest;
import com.kustacks.kuring.admin.adapter.in.web.dto.RealNotificationRequest;
import com.kustacks.kuring.admin.adapter.in.web.dto.TestNotificationRequest;
import com.kustacks.kuring.alert.adapter.in.web.dto.AlertCreateRequest;
import com.kustacks.kuring.support.IntegrationTestSupport;
import io.restassured.RestAssured;
import io.restassured.response.ExtractableResponse;
Expand All @@ -26,7 +26,7 @@
@DisplayName("인수 : 관리자")
class AdminAcceptanceTest extends IntegrationTestSupport {

AlertCreateRequest alertCreateCommand;
AdminAlertCreateRequest alertCreateCommand;

@Autowired
Clock clock;
Expand All @@ -36,7 +36,7 @@ class AdminAcceptanceTest extends IntegrationTestSupport {
public void setUp() {
super.setUp();
LocalDateTime expiredTime = LocalDateTime.now(clock).plus(1, ChronoUnit.HOURS);
alertCreateCommand = new AlertCreateRequest(
alertCreateCommand = new AdminAlertCreateRequest(
"title", "content", expiredTime.toString()
);
}
Expand Down
4 changes: 2 additions & 2 deletions src/test/java/com/kustacks/kuring/acceptance/AdminStep.java
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
package com.kustacks.kuring.acceptance;

import com.kustacks.kuring.alert.adapter.in.web.dto.AlertCreateRequest;
import com.kustacks.kuring.admin.adapter.in.web.dto.AdminAlertCreateRequest;
import io.restassured.RestAssured;
import io.restassured.response.ExtractableResponse;
import io.restassured.response.Response;
Expand Down Expand Up @@ -31,7 +31,7 @@ public class AdminStep {
.extract();
}

public static ExtractableResponse<Response> 알림_예약(String accessToken, AlertCreateRequest alertCreateCommand) {
public static ExtractableResponse<Response> 알림_예약(String accessToken, AdminAlertCreateRequest alertCreateCommand) {
return RestAssured
.given().log().all()
.header("Authorization", "Bearer " + accessToken)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,6 @@
import com.kustacks.kuring.alert.domain.Alert;
import com.kustacks.kuring.alert.domain.AlertStatus;
import com.kustacks.kuring.support.IntegrationTestSupport;
import org.assertj.core.api.Assertions;
import org.junit.jupiter.api.DisplayName;
import org.junit.jupiter.api.Test;
import org.springframework.beans.factory.annotation.Autowired;
Expand All @@ -14,7 +13,10 @@
import java.time.LocalDateTime;
import java.time.temporal.ChronoUnit;
import java.util.List;
import java.util.concurrent.TimeUnit;

import static org.assertj.core.api.Assertions.assertThat;
import static org.awaitility.Awaitility.await;
import static org.junit.jupiter.api.Assertions.assertAll;

class AlertServiceTest extends IntegrationTestSupport {
Expand Down Expand Up @@ -44,10 +46,10 @@ void creat_alert() {
// then
List<Alert> alertList = alertRepository.findAllByStatus(AlertStatus.PENDING);
assertAll(
() -> Assertions.assertThat(alertList).hasSize(1),
() -> Assertions.assertThat(alertList.get(0).getTitle()).isEqualTo("title"),
() -> Assertions.assertThat(alertList.get(0).getContent()).isEqualTo("content"),
() -> Assertions.assertThat(alertList.get(0).getAlertTime().truncatedTo(ChronoUnit.MICROS))
() -> assertThat(alertList).hasSize(1),
() -> assertThat(alertList.get(0).getTitle()).isEqualTo("title"),
() -> assertThat(alertList.get(0).getContent()).isEqualTo("content"),
() -> assertThat(alertList.get(0).getAlertTime().truncatedTo(ChronoUnit.MICROS))
.isEqualTo(expiredTime.truncatedTo(ChronoUnit.MICROS))
);
}
Expand All @@ -70,11 +72,33 @@ void cancel_alert() {
// then
List<Alert> alertList = alertRepository.findAllByStatus(AlertStatus.CANCELED);
assertAll(
() -> Assertions.assertThat(alertList).hasSize(1),
() -> Assertions.assertThat(alertList.get(0).getTitle()).isEqualTo("title"),
() -> Assertions.assertThat(alertList.get(0).getContent()).isEqualTo("content"),
() -> Assertions.assertThat(alertList.get(0).getAlertTime().truncatedTo(ChronoUnit.MICROS))
() -> assertThat(alertList).hasSize(1),
() -> assertThat(alertList.get(0).getTitle()).isEqualTo("title"),
() -> assertThat(alertList.get(0).getContent()).isEqualTo("content"),
() -> assertThat(alertList.get(0).getAlertTime().truncatedTo(ChronoUnit.MICROS))
.isEqualTo(expiredTime.truncatedTo(ChronoUnit.MICROS))
);
}

@DisplayName("알림이 울린 후 성공적으로 상태를 변경한다")
@Test
void alert_change_status() {
// given
LocalDateTime expiredTime = LocalDateTime.now(clock).plus(1, ChronoUnit.SECONDS);
AlertCreateCommand alertCreateCommand = new AlertCreateCommand(
"title", "content",
expiredTime
);
alertService.addAlertSchedule(alertCreateCommand);

// when : 1.5초 기다린 후 알림 상태를 확인합니다.
await().atLeast(1500, TimeUnit.MICROSECONDS).atMost(2, TimeUnit.SECONDS).until(() -> {
List<Alert> alertList = alertRepository.findAllByStatus(AlertStatus.COMPLETED);
return !alertList.isEmpty(); // 조건이 충족될 때까지 대기
});

// then
List<Alert> alertList = alertRepository.findAllByStatus(AlertStatus.COMPLETED);
assertThat(alertList).hasSize(1);
}
}

0 comments on commit b588b51

Please sign in to comment.