Skip to content

Commit

Permalink
Merge pull request #58 from potenday-project/develop
Browse files Browse the repository at this point in the history
Develop
  • Loading branch information
oU-Ua authored Jan 5, 2024
2 parents 8556824 + 433bb27 commit e022cc7
Show file tree
Hide file tree
Showing 16 changed files with 168 additions and 76 deletions.
2 changes: 1 addition & 1 deletion build.gradle
Original file line number Diff line number Diff line change
Expand Up @@ -44,7 +44,7 @@ dependencies {
implementation 'org.apache.httpcomponents:httpclient:4.5.13'
implementation 'org.apache.httpcomponents:httpmime:4.5.13'
implementation 'com.google.code.gson:gson:2.8.9'

implementation 'org.springdoc:springdoc-openapi-starter-webmvc-ui:2.0.2'
}

tasks.named('test') {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -38,4 +38,4 @@ public ResponseEntity<List<CalendarAndTodoAllByRoleDto>> calendarTodoAll(
return ResponseEntity.ok(calendarService.calendarAndtodoAll(projectId, localDate));
}

}
}
3 changes: 0 additions & 3 deletions src/main/java/mvc/promiseme/calendar/entity/Calendar.java
Original file line number Diff line number Diff line change
Expand Up @@ -2,14 +2,11 @@

import jakarta.persistence.*;
import lombok.*;

import mvc.promiseme.project.entity.Member;
import mvc.promiseme.project.entity.Project;
import mvc.promiseme.project.entity.Role;
import mvc.promiseme.todo.entity.Todo;

import java.time.LocalDate;
import java.time.LocalDateTime;
import java.util.ArrayList;
import java.util.List;

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -10,8 +10,9 @@
import java.util.List;
import java.util.Optional;


public interface CalendarRepository extends JpaRepository<Calendar, Long> {
// @Query("SELECT NEW mvc.promiseme.calendar.dto.CalendarResponseDTO(c.content, c.startDate, c.finishDate, u.nickname) from Calendar c join c.member m join m.users u where c.project = :project")
// List<CalendarResponseDTO> findByProject(Project project);
List<Calendar> findByProjectAndStartDateLessThanEqualAndFinishDateGreaterThanEqual(Project project, LocalDate startDate, LocalDate finishDate);
List<Calendar> findByProjectAndStartDateLessThanEqualAndFinishDateGreaterThanEqual(Project project, LocalDate startDate, LocalDate finishDate);
}
7 changes: 6 additions & 1 deletion src/main/java/mvc/promiseme/common/exception/ErrorCode.java
Original file line number Diff line number Diff line change
Expand Up @@ -16,8 +16,13 @@ public enum ErrorCode implements EnumModel{
INVALID_User_Password(401, "U002", "비밀번호가 일치하지 않습니다."),

//중복여부 체크
DUPLICATE_USER(400,"D001","중복된 이메일입니다.");
DUPLICATE_USER(400,"D001","중복된 이메일입니다."),

//조회시 발생 가능 예외
RPOJECT_NOT_FOUND(401,"P001","프로젝트를 찾을 수 없습니다."),
CATEGORY_SERVER_ERROR(500,"P002","카테고리 불러오는 것을 실패하였습니다."),
MEMBER_NOT_FOUND(401,"M001","해당하는 멤버를 찾을 수 없습니다."),
CALENDER_NOT_FOUND(401,"C001","해당하는 일정을 찾을 수 없습니다.");

private int status;
private String code;
Expand Down
26 changes: 26 additions & 0 deletions src/main/java/mvc/promiseme/config/SwaggerConfig.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
package mvc.promiseme.config;
import io.swagger.v3.oas.annotations.OpenAPIDefinition;
import io.swagger.v3.oas.annotations.info.Info;
import lombok.RequiredArgsConstructor;
import org.springdoc.core.models.GroupedOpenApi;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;

@OpenAPIDefinition(
info = @Info(title = "PromiseMe",
description = "약속해줘 api명세",
version = "v1"))
@RequiredArgsConstructor
@Configuration
public class SwaggerConfig {

@Bean
public GroupedOpenApi PromiseMeAPI() {
String[] paths = {"/**"};

return GroupedOpenApi.builder()
.group("PromiseMe v1")
.pathsToMatch(paths)
.build();
}
}
Original file line number Diff line number Diff line change
@@ -1,7 +1,6 @@
package mvc.promiseme.meeting.dto;

import lombok.*;
import org.springframework.web.bind.annotation.RequestParam;
@NoArgsConstructor
@AllArgsConstructor
@Getter
Expand Down
Original file line number Diff line number Diff line change
@@ -1,8 +1,16 @@
package mvc.promiseme.project.controller;

import io.swagger.v3.oas.annotations.Operation;
import io.swagger.v3.oas.annotations.Parameter;
import io.swagger.v3.oas.annotations.media.Content;
import io.swagger.v3.oas.annotations.media.Schema;
import io.swagger.v3.oas.annotations.responses.ApiResponse;
import io.swagger.v3.oas.annotations.responses.ApiResponses;
import io.swagger.v3.oas.annotations.tags.Tag;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import mvc.promiseme.calendar.dto.CalendarResponseDTO;
import mvc.promiseme.common.exception.ErrorCode;
import mvc.promiseme.common.exception.ErrorResponse;
import mvc.promiseme.project.dto.ProjectRequestDTO;
import mvc.promiseme.project.dto.ProjectResponseDTO;
import mvc.promiseme.project.dto.RecommendMemberRequestDTO;
Expand All @@ -18,24 +26,45 @@

@Slf4j
@RestController
@Tag(name = "Project", description = "프로젝트 API")
@RequiredArgsConstructor
@CrossOrigin(origins ="*", allowedHeaders = "*")
@RequestMapping("/project")
public class ProjectController {
private final ProjectService projectService;
private final RecommendService recommendService;
@GetMapping("/")
public ResponseEntity<List<ProjectResponseDTO>>calendarAll(@RequestParam("userId") Long userId){
@Operation(summary = "전체 프로젝트조회", description = "user가 포함된 모든 프로젝트를 조회")
@ApiResponses({
@ApiResponse(responseCode = "200", description = "성공", content = @Content(schema = @Schema(implementation = ProjectResponseDTO.class))),
@ApiResponse(responseCode = "401", description = "프로젝트를 찾을 수 없습니다.", content = @Content(schema = @Schema(implementation = ErrorResponse.class)))

})
public ResponseEntity<List<ProjectResponseDTO>> projectAll(@Parameter(description = "유저ID", required = true) @RequestParam("userId") Long userId){
return ResponseEntity.ok(projectService.projectAll(userId));

}
@GetMapping("/category")
@Operation(summary = "상위 카테고리 조회", description = "현재 존재하는 프로젝트 카테고리중 많은 순으로 6개 조회")
@ApiResponses({
@ApiResponse(responseCode = "200", description = "성공", content = @Content(schema = @Schema(implementation = List.class))),
@ApiResponse(responseCode = "501", description = "존재하는 프로젝트가 없어서 카테고리를 가져올 수 없습니다.", content = @Content(schema = @Schema(implementation = ErrorResponse.class)))

})
public ResponseEntity<List<String>> categoryRanking(){
// if(projectService.categoryRanking()==null)
// return ResponseEntity.status(ErrorCode.CATEGORY_SERVER_ERROR.getStatus()).body(ErrorCode.CATEGORY_SERVER_ERROR.getMessage());

return ResponseEntity.ok(projectService.categoryRanking());

}

@Operation(summary = "프로젝트 생성", description = "새로운 프로젝트 생성")
@ApiResponses({
@ApiResponse(responseCode = "200", description = "성공", content = @Content(schema = @Schema(implementation = Map.class))),
@ApiResponse(responseCode = "501", description = "프로젝트 생성 중 알 수 없는 에러가 발생하였습니다.", content = @Content(schema = @Schema(implementation = ErrorResponse.class)))

})
@PostMapping("/create")
public ResponseEntity<Map<String, Long>> insert(@RequestBody ProjectRequestDTO projectRequestDTO){
Map<String, Long> result = new HashMap<>();
Expand All @@ -44,25 +73,49 @@ public ResponseEntity<Map<String, Long>> insert(@RequestBody ProjectRequestDTO p
result.put("projectId",projectService.insert(projectRequestDTO));
return ResponseEntity.ok(result);
}
@Operation(summary = "프로젝트 진행척도", description = "현재 프로젝트가 얼마나 진행되었는지 퍼센트로 확인할 수 있다.")
@ApiResponses({
@ApiResponse(responseCode = "200", description = "성공", content = @Content(schema = @Schema(implementation = Map.class))),
@ApiResponse(responseCode = "401", description = "해당 프로젝트를 찾을 수 없습니다.", content = @Content(schema = @Schema(implementation = ErrorResponse.class)))

})
@GetMapping("/progress")
public ResponseEntity<Map<String, Integer>> progress(@RequestParam("projectId")Long projectId){
Map<String,Integer> progressResult = new HashMap<>();
progressResult.put("progress", projectService.progress(projectId));
return ResponseEntity.ok(progressResult);
}
@Operation(summary = "프로젝트 디데이", description = "해당하는 프로젝트의 디데이를 계산한다.")
@ApiResponses({
@ApiResponse(responseCode = "200", description = "성공", content = @Content(schema = @Schema(implementation = Map.class))),
@ApiResponse(responseCode = "401", description = "프로젝트를 찾을 수 없습니다.", content = @Content(schema = @Schema(implementation = ErrorResponse.class)))

})
@GetMapping("/dday")
public ResponseEntity <Map<String,Integer>> dday(@RequestParam("projectId") Long projectId){
Map<String,Integer> ddayResult = new HashMap<>();
ddayResult.put("Dday", projectService.dday(projectId));

return ResponseEntity.ok(ddayResult);
}

@Operation(summary = "멤버 추천", description = "입력한 값에 맞는 프로젝트 역할과 할일을 보여준다.")
@ApiResponses({
@ApiResponse(responseCode = "200", description = "성공", content = @Content(schema = @Schema(implementation = Map.class))),
@ApiResponse(responseCode = "401", description = "프로젝트를 찾을 수 없습니다.", content = @Content(schema = @Schema(implementation = ErrorResponse.class)))

})
@PostMapping("/recommend/member")
public ResponseEntity<Map<String,String>> recommendMember(@RequestBody RecommendMemberRequestDTO recommendMemberRequestDTO){
return ResponseEntity.ok(recommendService.recommendMember(recommendMemberRequestDTO));
}

@Operation(summary = "프로젝트 일정 추천", description = "입력한 값에 맞는 프로젝트 역할과 할일을 보여준다.")
@ApiResponses({
@ApiResponse(responseCode = "200", description = "성공", content = @Content(schema = @Schema(implementation = ProjectResponseDTO.class))),
@ApiResponse(responseCode = "401", description = "프로젝트를 찾을 수 없습니다.", content = @Content(schema = @Schema(implementation = ErrorResponse.class)))

})
@PostMapping("/recommend/schedule")
public ResponseEntity<List<Map<String, String>>> recommendSchedule(@RequestBody RecommendScheduleRequestDTO recommendScheduleRequestDTO){
return ResponseEntity.ok(recommendService.recommendSchedule(recommendScheduleRequestDTO));
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -6,8 +6,8 @@
import mvc.promiseme.users.entity.Users;
import org.springframework.data.jpa.repository.JpaRepository;

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

public interface MemberRepository extends JpaRepository<Member, Long> {
Optional<Member> findByUsersAndProject(Users users, Project project);
Expand Down
Original file line number Diff line number Diff line change
@@ -1,7 +1,5 @@
package mvc.promiseme.project.repository;

import mvc.promiseme.project.dto.ProjectResponseDTO;
import mvc.promiseme.project.entity.Member;
import mvc.promiseme.project.entity.Project;
import org.springframework.data.jpa.repository.JpaRepository;
import org.springframework.data.jpa.repository.Query;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,6 @@
import lombok.RequiredArgsConstructor;
import mvc.promiseme.common.exception.ErrorCode;
import mvc.promiseme.common.exception.UserException;
import mvc.promiseme.project.dto.MemberDTO;
import mvc.promiseme.project.dto.MemberRequestDTO;
import mvc.promiseme.project.dto.ProjectRequestDTO;
import mvc.promiseme.project.dto.ProjectResponseDTO;
Expand All @@ -14,15 +13,16 @@
import mvc.promiseme.project.repository.MemberRepository;
import mvc.promiseme.project.repository.ProjectRepository;
import mvc.promiseme.project.repository.RoleRepository;
import mvc.promiseme.todo.dto.TodoRequestDTO;
import mvc.promiseme.todo.entity.Todo;
import mvc.promiseme.todo.repository.TodoRepository;
import mvc.promiseme.users.entity.Users;
import mvc.promiseme.users.repository.UserRepository;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.*;
import java.util.ArrayList;
import java.util.List;
import java.util.NoSuchElementException;

@Service
@RequiredArgsConstructor
Expand Down
Original file line number Diff line number Diff line change
@@ -1,9 +1,7 @@
package mvc.promiseme.project.service;

import lombok.RequiredArgsConstructor;
import mvc.promiseme.project.dto.RecommendMemberRequestDTO;
import mvc.promiseme.project.dto.RecommendScheduleRequestDTO;
import org.springframework.stereotype.Service;

import java.util.List;
import java.util.Map;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -32,9 +32,7 @@ public class RecommendServiceImpl implements RecommendService{
private final RoleRepository roleRepository;
@Override
public Map<String, String> recommendMember(RecommendMemberRequestDTO recommendMemberRequestDTO) {
String url = clovaStudioRecommend.getUrl();
String apiKeyClovaStudio = clovaStudioRecommend.getApiKeyClovaStudio();

String requestId = clovaStudioRecommend.getRequestMemberId();

List<Message> messages = new ArrayList<>();

Expand All @@ -52,27 +50,7 @@ public Map<String, String> recommendMember(RecommendMemberRequestDTO recommendMe

Message requestMessage = new Message("user", "나는" + recommendMemberRequestDTO.getCategory() + "프로젝트를 진행할예정입니다. 시작날짜는" + recommendMemberRequestDTO.getStart() + ", 마감날짜는" + recommendMemberRequestDTO.getDeadline() + "입니다. 이때 필요한 팀의 구성원 역할을 알려주세요. 다른 말 필요없이\n\"역할\" : \"역할이 해야할일\"\n로만 대답해주세요. 다른 말 없이 역할과 역할이 해야할일만 작성해주세요.");
messages.add(requestMessage);

HttpHeaders headers = new HttpHeaders();
headers.set("X-NCP-CLOVASTUDIO-API-KEY", apiKeyClovaStudio);
headers.set("X-NCP-APIGW-API-KEY", clovaStudioRecommend.getApiGateWayKey());
headers.set("X-NCP-CLOVASTUDIO-REQUEST-ID", clovaStudioRecommend.getRequestMemberId());
headers.set("Content-Type", "application/json");

Map<String, Object> requestBody = new HashMap<>();
requestBody.put("messages", messages);
requestBody.put("topP", 0.8);
requestBody.put("topK", 0);
requestBody.put("maxTokens", 256);
requestBody.put("temperature", 0.5);
requestBody.put("repeatPenalty", 5.0);
requestBody.put("includeAiFilters", "True");

HttpEntity<Map<String, Object>> requestEntity = new HttpEntity<>(requestBody, headers);

RestTemplate restTemplate = new RestTemplate();
ResponseEntity<String> responseEntity = restTemplate.exchange(url, HttpMethod.POST, requestEntity, String.class);

ResponseEntity<String> responseEntity = fetchClovaAPI(messages,requestId);
JsonObject jsonObject = JsonParser.parseString(responseEntity.getBody()).getAsJsonObject();
JsonObject messageObject = jsonObject.getAsJsonObject("result").getAsJsonObject("message");
String content = messageObject.get("content").getAsString();
Expand All @@ -93,10 +71,8 @@ public Map<String, String> recommendMember(RecommendMemberRequestDTO recommendMe
}
@Transactional
public List<Map<String, String>> recommendSchedule(RecommendScheduleRequestDTO recommendScheduleRequestDTO) {
String url = clovaStudioRecommend.getUrl();
String apiKeyClovaStudio = clovaStudioRecommend.getApiKeyClovaStudio();


String requestId = clovaStudioRecommend.getRequestScheduleId();

List<Message> messages = new ArrayList<>();

// 첫 번째 메시지
Expand Down Expand Up @@ -138,26 +114,8 @@ public List<Map<String, String>> recommendSchedule(RecommendScheduleRequestDTO r
"\"해야할 업무\" (시작날짜 ~ 마감날짜)로만 대답해주세요. 다른 말 없이 역할과 해야할 업무, 시작날짜, 마감날짜만 작성해주세요. 역할 앞에 숫자를 넣지 말고, 업무 앞에 -를 넣지 마세요. ");
messages.add(requestMessage);

HttpHeaders headers = new HttpHeaders();
headers.set("X-NCP-CLOVASTUDIO-API-KEY", apiKeyClovaStudio);
headers.set("X-NCP-APIGW-API-KEY", clovaStudioRecommend.getApiGateWayKey());
headers.set("X-NCP-CLOVASTUDIO-REQUEST-ID", clovaStudioRecommend.getRequestScheduleId());
headers.set("Content-Type", "application/json");

Map<String, Object> requestBody = new HashMap<>();
requestBody.put("messages", messages);
requestBody.put("topP", 0.8);
requestBody.put("topK", 0);
requestBody.put("maxTokens", 256);
requestBody.put("temperature", 0.5);
requestBody.put("repeatPenalty", 5.0);
requestBody.put("includeAiFilters", "True");

HttpEntity<Map<String, Object>> requestEntity = new HttpEntity<>(requestBody, headers);

RestTemplate restTemplate = new RestTemplate();
ResponseEntity<String> responseEntity = restTemplate.exchange(url, HttpMethod.POST, requestEntity, String.class);

ResponseEntity<String> responseEntity = fetchClovaAPI(messages,requestId);

JsonObject jsonObject = JsonParser.parseString(responseEntity.getBody()).getAsJsonObject();
JsonObject messageObject = jsonObject.getAsJsonObject("result").getAsJsonObject("message");
String content = messageObject.get("content").getAsString();
Expand All @@ -178,7 +136,6 @@ public List<Map<String, String>> recommendSchedule(RecommendScheduleRequestDTO r
Matcher roleMatcher = roleRegex.matcher(role);

if (roleMatcher.matches()) {
String roleNumber = roleMatcher.group(1); // 1.
role = roleMatcher.group(2); // 기획자

// 숫자와 점을 제거한 role
Expand Down Expand Up @@ -259,6 +216,7 @@ public List<Map<String, String>> recommendSchedule(RecommendScheduleRequestDTO r

@Transactional
public void insertCalender(Long projectId, List<Map<String, String>> roleScheduleList) {

Project project = projectRepository.findById(projectId).orElseThrow(()->new NoSuchElementException("[ERROR] 해당하는 프로젝트가 존재하지 않습니다."));
for(Map<String,String> map : roleScheduleList){
Role r = new Role();
Expand All @@ -274,4 +232,31 @@ public void insertCalender(Long projectId, List<Map<String, String>> roleSchedul
}
}

public ResponseEntity<String> fetchClovaAPI(List<Message> messages, String requestId){
String url = clovaStudioRecommend.getUrl();
String apiKeyClovaStudio = clovaStudioRecommend.getApiKeyClovaStudio();
String apiGateWayKey = clovaStudioRecommend.getApiGateWayKey();

HttpHeaders headers = new HttpHeaders();
headers.set("X-NCP-CLOVASTUDIO-API-KEY", apiKeyClovaStudio);
headers.set("X-NCP-APIGW-API-KEY", apiGateWayKey);
headers.set("X-NCP-CLOVASTUDIO-REQUEST-ID", requestId);
headers.set("Content-Type", "application/json");

Map<java.lang.String, Object> requestBody = new HashMap<>();
requestBody.put("messages", messages);
requestBody.put("topP", 0.8);
requestBody.put("topK", 0);
requestBody.put("maxTokens", 256);
requestBody.put("temperature", 0.5);
requestBody.put("repeatPenalty", 5.0);
requestBody.put("includeAiFilters", "True");

HttpEntity<Map<java.lang.String, Object>> requestEntity = new HttpEntity<>(requestBody, headers);

RestTemplate restTemplate = new RestTemplate();
return restTemplate.exchange(url, HttpMethod.POST, requestEntity, String.class);

}

}
Loading

0 comments on commit e022cc7

Please sign in to comment.