diff --git a/src/main/java/com/savvato/tribeapp/controllers/AttributesAPIController.java b/src/main/java/com/savvato/tribeapp/controllers/AttributesAPIController.java index 515999ed..2a9df9d8 100644 --- a/src/main/java/com/savvato/tribeapp/controllers/AttributesAPIController.java +++ b/src/main/java/com/savvato/tribeapp/controllers/AttributesAPIController.java @@ -6,7 +6,7 @@ import com.savvato.tribeapp.controllers.annotations.controllers.AttributesAPIController.GetUserPhrasesToBeReviewed; import com.savvato.tribeapp.controllers.dto.AttributesRequest; import com.savvato.tribeapp.dto.AttributeDTO; -import com.savvato.tribeapp.dto.GenericResponseDTO; +import com.savvato.tribeapp.dto.AttributesApplyPhraseToUserDTO; import com.savvato.tribeapp.dto.ToBeReviewedDTO; import com.savvato.tribeapp.entities.NotificationType; import com.savvato.tribeapp.services.*; @@ -71,25 +71,18 @@ public ResponseEntity> getUserPhrasesToBeReviewed( @ApplyPhraseToUser @PostMapping - public ResponseEntity applyPhraseToUser(@RequestBody @Valid AttributesRequest req) { - if (phraseService.isPhraseValid(req.adverb, req.verb, req.preposition, req.noun)) { - boolean isPhraseApplied = - phraseService.applyPhraseToUser( - req.userId, req.adverb, req.verb, req.preposition, req.noun); - if (isPhraseApplied) { - sendNotification(true, req.userId); - GenericResponseDTO rtn = GenericResponseService.createDTO("true"); - return ResponseEntity.status(HttpStatus.OK).body(rtn); - } else { - sendNotification(false, req.userId); - GenericResponseDTO rtn = GenericResponseService.createDTO("false"); - return ResponseEntity.status(HttpStatus.OK).body(rtn); - } - } else { - sendNotification(false, req.userId); - GenericResponseDTO rtn = GenericResponseService.createDTO("false"); + public ResponseEntity applyPhraseToUser(@RequestBody @Valid AttributesRequest req) { + + if (!phraseService.isPhraseValid(req.adverb, req.verb, req.preposition, req.noun)) { + AttributesApplyPhraseToUserDTO rtn = phraseService.constructAttributesApplyPhraseToUserDTO(false, false, true, false); + sendNotification(rtn, req.userId); return ResponseEntity.status(HttpStatus.OK).body(rtn); } + + AttributesApplyPhraseToUserDTO rtn = phraseService.applyPhraseToUser(req.userId, req.adverb, req.verb, req.preposition, req.noun); + sendNotification(rtn, req.userId); + + return ResponseEntity.status(HttpStatus.OK).body(rtn); } ///api/attributes/?phraseId=xx&userId=xx @@ -100,15 +93,18 @@ public ResponseEntity deletePhraseFromUser(@Parameter(description = "Phrase ID o return ResponseEntity.ok().build(); } - private void sendNotification(Boolean approved, Long userId) { - if (approved) { + private void sendNotification(AttributesApplyPhraseToUserDTO dto, Long userId) { + if (dto.isSuccess && dto.isApproved) { notificationService.createNotification( NotificationType.ATTRIBUTE_REQUEST_APPROVED, userId, NotificationType.ATTRIBUTE_REQUEST_APPROVED.getName(), "Your attribute has been approved!"); - } else { + } else if (dto.isInReview) { + notificationService.createNotification(NotificationType.ATTRIBUTE_REQUEST_IN_REVIEW, userId, NotificationType.ATTRIBUTE_REQUEST_IN_REVIEW.getName(), "Your attribute will be reviewed."); + + } else if (dto.isRejected) { notificationService.createNotification( NotificationType.ATTRIBUTE_REQUEST_REJECTED, userId, diff --git a/src/main/java/com/savvato/tribeapp/controllers/annotations/controllers/AttributesAPIController/ApplyPhraseToUser.java b/src/main/java/com/savvato/tribeapp/controllers/annotations/controllers/AttributesAPIController/ApplyPhraseToUser.java index 0a756a27..ad25b357 100644 --- a/src/main/java/com/savvato/tribeapp/controllers/annotations/controllers/AttributesAPIController/ApplyPhraseToUser.java +++ b/src/main/java/com/savvato/tribeapp/controllers/annotations/controllers/AttributesAPIController/ApplyPhraseToUser.java @@ -3,6 +3,8 @@ import com.savvato.tribeapp.controllers.annotations.requests.DocumentedRequestBody; import com.savvato.tribeapp.controllers.annotations.responses.Success; import com.savvato.tribeapp.controllers.dto.AttributesRequest; +import com.savvato.tribeapp.dto.AttributesApplyPhraseToUserDTO; +import com.savvato.tribeapp.dto.ToBeReviewedDTO; import io.swagger.v3.oas.annotations.Operation; import io.swagger.v3.oas.annotations.media.ExampleObject; import java.lang.annotation.*; @@ -16,10 +18,5 @@ description = "Provided a valid AttributesRequest (see schemas), apply phrase to user.") @DocumentedRequestBody(implementation = AttributesRequest.class) @Success( - description = "Successfully applied phrase", - examples = { - @ExampleObject(name = "Phrase applied successfully", value = "true"), - @ExampleObject(name = "Failed to apply phrase", value = "false"), - @ExampleObject(name = "Phrase was invalid", value = "false") - }) + description = "Successfully applied phrase", implementation = AttributesApplyPhraseToUserDTO.class) public @interface ApplyPhraseToUser {} diff --git a/src/main/java/com/savvato/tribeapp/dto/AttributesApplyPhraseToUserDTO.java b/src/main/java/com/savvato/tribeapp/dto/AttributesApplyPhraseToUserDTO.java new file mode 100644 index 00000000..008c1de6 --- /dev/null +++ b/src/main/java/com/savvato/tribeapp/dto/AttributesApplyPhraseToUserDTO.java @@ -0,0 +1,22 @@ +package com.savvato.tribeapp.dto; + +import io.swagger.v3.oas.annotations.media.Schema; +import lombok.Builder; + +@Builder +@Schema(description = "Result of applying phrase to user") +public class AttributesApplyPhraseToUserDTO { + + @Schema(example = "true") + public boolean isSuccess; + + @Schema(example = "true") + public boolean isApproved; + + @Schema(example = "true") + public boolean isRejected; + + @Schema(example = "true") + public boolean isInReview; + +} diff --git a/src/main/java/com/savvato/tribeapp/entities/NotificationType.java b/src/main/java/com/savvato/tribeapp/entities/NotificationType.java index 7095572d..4cb2dfe0 100644 --- a/src/main/java/com/savvato/tribeapp/entities/NotificationType.java +++ b/src/main/java/com/savvato/tribeapp/entities/NotificationType.java @@ -7,7 +7,8 @@ public class NotificationType { public static final NotificationType ATTRIBUTE_REQUEST_APPROVED = new NotificationType(1L, "Attribute request approved", null); - public static final NotificationType ATTRIBUTE_REQUEST_REJECTED = new NotificationType(1L, "Attribute request rejected", null); + public static final NotificationType ATTRIBUTE_REQUEST_REJECTED = new NotificationType(2L, "Attribute request rejected", null); + public static final NotificationType ATTRIBUTE_REQUEST_IN_REVIEW = new NotificationType(3L, "Attribute request in review", null); @Id @GeneratedValue(strategy = GenerationType.IDENTITY) diff --git a/src/main/java/com/savvato/tribeapp/services/PhraseService.java b/src/main/java/com/savvato/tribeapp/services/PhraseService.java index 52d1411c..45a6b0ae 100644 --- a/src/main/java/com/savvato/tribeapp/services/PhraseService.java +++ b/src/main/java/com/savvato/tribeapp/services/PhraseService.java @@ -1,6 +1,7 @@ package com.savvato.tribeapp.services; import com.savvato.tribeapp.dto.PhraseDTO; +import com.savvato.tribeapp.dto.AttributesApplyPhraseToUserDTO; import java.util.Map; import java.util.Optional; @@ -9,9 +10,11 @@ public interface PhraseService { boolean isPhraseValid(String adverb, String verb, String preposition, String noun); - boolean applyPhraseToUser(Long userId, String adverb, String verb, String preposition, String noun); + AttributesApplyPhraseToUserDTO applyPhraseToUser(Long userId, String adverb, String verb, String preposition, String noun); Optional findPreviouslyApprovedPhraseId(String adverb, String verb, String preposition, String noun); Optional> getPhraseInformationByUserId(Long userId); + + AttributesApplyPhraseToUserDTO constructAttributesApplyPhraseToUserDTO(boolean success, boolean approved, boolean rejected, boolean inReview); } diff --git a/src/main/java/com/savvato/tribeapp/services/PhraseServiceImpl.java b/src/main/java/com/savvato/tribeapp/services/PhraseServiceImpl.java index 5934c140..bbb4f908 100644 --- a/src/main/java/com/savvato/tribeapp/services/PhraseServiceImpl.java +++ b/src/main/java/com/savvato/tribeapp/services/PhraseServiceImpl.java @@ -3,6 +3,7 @@ import com.savvato.tribeapp.constants.Constants; import com.savvato.tribeapp.dto.PhraseDTO; import com.savvato.tribeapp.dto.projections.PhraseWithUserCountDTO; +import com.savvato.tribeapp.dto.AttributesApplyPhraseToUserDTO; import com.savvato.tribeapp.entities.*; import com.savvato.tribeapp.repositories.*; import lombok.extern.slf4j.Slf4j; @@ -128,7 +129,7 @@ public boolean isPhrasePreviouslyRejected(String adverb, String verb, String pre } @Override - public boolean applyPhraseToUser(Long userId, String adverb, String verb, String preposition, String noun) { + public AttributesApplyPhraseToUserDTO applyPhraseToUser(Long userId, String adverb, String verb, String preposition, String noun) { String adverbLowerCase = adverb.isBlank() ? Constants.NULL_VALUE_WORD : changeToLowerCase(adverb); String verbLowerCase = changeToLowerCase(verb); @@ -144,7 +145,8 @@ public boolean applyPhraseToUser(Long userId, String adverb, String verb, String userPhraseRepository.save(userPhrase); log.info("Phrase added to user " + userId); - return true; + return constructAttributesApplyPhraseToUserDTO(true,true,false, false); + } else { Optional toBeReviewedPhrase = toBeReviewedRepository.findByAdverbAndVerbAndNounAndPreposition(adverbLowerCase, verbLowerCase, nounLowerCase, prepositionLowerCase); @@ -166,7 +168,7 @@ public boolean applyPhraseToUser(Long userId, String adverb, String verb, String log.info("ToBeReviewed phrase has been mapped to user " + userId); } - return false; + return constructAttributesApplyPhraseToUserDTO(true,false,false,true); } } @@ -277,4 +279,15 @@ public PhraseDTO constructPhraseDTOFromPhraseInformation(Long phraseId, Long adv .build(); } + @Override + public AttributesApplyPhraseToUserDTO constructAttributesApplyPhraseToUserDTO(boolean success, boolean approved, boolean rejected, boolean inReview){ + AttributesApplyPhraseToUserDTO rtn = AttributesApplyPhraseToUserDTO.builder() + .isSuccess(success) + .isApproved(approved) + .isRejected(rejected) + .isInReview(inReview) + .build(); + return rtn; + } + } diff --git a/src/main/resources/db/migration/changelog-202410031119.xml b/src/main/resources/db/migration/changelog-202410031119.xml new file mode 100644 index 00000000..14872e04 --- /dev/null +++ b/src/main/resources/db/migration/changelog-202410031119.xml @@ -0,0 +1,16 @@ + + + + + + + + + + + + \ No newline at end of file diff --git a/src/main/resources/db/migration/changelog-master.xml b/src/main/resources/db/migration/changelog-master.xml index f27bcfcc..9aeb657d 100644 --- a/src/main/resources/db/migration/changelog-master.xml +++ b/src/main/resources/db/migration/changelog-master.xml @@ -47,6 +47,7 @@ + diff --git a/src/test/java/com/savvato/tribeapp/integration/controllers/AttributesAPIIT.java b/src/test/java/com/savvato/tribeapp/integration/controllers/AttributesAPIIT.java index 5b0feea5..34aa7fea 100644 --- a/src/test/java/com/savvato/tribeapp/integration/controllers/AttributesAPIIT.java +++ b/src/test/java/com/savvato/tribeapp/integration/controllers/AttributesAPIIT.java @@ -8,10 +8,7 @@ import com.savvato.tribeapp.constants.UserTestConstants; import com.savvato.tribeapp.controllers.AttributesAPIController; import com.savvato.tribeapp.controllers.dto.AttributesRequest; -import com.savvato.tribeapp.dto.AttributeDTO; -import com.savvato.tribeapp.dto.PhraseDTO; -import com.savvato.tribeapp.dto.ToBeReviewedDTO; -import com.savvato.tribeapp.dto.GenericResponseDTO; +import com.savvato.tribeapp.dto.*; import com.savvato.tribeapp.entities.NotificationType; import com.savvato.tribeapp.entities.User; import com.savvato.tribeapp.services.*; @@ -156,27 +153,31 @@ public void applyPhraseToUserWhenPhraseValidAndApplicable() throws Exception { attributesRequest.noun = NOUN1_WORD; attributesRequest.preposition = PREPOSITION1_WORD; String notificationContent = "Your attribute has been approved!"; + + AttributesApplyPhraseToUserDTO expectedDTO = AttributesApplyPhraseToUserDTO + .builder() + .isSuccess(true) + .isApproved(true) + .isRejected(false) + .isInReview(false) + .build(); + when(phraseService.isPhraseValid(anyString(), anyString(), anyString(), anyString())) .thenReturn(true); when(phraseService.applyPhraseToUser( anyLong(), anyString(), anyString(), anyString(), anyString())) - .thenReturn(true); + .thenReturn(expectedDTO); when(notificationService.createNotification( any(NotificationType.class), anyLong(), anyString(), anyString())) .thenReturn(null); - when(GenericResponseService.createDTO( - anyString())) - .thenReturn(GenericResponseDTO.builder() - .responseMessage("true") - .build()); + ArgumentCaptor notificationTypeCaptor = ArgumentCaptor.forClass(NotificationType.class); ArgumentCaptor userIdCaptor = ArgumentCaptor.forClass(Long.class); ArgumentCaptor notificationTypeNameCaptor = ArgumentCaptor.forClass(String.class); ArgumentCaptor notificationContentCaptor = ArgumentCaptor.forClass(String.class); - String template = "{\"responseMessage\": \"%s\"}"; - String expectedMessage = String.format(template, "true"); + String expectedMessage = "{\"isSuccess\": true, \"isApproved\": true, \"isRejected\": false, \"isInReview\": false}"; this.mockMvc .perform( @@ -217,29 +218,32 @@ public void applyPhraseToUserWhenPhraseValidButNotApplied() throws Exception { attributesRequest.noun = NOUN1_WORD; attributesRequest.preposition = PREPOSITION1_WORD; + AttributesApplyPhraseToUserDTO expectedDTO = AttributesApplyPhraseToUserDTO + .builder() + .isSuccess(true) + .isApproved(false) + .isRejected(false) + .isInReview(true) + .build(); + when(phraseService.isPhraseValid(anyString(), anyString(), anyString(), anyString())) .thenReturn(true); when(phraseService.applyPhraseToUser( anyLong(), anyString(), anyString(), anyString(), anyString())) - .thenReturn(false); + .thenReturn(expectedDTO); when(notificationService.createNotification( any(NotificationType.class), anyLong(), anyString(), anyString())) .thenReturn(null); - when(GenericResponseService.createDTO( - anyString())) - .thenReturn(GenericResponseDTO.builder() - .responseMessage("false") - .build()); + ArgumentCaptor notificationTypeCaptor = ArgumentCaptor.forClass(NotificationType.class); ArgumentCaptor userIdCaptor = ArgumentCaptor.forClass(Long.class); ArgumentCaptor notificationTypeNameCaptor = ArgumentCaptor.forClass(String.class); ArgumentCaptor notificationContentCaptor = ArgumentCaptor.forClass(String.class); String notificationContent = - "Your attribute was rejected. This attribute is unsuitable and cannot be applied to users."; + "Your attribute will be reviewed."; - String template = "{\"responseMessage\": \"%s\"}"; - String expectedMessage = String.format(template, "false"); + String expectedMessage = "{\"isSuccess\": true, \"isApproved\": false, \"isRejected\": false, \"isInReview\": true}"; this.mockMvc .perform( @@ -258,11 +262,11 @@ public void applyPhraseToUserWhenPhraseValidButNotApplied() throws Exception { userIdCaptor.capture(), notificationTypeNameCaptor.capture(), notificationContentCaptor.capture()); - assertThat(notificationTypeCaptor.getValue()).usingRecursiveComparison().isEqualTo(NotificationType.ATTRIBUTE_REQUEST_REJECTED); + assertThat(notificationTypeCaptor.getValue()).usingRecursiveComparison().isEqualTo(NotificationType.ATTRIBUTE_REQUEST_IN_REVIEW); assertEquals(userIdCaptor.getValue(), userId); assertEquals( notificationTypeNameCaptor.getValue(), - NotificationType.ATTRIBUTE_REQUEST_REJECTED.getName()); + NotificationType.ATTRIBUTE_REQUEST_IN_REVIEW.getName()); assertEquals(notificationContentCaptor.getValue(), notificationContent); } @@ -280,16 +284,21 @@ public void applyPhraseToUserWhenPhraseInvalid() throws Exception { attributesRequest.noun = NOUN1_WORD; attributesRequest.preposition = PREPOSITION1_WORD; + AttributesApplyPhraseToUserDTO expectedDTO = AttributesApplyPhraseToUserDTO + .builder() + .isSuccess(false) + .isApproved(false) + .isRejected(true) + .isInReview(false) + .build(); + when(phraseService.isPhraseValid(anyString(), anyString(), anyString(), anyString())) .thenReturn(false); + when((phraseService.constructAttributesApplyPhraseToUserDTO(anyBoolean(),anyBoolean(),anyBoolean(),anyBoolean()))).thenReturn(expectedDTO); when(notificationService.createNotification( any(NotificationType.class), anyLong(), anyString(), anyString())) .thenReturn(null); - when(GenericResponseService.createDTO( - anyString())) - .thenReturn(GenericResponseDTO.builder() - .responseMessage("false") - .build()); + ArgumentCaptor notificationTypeCaptor = ArgumentCaptor.forClass(NotificationType.class); ArgumentCaptor userIdCaptor = ArgumentCaptor.forClass(Long.class); @@ -298,8 +307,7 @@ public void applyPhraseToUserWhenPhraseInvalid() throws Exception { String notificationContent = "Your attribute was rejected. This attribute is unsuitable and cannot be applied to users."; - String template = "{\"responseMessage\": \"%s\"}"; - String expectedMessage = String.format(template, "false"); + String expectedMessage = "{\"isSuccess\": false, \"isApproved\": false, \"isRejected\": true, \"isInReview\": false}"; this.mockMvc .perform( diff --git a/src/test/java/com/savvato/tribeapp/unit/services/PhraseServiceImplTest.java b/src/test/java/com/savvato/tribeapp/unit/services/PhraseServiceImplTest.java index ef9ee40d..66826956 100644 --- a/src/test/java/com/savvato/tribeapp/unit/services/PhraseServiceImplTest.java +++ b/src/test/java/com/savvato/tribeapp/unit/services/PhraseServiceImplTest.java @@ -3,6 +3,7 @@ import com.savvato.tribeapp.constants.Constants; import com.savvato.tribeapp.constants.PhraseTestConstants; import com.savvato.tribeapp.constants.UserTestConstants; +import com.savvato.tribeapp.dto.AttributesApplyPhraseToUserDTO; import com.savvato.tribeapp.dto.PhraseDTO; import com.savvato.tribeapp.dto.projections.PhraseWithUserCountDTO; import com.savvato.tribeapp.entities.*; @@ -10,6 +11,7 @@ import com.savvato.tribeapp.services.PhraseService; import com.savvato.tribeapp.services.PhraseServiceImpl; import com.savvato.tribeapp.services.UserPhraseService; +import org.assertj.core.api.AssertionsForClassTypes; import org.junit.jupiter.api.Test; import org.junit.jupiter.api.extension.ExtendWith; import org.junit.jupiter.params.ParameterizedTest; @@ -51,6 +53,9 @@ public PhraseService phraseService() { @Autowired PhraseService phraseService; + @Autowired + PhraseServiceImpl phraseServiceImpl; // for testing helper method + @MockBean PhraseRepository phraseRepository; @@ -147,7 +152,6 @@ public void testIsMissingVerbOrNounWhenNounMissing(String noun) { }); } - // test that false is returned when method is called with a rejected word @Test public void testIsWordRejectedHappyPath() { @@ -160,8 +164,7 @@ public void testIsWordRejectedHappyPath() { assertFalse(phraseService.isPhraseValid(rejectedWord, rejectedWord, rejectedWord, rejectedWord)); } - - // test that false is returned when method is called with a rejected phrase + @Test public void testIsPhrasePreviouslyRejectedHappyPath() { @@ -201,10 +204,18 @@ public void testApplyPhraseToUserWhenPhraseHasBeenPreviouslyApproved() { Mockito.when(userPhraseRepository.save(Mockito.any())).thenReturn(userPhrase); - boolean rtn = phraseService.applyPhraseToUser(user1.getId(), "testAdverb", "testVerb", "testPreposition", "testNoun"); + AttributesApplyPhraseToUserDTO expectedDTO = AttributesApplyPhraseToUserDTO + .builder() + .isSuccess(true) + .isApproved(true) + .isRejected(false) + .isInReview(false) + .build(); + + AttributesApplyPhraseToUserDTO actualDTO = phraseService.applyPhraseToUser(user1.getId(), "testAdverb", "testVerb", "testPreposition", "testNoun"); verify(userPhraseRepository, times(1)).save(Mockito.any()); - assertTrue(rtn); + AssertionsForClassTypes.assertThat(actualDTO).usingRecursiveComparison().isEqualTo(expectedDTO); } @@ -233,10 +244,18 @@ public void testApplyPhraseToUserWhenPhraseExistsInToBeReviewed() { Mockito.when(toBeReviewedRepository.findByAdverbAndVerbAndNounAndPreposition(anyString(), anyString(), anyString(), anyString())).thenReturn(Optional.of(toBeReviewed)); - boolean rtn = phraseService.applyPhraseToUser(user1.getId(), testWord, testWord, testWord, testWord); + AttributesApplyPhraseToUserDTO expectedDTO = AttributesApplyPhraseToUserDTO + .builder() + .isSuccess(true) + .isApproved(false) + .isRejected(false) + .isInReview(true) + .build(); + + AttributesApplyPhraseToUserDTO actualDTO = phraseService.applyPhraseToUser(user1.getId(), testWord, testWord, testWord, testWord); verify(reviewSubmittingUserRepository, times(1)).save(Mockito.any()); - assertFalse(rtn); + AssertionsForClassTypes.assertThat(actualDTO).usingRecursiveComparison().isEqualTo(expectedDTO); } // Test that reviewSubmittingUserRepository is called once when calling ApplyPhraseToUser and conditions: @@ -262,12 +281,21 @@ public void testApplyPhraseToUserWhenPhraseDoesNotExistInToBeReviewed() { Mockito.when(phraseRepository.findByAdverbIdAndVerbIdAndPrepositionIdAndNounId(any(Long.class), any(Long.class), any(Long.class), any(Long.class))).thenReturn(Optional.empty()); - Mockito.when(toBeReviewedRepository.findByAdverbAndVerbAndNounAndPreposition(anyString(), anyString(), anyString(), anyString())).thenReturn(Optional.of(toBeReviewed)); + Mockito.when(toBeReviewedRepository.findByAdverbAndVerbAndNounAndPreposition(anyString(), anyString(), anyString(), anyString())).thenReturn(Optional.empty()); + Mockito.when(toBeReviewedRepository.save(Mockito.any())).thenReturn(toBeReviewed); - boolean rtn = phraseService.applyPhraseToUser(user1.getId(), testWord, testWord, testWord, testWord); + AttributesApplyPhraseToUserDTO expectedDTO = AttributesApplyPhraseToUserDTO + .builder() + .isSuccess(true) + .isApproved(false) + .isRejected(false) + .isInReview(true) + .build(); + + AttributesApplyPhraseToUserDTO actualDTO = phraseService.applyPhraseToUser(user1.getId(), testWord, testWord, testWord, testWord); verify(reviewSubmittingUserRepository, times(1)).save(Mockito.any()); - assertFalse(rtn); + AssertionsForClassTypes.assertThat(actualDTO).usingRecursiveComparison().isEqualTo(expectedDTO); } @Test @@ -343,8 +371,17 @@ public void testApplyPhraseToUserWhenAdverbIsBlank() { // Should return false if the phrase has not been seen before Mockito.when(toBeReviewedRepository.save(any())).thenReturn(tbrSaved); - boolean applyPhraseToUser = phraseService.applyPhraseToUser(user1.getId(), testAdverbEmpty, testVerb, testPreposition, testNoun); - assertFalse(applyPhraseToUser); + + AttributesApplyPhraseToUserDTO expectedDTO = AttributesApplyPhraseToUserDTO + .builder() + .isSuccess(true) + .isApproved(false) + .isRejected(false) + .isInReview(true) + .build(); + + AttributesApplyPhraseToUserDTO actualDTO = phraseService.applyPhraseToUser(user1.getId(), testAdverbEmpty, testVerb, testPreposition, testNoun); + AssertionsForClassTypes.assertThat(actualDTO).usingRecursiveComparison().isEqualTo(expectedDTO); // Empty Adverb should be converted to "nullvalue" ArgumentCaptor argAdverb = ArgumentCaptor.forClass(String.class); @@ -376,8 +413,17 @@ public void testApplyPhraseToUserWhenPrepositionIsBlank() { Mockito.when(toBeReviewedRepository.save(any())).thenReturn(tbrSaved); when(nounRepository.findByWord(anyString())).thenReturn(Optional.of(new Noun(testNoun))); when(verbRepository.findByWord(anyString())).thenReturn(Optional.of(new Verb(testVerb))); - boolean applyPhraseToUser = phraseService.applyPhraseToUser(user1.getId(), testAdverb, testVerb, testPrepositionBlank, testNoun); - assertFalse(applyPhraseToUser); + + AttributesApplyPhraseToUserDTO expectedDTO = AttributesApplyPhraseToUserDTO + .builder() + .isSuccess(true) + .isApproved(false) + .isRejected(false) + .isInReview(true) + .build(); + + AttributesApplyPhraseToUserDTO actualDTO = phraseService.applyPhraseToUser(user1.getId(), testAdverb, testVerb, testPrepositionBlank, testNoun); + AssertionsForClassTypes.assertThat(actualDTO).usingRecursiveComparison().isEqualTo(expectedDTO); // Empty Preposition should be converted to "nullvalue" ArgumentCaptor argAdverb = ArgumentCaptor.forClass(String.class); @@ -388,4 +434,61 @@ public void testApplyPhraseToUserWhenPrepositionIsBlank() { assertEquals(argPreposition.getValue(), testPrepositionConverted); } + @Test + public void testConstructPhraseDTOFromPhraseInformationWhenPhraseHasAllFourWords() { + PhraseDTO expectedDTO = PhraseDTO.builder() + .id(PhraseTestConstants.PHRASE1_ID) + .adverb(PhraseTestConstants.ADVERB1_WORD) + .verb(PhraseTestConstants.VERB1_WORD) + .preposition(PhraseTestConstants.PREPOSITION1_WORD) + .noun(PhraseTestConstants.NOUN1_WORD) + .build(); + + when(adverbRepository.findAdverbById(anyLong())).thenReturn(Optional.of(ADVERB1_WORD)); + when(verbRepository.findVerbById(anyLong())).thenReturn(Optional.of(VERB1_WORD)); + when(prepositionRepository.findPrepositionById(anyLong())).thenReturn(Optional.of(PREPOSITION1_WORD)); + when(nounRepository.findNounById(anyLong())).thenReturn(Optional.of(NOUN1_WORD)); + + PhraseDTO actualDTO = phraseServiceImpl.constructPhraseDTOFromPhraseInformation(PHRASE1_ID, ADVERB1_ID, VERB1_ID, PREPOSITION1_ID, NOUN1_ID); + + AssertionsForClassTypes.assertThat(actualDTO).usingRecursiveComparison().isEqualTo(expectedDTO); + + } + + @Test + public void testConstructPhraseDTOFromPhraseInformationWhenPhraseOnlyHasVerbAndNoun() { + PhraseDTO expectedDTO = PhraseDTO.builder() + .id(PhraseTestConstants.PHRASE1_ID) + .adverb("") + .verb(PhraseTestConstants.VERB1_WORD) + .preposition("") + .noun(PhraseTestConstants.NOUN1_WORD) + .build(); + + when(adverbRepository.findAdverbById(anyLong())).thenReturn(Optional.of(Constants.NULL_VALUE_WORD)); + when(verbRepository.findVerbById(anyLong())).thenReturn(Optional.of(VERB1_WORD)); + when(prepositionRepository.findPrepositionById(anyLong())).thenReturn(Optional.of(Constants.NULL_VALUE_WORD)); + when(nounRepository.findNounById(anyLong())).thenReturn(Optional.of(NOUN1_WORD)); + + PhraseDTO actualDTO = phraseServiceImpl.constructPhraseDTOFromPhraseInformation(PHRASE1_ID, Constants.NULL_VALUE_ID, VERB1_ID, Constants.NULL_VALUE_ID, NOUN1_ID); + + AssertionsForClassTypes.assertThat(actualDTO).usingRecursiveComparison().isEqualTo(expectedDTO); + + } + + @Test + public void testConstructAttributesApplyPhraseToUserDTO() { + AttributesApplyPhraseToUserDTO expectedDTO = AttributesApplyPhraseToUserDTO.builder() + .isSuccess(true) + .isApproved(true) + .isRejected(true) + .isInReview(true) + .build(); + + AttributesApplyPhraseToUserDTO actualDTO = phraseService.constructAttributesApplyPhraseToUserDTO(true, true, true, true); + + AssertionsForClassTypes.assertThat(actualDTO).usingRecursiveComparison().isEqualTo(expectedDTO); + + } + }