diff --git a/src/main/java/com/ajouchong/controller/admin/LinkAdminController.java b/src/main/java/com/ajouchong/controller/admin/LinkAdminController.java new file mode 100644 index 0000000..371a233 --- /dev/null +++ b/src/main/java/com/ajouchong/controller/admin/LinkAdminController.java @@ -0,0 +1,40 @@ +package com.ajouchong.controller.admin; + +import com.ajouchong.common.ApiResponse; +import com.ajouchong.dto.request.LinkRequestDto; +import com.ajouchong.dto.response.LinkResponseDto; +import com.ajouchong.service.LinkService; +import lombok.RequiredArgsConstructor; +import org.springframework.web.bind.annotation.*; + +import jakarta.validation.Valid; +import java.util.List; + +@RestController +@RequestMapping("/api/admin/link") +@RequiredArgsConstructor +public class LinkAdminController { + + private final LinkService linkService; + + @PostMapping("/upload") + public ApiResponse uploadLink(@Valid @RequestBody LinkRequestDto requestDto) { + LinkResponseDto response = linkService.uploadLink(requestDto); + + return new ApiResponse<>(1, "링크가 성공적으로 업로드되었습니다.", response); + } + + @GetMapping + public ApiResponse> getAllLinks() { + List links = linkService.getAllLinks(); + + return new ApiResponse<>(1, "링크 목록을 조회했습니다.", links); + } + + @DeleteMapping("/{id}/delete") + public ApiResponse deleteLink(@PathVariable Long id) { + linkService.deleteLink(id); + + return new ApiResponse<>(1, "링크가 삭제되었습니다.", null); + } +} diff --git a/src/main/java/com/ajouchong/controller/user/LinkController.java b/src/main/java/com/ajouchong/controller/user/LinkController.java new file mode 100644 index 0000000..6e9a01b --- /dev/null +++ b/src/main/java/com/ajouchong/controller/user/LinkController.java @@ -0,0 +1,39 @@ +package com.ajouchong.controller.user; + +import com.ajouchong.common.ApiResponse; +import com.ajouchong.dto.request.LinkRequestDto; +import com.ajouchong.dto.response.LinkResponseDto; +import com.ajouchong.service.LinkService; +import lombok.RequiredArgsConstructor; +import org.springframework.web.bind.annotation.*; + +import jakarta.validation.Valid; +import java.util.List; + +@RestController +@RequestMapping("/api/link") +@RequiredArgsConstructor +public class LinkController { + private final LinkService linkService; + + @PostMapping("/upload") + public ApiResponse uploadLink(@Valid @RequestBody LinkRequestDto requestDto) { + LinkResponseDto response = linkService.uploadLink(requestDto); + + return new ApiResponse<>(1, "링크가 성공적으로 업로드되었습니다.", response); + } + + @GetMapping + public ApiResponse> getAllLinks() { + List links = linkService.getAllLinks(); + + return new ApiResponse<>(1, "링크 목록을 조회했습니다.", links); + } + + @DeleteMapping("/{id}/delete") + public ApiResponse deleteLink(@PathVariable Long id) { + linkService.deleteLink(id); + + return new ApiResponse<>(1, "링크가 삭제되었습니다.", null); + } +} diff --git a/src/main/java/com/ajouchong/dto/request/LinkRequestDto.java b/src/main/java/com/ajouchong/dto/request/LinkRequestDto.java new file mode 100644 index 0000000..02a8f0b --- /dev/null +++ b/src/main/java/com/ajouchong/dto/request/LinkRequestDto.java @@ -0,0 +1,15 @@ +package com.ajouchong.dto.request; + +import lombok.Data; + +import jakarta.validation.constraints.NotBlank; + +@Data +public class LinkRequestDto { + + @NotBlank(message = "제목은 필수입니다.") + private String title; + + @NotBlank(message = "링크는 필수입니다.") + private String link; +} diff --git a/src/main/java/com/ajouchong/dto/response/LinkResponseDto.java b/src/main/java/com/ajouchong/dto/response/LinkResponseDto.java new file mode 100644 index 0000000..64ab210 --- /dev/null +++ b/src/main/java/com/ajouchong/dto/response/LinkResponseDto.java @@ -0,0 +1,15 @@ +package com.ajouchong.dto.response; + +import lombok.Data; +import lombok.Builder; + +import java.time.LocalDateTime; + +@Data +@Builder +public class LinkResponseDto { + private Long id; + private String title; + private String link; + private LocalDateTime createdAt; +} diff --git a/src/main/java/com/ajouchong/entity/Link.java b/src/main/java/com/ajouchong/entity/Link.java new file mode 100644 index 0000000..128f720 --- /dev/null +++ b/src/main/java/com/ajouchong/entity/Link.java @@ -0,0 +1,37 @@ +package com.ajouchong.entity; + +import jakarta.persistence.*; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Data; +import lombok.NoArgsConstructor; + +import jakarta.persistence.PrePersist; +import java.time.LocalDateTime; + +@Entity +@Table(name = "links") +@Data +@Builder +@NoArgsConstructor +@AllArgsConstructor +public class Link { + + @Id + @GeneratedValue(strategy = GenerationType.IDENTITY) + private Long id; + + @Column(nullable = false) + private String title; + + @Column(nullable = false) + private String link; + + @Column(name = "created_at", nullable = false, updatable = false) + private LocalDateTime createdAt; + + @PrePersist + protected void onCreate() { + createdAt = LocalDateTime.now(); + } +} diff --git a/src/main/java/com/ajouchong/repository/LinkRepository.java b/src/main/java/com/ajouchong/repository/LinkRepository.java new file mode 100644 index 0000000..96924de --- /dev/null +++ b/src/main/java/com/ajouchong/repository/LinkRepository.java @@ -0,0 +1,13 @@ +package com.ajouchong.repository; + +import com.ajouchong.entity.Link; +import org.springframework.data.jpa.repository.JpaRepository; +import org.springframework.stereotype.Repository; + +import java.util.List; + +@Repository +public interface LinkRepository extends JpaRepository { + + List findAllByOrderByCreatedAtAsc(); +} diff --git a/src/main/java/com/ajouchong/service/LinkService.java b/src/main/java/com/ajouchong/service/LinkService.java new file mode 100644 index 0000000..199fb1d --- /dev/null +++ b/src/main/java/com/ajouchong/service/LinkService.java @@ -0,0 +1,58 @@ +package com.ajouchong.service; + +import com.ajouchong.dto.request.LinkRequestDto; +import com.ajouchong.dto.response.LinkResponseDto; +import com.ajouchong.entity.Link; +import com.ajouchong.repository.LinkRepository; +import lombok.RequiredArgsConstructor; +import org.springframework.stereotype.Service; +import org.springframework.transaction.annotation.Transactional; + +import java.util.List; +import java.util.stream.Collectors; + +@Service +@RequiredArgsConstructor +@Transactional(readOnly = true) +public class LinkService { + + private final LinkRepository linkRepository; + + @Transactional + public LinkResponseDto uploadLink(LinkRequestDto requestDto) { + Link link = Link.builder() + .title(requestDto.getTitle()) + .link(requestDto.getLink()) + .build(); + + Link savedLink = linkRepository.save(link); + + return LinkResponseDto.builder() + .id(savedLink.getId()) + .title(savedLink.getTitle()) + .link(savedLink.getLink()) + .createdAt(savedLink.getCreatedAt()) + .build(); + } + + public List getAllLinks() { + List links = linkRepository.findAllByOrderByCreatedAtAsc(); + + return links.stream() + .map(link -> LinkResponseDto.builder() + .id(link.getId()) + .title(link.getTitle()) + .link(link.getLink()) + .createdAt(link.getCreatedAt()) + .build()) + .collect(Collectors.toList()); + } + + @Transactional + public void deleteLink(Long id) { + Link link = linkRepository.findById(id) + .orElseThrow(() -> new IllegalArgumentException("링크를 찾을 수 없습니다. ID: " + id)); + + linkRepository.delete(link); + } +}