Skip to content

Commit

Permalink
Merge pull request #384 from ita-social-projects/email-notifications
Browse files Browse the repository at this point in the history
Changed logic of email notifications
  • Loading branch information
DmytroDmytruk authored Sep 4, 2024
2 parents 002b4ad + 9e9c7a0 commit d29733b
Show file tree
Hide file tree
Showing 8 changed files with 322 additions and 157 deletions.
36 changes: 8 additions & 28 deletions core/src/main/java/greencity/controller/EmailController.java
Original file line number Diff line number Diff line change
Expand Up @@ -147,42 +147,22 @@ public ResponseEntity<Void> sendTaggedUserInCommentNotification(
}

/**
* Sends email notification to user that received comment.
* Sends scheduled email notification to user.
*
* @param message {@link UserReceivedCommentMessage} - object with all necessary
* data for sending notification via email.
* @author Dmytro Dmytruk
*/
@Operation(summary = "Send email notification user that received comment")
@ApiResponses(value = {
@ApiResponse(responseCode = "200", description = HttpStatuses.OK),
@ApiResponse(responseCode = "400", description = HttpStatuses.BAD_REQUEST),
@ApiResponse(responseCode = "404", description = HttpStatuses.NOT_FOUND)
})
@PostMapping("/userReceivedComment/notification")
public ResponseEntity<Void> sendUserReceivedCommentNotification(
@RequestBody @Valid UserReceivedCommentMessage message) {
emailService.sendUserReceivedCommentNotificationEmail(message);
return ResponseEntity.ok().build();
}

/**
* Sends email notification to user that received comment reply.
*
* @param message {@link UserReceivedCommentReplyMessage} - object with all
* necessary data for sending notification via email.
* @param message {@link ScheduledEmailMessage} - object with all necessary data
* for sending notification via email.
* @author Dmytro Dmytruk
*/
@Operation(summary = "Send email notification user that received comment reply")
@Operation(summary = "Send scheduled email notification to user")
@ApiResponses(value = {
@ApiResponse(responseCode = "200", description = HttpStatuses.OK),
@ApiResponse(responseCode = "400", description = HttpStatuses.BAD_REQUEST),
@ApiResponse(responseCode = "404", description = HttpStatuses.NOT_FOUND)
})
@PostMapping("/userReceivedCommentReply/notification")
public ResponseEntity<Void> sendUserReceivedCommentReplyNotification(
@RequestBody @Valid UserReceivedCommentReplyMessage message) {
emailService.sendUserReceivedCommentReplyNotificationEmail(message);
@PostMapping("/scheduled/notification")
public ResponseEntity<Void> sendScheduledNotification(
@RequestBody @Valid ScheduledEmailMessage message) {
emailService.sendScheduledNotificationEmail(message);
return ResponseEntity.ok().build();
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,245 @@
<!DOCTYPE html>
<html xmlns:th="http://www.thymeleaf.org" xmlns="http://www.w3.org/1999/xhtml"
th:with="lang=${language}" th:lang="${lang}">
<head>
<meta charset="utf-8">
<meta http-equiv="x-ua-compatible" content="ie=edge">
<meta name="viewport" content="width=device-width, initial-scale=1">
<style type="text/css">
/**
* Google webfonts. Recommended to include the .woff version for cross-client compatibility.
*/
@media screen {
@font-face {
font-family: 'Source Sans Pro';
font-style: normal;
font-weight: 400;
src: local('Source Sans Pro Regular'), local('SourceSansPro-Regular'), url(https://fonts.gstatic.com/s/sourcesanspro/v10/ODelI1aHBYDBqgeIAH2zlBM0YzuT7MdOe03otPbuUS0.woff) format('woff');
}
@font-face {
font-family: 'Source Sans Pro';
font-style: normal;
font-weight: 700;
src: local('Source Sans Pro Bold'), local('SourceSansPro-Bold'), url(https://fonts.gstatic.com/s/sourcesanspro/v10/toadOcfmlt9b38dHJxOBGFkQc6VGVFSmCnC_l7QZG60.woff) format('woff');
}
}

/**
* Avoid browser level font resizing.
* 1. Windows Mobile
* 2. iOS / OSX
*/
body,
table,
td,
a {
-ms-text-size-adjust: 100%; /* 1 */
-webkit-text-size-adjust: 100%; /* 2 */
}

/**
* Remove extra space added to tables and cells in Outlook.
*/
table,
td {
mso-table-rspace: 0pt;
mso-table-lspace: 0pt;
}

/**
* Better fluid images in Internet Explorer.
*/
img {
-ms-interpolation-mode: bicubic;
}

/**
* Remove blue links for iOS devices.
*/
a[x-apple-data-detectors] {
font-family: inherit !important;
font-size: inherit !important;
font-weight: inherit !important;
line-height: inherit !important;
color: inherit !important;
text-decoration: none !important;
}

/**
* Fix centering issues in Android 4.4.
*/
div[style*="margin: 16px 0;"] {
margin: 0 !important;
}

body {
width: 100% !important;
height: 100% !important;
padding: 0 !important;
margin: 0 !important;
}

/**
* Collapse table borders to avoid space between cells.
*/
table {
border-collapse: collapse !important;
}

.site-clr {
background-color: #13aa57;
}

.background-clr {
background-color: #e9ecef;
}

.background-msg-clr {
background-color: #ffffff;
}

img {
height: auto;
line-height: 100%;
text-decoration: none;
border: 0;
outline: none;
}
</style>

</head>
<body class="background-clr">
<!-- start body -->
<table border="0" cellpadding="0" cellspacing="0" width="100%">
<!-- start logo -->
<tr>
<td class="background-clr" align="center">
<!--[if (gte mso 9)|(IE)]>
<table align="center" border="0" cellpadding="0" cellspacing="0" width="600">
<tr>
<td align="center" valign="top" width="600">
<![endif]-->
<table border="0" cellpadding="0" cellspacing="0" width="100%" style="max-width: 600px;">
<tr>
<td class="site-clr" align="center" valign="top" style="margin-top: 20px">
<a style="display: inline-block; padding: 20px 50px; font-weight:700; font-family: 'Source Sans Pro', Helvetica, Arial, sans-serif; font-size: 32px; color: #ffffff; text-decoration: none; border-radius: 6px;">GreenCity</a>
</td>
</tr>
</table>
<!--[if (gte mso 9)|(IE)]>
</td>
</tr>
</table>
<![endif]-->
</td>
</tr>
<!-- end logo -->

<!-- start hero -->
<tr>
<td class="background-clr" align="center">
<!--[if (gte mso 9)|(IE)]>
<table align="center" border="0" cellpadding="0" cellspacing="0" width="600">
<tr>
<td align="center" valign="top" width="600">
<![endif]-->
<table border="0" cellpadding="0" cellspacing="0" width="100%" style="max-width: 600px;">
<tr>
<td class="background-msg-clr" align="left"
style="padding: 36px 24px 0; font-family: 'Source Sans Pro', Helvetica, Arial, sans-serif;color: #000000; border-top: 3px solid #d4dadf;">
<p th:text="#{hello} + ${name} + ','"
style="margin: 0; font-size: 18px; font-weight: 700; letter-spacing: -1px; line-height: 12px;"></p>
</td>
</tr>
</table>
<!--[if (gte mso 9)|(IE)]>
</td>
</tr>
</table>
<![endif]-->
</td>
</tr>

<tr>
<td align="center" bgcolor="#e9ecef">
<!--[if (gte mso 9)|(IE)]>
<table align="center" border="0" cellpadding="0" cellspacing="0" width="600">
<tr>
<td align="center" valign="top" width="600">
<![endif]-->
<table border="0" cellpadding="0" cellspacing="0" width="100%" style="max-width: 600px;">
<!-- start copy -->
<tr>
<td class="background-msg-clr" align="left"
style="padding: 24px; font-family: 'Source Sans Pro', Helvetica, Arial, sans-serif; font-size: 16px; line-height: 24px;">
<div style="color: #000000">
<span th:text="${title}" style="margin: 0; line-height: 5vh; display: inline-block; color: #000000; vertical-align: middle;">qewqewqew</span>
<p th:utext="${body}">ererwerwerwewr</p>

</div>
<p style="margin: 0;">
<a style="display: inline-block;
padding: 10px 20px;
margin-top: 20px;
font-size: 16px;
color: #fff;
background-color: #14a958;
text-decoration: none;
border-radius: 10px;"
th:href="${clientLink}">Go to notification</a>
</p>
</td>
</tr>
<tr>
<td class="background-msg-clr" align="left"
style="padding: 24px; font-family: 'Source Sans Pro', Helvetica, Arial, sans-serif; font-size: 16px; line-height: 24px; color: #000000; border-bottom: 3px solid #d4dadf">
<p style="margin: 0;">Sincerely yours, GreenCity's team</p>
</td>
</tr>
<!-- end copy -->

</table>
<!--[if (gte mso 9)|(IE)]>
</td>
</tr>
</table>
<![endif]-->
</td>
</tr>


<tr>
<td class="background-clr" align="center" style="padding: 24px;">
<!--[if (gte mso 9)|(IE)]>
<table align="center" border="0" cellpadding="0" cellspacing="0" width="600">
<tr>
<td align="center" valign="top" width="600">
<![endif]-->
<table border="0" cellpadding="0" cellspacing="0" width="100%" style="max-width: 600px;">

<!-- start permission -->
<tr>
<td class="background-clr" align="center"
style="padding: 12px 24px; font-family: 'Source Sans Pro', Helvetica, Arial, sans-serif; font-size: 14px; line-height: 20px; color: #666;">
<p style="margin: 0;">
You received this email because you subscribed for notifications via e-mail.
If you didn't request this action you can safely delete this email.
</p>
</td>
</tr>
<!-- end permission -->

</table>
<!--[if (gte mso 9)|(IE)]>
</td>
</tr>
</table>
<![endif]-->
</td>
</tr>
<!-- end footer -->

</table>
<!-- end body -->
</body>
</html>
54 changes: 15 additions & 39 deletions core/src/test/java/greencity/controller/EmailControllerTest.java
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,13 @@
import com.fasterxml.jackson.datatype.jsr310.JavaTimeModule;
import greencity.dto.econews.EcoNewsForSendEmailDto;
import greencity.dto.violation.UserViolationMailDto;
import greencity.message.*;
import greencity.message.GeneralEmailMessage;
import greencity.message.HabitAssignNotificationMessage;
import greencity.message.ScheduledEmailMessage;
import greencity.message.SendChangePlaceStatusEmailMessage;
import greencity.message.SendHabitNotification;
import greencity.message.SendReportEmailMessage;
import greencity.message.UserTaggedInCommentMessage;
import greencity.service.EmailService;
import lombok.SneakyThrows;
import org.junit.jupiter.api.BeforeEach;
Expand Down Expand Up @@ -211,51 +217,21 @@ void sendUserTaggedInCommentNotification() {

@Test
@SneakyThrows
void sendUserReceivedCommentNotification() {
void sendUserReceivedScheduledNotification() {
ObjectMapper objectMapper = new ObjectMapper();
objectMapper.registerModule(new JavaTimeModule());
UserReceivedCommentMessage message = UserReceivedCommentMessage.builder()
.receiverEmail("receiver@example.com")
.receiverName("receiver")
.elementName("event")
.commentText("test")
.authorName("test")
.commentedElementId(1L)
ScheduledEmailMessage message = ScheduledEmailMessage.builder()
.body("test body")
.username("test user")
.email("test@gmail.com")
.subject("test subject")
.baseLink("test link")
.language("en")
.baseLink("testLink")
.creationDate(LocalDateTime.now())
.build();
String content = objectMapper.writeValueAsString(message);
mockMvc.perform(MockMvcRequestBuilders.post(LINK + "/userReceivedComment/notification")
mockMvc.perform(MockMvcRequestBuilders.post(LINK + "/scheduled/notification")
.contentType(MediaType.APPLICATION_JSON)
.content(content))
.andExpect(status().isOk());
}

@Test
@SneakyThrows
void sendUserReceivedCommentReplyNotification() {
ObjectMapper objectMapper = new ObjectMapper();
objectMapper.registerModule(new JavaTimeModule());
UserReceivedCommentReplyMessage message = UserReceivedCommentReplyMessage.builder()
.receiverEmail("receiver@example.com")
.receiverName("receiver")
.elementName("event")
.commentText("test")
.authorName("test")
.baseLink("testLink")
.commentedElementId(1L)
.language("en")
.parentCommentAuthorName("parent")
.parentCommentText("parentText")
.parentCommentCreationDate(LocalDateTime.now())
.creationDate(LocalDateTime.now())
.build();
String content = objectMapper.writeValueAsString(message);
mockMvc.perform(MockMvcRequestBuilders.post(LINK + "/userReceivedCommentReply/notification")
.contentType(MediaType.APPLICATION_JSON)
.content(content))
.andExpect(status().isOk());
}

}
Original file line number Diff line number Diff line change
Expand Up @@ -48,6 +48,8 @@ public class EmailConstants {
public static final String SENDER_NAME = "senderName";
public static final String HABIT_NAME = "habitName";
public static final String ELEMENT_NAME = "elementName";
public static final String TITLE = "title";
public static final String BODY = "body";
// templates
public static final String VERIFY_EMAIL_PAGE = "verify-email-page";
public static final String RESTORE_EMAIL_PAGE = "restore-email-page";
Expand All @@ -64,4 +66,5 @@ public class EmailConstants {
public static final String USER_TAGGED_IN_COMMENT_PAGE = "user-tagged-in-comment-email-page";
public static final String USER_RECEIVED_COMMENT_PAGE = "user-received-comment-email-page";
public static final String USER_RECEIVED_COMMENT_REPLY_PAGE = "user-received-comment-reply-email-page";
public static final String SCHEDULED_NOTIFICATION_PAGE = "scheduled-notification-email-page";
}
Loading

0 comments on commit d29733b

Please sign in to comment.