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 @@ -43,7 +43,7 @@ public RsData<Integer> enrich(
public RsData<Void> create(
@RequestBody CreateRequest reqBody
) {
artistService.createArtist(reqBody.artistName(), reqBody.artistGroup(), reqBody.artistGroup(), reqBody.genreName());
artistService.createArtist(reqBody.artistName(), reqBody.artistGroup(), reqBody.artistType(), reqBody.genreName());
return RsData.success("아티스트 생성이 완료되었습니다.", null);
}

Expand Down
Original file line number Diff line number Diff line change
@@ -1,9 +1,22 @@
package com.back.web7_9_codecrete_be.domain.artists.dto.request;

import com.back.web7_9_codecrete_be.domain.artists.entity.ArtistType;
import jakarta.validation.constraints.NotNull;
import jakarta.validation.constraints.Size;

public record CreateRequest(
@NotNull(message = "아티스트 이름은 필수로 입력해야합니다.")
@Size(max = 200, message = "아티스트 이름은 200자를 넘길 수 없습니다.")
String artistName,

@Size(max = 150, message = "아티스트 그룹 이름은 150자를 넘길 수 없습니다.")
String artistGroup,
String artistType,

@NotNull(message = "아티스트 타입은 필수로 입력해야합니다(SOLO or GROUP)")
ArtistType artistType,

@NotNull(message = "장르는 필수로 입력해야합니다.")
@Size(max = 30, message = "장르는 30자를 넘길 수 없습니다.")
String genreName
) {
}
Original file line number Diff line number Diff line change
@@ -1,9 +1,18 @@
package com.back.web7_9_codecrete_be.domain.artists.dto.request;

import com.back.web7_9_codecrete_be.domain.artists.entity.ArtistType;
import jakarta.validation.constraints.Size;

public record UpdateRequest(
@Size(max = 200, message = "아티스트 이름은 200자를 넘길 수 없습니다.")
String artistName,

@Size(max = 150, message = "아티스트 그룹 이름은 150자를 넘길 수 없습니다.")
String artistGroup,
String artistType,

ArtistType artistType,

@Size(max = 30, message = "장르 이름은 30자를 넘길 수 없습니다.")
String genreName
) {
}
Original file line number Diff line number Diff line change
@@ -1,11 +1,13 @@
package com.back.web7_9_codecrete_be.domain.artists.dto.response;

import com.back.web7_9_codecrete_be.domain.artists.entity.ArtistType;

import java.util.List;

public record ArtistDetailResponse(
String artistName,
String artistGroup,
String artistType,
ArtistType artistType,
String profileImageUrl,
long likeCount,
int totalAlbums,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -24,8 +24,9 @@ public class Artist {
@Column(name = "artist_group")
private String artistGroup;

@Enumerated(EnumType.STRING)
@Column(name = "artist_type")
private String artistType;
private ArtistType artistType;

@ManyToOne(fetch = FetchType.LAZY)
private Genre genre;
Expand All @@ -36,22 +37,22 @@ public class Artist {
@Column(name = "name_ko", length = 200)
private String nameKo;

public Artist(String spotifyArtistId, String artistName, String artistGroup, String artistType, Genre genre) {
public Artist(String spotifyArtistId, String artistName, String artistGroup, ArtistType artistType, Genre genre) {
this.spotifyArtistId = spotifyArtistId;
this.artistName = artistName;
this.artistGroup = artistGroup; // 옵션 B: seed에서는 null
this.artistType = artistType; // 옵션 B: seed에서는 "SINGER"
this.genre = genre;
}

public Artist(String artistName, String artistGroup, String artistType, Genre genre) {
public Artist(String artistName, String artistGroup, ArtistType artistType, Genre genre) {
this.artistName = artistName;
this.artistGroup = artistGroup;
this.artistType = artistType;
this.genre = genre;
}

public void updateProfile(String nameKo, String artistGroup, String artistType) {
public void updateProfile(String nameKo, String artistGroup, ArtistType artistType) {
this.nameKo = nameKo;
this.artistGroup = artistGroup; // nullable
this.artistType = artistType; // "SOLO" / "GROUP"
Expand All @@ -65,7 +66,7 @@ public void changeGroup(String group) {
this.artistGroup = group;
}

public void changeType(String type) {
public void changeType(ArtistType type) {
this.artistType = type;
}

Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
package com.back.web7_9_codecrete_be.domain.artists.entity;

public enum ArtistType {
SOLO,
GROUP
}
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
package com.back.web7_9_codecrete_be.domain.artists.service;

import com.back.web7_9_codecrete_be.domain.artists.entity.Artist;
import com.back.web7_9_codecrete_be.domain.artists.entity.ArtistType;
import com.back.web7_9_codecrete_be.domain.artists.repository.ArtistRepository;
import com.back.web7_9_codecrete_be.global.musicbrainz.MusicBrainzClient;
import com.back.web7_9_codecrete_be.global.wikidata.WikidataClient;
Expand Down Expand Up @@ -95,13 +96,28 @@ protected void enrichSingleArtist(Artist artist) {
}

// 기존 artistType이 있으면 유지, 없으면 가져온 값 사용
String artistType = result.artistType != null ? result.artistType : artist.getArtistType();
String artistTypeStr = result.artistType != null ? result.artistType :
(artist.getArtistType() != null ? artist.getArtistType().name() : null);

// String을 ArtistType enum으로 변환
ArtistType artistType;
if (artistTypeStr != null) {
try {
artistType = ArtistType.valueOf(artistTypeStr);
} catch (IllegalArgumentException e) {
log.warn("잘못된 artistType 값: {}, 기본값 SOLO 사용", artistTypeStr);
artistType = ArtistType.SOLO;
}
} else {
// 기존 값이 없고 새 값도 없으면 기본값 사용
artistType = artist.getArtistType() != null ? artist.getArtistType() : ArtistType.SOLO;
}

// 기존 row를 "보강"
// 기존 row를 "보강"
artist.updateProfile(result.nameKo, result.artistGroup, artistType);
// 명시적으로 save하여 변경사항을 DB에 즉시 반영
artistRepository.save(artist);
log.info("Enrich 성공: artistId={}, name={}, nameKo={}, group={}, type={}, source={}",
log.info("Enrich 성공: artistId={}, name={}, nameKo={}, group={}, type={}, source={}",
artist.getId(), artist.getArtistName(), result.nameKo,
result.artistGroup, artistType, result.source);
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@
import com.back.web7_9_codecrete_be.domain.artists.dto.response.ArtistListResponse;
import com.back.web7_9_codecrete_be.domain.artists.dto.response.ArtistDetailResponse;
import com.back.web7_9_codecrete_be.domain.artists.entity.Artist;
import com.back.web7_9_codecrete_be.domain.artists.entity.ArtistType;
import com.back.web7_9_codecrete_be.domain.artists.entity.Genre;
import com.back.web7_9_codecrete_be.domain.artists.repository.ArtistRepository;
import com.back.web7_9_codecrete_be.domain.artists.repository.ArtistLikeRepository;
Expand All @@ -30,7 +31,7 @@ public int setArtist() {
}

@Transactional
public Artist createArtist(String artistName, String artistGroup, String artistType, String genreName) {
public Artist createArtist(String artistName, String artistGroup, ArtistType artistType, String genreName) {
Genre genre = genreService.findByGenreName(genreName);
if(artistRepository.existsByArtistName(artistName) || artistRepository.existsByNameKo(artistName)) {
throw new BusinessException(ArtistErrorCode.ARTIST_ALREADY_EXISTS);
Expand Down Expand Up @@ -85,8 +86,8 @@ public void updateArtist(Long id, UpdateRequest req) {
changed = true;
}

if (req.artistType() != null && !req.artistType().isBlank()) {
artist.changeType(req.artistType().trim());
if (req.artistType() != null) {
artist.changeType(req.artistType());
changed = true;
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,8 @@
import com.back.web7_9_codecrete_be.domain.artists.dto.response.ArtistDetailResponse;
import com.back.web7_9_codecrete_be.domain.artists.dto.response.RelatedArtistResponse;
import com.back.web7_9_codecrete_be.domain.artists.dto.response.TopTrackResponse;
import com.back.web7_9_codecrete_be.domain.artists.entity.Artist;
import com.back.web7_9_codecrete_be.domain.artists.entity.ArtistType;
import com.back.web7_9_codecrete_be.domain.artists.entity.Genre;
import com.back.web7_9_codecrete_be.domain.artists.repository.ArtistRepository;
import com.back.web7_9_codecrete_be.domain.artists.repository.GenreRepository;
Expand All @@ -19,7 +21,6 @@
import se.michaelthelin.spotify.enums.AlbumType;
import se.michaelthelin.spotify.exceptions.detailed.NotFoundException;
import se.michaelthelin.spotify.model_objects.specification.AlbumSimplified;
import se.michaelthelin.spotify.model_objects.specification.Artist;
import se.michaelthelin.spotify.model_objects.specification.Image;
import se.michaelthelin.spotify.model_objects.specification.Paging;
import se.michaelthelin.spotify.model_objects.specification.Track;
Expand Down Expand Up @@ -63,7 +64,7 @@ public int seedKoreanArtists300() {
int offset = 0;

while (totalSaved < targetCount) {
Paging<Artist> paging = api.searchArtists(q)
Paging<se.michaelthelin.spotify.model_objects.specification.Artist> paging = api.searchArtists(q)
.limit(limit)
.offset(offset)
.build()
Expand All @@ -85,10 +86,10 @@ public int seedKoreanArtists300() {
String mainGenreName = pickMainGenreName(spotifyArtist);
Genre genre = findOrCreateGenreByName(mainGenreName, null);

String artistType = inferArtistType(spotifyArtist);
String artistTypeStr = inferArtistType(spotifyArtist);
ArtistType artistType = ArtistType.valueOf(artistTypeStr);

com.back.web7_9_codecrete_be.domain.artists.entity.Artist artistEntity =
new com.back.web7_9_codecrete_be.domain.artists.entity.Artist(
Artist artistEntity = new Artist(
spotifyId,
name.trim(),
null, // artistGroup
Expand Down Expand Up @@ -127,7 +128,7 @@ public int seedKoreanArtists300() {
"korean indie", "korean rock"
);

private boolean isLikelyKoreanMusic(Artist a) {
private boolean isLikelyKoreanMusic(se.michaelthelin.spotify.model_objects.specification.Artist a) {
String[] genres = a.getGenres();
if (genres != null) {
for (String g : genres) {
Expand All @@ -142,7 +143,7 @@ private boolean isLikelyKoreanMusic(Artist a) {
return name != null && name.matches(".*[가-힣].*");
}

private String pickMainGenreName(Artist a) {
private String pickMainGenreName(se.michaelthelin.spotify.model_objects.specification.Artist a) {
String[] genres = a.getGenres();
if (genres == null || genres.length == 0) return "k-pop";

Expand All @@ -161,7 +162,7 @@ private String pickMainGenreName(Artist a) {
return "k-pop";
}

private String inferArtistType(Artist a) {
private String inferArtistType(se.michaelthelin.spotify.model_objects.specification.Artist a) {
String[] genres = a.getGenres();
if (genres != null) {
for (String g : genres) {
Expand All @@ -182,15 +183,15 @@ private Genre findOrCreateGenreByName(String genreName, String genreGroup) {
public ArtistDetailResponse getArtistDetail(
String spotifyArtistId,
String artistGroup,
String artistType,
ArtistType artistType,
long likeCount,
long artistId,
Long genreId
) {
try {
SpotifyApi api = spotifyClient.getAuthorizedApi();

Artist artist = api.getArtist(spotifyArtistId).build().execute(); // 메인 정보는 실패 시 예외 발생
se.michaelthelin.spotify.model_objects.specification.Artist artist = api.getArtist(spotifyArtistId).build().execute(); // 메인 정보는 실패 시 예외 발생
Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

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

왜 풀path로 쓰시지 싶었는데 기존 artist엔티티랑 충돌이 나셔서 쓰는거였군요!

Copy link
Copy Markdown
Collaborator Author

Choose a reason for hiding this comment

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

맞아요 ㅜ.ㅜ...

Copy link
Copy Markdown
Collaborator Author

Choose a reason for hiding this comment

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

멘토링 때 질문 한 번 해보겠습니당


Track[] topTracks = safeGetTopTracks(api, spotifyArtistId);
Paging<AlbumSimplified> albums = safeGetAlbums(api, spotifyArtistId);
Expand All @@ -210,8 +211,8 @@ public ArtistDetailResponse getArtistDetail(
pickImageUrl(artist.getImages()),
likeCount,
albums != null ? albums.getTotal() : 0,
artist.getPopularity(), // (너가 별점으로 바꾸고 싶으면 여기 가공)
"", // Spotify에서는 설명을 제공하지 않아 공란 처리
artist.getPopularity(), // 별점으로 수정
"", // 설명
toAlbumResponses(albums != null ? albums.getItems() : null, spotifyArtistId),
toTopTrackResponses(topTracks),
relatedResponses
Expand Down Expand Up @@ -252,14 +253,9 @@ private Paging<AlbumSimplified> safeGetAlbums(SpotifyApi api, String artistId) {
}
}

/**
* ✅ related artists
* - 정상 호출
* - related가 비거나 404면 fallback(장르 기반 검색)으로 대체
*/
private List<RelatedArtistResponse> safeGetRelated(
SpotifyApi api,
Artist me,
se.michaelthelin.spotify.model_objects.specification.Artist me,
String artistGroup,
long artistId,
Long genreId
Expand All @@ -271,7 +267,7 @@ private List<RelatedArtistResponse> safeGetRelated(
}

try {
Artist[] related = api.getArtistsRelatedArtists(id).build().execute();
se.michaelthelin.spotify.model_objects.specification.Artist[] related = api.getArtistsRelatedArtists(id).build().execute();
if (related != null && related.length > 0) {
log.info("Spotify related artists fetched: size={} spotifyArtistId={}", related.length, id);
return toRelatedArtistResponses(related);
Expand Down Expand Up @@ -365,7 +361,7 @@ private List<TopTrackResponse> toTopTrackResponses(Track[] tracks) {
.collect(toList());
}

private List<RelatedArtistResponse> toRelatedArtistResponses(Artist[] artists) {
private List<RelatedArtistResponse> toRelatedArtistResponses(se.michaelthelin.spotify.model_objects.specification.Artist[] artists) {
if (artists == null) return List.of();
return Stream.of(artists)
.filter(Objects::nonNull)
Expand Down