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

Json 과제 #23

Open
wants to merge 15 commits into
base: main
Choose a base branch
from
5 changes: 5 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
@@ -1 +1,6 @@
# UMC Spring A팀 레포지토리입니다.
Json의 브랜치입니다 😀

## ERD
![image](https://github.com/UMC-CAU-6th/Spring-A/assets/54016683/a2b739bc-4e01-45ae-b57f-5de76c454c2a)

20 changes: 14 additions & 6 deletions umc/build.gradle
Original file line number Diff line number Diff line change
Expand Up @@ -26,21 +26,29 @@ dependencies {
implementation 'org.springframework.boot:spring-boot-starter-data-jpa'
implementation 'org.springframework.boot:spring-boot-starter-security'
implementation 'org.springframework.boot:spring-boot-starter-web'
testImplementation 'junit:junit:4.13.1'

compileOnly 'org.projectlombok:lombok'
annotationProcessor 'org.projectlombok:lombok'

testImplementation 'junit:junit:4.13.1'
testImplementation 'org.springframework.boot:spring-boot-starter-test'
testImplementation 'org.springframework.security:spring-security-test'
implementation 'org.springframework.boot:spring-boot-starter-validation'
runtimeOnly 'com.mysql:mysql-connector-j'
implementation group: 'org.hibernate', name: 'hibernate-spatial', version: '5.6.15.Final'

//runtimeOnly 'com.mysql:mysql-connector-j'
runtimeOnly 'com.h2database:h2'
//implementation group: 'org.hibernate', name: 'hibernate-spatial', version: '5.6.15.Final'
// jwt
implementation 'io.jsonwebtoken:jjwt-api:0.11.5'
implementation 'io.jsonwebtoken:jjwt-impl:0.11.5'
implementation 'io.jsonwebtoken:jjwt-jackson:0.11.5'
implementation 'org.springdoc:springdoc-openapi-ui:1.6.15'
implementation 'io.springfox:springfox-swagger2:2.9.2'
implementation 'io.springfox:springfox-swagger-ui:2.9.2'

implementation 'org.springdoc:springdoc-openapi-starter-webmvc-ui:2.2.0'
// implementation 'org.springdoc:springdoc-openapi-ui:1.6.15'
// implementation 'io.springfox:springfox-swagger2:2.9.2'
// implementation 'io.springfox:springfox-swagger-ui:2.9.2'
// implementation 'io.springfox:springfox-boot-starter:3.0.0'
// implementation 'io.springfox:springfox-swagger-ui:3.0.0'

}

Expand Down
3 changes: 2 additions & 1 deletion umc/src/main/java/com/umc/common/config/SecurityConfig.java
Original file line number Diff line number Diff line change
Expand Up @@ -38,8 +38,9 @@ public SecurityFilterChain securityFilterChain(HttpSecurity http) throws Excepti
.requestMatchers("/upload").permitAll()
.requestMatchers("/api/**").permitAll()
.requestMatchers("/swagger-ui/**").permitAll()
.requestMatchers("/swagger-ui.html").permitAll()
.requestMatchers("/v3/api-docs/**").permitAll()
.anyRequest().authenticated()
.anyRequest().permitAll()
)
.addFilterBefore(new JwtAuthenticationFilter(jwtTokenProvider), UsernamePasswordAuthenticationFilter.class);

Expand Down
4 changes: 2 additions & 2 deletions umc/src/main/java/com/umc/common/config/SwaggerConfig.java
Original file line number Diff line number Diff line change
Expand Up @@ -15,8 +15,8 @@ public class SwaggerConfig {
@Bean
public OpenAPI SchrodingerApi() {
Info info = new Info()
.title("BuddyU API")
.description("BuddyU API 명세서")
.title("제목")
.description("명세서 설명")
.version("1.0.0");

String jwtSchemeName = "JWT TOKEN";
Expand Down
6 changes: 3 additions & 3 deletions umc/src/main/java/com/umc/common/entity/BaseTimeEntity.java
Original file line number Diff line number Diff line change
Expand Up @@ -2,9 +2,9 @@


import java.time.LocalDateTime;
import javax.persistence.Column;
import javax.persistence.EntityListeners;
import javax.persistence.MappedSuperclass;
import jakarta.persistence.Column;
import jakarta.persistence.EntityListeners;
import jakarta.persistence.MappedSuperclass;
import lombok.Getter;
import org.springframework.data.annotation.CreatedDate;
import org.springframework.data.annotation.LastModifiedDate;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,8 @@ public enum ErrorCode implements BaseErrorCode {
MEMBER_SIGNUP_ERROR(HttpStatus.BAD_REQUEST, "SIGNUP4001", "회원가입 유효성 검사 실패"),
EMAIL_ALREADY_EXIST(HttpStatus.BAD_REQUEST, "SIGNUP4002", "이미 존재하는 이메일입니다."),

// 게시글 관련 에러
LIKE_ALREADY_EXISTS(HttpStatus.BAD_REQUEST, "POST4001", "이미 좋아요를 눌렀습니다."),
;


Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,48 @@
package com.umc.domain.board.controller;

import com.umc.common.response.ApiResponse;
import com.umc.domain.board.dto.BoardRequestDTO;
import com.umc.domain.board.service.BoardService;
import io.swagger.v3.oas.annotations.Operation;
import jakarta.validation.Valid;
import jakarta.validation.constraints.NotEmpty;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.springframework.web.bind.annotation.*;

@Slf4j
@RequiredArgsConstructor
@RequestMapping("/api/board")
@RestController
public class BoardController {
private final BoardService boardService;

@CrossOrigin
@Operation(summary = "게시판 생성 API")
@PostMapping("/")
public ApiResponse<Object> createBoard(@Valid @RequestBody BoardRequestDTO boardRequestDTO){
return boardService.createBoard(boardRequestDTO);
}

@CrossOrigin
@Operation(summary = "게시판 게시글 조회 API")
@GetMapping("/{boardId}")
public ApiResponse<Object> readBoard(@PathVariable String boardId){
return boardService.readBoardPosts(boardId);
}

@CrossOrigin
@Operation(summary = "게시판 삭제 API")
@DeleteMapping("/{boardId}")
public ApiResponse<Object> deleteBoard(@PathVariable String boardId){
return boardService.delete(boardId);
}

@CrossOrigin
@Operation(summary = "게시판 수정 API")
@PutMapping("/{boardId}")
public ApiResponse<Object> updateBoard(@PathVariable String boardId,
@Valid @RequestBody BoardRequestDTO boardUpdateDTO){
return boardService.update(boardId, boardUpdateDTO);
}
}
12 changes: 12 additions & 0 deletions umc/src/main/java/com/umc/domain/board/dto/BoardRequestDTO.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
package com.umc.domain.board.dto;

import jakarta.validation.constraints.NotEmpty;
import lombok.Builder;
import lombok.Getter;

@Getter
@Builder
public class BoardRequestDTO {
@NotEmpty(message = "제목은 필수 입력값입니다.")
private String title;
}
23 changes: 23 additions & 0 deletions umc/src/main/java/com/umc/domain/board/entity/Board.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
package com.umc.domain.board.entity;

import com.umc.common.entity.BaseTimeEntity;
import jakarta.persistence.*;
import lombok.*;

@Getter
@Builder
@Setter
@NoArgsConstructor
@Entity
@Table(name= "board")
@AllArgsConstructor
public class Board extends BaseTimeEntity {

@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
private Long id;

@Column
private String title;

}
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
package com.umc.domain.board.repository;

import com.umc.domain.board.entity.Board;
import org.springframework.data.jpa.repository.JpaRepository;
import org.springframework.stereotype.Repository;

@Repository
public interface BoardRepository extends JpaRepository<Board, Long> {
}
63 changes: 63 additions & 0 deletions umc/src/main/java/com/umc/domain/board/service/BoardService.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,63 @@
package com.umc.domain.board.service;

import com.umc.common.response.ApiResponse;
import com.umc.common.response.status.SuccessCode;
import com.umc.domain.board.dto.BoardRequestDTO;
import com.umc.domain.board.entity.Board;
import com.umc.domain.board.repository.BoardRepository;
import com.umc.domain.post.dto.SimplePostResponseDTO;
import com.umc.domain.post.entity.Post;
import com.umc.domain.post.repository.PostRepository;
import lombok.RequiredArgsConstructor;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.List;

@Service
@RequiredArgsConstructor
public class BoardService {
private final BoardRepository boardRepository;
private final PostRepository postRepository;

public ApiResponse<Object> createBoard(BoardRequestDTO boardRequestDTO) {
Board board = Board.builder()
.title(boardRequestDTO.getTitle())
.build();

boardRepository.save(board);
return ApiResponse.of(SuccessCode._OK, "저장되었습니다");
}

@Transactional
public ApiResponse<Object> readBoardPosts(String boardId) {
List<Post> posts = postRepository.findAllByBoardId(Long.getLong(boardId));

List<SimplePostResponseDTO> postDTOs = posts.stream().map(post ->
SimplePostResponseDTO.builder()
.boardId(Long.getLong(boardId))
.writerNickname(post.getWriter().getNickname())
.title(post.getTitle())
.createdAt(post.getCreatedAt())
.modifiedAt(post.getModifiedAt())
.build()
).toList();

return ApiResponse.of(SuccessCode._OK, postDTOs);
}

public ApiResponse<Object> delete(String boardId) {
Board target = boardRepository.findById(Long.getLong(boardId)).orElseThrow();
boardRepository.delete(target);

return ApiResponse.of(SuccessCode._OK, "삭제되었습니다");
}

public ApiResponse<Object> update(String boardId, BoardRequestDTO boardUpdateDTO) {
Board target = boardRepository.findById(Long.getLong(boardId)).orElseThrow();
target.setTitle(boardUpdateDTO.getTitle());
boardRepository.save(target);

return ApiResponse.of(SuccessCode._OK, "수정되었습니다");
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,52 @@
package com.umc.domain.comment.controller;

import com.umc.common.response.ApiResponse;
import com.umc.domain.comment.dto.CommentRequestDTO;
import com.umc.domain.comment.entity.Comment;
import com.umc.domain.comment.service.CommentService;
import io.swagger.v3.oas.annotations.Operation;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.springframework.web.bind.annotation.*;

import java.util.List;

@Slf4j
@RequiredArgsConstructor
@RequestMapping("/api")
@RestController
public class CommentController {
private final CommentService commentService;

@CrossOrigin
@Operation(summary = "댓글 조회 API")
@GetMapping("/posts/{postId}/comments")
public ApiResponse<List<Comment>> findComments(@PathVariable String postId){
return commentService.findByPostId(postId);
}

@CrossOrigin
@Operation(summary = "댓글 작성 API")
@PostMapping("/posts/{postId}/comments")
public ApiResponse<String> writeComment(@PathVariable String postId,
@RequestBody CommentRequestDTO commentRequestDTO){
return commentService.save(postId, commentRequestDTO);
}

@CrossOrigin
@Operation(summary = "댓글 삭제 API")
@DeleteMapping("/posts/{postId}/comments/{commentId}")
public ApiResponse<Object> deleteComment(@PathVariable String postId,
@PathVariable String commentId){
return commentService.delete(commentId);
}

@CrossOrigin
@Operation(summary = "댓글 수정 API")
@PutMapping("/posts/{postId}/comments/{commentId}")
public ApiResponse<Object> updateComment(@PathVariable String postId,
@PathVariable String commentId,
@RequestBody CommentRequestDTO commentUpdateRequestDTO){
return commentService.update(commentId, commentUpdateRequestDTO);
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
package com.umc.domain.comment.dto;

import lombok.Builder;
import lombok.Getter;

@Getter
@Builder
public class CommentRequestDTO {
private String content;
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
package com.umc.domain.comment.dto;

import lombok.Builder;
import lombok.Getter;

@Getter
@Builder
public class CommentResponseDTO {
private Long id;
private String writerNickname;
private String content;
}
36 changes: 36 additions & 0 deletions umc/src/main/java/com/umc/domain/comment/entity/Comment.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,36 @@
package com.umc.domain.comment.entity;

import com.umc.common.entity.BaseTimeEntity;
import com.umc.domain.post.entity.Post;
import com.umc.domain.user.entity.Member;
import jakarta.persistence.*;
import lombok.*;

@Getter
@Builder
@Setter
@NoArgsConstructor
@Entity
@Table(name= "comment")
@AllArgsConstructor
public class Comment extends BaseTimeEntity {

@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
private Long id;

@ManyToOne(fetch = FetchType.LAZY)
@JoinColumn(name = "writer_id")
private Member writer;

@ManyToOne(fetch = FetchType.LAZY)
@JoinColumn(name = "post_id")
private Post post;

private String content;

public void setPost(Post post){
this.post = post;
post.getComments().add(this);
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
package com.umc.domain.comment.repository;

import com.umc.domain.comment.entity.Comment;
import org.springframework.data.jpa.repository.JpaRepository;

import java.util.List;

public interface CommentRepository extends JpaRepository<Comment, Long> {
List<Comment> findAllByPostId(Long postId);
}
Loading