Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: Calender #43

Open
wants to merge 2 commits into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -2,65 +2,116 @@

import KKSC.page.domain.calendar.dto.EventRequest;
import KKSC.page.domain.calendar.dto.EventResponse;
import KKSC.page.domain.calendar.exception.CalendarException;
import KKSC.page.domain.calendar.dto.EventResponseInterface;
import KKSC.page.domain.calendar.exception.EventException;
import KKSC.page.domain.calendar.repoAndService.EventService;
import KKSC.page.global.auth.service.JwtService;
import KKSC.page.global.exception.ErrorCode;
import KKSC.page.global.exception.dto.ErrorResponseVO;
import KKSC.page.global.exception.dto.ResponseVO;
import io.swagger.v3.oas.annotations.Operation;
import io.swagger.v3.oas.annotations.Parameter;
import io.swagger.v3.oas.annotations.Parameters;
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 jakarta.servlet.http.HttpServletRequest;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;

import org.springframework.web.bind.annotation.*;

import java.util.List;

@Tag(name = "Event", description = "일정관리 API")
@RestController
@RequiredArgsConstructor
@RequestMapping("/calendar")
@RequestMapping("/event")
@Slf4j
public class EventController {

private final EventService eventService;
private final JwtService jwtService;

// 캘린더 일정 추가
@ApiResponses(value = {
@ApiResponse(responseCode = "200", description = "API 정상 작동",content = @Content(schema = @Schema(implementation = ResponseVO.class))),
@ApiResponse(responseCode = "???", description = "서버 에러",content = @Content(schema = @Schema(implementation = ErrorResponseVO.class)))}
)
@Operation(summary = "일정 추가", description = " 일정 추가 API ")
@PostMapping("/")
public ResponseVO<Long> addEvent(@RequestBody EventRequest eventRequest) {
return new ResponseVO<>(eventService.createSchedule(eventRequest));
return new ResponseVO<>(eventService.createEvent(eventRequest));
}

// 캘린더 일정 삭제
@DeleteMapping("/{id}")
public ResponseVO<String> deleteEvent(@PathVariable Long id) {
eventService.deleteSchedule(id);
// 캘린더 일정 수정
@ApiResponses(value = {
@ApiResponse(responseCode = "200", description = "API 정상 작동",content = @Content(schema = @Schema(implementation = ResponseVO.class))),
@ApiResponse(responseCode = "???", description = "서버 에러",content = @Content(schema = @Schema(implementation = ErrorResponseVO.class)))}
)
@Parameter(name = "eventId", description = "일정 번호")
@Operation(summary = " 일정 수정 ", description = " 일정 수정 API ")
@PutMapping("/{eventId}")
public ResponseVO<EventResponse> updateEvent(@PathVariable Long eventId, @RequestBody EventRequest eventRequest) {
return new ResponseVO<>(eventService.updateEvent(eventId, eventRequest));
}

return new ResponseVO<>("Delete Success");
// 캘린더 일정 삭제
@ApiResponses(value = {
@ApiResponse(responseCode = "200", description = "API 정상 작동",content = @Content(schema = @Schema(implementation = ResponseVO.class))),
@ApiResponse(responseCode = "???", description = "서버 에러",content = @Content(schema = @Schema(implementation = ErrorResponseVO.class)))}
)
@Parameter(name = "eventId", description = "일정 번호")
@Operation(summary = " 일정 삭제 ", description = " 일정 삭제 API ")
@DeleteMapping("/{eventId}")
public ResponseVO<String> deleteEvent(@PathVariable Long eventId) {
return new ResponseVO<>("Delete success");
}

// 캘린더 일정 수정
@PutMapping("/{id}")
public ResponseVO<EventResponse> updateEvent(@PathVariable Long id, @RequestBody EventRequest eventRequest) {
return new ResponseVO<>(eventService.updateSchedule(id, eventRequest));
// 캘린더 일정 목록 조회 완성
@ApiResponses(value = {
@ApiResponse(responseCode = "200", description = "API 정상 작동",content = @Content(schema = @Schema(implementation = ResponseVO.class))),
@ApiResponse(responseCode = "???", description = "서버 에러",content = @Content(schema = @Schema(implementation = ErrorResponseVO.class)))}
)
@Parameters({
@Parameter(name = "year", description = "일정 검색 년도"),
@Parameter(name = "month", description = "일정 검색 월"),
})
@Operation(summary = " 일정 조회 ", description = " 일정 조회 API ")
@GetMapping("")
public ResponseVO<List<EventResponseInterface>> getEventList(@RequestParam int year, @RequestParam int month) {
return new ResponseVO<>(eventService.getEventList(year, month));
}

// 캘린더 일정 참가
@PostMapping("/{id}/join")
public ResponseVO<Long> joinEvent(HttpServletRequest request, @PathVariable Long id) {
@ApiResponses(value = {
@ApiResponse(responseCode = "200", description = "API 정상 작동",content = @Content(schema = @Schema(implementation = ResponseVO.class))),
@ApiResponse(responseCode = "???", description = "서버 에러",content = @Content(schema = @Schema(implementation = ErrorResponseVO.class)))}
)
@Parameter(name = "eventId", description = "일정 번호")
@Operation(summary = " 일정 참가 ", description = " 일정 참가 API ")
@PostMapping("/join/{eventId}")
public ResponseVO<Long> joinEvent(HttpServletRequest request, @PathVariable Long eventId) {
String username = jwtService.extractUsername(request)
.orElseThrow(() -> new CalendarException(ErrorCode.ACCESS_DENIED));

return new ResponseVO<>(eventService.joinSchedule(id, username));
.orElseThrow(() -> new EventException(ErrorCode.ACCESS_DENIED));
return new ResponseVO<>(eventService.joinEvent(eventId, username));
}

// 캘린더 일정 참가 취소
@DeleteMapping("/cancel/{id}")
public ResponseVO<String> cancelEvent(@PathVariable Long id) {
eventService.cancelSchedule(id);

return new ResponseVO<>("Cancel Success");
}
@ApiResponses(value = {
@ApiResponse(responseCode = "200", description = "API 정상 작동",content = @Content(schema = @Schema(implementation = ResponseVO.class))),
@ApiResponse(responseCode = "???", description = "서버 에러",content = @Content(schema = @Schema(implementation = ErrorResponseVO.class)))}
)
@Parameter(name = "eventId", description = "일정 번호")
@Operation(summary = " 일정 참가 취소 ", description = " 일정 참가 취소 API ")
@DeleteMapping("/cancel/{eventId}")
public ResponseVO<String> cancelEvent(HttpServletRequest request, @PathVariable Long eventId) {
String username = jwtService.extractUsername(request)
.orElseThrow(() -> new EventException(ErrorCode.ACCESS_DENIED));

// 캘린더 일정 목록 조회
@GetMapping("/")
public ResponseVO<List<EventResponse>> getEventList(@RequestParam Long year, @RequestParam Long month) {
return new ResponseVO<>(eventService.getScheduleList(year, month));
return new ResponseVO<>(eventService.cancelEvent(eventId, username));
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
package KKSC.page.domain.calendar.dto;

import java.time.LocalDateTime;
import com.fasterxml.jackson.annotation.JsonFormat;

import KKSC.page.domain.calendar.entity.Category;

public interface EventResponseInterface {

Long getId();
String getTitle();
String getDetail();

Category getCategory();

@JsonFormat(shape = JsonFormat.Shape.STRING, pattern = "yyyy-MM-dd hh:mm:ss", timezone = "Asia/Seoul")
LocalDateTime getStartDate();

@JsonFormat(shape = JsonFormat.Shape.STRING, pattern = "yyyy-MM-dd hh:mm:ss", timezone = "Asia/Seoul")
LocalDateTime getEndDate();

Long getMaxParticipant();
Comment on lines +8 to +22
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Response는 단순 dto 용도로만 사용되는 걸로 아는데 요러면 이점이 뭔가여 형님

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

일단 nativequery 를 DTO 맵핑 시켜주기 위해서 interface로 생성했고
프론트엔드에서 가공없이 보여줄수있게끔 jsonformat 설정해서 값을 반환하게끔 하였숨

이점은...
nativequery 에서 바로 DTO 맵핑가능해서 편하다 ( 일반 querydsl 이나 jpa 처럼 바로 맵핑해서 보내면 됨 )

이게 궁금한게 아닝가..?

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

오.. 이런 방식은 첨 알았네요 👍

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

방법은 직접 map을 생성해서 맵핑해줄수도 있고.. 뭐 그렇다고는 하던데

중요한것은 nativeQuery<<<<<<<<<<<Querydsl 이라는 것인데

관련사항은 검색해보면 나올고야


}
21 changes: 9 additions & 12 deletions src/main/java/KKSC/page/domain/calendar/entity/Event.java
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
package KKSC.page.domain.calendar.entity;

import KKSC.page.domain.member.entity.Member;
import KKSC.page.domain.calendar.dto.EventRequest;
import KKSC.page.global.common.BaseTimeEntity;
import jakarta.persistence.*;
import lombok.AllArgsConstructor;
Expand All @@ -26,10 +26,6 @@ public class Event extends BaseTimeEntity {
@OneToMany(mappedBy = "event")
private List<Participant> participants;

@ManyToOne(fetch = FetchType.LAZY)
@JoinColumn(name = "member_id")
private Member member;

// 일정 제목
private String title;

Expand All @@ -50,12 +46,13 @@ public class Event extends BaseTimeEntity {
private String detail;

// 일정 수정(시작 날짜, 종료 날짜, 세부 사항 수정)
public void update(String title, String detail, Category category, LocalDateTime startDate, LocalDateTime endDate, Long maxParticipant) {
this.title = title;
this.detail = detail;
this.category = category;
this.startDate = startDate;
this.endDate = endDate;
this.maxParticipant = maxParticipant;
public void update(Long eventId, EventRequest eventRequest) {
this.id = eventId;
this.title = eventRequest.title();
this.detail = eventRequest.detail();
this.category = eventRequest.category();
this.startDate = eventRequest.startDate();
this.endDate = eventRequest.endDate();
this.maxParticipant = eventRequest.maxParticipant();
}
}
10 changes: 7 additions & 3 deletions src/main/java/KKSC/page/domain/calendar/entity/Participant.java
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
package KKSC.page.domain.calendar.entity;

import KKSC.page.domain.member.entity.Member;
import KKSC.page.global.common.BaseTimeEntity;
import jakarta.persistence.*;
import lombok.AllArgsConstructor;
Expand All @@ -18,9 +19,12 @@ public class Participant extends BaseTimeEntity {
@Column(name = "participant_id")
private Long id;

@ManyToOne(fetch = FetchType.LAZY)
@ManyToOne
@JoinColumn(name = "event_id")
private Event event;

private String name;
}
@OneToOne
@JoinColumn(name = "member_id")
private Member member;

}
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@

@Getter
@RequiredArgsConstructor
public class CalendarException extends RuntimeException {
public class EventException extends RuntimeException {

private final ErrorCode errorCode;
}
Original file line number Diff line number Diff line change
@@ -1,7 +1,27 @@
package KKSC.page.domain.calendar.repoAndService;

import KKSC.page.domain.calendar.dto.EventResponseInterface;
import KKSC.page.domain.calendar.entity.Event;

import java.util.List;

import org.springframework.data.jpa.repository.JpaRepository;
import org.springframework.data.jpa.repository.Query;
import org.springframework.data.repository.query.Param;


public interface EventRepository extends JpaRepository<Event, Long>, EventRepositoryCustom {
@Query(value = "SELECT "+
"event_id as id,"+
"title as title,"+
"detail as detail,"+
"category as category,"+
"start_date as startDate,"+
"end_date as endDate ,"+
"max_participant as maxParticipant "+
"FROM event "+
"WHERE YEAR(end_date) = :Year "+
"AND MONTH(end_date) = :Month "
, nativeQuery = true)
List<EventResponseInterface> EventList(@Param("Year") int Year,@Param("Month") int Month);
}
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@

import KKSC.page.domain.calendar.dto.EventRequest;
import KKSC.page.domain.calendar.dto.EventResponse;
import KKSC.page.domain.calendar.dto.EventResponseInterface;

import org.springframework.stereotype.Service;

Expand All @@ -15,26 +16,27 @@ public interface EventService {

// 일정 목록 조회
@PreAuthorize("hasRole('permission_level1')")
List<EventResponse> getScheduleList(Long year, Long month);
List<EventResponseInterface> getEventList(int year, int month);

// 일정 생성
@PreAuthorize("hasRole('permission_level0')")
Long createSchedule(EventRequest eventRequest);
Long createEvent(EventRequest eventRequest);

// 일정 삭제
// 일정 수정
@PreAuthorize("hasRole('permission_level0')")
void deleteSchedule(Long id);
EventResponse updateEvent(Long evetnId, EventRequest eventRequest);

// 일정 수정
// 일정 삭제
@PreAuthorize("hasRole('permission_level0')")
EventResponse updateSchedule(Long id, EventRequest eventRequest);
void deleteEvent(Long evetnId);


// 일정 참가
@PreAuthorize("hasRole('permission_level1')")
Long joinSchedule(Long id, String name);
Long joinEvent(Long evetnId, String userName);

// 일정 참가 취소
@PreAuthorize("hasRole('permission_level1')")
void cancelSchedule (Long id);
String cancelEvent (Long evetnId, String userName);

}
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
package KKSC.page.domain.calendar.repoAndService;

import org.springframework.data.jpa.repository.JpaRepository;

import KKSC.page.domain.calendar.entity.Participant;

public interface ParticipantRepository extends JpaRepository<Participant, Long> {

}
Loading
Loading