Skip to content

Commit

Permalink
Event handlers for new comment (#63)
Browse files Browse the repository at this point in the history
  • Loading branch information
haiphucnguyen authored Jan 29, 2025
1 parent c126e00 commit 52b3662
Show file tree
Hide file tree
Showing 20 changed files with 330 additions and 58 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,7 @@ public EmailContext(Locale locale) {

public EmailContext setToUser(UserDTO toUser) {
this.toUser = toUser;
thymeleafContext.setVariable("user", toUser);
return this;
}

Expand Down
Original file line number Diff line number Diff line change
@@ -1,6 +1,5 @@
package io.flowinquiry.modules.collab.controller;

import io.flowinquiry.modules.collab.domain.Comment;
import io.flowinquiry.modules.collab.domain.EntityType;
import io.flowinquiry.modules.collab.service.CommentService;
import io.flowinquiry.modules.collab.service.dto.CommentDTO;
Expand Down Expand Up @@ -32,9 +31,8 @@ public ResponseEntity<CommentDTO> saveComment(@RequestBody CommentDTO comment) {
}

@GetMapping("/{id}")
public ResponseEntity<Comment> getCommentById(@PathVariable("id") Long id) {
Comment comment = commentService.getCommentById(id);
return ResponseEntity.ok(comment);
public CommentDTO getCommentById(@PathVariable("id") Long id) {
return commentService.getCommentById(id);
}

@GetMapping
Expand Down
Original file line number Diff line number Diff line change
@@ -1,11 +1,10 @@
package io.flowinquiry.modules.collab.service;

import io.flowinquiry.modules.collab.domain.Comment;
import io.flowinquiry.modules.collab.domain.EntityType;
import io.flowinquiry.modules.collab.repository.CommentRepository;
import io.flowinquiry.modules.collab.service.dto.CommentDTO;
import io.flowinquiry.modules.collab.service.mapper.CommentMapper;
import io.flowinquiry.modules.teams.service.event.TeamRequestNewCommentEvent;
import io.flowinquiry.modules.teams.service.event.TeamRequestCommentCreatedEvent;
import java.util.List;
import org.springframework.context.ApplicationEventPublisher;
import org.springframework.stereotype.Service;
Expand Down Expand Up @@ -34,14 +33,15 @@ public CommentDTO saveComment(CommentDTO comment) {
CommentDTO savedComment =
commentMapper.toDTO(commentRepository.save(commentMapper.toEntity(comment)));
if (savedComment.getEntityType() == EntityType.Team_Request) {
eventPublisher.publishEvent(new TeamRequestNewCommentEvent(this, savedComment));
eventPublisher.publishEvent(new TeamRequestCommentCreatedEvent(this, savedComment));
}
return savedComment;
}

public Comment getCommentById(Long id) {
public CommentDTO getCommentById(Long id) {
return commentRepository
.findById(id)
.map(commentMapper::toDTO)
.orElseThrow(
() -> new IllegalArgumentException("Comment not found with id: " + id));
}
Expand Down
Original file line number Diff line number Diff line change
@@ -1,10 +1,11 @@
package io.flowinquiry.modules.teams.service;

import static io.flowinquiry.utils.StringUtils.polishedHtmlTagsMessage;

import io.flowinquiry.modules.ai.service.ChatModelService;
import io.flowinquiry.modules.teams.domain.TeamRequest;
import io.flowinquiry.modules.teams.domain.TeamRequestConversationHealth;
import io.flowinquiry.modules.teams.repository.TeamRequestConversationHealthRepository;
import org.apache.commons.text.StringEscapeUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.ai.chat.prompt.Prompt;
Expand Down Expand Up @@ -177,9 +178,4 @@ private TeamRequestConversationHealth createNewConversationHealth(
health.setSummary(generateSummary(firstMessage));
return teamRequestConversationHealthRepository.save(health);
}

private String polishedHtmlTagsMessage(String message) {
String preProcessedHtml = message.replaceAll(">(\\s*)<", "> <");
return StringEscapeUtils.unescapeHtml4(preProcessedHtml).replaceAll("<[^>]+>", "");
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -5,10 +5,10 @@
import org.springframework.context.ApplicationEvent;

@Getter
public class TeamRequestNewCommentEvent extends ApplicationEvent {
public class TeamRequestCommentCreatedEvent extends ApplicationEvent {
private final CommentDTO commentDTO;

public TeamRequestNewCommentEvent(Object source, CommentDTO commentDTO) {
public TeamRequestCommentCreatedEvent(Object source, CommentDTO commentDTO) {
super(source);
this.commentDTO = commentDTO;
}
Expand Down

This file was deleted.

Original file line number Diff line number Diff line change
Expand Up @@ -50,7 +50,7 @@ public void onNewTeamRequestCreated(NewTeamRequestCreatedEvent event) {
new EmailContext(Locale.forLanguageTag("en"))
.setToUser(watcherMapper.toUserDto(watcher))
.setSubject(
"mail.newticket.title",
"email.new.ticket.subject",
teamRequestDTO.getRequestTitle())
.addVariable("ticket", teamRequestDTO)
.setTemplate("mail/newTicketEmail");
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@
import static j2html.TagCreator.p;
import static j2html.TagCreator.text;

import io.flowinquiry.exceptions.ResourceNotFoundException;
import io.flowinquiry.modules.collab.domain.ActivityLog;
import io.flowinquiry.modules.collab.domain.EntityType;
import io.flowinquiry.modules.collab.domain.Notification;
Expand All @@ -13,6 +14,7 @@
import io.flowinquiry.modules.teams.service.dto.TeamRequestDTO;
import io.flowinquiry.modules.teams.service.event.NewTeamRequestCreatedEvent;
import io.flowinquiry.modules.usermanagement.domain.User;
import io.flowinquiry.modules.usermanagement.repository.UserRepository;
import io.flowinquiry.modules.usermanagement.service.dto.UserWithTeamRoleDTO;
import io.flowinquiry.utils.Obfuscator;
import java.util.List;
Expand All @@ -26,24 +28,35 @@ public class NewTeamRequestCreatedNotificationEventListener {
private final NotificationRepository notificationRepository;
private final TeamRepository teamRepository;
private final ActivityLogRepository activityLogRepository;
private final UserRepository userRepository;

public NewTeamRequestCreatedNotificationEventListener(
NotificationRepository notificationRepository,
TeamRepository teamRepository,
ActivityLogRepository activityLogRepository) {
ActivityLogRepository activityLogRepository,
UserRepository userRepository) {
this.notificationRepository = notificationRepository;
this.teamRepository = teamRepository;
this.activityLogRepository = activityLogRepository;
this.userRepository = userRepository;
}

@Async("asyncTaskExecutor")
@Transactional
@EventListener
public void onNewTeamRequestCreated(NewTeamRequestCreatedEvent event) {
TeamRequestDTO teamRequestDTO = event.getTeamRequest();
User requestUser =
userRepository
.findOneById(teamRequestDTO.getRequestUserId())
.orElseThrow(
() ->
new ResourceNotFoundException(
"User not found: "
+ teamRequestDTO.getRequestUserId()));
String html =
p(
a(teamRequestDTO.getRequestUserName())
a(requestUser.getFirstName() + " " + requestUser.getLastName())
.withHref(
"/portal/users/"
+ Obfuscator.obfuscate(
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@
import org.springframework.transaction.annotation.Transactional;

@Component
public class RemoveUserOutOfTeamEmailEventListener {
public class RemoveUserOutOfTeamMailEventListener {

@Async("asyncTaskExecutor")
@EventListener
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@
import io.flowinquiry.modules.teams.service.TeamRequestHealthEvalService;
import io.flowinquiry.modules.teams.service.TeamRequestService;
import io.flowinquiry.modules.teams.service.dto.TeamRequestDTO;
import io.flowinquiry.modules.teams.service.event.TeamRequestNewCommentEvent;
import io.flowinquiry.modules.teams.service.event.TeamRequestCommentCreatedEvent;
import java.util.Objects;
import org.springframework.boot.autoconfigure.condition.ConditionalOnBean;
import org.springframework.context.event.EventListener;
Expand All @@ -13,13 +13,13 @@

@Component
@ConditionalOnBean(TeamRequestHealthEvalService.class)
public class TeamRequestNewCommentAiEvaluateConversationHealthEventListener {
public class TeamRequestCommentCreatedAiEvaluateConversationHealthEventListener {

private final TeamRequestService teamRequestService;

private final TeamRequestHealthEvalService teamRequestHealthEvalService;

public TeamRequestNewCommentAiEvaluateConversationHealthEventListener(
public TeamRequestCommentCreatedAiEvaluateConversationHealthEventListener(
TeamRequestService teamRequestService,
TeamRequestHealthEvalService teamRequestHealthEvalService) {
this.teamRequestHealthEvalService = teamRequestHealthEvalService;
Expand All @@ -29,7 +29,7 @@ public TeamRequestNewCommentAiEvaluateConversationHealthEventListener(
@Async("asyncTaskExecutor")
@EventListener
public void onTeamRequestNewCommentAiEvaluateConversationHealthEvent(
TeamRequestNewCommentEvent event) {
TeamRequestCommentCreatedEvent event) {
CommentDTO comment = event.getCommentDTO();
TeamRequestDTO teamRequestDTO =
teamRequestService.getTeamRequestById(comment.getEntityId());
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,80 @@
package io.flowinquiry.modules.teams.service.listener;

import io.flowinquiry.modules.collab.EmailContext;
import io.flowinquiry.modules.collab.service.CommentService;
import io.flowinquiry.modules.collab.service.MailService;
import io.flowinquiry.modules.collab.service.dto.CommentDTO;
import io.flowinquiry.modules.teams.repository.TeamRequestWatcherRepository;
import io.flowinquiry.modules.teams.service.TeamRequestService;
import io.flowinquiry.modules.teams.service.dto.TeamRequestDTO;
import io.flowinquiry.modules.teams.service.dto.WatcherDTO;
import io.flowinquiry.modules.teams.service.event.TeamRequestCommentCreatedEvent;
import io.flowinquiry.modules.teams.service.mapper.WatcherMapper;
import io.flowinquiry.utils.Obfuscator;
import java.util.List;
import java.util.Locale;
import org.springframework.context.event.EventListener;
import org.springframework.scheduling.annotation.Async;
import org.springframework.stereotype.Component;
import org.springframework.transaction.annotation.Transactional;

@Component
public class TeamRequestCommentCreatedMailEventListener {
private final CommentService commentService;
private final WatcherMapper watcherMapper;
private final TeamRequestWatcherRepository teamRequestWatcherRepository;
private final TeamRequestService teamRequestService;
private final MailService mailService;

public TeamRequestCommentCreatedMailEventListener(
CommentService commentService,
WatcherMapper watcherMapper,
TeamRequestWatcherRepository teamRequestWatcherRepository,
TeamRequestService teamRequestService,
MailService mailService) {
this.commentService = commentService;
this.watcherMapper = watcherMapper;
this.teamRequestWatcherRepository = teamRequestWatcherRepository;
this.teamRequestService = teamRequestService;
this.mailService = mailService;
}

@Async("asyncTaskExecutor")
@Transactional
@EventListener
public void onTeamRequestCommentCreated(TeamRequestCommentCreatedEvent event) {
CommentDTO commentDTO = commentService.getCommentById(event.getCommentDTO().getId());
List<WatcherDTO> watchers =
teamRequestWatcherRepository.findWatchersByRequestId(commentDTO.getEntityId());

TeamRequestDTO teamRequestDTO =
teamRequestService.getTeamRequestById(commentDTO.getEntityId());

if (!watchers.isEmpty()) {
for (WatcherDTO watcher : watchers) {
// Skip sending email if the watcher is the comment creator
if (watcher.getId().equals(commentDTO.getCreatedById())) {
continue;
}

EmailContext emailContext =
new EmailContext(Locale.forLanguageTag("en"))
.setToUser(watcherMapper.toUserDto(watcher))
.setSubject(
"email.new.ticket.comment.subject",
teamRequestDTO.getRequestTitle())
.addVariable("ticket", teamRequestDTO)
.addVariable("comment", commentDTO)
.addVariable(
"obfuscatedTeamId",
Obfuscator.obfuscate(teamRequestDTO.getTeamId()))
.addVariable(
"obfuscatedTicketId",
Obfuscator.obfuscate(teamRequestDTO.getId()))
.setTemplate("mail/newTicketCommentEmail");

mailService.sendEmail(emailContext);
}
}
}
}
Loading

0 comments on commit 52b3662

Please sign in to comment.