From 5d6697ab58dbfcf3ace9765ed30cde617620667f Mon Sep 17 00:00:00 2001 From: EnesBaserr Date: Thu, 5 Dec 2024 00:22:01 +0300 Subject: [PATCH] Get Questions and Answers for UserProfile --- .../Config/ModelMapperConfig.java | 7 ++++ .../Controllers/UserController.java | 20 ++++++++--- .../Responses/GetAnswerDtoForProfile.java | 31 +++++++++++++++++ .../Responses/SelfProfileResponseDto.java | 5 +++ .../Repositories/AnswerRepository.java | 7 ++++ .../Repositories/QuestionRepository.java | 2 ++ .../Services/AnswerService.java | 34 +++++++++++++++++++ .../Services/QuestionService.java | 5 +++ 8 files changed, 106 insertions(+), 5 deletions(-) create mode 100644 backend/src/main/java/com/group1/programminglanguagesforum/DTOs/Responses/GetAnswerDtoForProfile.java diff --git a/backend/src/main/java/com/group1/programminglanguagesforum/Config/ModelMapperConfig.java b/backend/src/main/java/com/group1/programminglanguagesforum/Config/ModelMapperConfig.java index 5ca89f3b..4f5f19b5 100644 --- a/backend/src/main/java/com/group1/programminglanguagesforum/Config/ModelMapperConfig.java +++ b/backend/src/main/java/com/group1/programminglanguagesforum/Config/ModelMapperConfig.java @@ -30,6 +30,13 @@ protected void configure() { skip(destination.getFollowing()); } }); + modelMapper.addMappings(new PropertyMap() { + @Override + protected void configure() { + skip(destination.getQuestions()); + skip(destination.getAnswers()); + } + }); modelMapper.addMappings(new PropertyMap () { @Override protected void configure() { diff --git a/backend/src/main/java/com/group1/programminglanguagesforum/Controllers/UserController.java b/backend/src/main/java/com/group1/programminglanguagesforum/Controllers/UserController.java index 0cc0db0b..d15adf83 100644 --- a/backend/src/main/java/com/group1/programminglanguagesforum/Controllers/UserController.java +++ b/backend/src/main/java/com/group1/programminglanguagesforum/Controllers/UserController.java @@ -2,14 +2,12 @@ import com.group1.programminglanguagesforum.Constants.EndpointConstants; import com.group1.programminglanguagesforum.DTOs.Requests.UserProfileUpdateRequestDto; -import com.group1.programminglanguagesforum.DTOs.Responses.ErrorResponse; -import com.group1.programminglanguagesforum.DTOs.Responses.GenericApiResponse; -import com.group1.programminglanguagesforum.DTOs.Responses.SelfProfileResponseDto; -import com.group1.programminglanguagesforum.DTOs.Responses.UserProfileResponseDto; -import com.group1.programminglanguagesforum.DTOs.Responses.UserSummaryDto; +import com.group1.programminglanguagesforum.DTOs.Responses.*; import com.group1.programminglanguagesforum.Entities.User; import com.group1.programminglanguagesforum.Exceptions.UnauthorizedAccessException; import com.group1.programminglanguagesforum.Exceptions.UserNotFoundException; +import com.group1.programminglanguagesforum.Services.AnswerService; +import com.group1.programminglanguagesforum.Services.QuestionService; import com.group1.programminglanguagesforum.Services.UserContextService; import com.group1.programminglanguagesforum.Services.UserService; import com.group1.programminglanguagesforum.Util.ApiResponseBuilder; @@ -33,6 +31,8 @@ public class UserController extends BaseController { private final UserContextService userContextService; private final UserService userService; private final ModelMapper modelMapper; + private final QuestionService questionService; + private final AnswerService answerService; @GetMapping(value = EndpointConstants.UserEndpoints.USER_ME) public ResponseEntity> getUser() { @@ -41,6 +41,16 @@ public ResponseEntity> getUser() { User user = userContextService.getCurrentUser(); SelfProfileResponseDto selfProfileResponseDto = modelMapper.map(user, SelfProfileResponseDto.class); + List questions = questionService.findByAuthorId(user.getId()); + List answers = answerService.findByAnsweredBy(user.getId()); + selfProfileResponseDto.setQuestionCount((long) questions.size()); + selfProfileResponseDto.setQuestions( + questions); + selfProfileResponseDto.setAnswerCount((long) answers.size()); + selfProfileResponseDto.setAnswers( + answers); + + GenericApiResponse response = ApiResponseBuilder.buildSuccessResponse( selfProfileResponseDto.getClass(), "User retrieved successfully", diff --git a/backend/src/main/java/com/group1/programminglanguagesforum/DTOs/Responses/GetAnswerDtoForProfile.java b/backend/src/main/java/com/group1/programminglanguagesforum/DTOs/Responses/GetAnswerDtoForProfile.java new file mode 100644 index 00000000..f01a6beb --- /dev/null +++ b/backend/src/main/java/com/group1/programminglanguagesforum/DTOs/Responses/GetAnswerDtoForProfile.java @@ -0,0 +1,31 @@ +package com.group1.programminglanguagesforum.DTOs.Responses; + +import lombok.*; + +@Builder +@Getter +@Setter +@NoArgsConstructor +@AllArgsConstructor +public class GetAnswerDtoForProfile { + private Long id; + private String content; + private AuthorDto author; + private String createdAt; + private String updatedAt; + private Long upvoteCount; + private Long downvoteCount; + private boolean selfAnswer; + private Integer selfVoted; + @Builder + @Getter + @Setter + @NoArgsConstructor + @AllArgsConstructor + public static class QuesitonInfoForAnswer { + private Long id; + private String title; + } + private QuesitonInfoForAnswer question; + +} diff --git a/backend/src/main/java/com/group1/programminglanguagesforum/DTOs/Responses/SelfProfileResponseDto.java b/backend/src/main/java/com/group1/programminglanguagesforum/DTOs/Responses/SelfProfileResponseDto.java index ab3ac826..2685cc1f 100644 --- a/backend/src/main/java/com/group1/programminglanguagesforum/DTOs/Responses/SelfProfileResponseDto.java +++ b/backend/src/main/java/com/group1/programminglanguagesforum/DTOs/Responses/SelfProfileResponseDto.java @@ -2,6 +2,8 @@ import com.group1.programminglanguagesforum.Entities.ExperienceLevel; import lombok.*; +import java.util.List; + @Builder @NoArgsConstructor @AllArgsConstructor @@ -19,5 +21,8 @@ public class SelfProfileResponseDto { private int followersCount; private int followingCount; private int reputationPoints; + private Long questionCount; private ExperienceLevel experienceLevel; + private List questions; + private List answers; } diff --git a/backend/src/main/java/com/group1/programminglanguagesforum/Repositories/AnswerRepository.java b/backend/src/main/java/com/group1/programminglanguagesforum/Repositories/AnswerRepository.java index 2ab6d5d5..23f04ead 100644 --- a/backend/src/main/java/com/group1/programminglanguagesforum/Repositories/AnswerRepository.java +++ b/backend/src/main/java/com/group1/programminglanguagesforum/Repositories/AnswerRepository.java @@ -1,9 +1,16 @@ package com.group1.programminglanguagesforum.Repositories; import com.group1.programminglanguagesforum.Entities.Answer; +import com.group1.programminglanguagesforum.Entities.User; import org.springframework.data.jpa.repository.JpaRepository; +import org.springframework.data.jpa.repository.Query; import org.springframework.stereotype.Repository; +import java.util.List; + @Repository public interface AnswerRepository extends JpaRepository { + + @Query("SELECT a FROM Answer a WHERE a.answeredBy.id = :userId") + List findByAnsweredBy(Long userId); } diff --git a/backend/src/main/java/com/group1/programminglanguagesforum/Repositories/QuestionRepository.java b/backend/src/main/java/com/group1/programminglanguagesforum/Repositories/QuestionRepository.java index 60ae3421..369c287f 100644 --- a/backend/src/main/java/com/group1/programminglanguagesforum/Repositories/QuestionRepository.java +++ b/backend/src/main/java/com/group1/programminglanguagesforum/Repositories/QuestionRepository.java @@ -28,4 +28,6 @@ Page searchQuestions( @Param("tagIds") List tagIds, @Param("difficulty") DifficultyLevel difficulty, Pageable pageable); + @Query("SELECT q FROM Question q WHERE q.askedBy.id = :author") + List findByAuthorId(@Param("author") Long authorId); } diff --git a/backend/src/main/java/com/group1/programminglanguagesforum/Services/AnswerService.java b/backend/src/main/java/com/group1/programminglanguagesforum/Services/AnswerService.java index da648692..b0de9053 100644 --- a/backend/src/main/java/com/group1/programminglanguagesforum/Services/AnswerService.java +++ b/backend/src/main/java/com/group1/programminglanguagesforum/Services/AnswerService.java @@ -3,6 +3,7 @@ import com.group1.programminglanguagesforum.DTOs.Requests.CreateAnswerRequestDto; import com.group1.programminglanguagesforum.DTOs.Responses.AuthorDto; import com.group1.programminglanguagesforum.DTOs.Responses.CreateAnswerResponseDto; +import com.group1.programminglanguagesforum.DTOs.Responses.GetAnswerDtoForProfile; import com.group1.programminglanguagesforum.DTOs.Responses.GetAnswersResponseDto; import com.group1.programminglanguagesforum.Entities.Answer; import com.group1.programminglanguagesforum.Entities.Question; @@ -23,6 +24,13 @@ public class AnswerService { private final QuestionService questionService; private final VoteRepository voteRepository; + + public java.util.List findByAnsweredBy(Long userId) { + return answerRepository.findByAnsweredBy(userId).stream() + .map(this::mapAnswerToProfileDto) + .toList(); + } + public CreateAnswerResponseDto createAnswer(Long questionId, CreateAnswerRequestDto createAnswerRequestDto) throws UnauthorizedAccessException { User currentUser = userContextService.getCurrentUser(); Question question = questionService.findById(questionId).orElseThrow(); @@ -101,6 +109,32 @@ public GetAnswersResponseDto getAnswersForQuestion(Long questionId) { .build(); } + public GetAnswerDtoForProfile mapAnswerToProfileDto(Answer answer){ + final User currentUser = getCurrentUserOrNull(); + return GetAnswerDtoForProfile.builder() + .id(answer.getId()) + .content(answer.getAnswerBody()) + .author( + AuthorDto.builder() + .id(answer.getAnsweredBy().getId()) + .username(answer.getAnsweredBy().getUsername()) + .reputationPoints(answer.getAnsweredBy().getReputationPoints()) + .name(answer.getAnsweredBy().getFirstName() + " " + answer.getAnsweredBy().getLastName()) + .build() + ) + .createdAt(answer.getCreatedAt()) + .updatedAt(answer.getUpdatedAt()) + .upvoteCount(answer.getUpvoteCount()) + .downvoteCount(answer.getDownvoteCount()) + .selfAnswer(currentUser != null && currentUser.getId().equals(answer.getAnsweredBy().getId())) + .selfVoted(currentUser != null && voteRepository.findByUserAndAnswer(currentUser, answer).isPresent() ? voteRepository.findByUserAndAnswer(currentUser, answer).get().isUpvote()? 1 : -1 : 0) + .question(GetAnswerDtoForProfile.QuesitonInfoForAnswer.builder() + .id(answer.getQuestion().getId()) + .title(answer.getQuestion().getTitle()) + .build()) + .build(); + } + private User getCurrentUserOrNull() { try { return userContextService.getCurrentUser(); diff --git a/backend/src/main/java/com/group1/programminglanguagesforum/Services/QuestionService.java b/backend/src/main/java/com/group1/programminglanguagesforum/Services/QuestionService.java index 4d6e9646..cf9404cf 100644 --- a/backend/src/main/java/com/group1/programminglanguagesforum/Services/QuestionService.java +++ b/backend/src/main/java/com/group1/programminglanguagesforum/Services/QuestionService.java @@ -38,6 +38,11 @@ public class QuestionService { public Optional findById(Long id) { return questionRepository.findById(id); } + public List findByAuthorId(Long authorId) { + return questionRepository.findByAuthorId(authorId).stream() + .map(this::mapToQuestionSummary) + .collect(Collectors.toList()); + } public CreateQuestionResponseDto createQuestion(CreateQuestionRequestDto dto) throws UnauthorizedAccessException {