Skip to content
Merged
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 @@ -78,7 +78,7 @@ public UserRegisterResponse register(UserRegisterRequest req) {
.build();
userAuthRepository.save(userAuth);

eventPublisher.publishEvent(new UserRegisteredEvent(email));
eventPublisher.publishEvent(new UserRegisteredEvent(email, userId));

return UserRegisterResponse.from(userId);
}
Expand Down
Original file line number Diff line number Diff line change
@@ -1,36 +1,32 @@
package project.flipnote.cardset.controller;

import org.springframework.http.HttpStatus;
import org.springframework.http.ResponseEntity;
import org.springframework.security.core.annotation.AuthenticationPrincipal;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.ModelAttribute;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;

import jakarta.validation.Valid;
import lombok.RequiredArgsConstructor;
import project.flipnote.cardset.model.CreateCardSetRequest;
import project.flipnote.cardset.model.CreateCardSetResponse;
import project.flipnote.cardset.controller.docs.CardSetControllerDocs;
import project.flipnote.cardset.model.CardSetSearchRequest;
import project.flipnote.cardset.model.CardSetSummaryResponse;
import project.flipnote.cardset.service.CardSetService;
import project.flipnote.common.security.dto.AuthPrinciple;
import project.flipnote.common.model.response.PagingResponse;

@RequiredArgsConstructor
@RestController
@RequestMapping("/v1/groups/{groupId}/card-sets")
public class CardSetController {
@RequestMapping("/v1/card-sets")
public class CardSetController implements CardSetControllerDocs {

private final CardSetService cardSetService;

@PostMapping("")
public ResponseEntity<CreateCardSetResponse> createCardSet(
@AuthenticationPrincipal AuthPrinciple authPrinciple,
@PathVariable("groupId") Long groupId,
@RequestBody @Valid CreateCardSetRequest req
@GetMapping
public ResponseEntity<PagingResponse<CardSetSummaryResponse>> getCardSets(
@Valid @ModelAttribute CardSetSearchRequest req
) {
CreateCardSetResponse res = cardSetService.createCardSet(groupId, authPrinciple, req);
PagingResponse<CardSetSummaryResponse> res = cardSetService.getCardSets(req);

return ResponseEntity.status(HttpStatus.CREATED).body(res);
return ResponseEntity.ok(res);
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,65 @@
package project.flipnote.cardset.controller;

import org.springframework.http.HttpStatus;
import org.springframework.http.ResponseEntity;
import org.springframework.security.core.annotation.AuthenticationPrincipal;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.PutMapping;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;

import jakarta.validation.Valid;
import lombok.RequiredArgsConstructor;
import project.flipnote.cardset.controller.docs.GroupCardSetControllerDocs;
import project.flipnote.cardset.model.CardSetDetailResponse;
import project.flipnote.cardset.model.CardSetUpdateRequest;
import project.flipnote.cardset.model.CreateCardSetRequest;
import project.flipnote.cardset.model.CreateCardSetResponse;
import project.flipnote.cardset.service.CardSetService;
import project.flipnote.common.security.dto.AuthPrinciple;

@RequiredArgsConstructor
@RestController
@RequestMapping("/v1/groups/{groupId}/card-sets")
public class GroupCardSetController implements GroupCardSetControllerDocs {

private final CardSetService cardSetService;

@PostMapping("")
public ResponseEntity<CreateCardSetResponse> createCardSet(
@AuthenticationPrincipal AuthPrinciple authPrinciple,
@PathVariable("groupId") Long groupId,
@RequestBody @Valid CreateCardSetRequest req
) {
CreateCardSetResponse res = cardSetService.createCardSet(groupId, authPrinciple, req);

return ResponseEntity.status(HttpStatus.CREATED).body(res);
}

@GetMapping("/{cardSetId}")
public ResponseEntity<CardSetDetailResponse> getCardSet(
@PathVariable("groupId") Long groupId,
@PathVariable("cardSetId") Long cardSetId,
@AuthenticationPrincipal AuthPrinciple authPrinciple
) {
CardSetDetailResponse res = cardSetService.getCardSet(authPrinciple.userId(), groupId, cardSetId);

return ResponseEntity.ok(res);
}

@PutMapping("/{cardSetId}")
public ResponseEntity<CardSetDetailResponse> updateCardSet(
@PathVariable("groupId") Long groupId,
@PathVariable("cardSetId") Long cardSetId,
@Valid @RequestBody CardSetUpdateRequest req,
@AuthenticationPrincipal AuthPrinciple authPrinciple
) {
CardSetDetailResponse res = cardSetService.updateCardSet(authPrinciple.userId(), groupId, cardSetId, req);

return ResponseEntity.ok(res);
}

}
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
package project.flipnote.cardset.controller.docs;

import org.springframework.http.ResponseEntity;

import io.swagger.v3.oas.annotations.Operation;
import io.swagger.v3.oas.annotations.security.SecurityRequirement;
import io.swagger.v3.oas.annotations.tags.Tag;
import project.flipnote.cardset.model.CardSetSearchRequest;
import project.flipnote.cardset.model.CardSetSummaryResponse;
import project.flipnote.common.model.response.PagingResponse;

@Tag(name = "CardSet", description = "CardSet API")
public interface CardSetControllerDocs {

@Operation(summary = "카드셋 목록 조회(검색)", security = {@SecurityRequirement(name = "access-token")})
ResponseEntity<PagingResponse<CardSetSummaryResponse>> getCardSets(
CardSetSearchRequest req
);
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,32 @@
package project.flipnote.cardset.controller.docs;

import org.springframework.http.ResponseEntity;

import io.swagger.v3.oas.annotations.Operation;
import io.swagger.v3.oas.annotations.security.SecurityRequirement;
import io.swagger.v3.oas.annotations.tags.Tag;
import project.flipnote.cardset.model.CardSetDetailResponse;
import project.flipnote.cardset.model.CardSetUpdateRequest;
import project.flipnote.cardset.model.CreateCardSetRequest;
import project.flipnote.cardset.model.CreateCardSetResponse;
import project.flipnote.common.security.dto.AuthPrinciple;

@Tag(name = "CardSet", description = "CardSet API")
public interface GroupCardSetControllerDocs {

@Operation(summary = "카드셋 생성", security = {@SecurityRequirement(name = "access-token")})
ResponseEntity<CreateCardSetResponse> createCardSet(
AuthPrinciple authPrinciple, Long groupId, CreateCardSetRequest req
);

@Operation(summary = "카드셋 상세 조회", security = {@SecurityRequirement(name = "access-token")})
ResponseEntity<CardSetDetailResponse> getCardSet(Long groupId, Long cardSetId, AuthPrinciple authPrinciple);

@Operation(summary = "카드셋 수정", security = {@SecurityRequirement(name = "access-token")})
ResponseEntity<CardSetDetailResponse> updateCardSet(
Long groupId,
Long cardSetId,
CardSetUpdateRequest req,
AuthPrinciple authPrinciple
);
}
9 changes: 9 additions & 0 deletions src/main/java/project/flipnote/cardset/entity/CardSet.java
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,7 @@
import lombok.Builder;
import lombok.Getter;
import lombok.NoArgsConstructor;
import project.flipnote.cardset.model.CardSetUpdatePayload;
import project.flipnote.common.entity.BaseEntity;
import project.flipnote.group.entity.Category;
import project.flipnote.group.entity.Group;
Expand Down Expand Up @@ -57,4 +58,12 @@ private CardSet(String name, Group group, Boolean publicVisible, Category catego
this.hashtag = hashtag;
this.imageUrl = imageUrl;
}

public void update(CardSetUpdatePayload payload) {
this.name = payload.name();
this.publicVisible = payload.publicVisible();
this.category = payload.category();
this.hashtag = payload.hashtag();
this.imageUrl = payload.imageUrl();
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,10 @@
@RequiredArgsConstructor
public enum CardSetErrorCode implements ErrorCode {

GROUP_MEMBER_NOT_FOUND(HttpStatus.FORBIDDEN, "CARDSET_001", "해당 그룹의 멤버가 아닙니다.");
GROUP_MEMBER_NOT_FOUND(HttpStatus.FORBIDDEN, "CARDSET_001", "해당 그룹의 멤버가 아닙니다."),
CARD_SET_NOT_FOUND(HttpStatus.NOT_FOUND, "CARDSET_002", "카드셋이 존재하지 않습니다."),
CARD_SET_PRIVATE(HttpStatus.FORBIDDEN, "CARDSET_003", "비공개 카드셋입니다."),
CARD_SET_NO_EDIT_PERMISSION(HttpStatus.FORBIDDEN, "CARDSET_004", "카드셋 수정 권한이 없습니다.");

private final HttpStatus httpStatus;
private final String code;
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,38 @@
package project.flipnote.cardset.model;

import java.time.LocalDateTime;

import com.fasterxml.jackson.annotation.JsonFormat;

import project.flipnote.cardset.entity.CardSet;

public record CardSetDetailResponse(
Long cardSetId,
Long groupId,
String name,
String category,
String hashtag,
String imageUrl,
boolean publicVisible,

@JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss")
LocalDateTime createdAt,

@JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss")
LocalDateTime modifiedAt
) {

public static CardSetDetailResponse from(CardSet cardSet) {
return new CardSetDetailResponse(
cardSet.getId(),
cardSet.getGroup().getId(),
cardSet.getName(),
cardSet.getCategory().name(),
cardSet.getHashtag(),
cardSet.getImageUrl(),
cardSet.getPublicVisible(),
cardSet.getCreatedAt(),
cardSet.getModifiedAt()
);
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,35 @@
package project.flipnote.cardset.model;

import java.util.Set;

import org.springframework.data.domain.PageRequest;
import org.springframework.data.domain.Sort;

import lombok.Getter;
import lombok.Setter;
import project.flipnote.common.model.request.PagingRequest;

@Getter
@Setter
public class CardSetSearchRequest extends PagingRequest {

private static final Set<String> ALLOWED_SORT_FIELDS = Set.of("id");

private String keyword;
private String category;

@Override
public PageRequest getPageRequest() {
String sortBy = this.getSortBy();
String effectiveSortBy = (sortBy != null && ALLOWED_SORT_FIELDS.contains(sortBy)) ? sortBy : "id";

Sort.Direction direction;
try {
direction = Sort.Direction.fromString(this.getOrder());
} catch (IllegalArgumentException e) {
direction = Sort.Direction.DESC;
}

return PageRequest.of(getPage() - 1, getSize() + 1, Sort.by(direction, effectiveSortBy));
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
package project.flipnote.cardset.model;

import project.flipnote.cardset.entity.CardSet;

public record CardSetSummaryResponse(
Long cardSetId,
Long groupId,
String name,
String category,
String hashtag,
String imageUrl
) {

public static CardSetSummaryResponse from(CardSet cardSet) {
return new CardSetSummaryResponse(
cardSet.getId(),
cardSet.getGroup().getId(),
cardSet.getName(),
cardSet.getCategory().name(),
cardSet.getHashtag(),
cardSet.getImageUrl()
);
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
package project.flipnote.cardset.model;

import project.flipnote.group.entity.Category;

public record CardSetUpdatePayload(
String name,
Boolean publicVisible,
Category category,
String hashtag,
String imageUrl
) {

public static CardSetUpdatePayload from(CardSetUpdateRequest req) {
return new CardSetUpdatePayload(
req.name(),
req.publicVisible(),
req.category(),
req.getHashTag(),
req.image()
);
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,36 @@
package project.flipnote.cardset.model;

import java.util.List;

import org.hibernate.validator.constraints.URL;

import io.swagger.v3.oas.annotations.media.Schema;
import jakarta.validation.constraints.NotBlank;
import jakarta.validation.constraints.NotNull;
import jakarta.validation.constraints.Size;
import project.flipnote.group.entity.Category;

public record CardSetUpdateRequest(

@NotBlank
@Size(max = 50)
String name,

@NotNull
Boolean publicVisible,

@NotNull
Category category,

@NotNull
List<String> hashtag,

@URL
String image
) {

@Schema(hidden = true)
public String getHashTag() {
return hashtag != null && !hashtag.isEmpty() ? String.join(",", hashtag) : null;
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -7,4 +7,6 @@

@Repository
public interface CardSetManagerRepository extends JpaRepository<CardSetManager, Long> {

boolean existsByUser_IdAndCardSet_Id(Long userId, Long cardSetId);
}
Loading
Loading