Skip to content

Commit

Permalink
Chore: Merge prod from dev (#107)
Browse files Browse the repository at this point in the history
* ✨ Feat: 도메인 생성 #31  (#34)

* Feat: User 도메인 생성

* Feat: Member 도메인 생성

* Feat: Team 도메인 생성

* Feat: Scrum 도메인 생성

* Feat: 도메인 상태 관리

* ✨ [Feature/#2] - boiler plate 추가 (#37)

* Feat: dependency 추가 및 정리

* Feat: global dto -> ResponseDto, ExceptionDto 생성

* Feat: ErrorCode 지정, CommonException 생성

* Feat: Global Exception Handler 추가

* Feat: Custom Annotation 생성

* Feat: UserId annotation -> interceptor, resolver 추가

* Feat: annotation 적용

* Feat: response status code 일치해주는 interceptor 생성

* Feat: 문자열 파편화 방지 클래스 생성

* ✨ [Feature/#3] - Spring Security 적용하기 (#39)

* Chore: json dependency 추가

* Feat: authentication filter, exception filter 생성

* Feat: authentication manager, provider 생성

* Feat: CustomUserDetailService 생성

* Feat: login handler 추가

* Feat: logout handler 추가

* Feat: exception handler 추가

* Feat: spring security info 생성

* Feat: 쿠키 유틸 생성

* Feat: 헤더 유틸 생성

* Feat: jwt util 생성

* Feat: Security Config 설정

* Feat: Token Dto 생성

* Feat: user repository -> security용 조회 로직 생성

* Feat: Passowrd Encoder 등록

* Feat: Spring Security 등록

* fix: Credential 업데이트

* ✨ [Feat/#3] - Spring Security api test (#43)

* Chore: json dependency 추가

* Feat: authentication filter, exception filter 생성

* Feat: authentication manager, provider 생성

* Feat: CustomUserDetailService 생성

* Feat: login handler 추가

* Feat: logout handler 추가

* Feat: exception handler 추가

* Feat: spring security info 생성

* Feat: 쿠키 유틸 생성

* Feat: 헤더 유틸 생성

* Feat: jwt util 생성

* Feat: Security Config 설정

* Feat: Token Dto 생성

* Feat: user repository -> security용 조회 로직 생성

* Feat: Passowrd Encoder 등록

* Feat: Spring Security 등록

* Chore: api path 수정

* Feat: refresh token update 추가

* Chore: api path 수정

* Chore: response json 수정

* Feat: 회원가입, reissue api 생성

* ✨ [ Feature /#4 ] - QuestionList API 구현 (#45)

* feat: QuestionList API 구현

* feat: TeamRepository 생성

* ✨ [Feature/#5] - 웹과 연동하기 discord action 구현 (#46)

* Chore: discord token 추가

* Chore: jda dependency 추가

* Feat: builder 추가, 칼럼 수정

* Feat: leader 추가 로직 생성

* Feat: user 조회 로직 추가

* Feat: 생성 로직 추가

* Feat: jda 적용, slash command 추가

* Feat: 웹과 연동하기 명령어 액션 추가

* Chore: discord token 추가 (#47)

* Chore: discord token 추가 (#48)

* 🐛 [Fix/#6] - user, team 예외처리 추가 (#50)

* Chore: discord token 추가

* Feat: 팀 구분용 칼럼 추가, builder 수정

* Feat: 조회 로직 추가

* Chore: 주석 추가, 약간의 최적화

* Feat: Team 유일성 부여

* ✨ [Feature/#7] - discord slash command, 질문하기 (#52)

* Chore: discord token 추가

* Feat: Question column 추가

* Feat: code 관련 조회 로직 추가

* Chore: 서비스 단 조회 로직 추가

* Feat: generate code 로직 생성

* Feat: 질문하기 slash command 추가

* Feat: slash command action 추가

* 🐛  [Fix/#4] - 팀 작업 기록 페이지 API 구현 (#55)

* feat: QuestionList API 구현

* feat: TeamRepository 생성

* fix: questionDtoList의 길이를 재는 것으로 수정

* feat: 팀 멤버 목록 조회 API 구현

* fix: 멤버가 존재하는지 예외처리

* refactor: 메소드 이름 수정 findByReceiverAndStatus => findAllByReceiverAndStatus

* feat: 팀원들의 작업 목록 서비스, 팀 작업 척도 서비스 구현

* refactor: Repository의 메소드 수정에 따른 메소드 수정

* feat: 팀 작업 척도 서비스 구현

* ✨ [Feature/#9] - discord '답변하기' command 생성 (#57)

* Chore: discord token 추가

* Feat: builder 추가

* Feat: Answer Repository 생성

* Feat: question status update 로직 생성

* Feat: Answer 생성 로직 추가

* Feat: question 조회, 수정 서비스 로직 추가

* Feat: NOT_FOUND_QUESTION error 추가

* Feat: 답변하기 slash commnad 추가

* Feat: slash command action 추가

* ✨ [Feature/#10] - discord 업무 시간 파악 (#59)

* Chore: discord token 추가

* Feat: builder 추가

* Feat: errorcode 추가

* Feat: 업무 중인 작업 조회 로직 추가

* Feat: Scrum 상태에 따른 조회 추가

* Feat: DB 조회 로직 적용

* Feat: 업무 시작 하기 slash command 추가

* Feat: 업무 시작 답변 action 추가

* ✨ [Feature/#8] - 질문 목록 페이지 API 구현 (#60)

* feat: 전체 프로젝트 목록 API

* feat: 질문 남기기 API 구현

* feat: Member 연결

* feat: 답변 남기기 API 구현

* feat: 질문 목록(받은 질문) API 구현

* feat: 질문 목록(보낸 질문) API 구현

* fix: 사용하지 않는 라이브러리 삭제

* 🐛 [!HOTFIX] - 오류 수정 (#61)

* Chore: discord token 추가

* Hotfix: api path 수정

* Fix: db 구조 변경에 따른 builder 수정

* Fix: db 구조 변경에 따른 builder 수정

* ✨ [Feature/#12] - discord command 업무 종료 (#64)

* Chore: discord token 추가

* Hotfix: api path 수정

* Fix: db 구조 변경에 따른 builder 수정

* Fix: db 구조 변경에 따른 builder 수정

* Chore: member 업무 기본값 추가

* Chore: error code 추가

* Feat: 누적 업무 시간, 업무 종료시 데이터 업데이트 로직 추가

* Chore: 조회 로직 추가

* Feat: 업무 시간 관련 update 서비스 로직 생성

* Feat: 업무 종료 slash command 추가

* Feat: 업무 종료시 이벤트 처리 로직 생성

* ✨ [Feature/#11] - 작업 기록 API 구현 (#65)

* feat: 스크럼 타임라인 API 구현

* fix: 필요없는 코드 삭제

* fix: 예외처리 코드 오류 수정

* feat: 프로젝트 팀 정보(상세) API 구현

* feat: 팀 권한 조회 API 구현

* feat: 권한 수정 API 구현

* fix: 프로젝트 Public 여부를 Team에서 Member에서 관리 (#67)

* ✨ [Feature] - 나의 대시보드 API #13 (#69)

* fix: 프로젝트 Public 여부를 Team에서 Member에서 관리

* feat: 프로필 정보 조회 API 구현

* feat: 프로필 정보 수정 API 구현

* fix: 프로젝트 팀 정보(상세)의 Dto 이름 수정

* feat: 참여 프로젝트 목록 API 구현

* feat: 프로젝트 공개 여부 전환 API 구현

* feat: 개인 프로젝트 기여도 API 구현

* ✨ [Feature/#14] - discord command 스크럼 종료 (#71)

* Chore: discord token 추가

* Hotfix: api path 수정

* Fix: db 구조 변경에 따른 builder 수정

* Fix: db 구조 변경에 따른 builder 수정

* Feat: gpt api용 request, response dto 생성

* Feat: 스크럼 종료 시 데이터 업데이트 로직 작성

* Feat: using gpt api 서비스 로직 작성

* Chore: 코드 수정

* Feat: slash command 추가

* Feat: slash command action 추가

* ✨ [Feature/#15] - 동료 평가 API 구현 (#72)

* feat: 동료 평가 조회 API 구현

* fix: 동료 평가 조회 로직 수정

* feat: 동료 평가 작성 API 구현

* ✨ [Feature/#17] - discord command 프로젝트 종료 (#75)

* Chore: discord token 추가

* Hotfix: api path 수정

* Fix: db 구조 변경에 따른 builder 수정

* Fix: db 구조 변경에 따른 builder 수정

* Feat: 프로젝트 상태 변경 로직 추가

* Feat: 프로젝트 종료, slash command 생성

* Feat: 프로젝트 종료, event 처리

* ✨ [Feature/#18] - 팀 관리 API 구현 (#76)

* feat: 업무 시간 상세 조회 API 구현

* feat: 업무 시간 상세 수정 API 구현

* ✨ [Feature/#19] - discord command 서버 최신화 적용 (#79)

* Chore: discord token 추가

* Hotfix: api path 수정

* Fix: db 구조 변경에 따른 builder 수정

* Fix: db 구조 변경에 따른 builder 수정

* Feat: Team information 최신화 로직 추가

* Feat: 서버 최신화 slash command 추가

* Feat: 서버 최신화 slash command action 추가

* ✨ [Feature/#20] - 작업 척도 API (#80)

* fix: uri path 수정

* feat: 개인 작업 척도 API 구현

* fix: uri 경로 수정

* feat: 개인 전체 프로젝트 작업 척도 API 구현

* 🎨 [Refactor/#21] - discord command 질문 & 답변하기 완료  (#83)

* Chore: discord token 추가

* Hotfix: api path 수정

* Fix: db 구조 변경에 따른 builder 수정

* Fix: db 구조 변경에 따른 builder 수정

* Refactor: Quetion 저장 로직 변경

* Refactor: 예외처리 추가, 로직 변경점 적용

* 🎨 [Refactor/#22] - discord command 업무시작 & 업무종료  (#85)

* Chore: discord token 추가

* Hotfix: api path 수정

* Fix: db 구조 변경에 따른 builder 수정

* Fix: db 구조 변경에 따른 builder 수정

* Refactor: discord bot 예외처리 추가

* Refactor: 코드 리팩토링, 변경점 적용

* feat: 프로젝트 R&R 작성 및 수정 (#87)

* chore: 크레덴셜 수정 (#89)

* ✨ [Feature/#23] discord command '파트 입력' (#91)

* Chore: discord token 추가

* Hotfix: api path 수정

* Fix: db 구조 변경에 따른 builder 수정

* Fix: db 구조 변경에 따른 builder 수정

* Feat: EPart 매칭 로직 작성

* Feat: 팀원의 파트를 입력하는 로직 생성

* Feat: slash command 추가

* Feat: action 추가, 예외처리 추가

* 🐛 [FIX/#26] - 테스트에서 확인된 오류 수정 (#93)

* chore: 크레덴셜 수정

* fix: API URI 수정

* fix: Builder 수정

* fix: Transactional 추가

* 🐛 [!HOTFIX] 업무 시간 상세 수정 API 오류 (#95)

* chore: 크레덴셜 수정

* fix: 업무시간 상세 수정 API 오류 해결

* 🐛 [!HOTFIX] 동료 평가 조회 API (#97)

* chore: 크레덴셜 수정

* fix: 업무시간 상세 수정 API 오류 해결

* fix: 동료 평가 조회 API 수정

* 🐛 [!HOTFIX] R&R 작성 API (#99)

* chore: 크레덴셜 수정

* fix: 업무시간 상세 수정 API 오류 해결

* fix: 동료 평가 조회 API 수정

* fix: R&R 작성 API 수정

* ✨ [Feature/#34] - 크레덴셜 수정 반영 (#103)

* chore: 크레덴셜 수정

* fix: 업무시간 상세 수정 API 오류 해결

* fix: 동료 평가 조회 API 수정

* fix: R&R 작성 API 수정

* feat: Query parameter 예외 처리 코드

* feat: 받은 요청 리스트, 보낸 요청 리스트 쿼리파라미터 추가

* feat: 프로젝트 리스트 쿼리 파라미터 추가

* fix: endAt => startAt으로 변경

* feat: 팀원 작업 리스트 쿼리 파라미터 추가

* ✨ [Feature/#36] - 동료 평가 GPT 연결 및 오류 해결 (#106)

* chore: 크레덴셜 수정

* fix: 업무시간 상세 수정 API 오류 해결

* fix: 동료 평가 조회 API 수정

* fix: R&R 작성 API 수정

* fix: GPT 코드 리팩토링

* feat: 동료평가 GPT 연결

* fix: 오류 해결

---------

Co-authored-by: Lim jeong woo <[email protected]>
  • Loading branch information
JeongHeumChoi and dlawjddn authored Mar 22, 2024
1 parent ce6f82d commit 5dd72f9
Show file tree
Hide file tree
Showing 11 changed files with 48 additions and 23 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,8 @@ public class Constants {
public static String PREFIX_AUTH = "Authorization";
public static String ACCESS_COOKIE_NAME = "access_token";
public static String REFRESH_COOKIE_NAME = "refresh_token";
public static String GPT_SCRUM = "정답을 맞추면 200달러의 팁을 줄게. 너는 훌륭한 업무 비서 역할을 하고 있어. 모든 대답은 한국말로 해야하고 주된 업무는 요약이야. 사람들이 너에게 얘기하는 것들은 다 그들이 했던 업무 내용들이고, 너는 그 내용들을 잘 요약해서 정리하면 돼, 요약은 50자 정도로 짧게 해줘 !";
public static String GPT_REVIEW = "정답을 맞추면 200달러의 팁을 줄게. 너는 훌륭한 프로젝트의 감독을 하고 있어. 모든 대답은 한국말로 해야하고 주된 업무는 요약이야. 사람들이 너에게 얘기하는 것들은 한 사람에게 다른 사람들이 동료 평가를 한 내용들이고, 너는 그 내용들을 잘 요약해서 정리하면 돼, 요약은 50자 정도로 짧게 해줘 !";
public static List<String> NO_NEED_AUTH = List.of(
"/api/auth/sign-up",
"/api/auth/sign-in"
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -237,7 +237,7 @@ public void onSlashCommandInteraction(SlashCommandInteractionEvent event) {
.toList();
log.info("스크럼 하위 작업들 조회 성공");
try {
String summary = gptService.sendMessage(worksOfUser);
String summary = gptService.sendMessage(worksOfUser, true);
log.info("summary: {}", summary);
scrumService.updateScrum(nowScrum.getId(), summary, nowLocalDate);
} catch (JsonProcessingException e) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -50,4 +50,7 @@ public void toggleIsPublic() {
public void updateRetrospection(String retrospection) {
this.retrospection = retrospection;
}
public void updatePeerReviewSummary(String peerReviewSummary) {
this.peerReviewSummary = peerReviewSummary;
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@
public class GptRequest {
private final String model = "gpt-3.5-turbo";
private List<Message> messages;
private final int max_tokens = 50;
private final int max_tokens = 256;
private double temperature;
@Builder
public GptRequest(List<Message> messages, double temperature) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -12,16 +12,10 @@ public Message(String role, String content) {
this.role = role;
this.content = content;
}
public static Message makeFirstMessage(){
public static Message makeContent(String role, String content){
return Message.builder()
.role("system")
.content("너는 훌륭한 업무 비서 역할을 하고 있어. 모든 대답은 한국말로 해야하고 주된 업무는 요약이야. 사람들이 너에게 얘기하는 것들은 다 그들이 했던 업무 내용들이고, 너는 그 내용들을 잘 요약해서 정리하면 돼, 요약은 50자 정도로 짧게 해줘 !")
.build();
}
public static Message makeUserWork(String work){
return Message.builder()
.role("user")
.content(work)
.role(role)
.content(content)
.build();
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -5,10 +5,12 @@
import org.springframework.data.jpa.repository.JpaRepository;
import org.springframework.stereotype.Repository;

import java.util.List;
import java.util.Optional;

@Repository
public interface ReviewRepository extends JpaRepository<Review, Long> {
Optional<Review> findBySender(Member sender);
Optional<Review> findBySenderAndReceiver(Member sender, Member receiver);
List<Review> findAllByReceiver(Member receiver);
Boolean existsBySender(Member sender);
}
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@

public interface ScrumRepository extends JpaRepository<Scrum, Long> {
Optional<Scrum> findByWorkerAndStatus(Member worker, EScrumStatus status);
List<Scrum> findAllByWorkerOrderByEndAtDesc(Member worker);
List<Scrum> findAllByWorkerAndStatusOrderByEndAtDesc(Member worker, EScrumStatus status);
@Modifying(clearAutomatically = true)
@Query("update Scrum s set s.endAt = :end, s.status = :status, s.summary = :summary where s.id = :scrumId")
void updateScrumAfterOver(Long scrumId, String summary, EScrumStatus status, LocalDate end);
Expand Down
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
package goormthon.team28.startup_valley.service;

import com.fasterxml.jackson.core.JsonProcessingException;
import com.fasterxml.jackson.databind.ObjectMapper;
import goormthon.team28.startup_valley.constants.Constants;
import goormthon.team28.startup_valley.dto.gpt.request.GptRequest;
import goormthon.team28.startup_valley.dto.gpt.request.Message;
import goormthon.team28.startup_valley.dto.gpt.response.GptResponse;
Expand All @@ -23,13 +23,13 @@ public class GptService {
@Value("${gpt.token}")
private String gptSecretKey;
private RestTemplate restTemplate = new RestTemplate();
public String sendMessage(List<String> works) throws JsonProcessingException {
public String sendMessage(List<String> works, Boolean checkPoint) throws JsonProcessingException {
HttpHeaders headers = new HttpHeaders();
headers.setContentType(MediaType.APPLICATION_JSON);
headers.setBearerAuth(gptSecretKey);
log.info("gpt 헤더 설정 완료");

HttpEntity httpEntity = new HttpEntity(makeRequest(works), headers);
HttpEntity httpEntity = new HttpEntity(makeRequest(works, checkPoint), headers);
log.info("gpt http entity 생성 완료");

GptResponse gptResponse = restTemplate.exchange(
Expand All @@ -42,10 +42,13 @@ public String sendMessage(List<String> works) throws JsonProcessingException {

return gptResponse.getChoices().get(0).getMessage().getContent();
}
private GptRequest makeRequest(List<String> works){
private GptRequest makeRequest(List<String> works, boolean checkPoint){
List<Message> messages = new ArrayList<>();
messages.add(Message.makeFirstMessage());
works.forEach(work -> messages.add(Message.makeUserWork(work)));
if (checkPoint)
messages.add(Message.makeContent("system", Constants.GPT_SCRUM));
else
messages.add(Message.makeContent("system", Constants.GPT_REVIEW));
works.forEach(work -> messages.add(Message.makeContent("user", work)));
log.info("message size = work's size + 1 = {}", messages.size());
return GptRequest.builder()
.messages(messages)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@
import goormthon.team28.startup_valley.dto.response.MemberListDto;
import goormthon.team28.startup_valley.dto.response.ScrumContributionDto;
import goormthon.team28.startup_valley.dto.type.EPart;
import goormthon.team28.startup_valley.dto.type.EScrumStatus;
import goormthon.team28.startup_valley.exception.CommonException;
import goormthon.team28.startup_valley.exception.ErrorCode;
import goormthon.team28.startup_valley.repository.MemberRepository;
Expand Down Expand Up @@ -104,7 +105,8 @@ public MemberContributionDto retrieveContributionMember(Long userId, Long member
// 조회하려는 멤버의 기여도가 비공개면서 조회하려는 멤버와 로그인 유저가 다른 경우 조회 불가능 처리
if (!targetMember.getUser().equals(currentUser) && !targetMember.getIsPublic())
throw new CommonException(ErrorCode.INVALID_CHECK_TEAM_CONTRIBUTION);
List<Scrum> scrumList = scrumRepository.findAllByWorkerOrderByEndAtDesc(targetMember);
List<Scrum> scrumList = scrumRepository
.findAllByWorkerAndStatusOrderByEndAtDesc(targetMember, EScrumStatus.FINISH);
List<ScrumContributionDto> scrumContributionDtoList = scrumList.stream()
.map(scrum -> ScrumContributionDto.of(
scrum.getId(),
Expand Down
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
package goormthon.team28.startup_valley.service;

import com.fasterxml.jackson.core.JsonProcessingException;
import goormthon.team28.startup_valley.domain.Member;
import goormthon.team28.startup_valley.domain.Review;
import goormthon.team28.startup_valley.domain.Team;
Expand Down Expand Up @@ -29,6 +30,7 @@ public class ReviewService {
private final UserRepository userRepository;
private final MemberRepository memberRepository;
private final TeamRepository teamRepository;
private final GptService gptService;

public PeerReviewListDto listPeerReview(Long userId, Long teamsId) {

Expand All @@ -47,7 +49,7 @@ public PeerReviewListDto listPeerReview(Long userId, Long teamsId) {
member.getUser().getNickname(),
member.getUser().getProfileImage(),
member.getPart(),
reviewRepository.findBySender(currentMember)
reviewRepository.findBySenderAndReceiver(currentMember, member)
.map(Review::getContent)
.orElse(null)
))
Expand Down Expand Up @@ -86,8 +88,24 @@ public Boolean postPeerReview(Long userId, Long teamsId, ReviewCreateDto reviewC
.build();
reviewRepository.save(review);

// 추후에 GPT API 추가
List<Member> teamMemberList = memberRepository.findAllByTeam(team);
List<Review> reviewList = reviewRepository.findAllByReceiver(targetMember);
// 자신을 제외한 모든 팀원들에게 동료 평가를 받은 경우
if (teamMemberList.size() == reviewList.size() + 1) {
List<String> reviewStringList = reviewList.stream()
.map(Review::getContent)
.toList();
String peerReviewSummary = null;
try {
peerReviewSummary = gptService.sendMessage(reviewStringList, false);
} catch (JsonProcessingException e) {
throw new CommonException(ErrorCode.INTERNAL_SERVER_ERROR);
} finally {
targetMember.updatePeerReviewSummary(peerReviewSummary);
}
}

return Boolean.TRUE;
}

}
Original file line number Diff line number Diff line change
Expand Up @@ -64,7 +64,8 @@ public ScrumListDto listScrum(Long userId, Long membersId) {

List<ScrumDto> scrumDtoList = new ArrayList<>();
for (Member tempMember : memberList) {
List<Scrum> scrumList = scrumRepository.findAllByWorkerOrderByEndAtDesc(tempMember);
List<Scrum> scrumList = scrumRepository
.findAllByWorkerAndStatusOrderByEndAtDesc(tempMember, EScrumStatus.FINISH);
scrumDtoList.addAll(
scrumList.stream()
.map(scrum -> ScrumDto.of(
Expand Down

0 comments on commit 5dd72f9

Please sign in to comment.