Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Pet 287 feat : 에러코드 인터페이스에 http 상태 코드 조회 추가 #203

Merged
merged 10 commits into from
Jan 20, 2024
Merged
Show file tree
Hide file tree
Changes from 8 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
@@ -1,23 +1,19 @@
package com.pawith.alarmmodule.exception;

import com.pawith.commonmodule.exception.Error;
import lombok.AllArgsConstructor;
import lombok.Getter;
import lombok.RequiredArgsConstructor;
import org.springframework.http.HttpStatus;
import org.springframework.http.HttpStatusCode;

@AllArgsConstructor
@Getter
@RequiredArgsConstructor
public enum AlarmError implements Error {
DEVICE_TOKEN_NOT_FOUND("FCM 디바이스 토큰이 없습니다.", 5000),
FCM_SEND_ERROR("FCM 전송에 실패하였습니다.", 5001),;
DEVICE_TOKEN_NOT_FOUND("FCM 디바이스 토큰이 없습니다.", 5000, HttpStatus.NOT_FOUND),
FCM_SEND_ERROR("FCM 전송에 실패하였습니다.", 5001, HttpStatus.INTERNAL_SERVER_ERROR),
;

private String message;
private Integer errorCode;

@Override
public String getMessage() {
return message;
}

@Override
public int getErrorCode() {
return errorCode;
}
private final String message;
private final Integer errorCode;
private final HttpStatusCode httpStatusCode;
}
Original file line number Diff line number Diff line change
@@ -1,6 +1,11 @@
package com.pawith.commonmodule.exception;

import org.springframework.http.HttpStatusCode;


public interface Error {
String getMessage();
int getErrorCode();

HttpStatusCode getHttpStatusCode();
}
Original file line number Diff line number Diff line change
@@ -1,6 +1,5 @@
package com.pawith.commonmodule.exception;

import org.springframework.http.HttpStatus;
import org.springframework.http.ResponseEntity;
import org.springframework.web.bind.annotation.ExceptionHandler;
import org.springframework.web.bind.annotation.RestControllerAdvice;
Expand All @@ -11,6 +10,6 @@ public class GlobalExceptionHandler {
@ExceptionHandler(BusinessException.class)
public ResponseEntity<ErrorResponse> handleJwtException(BusinessException e) {
final ErrorResponse errorResponse = ErrorResponse.from(e);
return new ResponseEntity<>(errorResponse, HttpStatus.BAD_REQUEST);
return new ResponseEntity<>(errorResponse, e.getHttpStatusCode());
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -2,22 +2,22 @@

import com.pawith.commonmodule.exception.Error;
import lombok.Getter;
import lombok.RequiredArgsConstructor;
import org.springframework.http.HttpStatus;
import org.springframework.http.HttpStatusCode;

@Getter
@RequiredArgsConstructor
public enum AuthError implements Error {

INVALID_TOKEN("유효하지 않은 토큰입니다.", 1000),
EXPIRED_TOKEN("만료된 토큰입니다.", 1001),
NOT_EXIST_TOKEN("토큰이 존재하지 않습니다.", 1002),
INVALID_AUTHORIZATION_TYPE("유효하지 않은 Authorization Type 입니다.", 1003),
EMPTY_AUTHORIZATION_HEADER("Authorization Header가 비어있습니다.", 1004),
OAUTH_FAIL("OAuth 인증에 실패하였습니다.", 1005);
INVALID_TOKEN("유효하지 않은 토큰입니다.", 1000, HttpStatus.BAD_REQUEST),
EXPIRED_TOKEN("만료된 토큰입니다.", 1001, HttpStatus.BAD_REQUEST),
NOT_EXIST_TOKEN("토큰이 존재하지 않습니다.", 1002, HttpStatus.BAD_REQUEST),
INVALID_AUTHORIZATION_TYPE("유효하지 않은 Authorization Type 입니다.", 1003, HttpStatus.BAD_REQUEST),
EMPTY_AUTHORIZATION_HEADER("Authorization Header가 비어있습니다.", 1004, HttpStatus.BAD_REQUEST),
OAUTH_FAIL("OAuth 인증에 실패하였습니다.", 1005, HttpStatus.BAD_REQUEST);

private final String message;
private final int errorCode;

AuthError(String message, int errorCode) {
this.message = message;
this.errorCode = errorCode;
}
private final HttpStatusCode httpStatusCode;
}
Original file line number Diff line number Diff line change
Expand Up @@ -10,15 +10,16 @@
import lombok.extern.slf4j.Slf4j;
import org.springframework.context.ApplicationEventPublisher;
import org.springframework.data.domain.Pageable;
import org.springframework.stereotype.Component;

import java.util.List;
import java.util.concurrent.TimeUnit;

@Slf4j
//@Component
@Component
public class IncompleteTodoCountNotificationHandler extends AbstractBatchSchedulingHandler<IncompleteTodoCountInfoDao> {
private static final Integer BATCH_SIZE = 100;
private static final String CRON_EXPRESSION = "0 0 0 0 0 0";
private static final String CRON_EXPRESSION = "0 0 20 * * *"; // 매일 20시에 실행
private static final String NOTIFICATION_MESSAGE = "[%s] 오늘이 지나기 전, %s님에게 남은 %d개의 todo를 완료해주세요!";

private final RegisterRepository registerRepository;
Expand All @@ -43,6 +44,7 @@ protected List<IncompleteTodoCountInfoDao> extractBatchData(Pageable pageable) {
protected void processBatch(List<IncompleteTodoCountInfoDao> executionResult) {
cachingUserInfo(executionResult);
final List<NotificationEvent> notificationEventList = executionResult.stream()
.filter(incompleteTodoCountInfoDao -> incompleteTodoCountInfoDao.getIncompleteTodoCount() > 0)
.map(incompleteTodoCountInfoDao -> {
final String userNickname = valueOperator.get(incompleteTodoCountInfoDao.getUserId());
final String message = String.format(NOTIFICATION_MESSAGE, incompleteTodoCountInfoDao.getTodoTeamName(), userNickname, incompleteTodoCountInfoDao.getIncompleteTodoCount());
Expand Down
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
package com.pawith.todoapplication.handler;

import com.pawith.todoapplication.handler.event.TodoCompletionCheckEvent;
import com.pawith.todoapplication.handler.event.TodoAssignStatusChangeEvent;
import com.pawith.tododomain.entity.Assign;
import com.pawith.tododomain.entity.Todo;
import com.pawith.tododomain.service.AssignQueryService;
Expand All @@ -23,11 +23,11 @@ public class TodoCompletionCheckOnTodoHandler {
private final TodoQueryService todoQueryService;

@EventListener
public void changeTodoStatus(TodoCompletionCheckEvent todoCompletionCheckEvent) throws InterruptedException {
public void changeTodoStatus(TodoAssignStatusChangeEvent todoAssignStatusChangeEvent) throws InterruptedException {
while(true) {
try {
final List<Assign> assigns = assignQueryService.findAllAssignByTodoId(todoCompletionCheckEvent.todoId());
final Todo todo = todoQueryService.findTodoByTodoId(todoCompletionCheckEvent.todoId());
final List<Assign> assigns = assignQueryService.findAllAssignByTodoId(todoAssignStatusChangeEvent.todoId());
final Todo todo = todoQueryService.findTodoByTodoId(todoAssignStatusChangeEvent.todoId());
final boolean isAllCompleteTodo = assigns.stream().allMatch(Assign::isCompleted);
todo.updateCompletionStatus(isAllCompleteTodo);
break;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@
import com.pawith.commonmodule.cache.CacheTemplate;
import com.pawith.commonmodule.event.MultiNotificationEvent;
import com.pawith.commonmodule.event.NotificationEvent;
import com.pawith.todoapplication.handler.event.TodoCompletionCheckEvent;
import com.pawith.todoapplication.handler.event.TodoAssignStatusChangeEvent;
import com.pawith.tododomain.entity.CompletionStatus;
import com.pawith.tododomain.repository.dao.IncompleteAssignInfoDao;
import com.pawith.tododomain.service.AssignQueryService;
Expand Down Expand Up @@ -31,8 +31,8 @@ public class TodoRemindHandler {
private final ApplicationEventPublisher applicationEventPublisher;

@EventListener
public void remindTodo(final TodoCompletionCheckEvent todoCompletionCheckEvent){
final Long todoId = todoCompletionCheckEvent.todoId();
public void remindTodo(final TodoAssignStatusChangeEvent todoAssignStatusChangeEvent){
final Long todoId = todoAssignStatusChangeEvent.todoId();
final String cacheKey = String.format(REMIND_CACHE_KEY, todoId);
final long completeAssignNumber = assignQueryService.countAssignByTodoIdAndCompleteStatus(todoId, CompletionStatus.COMPLETE);
if(isRemindable(todoId, completeAssignNumber)&& !cacheTemplate.opsForSet().contains(cacheKey)){
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
package com.pawith.todoapplication.handler.event;

public record TodoAssignStatusChangeEvent(Long todoId) {
}

This file was deleted.

Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@

import com.pawith.commonmodule.annotation.ApplicationService;
import com.pawith.todoapplication.dto.request.AssignChangeRequest;
import com.pawith.todoapplication.handler.event.TodoCompletionCheckEvent;
import com.pawith.todoapplication.handler.event.TodoAssignStatusChangeEvent;
import com.pawith.tododomain.entity.Assign;
import com.pawith.tododomain.entity.Register;
import com.pawith.tododomain.entity.Todo;
Expand Down Expand Up @@ -38,7 +38,7 @@ public void changeAssignStatus(Long todoId){
final User user = userUtils.getAccessUser();
final Assign assign = assignQueryService.findAssignByTodoIdAndUserId(todo.getId(), user.getId());
assign.updateCompletionStatus();
applicationEventPublisher.publishEvent(new TodoCompletionCheckEvent(todo.getId()));
applicationEventPublisher.publishEvent(new TodoAssignStatusChangeEvent(todo.getId()));
}

public void changeAssign(Long todoId, AssignChangeRequest request) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -54,7 +54,7 @@ public ListResponse<CategorySubTodoResponse> getTodoListByCategoryId(final Long
final List<Assign> assignList = assignQueryService.findAllAssignByCategoryIdAndScheduledDate(categoryId, moveDate);

final Map<Todo, List<Assign>> todoAssignMap = AssignUtils.convertToTodoAssignMap(assignList);
final List<Todo> todoList = List.copyOf(todoAssignMap.keySet());
final Collection<Todo> todoList = todoAssignMap.keySet();

final Map<Long, TodoNotification> todoNotificationMap =
todoNotificationQueryService.findMapTodoIdKeyAndTodoNotificationValueByTodoIdsAndUserId(todoList, accessUser.getId());
Expand All @@ -78,7 +78,7 @@ private List<AssignUserInfoResponse> getAssignUserInfoResponses(final List<Assig
.map(assign -> {
final Register register = assign.getRegister();
final User findUser = userMap.get(register.getUserId());
if (Objects.equals(findUser.getId(), accessUserId)) {
if (findUser.isMatchingUser(accessUserId)) {
isAssigned.set(true);
}
return new AssignUserInfoResponse(findUser.getId(), findUser.getNickname(), assign.getCompletionStatus());
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@
import static org.mockito.BDDMockito.given;

import com.pawith.commonmodule.UnitTestConfig;
import com.pawith.todoapplication.handler.event.TodoCompletionCheckEvent;
import com.pawith.todoapplication.handler.event.TodoAssignStatusChangeEvent;
import com.pawith.commonmodule.utils.FixtureMonkeyUtils;
import com.pawith.tododomain.entity.Assign;
import com.pawith.tododomain.entity.CompletionStatus;
Expand Down Expand Up @@ -36,8 +36,8 @@ void init(){
@DisplayName("Todo 완료 여부 변경 테스트-담당자가 모두 완료하면 Todo 완료")
void changeTodoStatus() throws InterruptedException {
// given
final TodoCompletionCheckEvent todoCompletionCheckEvent = FixtureMonkeyUtils.getConstructBasedFixtureMonkey()
.giveMeOne(TodoCompletionCheckEvent.class);
final TodoAssignStatusChangeEvent todoAssignStatusChangeEvent = FixtureMonkeyUtils.getConstructBasedFixtureMonkey()
.giveMeOne(TodoAssignStatusChangeEvent.class);
final List<Assign> mockAssigns = FixtureMonkeyUtils.getReflectionbasedFixtureMonkey()
.giveMeBuilder(Assign.class)
.set("completionStatus", CompletionStatus.COMPLETE)
Expand All @@ -46,10 +46,10 @@ void changeTodoStatus() throws InterruptedException {
.giveMeBuilder(Todo.class)
.set("completionStatus", CompletionStatus.INCOMPLETE)
.sample();
given(assignQueryService.findAllAssignByTodoId(todoCompletionCheckEvent.todoId())).willReturn(mockAssigns);
given(todoQueryService.findTodoByTodoId(todoCompletionCheckEvent.todoId())).willReturn(mockTodo);
given(assignQueryService.findAllAssignByTodoId(todoAssignStatusChangeEvent.todoId())).willReturn(mockAssigns);
given(todoQueryService.findTodoByTodoId(todoAssignStatusChangeEvent.todoId())).willReturn(mockTodo);
// when
todoCompletionCheckOnTodoHandler.changeTodoStatus(todoCompletionCheckEvent);
todoCompletionCheckOnTodoHandler.changeTodoStatus(todoAssignStatusChangeEvent);
// then
Assertions.assertEquals(CompletionStatus.COMPLETE, mockTodo.getCompletionStatus());
}
Expand All @@ -58,8 +58,8 @@ void changeTodoStatus() throws InterruptedException {
@DisplayName("Todo 완료 여부 변경 테스트-담당자가 하나라도 미완료면 Todo 미완료")
void changeTodoStatusWithIncompletedAssignee() throws InterruptedException {
// given
final TodoCompletionCheckEvent todoCompletionCheckEvent = FixtureMonkeyUtils.getConstructBasedFixtureMonkey()
.giveMeOne(TodoCompletionCheckEvent.class);
final TodoAssignStatusChangeEvent todoAssignStatusChangeEvent = FixtureMonkeyUtils.getConstructBasedFixtureMonkey()
.giveMeOne(TodoAssignStatusChangeEvent.class);
final List<Assign> mockAssigns = FixtureMonkeyUtils.getReflectionbasedFixtureMonkey()
.giveMeBuilder(Assign.class)
.set("completionStatus", CompletionStatus.COMPLETE)
Expand All @@ -73,10 +73,10 @@ void changeTodoStatusWithIncompletedAssignee() throws InterruptedException {
.giveMeBuilder(Todo.class)
.set("completionStatus", CompletionStatus.INCOMPLETE)
.sample();
given(assignQueryService.findAllAssignByTodoId(todoCompletionCheckEvent.todoId())).willReturn(mockAssigns);
given(todoQueryService.findTodoByTodoId(todoCompletionCheckEvent.todoId())).willReturn(mockTodo);
given(assignQueryService.findAllAssignByTodoId(todoAssignStatusChangeEvent.todoId())).willReturn(mockAssigns);
given(todoQueryService.findTodoByTodoId(todoAssignStatusChangeEvent.todoId())).willReturn(mockTodo);
// when
todoCompletionCheckOnTodoHandler.changeTodoStatus(todoCompletionCheckEvent);
todoCompletionCheckOnTodoHandler.changeTodoStatus(todoAssignStatusChangeEvent);
// then
Assertions.assertEquals(CompletionStatus.INCOMPLETE, mockTodo.getCompletionStatus());
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -2,27 +2,27 @@

import com.pawith.commonmodule.exception.Error;
import lombok.Getter;
import lombok.RequiredArgsConstructor;
import org.springframework.http.HttpStatus;
import org.springframework.http.HttpStatusCode;

@Getter
@RequiredArgsConstructor
public enum TodoError implements Error {
TODO_TEAM_NOT_FOUND("패밀리를 찾을 수 없습니다.", 3000),
NOT_REGISTER_USER("패밀리에 등록되지 않은 사용자입니다.", 3001),
REGISTER_NOT_FOUND("등록된 패밀리를 찾을 수 없습니다.", 3002),
ALREADY_REGISTER_TODO_TEAM("이미 등록된 패밀리입니다.", 3003),
TODO_NOT_FOUND("Todo를 찾을 수 없습니다.", 3004),
WRONG_SCHEDULED_DATE("예정일이 잘못되었습니다.", 3005),
CATEGORY_NOT_FOUND("카테고리를 찾을 수 없습니다.", 3006),
CANNOT_PRESIDENT_UNREGISTRABLE("팀장 탈퇴시 탈퇴 후 팀장이 1명 이상 있어야 합니다.", 3007),
CANNOT_CHANGE_AUTHORITY("권한을 변경할 수 없습니다", 3008),
ASSIGN_NOT_FOUND("할당된 Todo를 찾을 수 없습니다.", 3009),
TODO_MODIFICATION_NOT_ALLOWED("Todo 수정 및 삭제가 허용되지 않습니다.", 3010),
TODO_TEAM_NOT_FOUND("패밀리를 찾을 수 없습니다.", 3000, HttpStatus.NOT_FOUND),
NOT_REGISTER_USER("패밀리에 등록되지 않은 사용자입니다.", 3001, HttpStatus.BAD_REQUEST),
REGISTER_NOT_FOUND("등록된 패밀리를 찾을 수 없습니다.", 3002, HttpStatus.NOT_FOUND),
ALREADY_REGISTER_TODO_TEAM("이미 등록된 패밀리입니다.", 3003, HttpStatus.BAD_REQUEST),
TODO_NOT_FOUND("Todo를 찾을 수 없습니다.", 3004, HttpStatus.NOT_FOUND),
WRONG_SCHEDULED_DATE("예정일이 잘못되었습니다.", 3005, HttpStatus.BAD_REQUEST),
CATEGORY_NOT_FOUND("카테고리를 찾을 수 없습니다.", 3006, HttpStatus.NOT_FOUND),
CANNOT_PRESIDENT_UNREGISTRABLE("팀장 탈퇴시 탈퇴 후 팀장이 1명 이상 있어야 합니다.", 3007, HttpStatus.BAD_REQUEST),
CANNOT_CHANGE_AUTHORITY("권한을 변경할 수 없습니다", 3008, HttpStatus.BAD_REQUEST),
ASSIGN_NOT_FOUND("할당된 Todo를 찾을 수 없습니다.", 3009, HttpStatus.NOT_FOUND),
TODO_MODIFICATION_NOT_ALLOWED("Todo 수정 및 삭제가 허용되지 않습니다.", 3010, HttpStatus.BAD_REQUEST),
;

private final String message;
private final int errorCode;

TodoError(String message, int errorCode) {
this.message = message;
this.errorCode = errorCode;
}
private final HttpStatusCode httpStatusCode;
}
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@
import lombok.RequiredArgsConstructor;
import org.springframework.transaction.annotation.Transactional;

import java.util.Collection;
import java.util.List;
import java.util.Map;
import java.util.stream.Collectors;
Expand All @@ -19,7 +20,7 @@ public class TodoNotificationQueryService {

private final TodoNotificationRepository todoNotificationRepository;

public Map<Long, TodoNotification> findMapTodoIdKeyAndTodoNotificationValueByTodoIdsAndUserId(List<Todo> todoList, Long userId) {
public Map<Long, TodoNotification> findMapTodoIdKeyAndTodoNotificationValueByTodoIdsAndUserId(Collection<Todo> todoList, Long userId) {
final List<Long> todoIds = todoList.stream().map(Todo::getId).collect(Collectors.toList());
return todoNotificationRepository.findAllByTodoIdsAndUserIdWithInCompleteAssignQuery(todoIds, userId)
.stream()
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -69,4 +69,8 @@ public Long getJoinTerm() {
LocalDate joinDate = this.createdAt.toLocalDate();
return ChronoUnit.DAYS.between(joinDate, nowDate) + 1;
}

public Boolean isMatchingUser(Long userId) {
return this.id.equals(userId);
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -2,18 +2,18 @@

import com.pawith.commonmodule.exception.Error;
import lombok.Getter;
import lombok.RequiredArgsConstructor;
import org.springframework.http.HttpStatus;
import org.springframework.http.HttpStatusCode;

@Getter
@RequiredArgsConstructor
public enum UserError implements Error {
USER_NOT_FOUND("사용자를 찾을 수 없습니다.", 2000),
USER_AUTHORITY_NOT_FOUND("사용자 권한을 찾을 수 없습니다.", 2001),
ACCOUNT_ALREADY_EXIST("이미 가입한 계정이 있습니다", 2002);
USER_NOT_FOUND("사용자를 찾을 수 없습니다.", 2000, HttpStatus.NOT_FOUND),
USER_AUTHORITY_NOT_FOUND("사용자 권한을 찾을 수 없습니다.", 2001, HttpStatus.NOT_FOUND),
ACCOUNT_ALREADY_EXIST("이미 가입한 계정이 있습니다", 2002, HttpStatus.BAD_REQUEST);

private final String message;
private final int errorCode;

UserError(String message, int errorCode) {
this.message = message;
this.errorCode = errorCode;
}
private final HttpStatusCode httpStatusCode;
}
Original file line number Diff line number Diff line change
Expand Up @@ -2,18 +2,18 @@

import com.pawith.commonmodule.exception.Error;
import lombok.Getter;
import lombok.RequiredArgsConstructor;
import org.springframework.http.HttpStatus;
import org.springframework.http.HttpStatusCode;

@Getter
@RequiredArgsConstructor
public enum FileError implements Error {
FILE_EXTENTION_ERROR("잘못된 형식의 파일입니다.", 4000),
FILE_UPLOAD_ERROR("파일 업로드에 실패했습니다.", 4001),
FILE_DELETE_ERROR("파일 삭제에 실패했습니다.", 4002);
FILE_EXTENTION_ERROR("잘못된 형식의 파일입니다.", 4000, HttpStatus.BAD_REQUEST),
FILE_UPLOAD_ERROR("파일 업로드에 실패했습니다.", 4001, HttpStatus.INTERNAL_SERVER_ERROR),
FILE_DELETE_ERROR("파일 삭제에 실패했습니다.", 4002, HttpStatus.INTERNAL_SERVER_ERROR);

private final String message;
private final int errorCode;

FileError(String message, int errorCode) {
this.message = message;
this.errorCode = errorCode;
}
private final HttpStatusCode httpStatusCode;
}
Loading