Skip to content
Merged
Show file tree
Hide file tree
Changes from all 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
Expand Up @@ -6,10 +6,12 @@
import lombok.RequiredArgsConstructor;
import org.springframework.http.ResponseEntity;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.RestController;
import org.websoso.WSSServer.domain.User;
import org.websoso.WSSServer.dto.notification.NotificationGetResponse;
import org.websoso.WSSServer.dto.notification.NotificationsGetResponse;
import org.websoso.WSSServer.service.NotificationService;
import org.websoso.WSSServer.service.UserService;
Expand All @@ -31,4 +33,14 @@ public ResponseEntity<NotificationsGetResponse> getNotifications(Principal princ
.status(OK)
.body(notificationService.getNotifications(lastNotificationId, size, user));
}

@GetMapping("/{notificationId}")
public ResponseEntity<NotificationGetResponse> getNotification(Principal principal,
@PathVariable("notificationId") Long notificationId) {
User user = userService.getUserOrException(Long.valueOf(principal.getName()));

return ResponseEntity
.status(OK)
.body(notificationService.getNotification(user, notificationId));
}
}
16 changes: 8 additions & 8 deletions src/main/java/org/websoso/WSSServer/domain/Notification.java
Original file line number Diff line number Diff line change
Expand Up @@ -28,9 +28,9 @@ public class Notification extends BaseEntity {
private String notificationTitle;

@Column(nullable = false)
private String notificationDescription;
private String notificationBody;

private String notificationContent;
private String notificationDetail;

@Column(nullable = false)
private Long userId;
Expand All @@ -41,20 +41,20 @@ public class Notification extends BaseEntity {
@JoinColumn(name = "notification_type_id", nullable = false)
private NotificationType notificationType;

private Notification(String notificationTitle, String notificationDescription, String notificationContent,
private Notification(String notificationTitle, String notificationBody, String notificationDetail,
Long userId, Long feedId, NotificationType notificationType) {
this.notificationTitle = notificationTitle;
this.notificationDescription = notificationDescription;
this.notificationContent = notificationContent;
this.notificationBody = notificationBody;
this.notificationDetail = notificationDetail;
this.userId = userId;
this.feedId = feedId;
this.notificationType = notificationType;
}

public static Notification create(String notificationTitle, String notificationDescription,
String notificationContent, Long userId, Long feedId,
public static Notification create(String notificationTitle, String notificationBody,
String notificationDetail, Long userId, Long feedId,
NotificationType notificationType) {
return new Notification(notificationTitle, notificationDescription, notificationContent, userId, feedId,
return new Notification(notificationTitle, notificationBody, notificationDetail, userId, feedId,
notificationType);
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
package org.websoso.WSSServer.dto.notification;

import java.time.format.DateTimeFormatter;
import org.websoso.WSSServer.domain.Notification;

public record NotificationGetResponse(
String notificationTitle,
String notificationCreatedDate,
String notificationDetail
) {
private static final String DATE_PATTERN = "yyyy.MM.dd";

static public NotificationGetResponse of(Notification notification) {
return new NotificationGetResponse(
notification.getNotificationTitle(),
notification.getCreatedDate().format(DateTimeFormatter.ofPattern(DATE_PATTERN)),
notification.getNotificationDetail()
);
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@ public record NotificationInfo(
Long notificationId,
String notificationImage,
String notificationTitle,
String notificationDescription,
String notificationBody,
String createdDate,
Boolean isRead,
Boolean isNotice,
Expand All @@ -26,7 +26,7 @@ static public NotificationInfo of(Notification notification, Boolean isRead) {
notification.getNotificationId(),
notification.getNotificationType().getNotificationTypeImage(),
notification.getNotificationTitle(),
notification.getNotificationDescription(),
notification.getNotificationBody(),
formatCreatedDate(notification.getCreatedDate()),
isRead,
notification.getNotificationType().getNotificationTypeName().equals("공지"),
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
package org.websoso.WSSServer.exception.error;

import static org.springframework.http.HttpStatus.BAD_REQUEST;
import static org.springframework.http.HttpStatus.FORBIDDEN;
import static org.springframework.http.HttpStatus.NOT_FOUND;

import lombok.AllArgsConstructor;
import lombok.Getter;
import org.springframework.http.HttpStatus;
import org.websoso.WSSServer.exception.common.ICustomError;

@AllArgsConstructor
@Getter
public enum CustomNotificationError implements ICustomError {

NOTIFICATION_NOT_FOUND("NOTIFICATION-001", "해당 ID를 가진 공지사항을 찾을 수 없습니다.", NOT_FOUND),
NOTIFICATION_READ_FORBIDDEN("NOTIFICATION-002", "해당 알림의 대상 유저가 아닙니다.", FORBIDDEN),
NOTIFICATION_TYPE_INVALID("NOTIFICATION-003", "해당 알림은 공지사항에 적합한 타입이 아닙니다.", BAD_REQUEST);

private final String code;
private final String description;
private final HttpStatus statusCode;
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
package org.websoso.WSSServer.exception.exception;

import lombok.Getter;
import org.websoso.WSSServer.exception.common.AbstractCustomException;
import org.websoso.WSSServer.exception.error.CustomNotificationError;

@Getter
public class CustomNotificationException extends AbstractCustomException {

public CustomNotificationException(CustomNotificationError customNotificationError, String message) {
super(customNotificationError, message);
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -3,11 +3,14 @@
import java.util.List;
import org.springframework.data.jpa.repository.JpaRepository;
import org.springframework.stereotype.Repository;
import org.websoso.WSSServer.domain.Notification;
import org.websoso.WSSServer.domain.ReadNotification;
import org.websoso.WSSServer.domain.User;

@Repository
public interface ReadNotificationRepository extends JpaRepository<ReadNotification, Long> {

List<ReadNotification> findAllByUser(User user);

boolean existsByUserAndNotification(User user, Notification notification);
}
Original file line number Diff line number Diff line change
@@ -1,5 +1,9 @@
package org.websoso.WSSServer.service;

import static org.websoso.WSSServer.exception.error.CustomNotificationError.NOTIFICATION_NOT_FOUND;
import static org.websoso.WSSServer.exception.error.CustomNotificationError.NOTIFICATION_READ_FORBIDDEN;
import static org.websoso.WSSServer.exception.error.CustomNotificationError.NOTIFICATION_TYPE_INVALID;

import java.util.List;
import java.util.Set;
import java.util.stream.Collectors;
Expand All @@ -11,8 +15,10 @@
import org.websoso.WSSServer.domain.Notification;
import org.websoso.WSSServer.domain.ReadNotification;
import org.websoso.WSSServer.domain.User;
import org.websoso.WSSServer.dto.notification.NotificationGetResponse;
import org.websoso.WSSServer.dto.notification.NotificationInfo;
import org.websoso.WSSServer.dto.notification.NotificationsGetResponse;
import org.websoso.WSSServer.exception.exception.CustomNotificationException;
import org.websoso.WSSServer.repository.NotificationRepository;
import org.websoso.WSSServer.repository.ReadNotificationRepository;

Expand All @@ -25,6 +31,13 @@ public class NotificationService {
private final NotificationRepository notificationRepository;
private final ReadNotificationRepository readNotificationRepository;

@Transactional(readOnly = true)
public Notification getNotificationOrException(Long notificationId) {
return notificationRepository.findById(notificationId)
.orElseThrow(() -> new CustomNotificationException(NOTIFICATION_NOT_FOUND,
"notification with the given id is not found"));
}

@Transactional(readOnly = true)
public NotificationsGetResponse getNotifications(Long lastNotificationId, int size, User user) {
Slice<Notification> notifications = notificationRepository.findNotifications(lastNotificationId,
Expand All @@ -40,4 +53,33 @@ public NotificationsGetResponse getNotifications(Long lastNotificationId, int si

return NotificationsGetResponse.of(notifications.hasNext(), notificationInfos);
}

public NotificationGetResponse getNotification(User user, Long notificationId) {
Notification notification = getNotificationOrException(notificationId);
verifyIsNotice(notification);
validateNotificationRecipient(user, notification);
if (!readNotificationRepository.existsByUserAndNotification(user, notification)) {
readNotificationRepository.save(ReadNotification.create(notification, user));
}
return NotificationGetResponse.of(notification);
}

private void verifyIsNotice(Notification notification) {
Set<String> noticeTypes = Set.of("공지", "이벤트");
if (noticeTypes.contains(notification.getNotificationType().getNotificationTypeName())) {
return;
}
throw new CustomNotificationException(NOTIFICATION_TYPE_INVALID,
"Notification does not have a type suitable for a notice.");
}

private void validateNotificationRecipient(User user, Notification notification) {
Long userId = user.getUserId();
Long notificationUserId = notification.getUserId();
if (notificationUserId == 0 || notificationUserId.equals(userId)) {
return;
}
throw new CustomNotificationException(NOTIFICATION_READ_FORBIDDEN,
"User does not have permission to access this notification.");
}
}