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

Feature/#901 온보딩에서 활동 설정 시 관심태그도 함께 설정 #903

Open
wants to merge 4 commits into
base: backend-main
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from 1 commit
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 @@ -8,7 +8,6 @@
import com.emmsale.member.application.dto.DescriptionRequest;
import com.emmsale.member.application.dto.MemberActivityAddRequest;
import com.emmsale.member.application.dto.MemberActivityInitialRequest;
import com.emmsale.member.application.dto.MemberActivityResponse;
import com.emmsale.member.application.dto.MemberDetailResponse;
import com.emmsale.member.application.dto.MemberImageResponse;
import com.emmsale.member.domain.Member;
Expand Down Expand Up @@ -42,7 +41,7 @@ public ResponseEntity<Void> register(
final Member member,
@RequestBody final MemberActivityInitialRequest memberActivityInitialRequest
) {
memberActivityCommandService.registerActivities(member, memberActivityInitialRequest);
memberCommandService.initializeMember(member, memberActivityInitialRequest);
return ResponseEntity.noContent().build();
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -33,6 +33,17 @@ public List<InterestTagResponse> findInterestTags(final Long memberId) {
return InterestTagResponse.convertAllFrom(interestTags);
}

public void initializeInterestTags(final Member member, final List<String> tagNames) {
if (member.isOnboarded()) {
Copy link
Collaborator

Choose a reason for hiding this comment

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

멤버의 온보딩 여부를 interestTag에서 해주고 있는데,

Member를 initializae 시키는 initializeMember에서 예외처리하는게 적절해보여요.

그러면 온보딩이 된 멤버의 경우 불필요한 activity 조회 등록도 안 일어날 것 같고요.

Copy link
Collaborator Author

Choose a reason for hiding this comment

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

넵 반영하겠습니다!

throw new MemberException(MemberExceptionType.ALREADY_ONBOARDING);
}
final List<Tag> tags = tagRepository.findByNameIn(tagNames);
final List<InterestTag> interestTags = tags.stream()
.map(tag -> new InterestTag(member, tag))
.collect(Collectors.toList());
interestTagRepository.saveAll(interestTags);
}

public List<InterestTagResponse> addInterestTag(final Member member,
final InterestTagAddRequest request) {
final List<Long> tagIds = request.getTagIds();
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,6 @@
import com.emmsale.activity.domain.ActivityRepository;
import com.emmsale.member.application.dto.MemberActivityAddRequest;
import com.emmsale.member.application.dto.MemberActivityInitialRequest;
import com.emmsale.member.application.dto.MemberActivityResponse;
import com.emmsale.member.domain.Member;
import com.emmsale.member.domain.MemberActivity;
import com.emmsale.member.domain.MemberActivityRepository;
Expand All @@ -26,28 +25,27 @@ public class MemberActivityCommandService {
private final MemberActivityRepository memberActivityRepository;
private final ActivityRepository activityRepository;

public void registerActivities(
public List<MemberActivity> registerActivities(
final Member member,
final MemberActivityInitialRequest memberActivityInitialRequest
) {
if (member.isOnboarded()) {
throw new MemberException(MemberExceptionType.ALREADY_ONBOARDING);
}
final List<Long> activityIds = memberActivityInitialRequest.getActivityIds();
saveMemberActivities(member, activityIds);

member.updateName(memberActivityInitialRequest.getName());
return saveMemberActivities(member, activityIds);
}

private void saveMemberActivities(final Member member, final List<Long> activityIds) {
private List<MemberActivity> saveMemberActivities(final Member member,
final List<Long> activityIds) {
final List<MemberActivity> memberActivities = activityRepository.findAllById(activityIds)
.stream()
.map(it -> new MemberActivity(it, member))
.collect(toUnmodifiableList());

validateAllActivityIdsExist(activityIds, memberActivities);

memberActivityRepository.saveAll(memberActivities);
return memberActivities;
}

private void validateAllActivityIdsExist(
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -2,12 +2,15 @@

import com.emmsale.image.application.S3Client;
import com.emmsale.member.application.dto.DescriptionRequest;
import com.emmsale.member.application.dto.MemberActivityInitialRequest;
import com.emmsale.member.application.dto.MemberImageResponse;
import com.emmsale.member.domain.Member;
import com.emmsale.member.domain.MemberActivity;
import com.emmsale.member.domain.MemberRepository;
import com.emmsale.member.exception.MemberException;
import com.emmsale.member.exception.MemberExceptionType;
import java.util.List;
import java.util.stream.Collectors;
import javax.transaction.Transactional;
import lombok.RequiredArgsConstructor;
import org.springframework.stereotype.Service;
Expand All @@ -19,8 +22,22 @@
public class MemberCommandService {

private final MemberRepository memberRepository;
private final MemberActivityCommandService memberActivityCommandService;
private final InterestTagService interestTagService;
private final S3Client s3Client;

public void initializeMember(final Member member, final MemberActivityInitialRequest request) {
final List<MemberActivity> memberActivities = memberActivityCommandService.registerActivities(
member, request);
final List<String> activityNames = memberActivities.stream()
.filter(MemberActivity::isJobActivity)
.map(MemberActivity::getActivityName)
.collect(Collectors.toList());
interestTagService.initializeInterestTags(member, activityNames);

member.updateName(request.getName());
}

public void updateDescription(final Member member, final DescriptionRequest descriptionRequest) {
final String description = descriptionRequest.getDescription();

Expand Down
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
package com.emmsale.member.domain;

import com.emmsale.activity.domain.Activity;
import com.emmsale.activity.domain.ActivityType;
import com.emmsale.base.BaseEntity;
import javax.persistence.Entity;
import javax.persistence.FetchType;
Expand Down Expand Up @@ -34,4 +35,12 @@ public MemberActivity(final Activity activity, final Member member) {
this.activity = activity;
this.member = member;
}

public String getActivityName() {
return activity.getName();
}

public Boolean isJobActivity() {
return activity.getActivityType() == ActivityType.JOB;
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -42,6 +42,7 @@ class InterestTagServiceTest extends ServiceIntegrationTestHelper {
private TagRepository tagRepository;

private Member 사용자;
private Member 새로운_사용자;
private Tag 백엔드;
private Tag 프론트엔드;
private Tag 안드로이드;
Expand All @@ -50,6 +51,7 @@ class InterestTagServiceTest extends ServiceIntegrationTestHelper {
@BeforeEach
void init() {
사용자 = memberRepository.findById(1L).get();
새로운_사용자 = memberRepository.findById(3L).get();

백엔드 = tagRepository.save(백엔드());
프론트엔드 = tagRepository.save(프론트엔드());
Expand All @@ -60,6 +62,23 @@ void init() {
interestTagRepository.save(new InterestTag(사용자, 프론트엔드));
}

@Test
@DisplayName("태그 이름을 입력받으면 부합하는 태그가 관심 태그로 설정된다.")
void initializeInterestTags() {
// given
final List<String> tagNames = List.of("백엔드", "프론트엔드");
final List<InterestTagResponse> expected = InterestTagResponse.convertAllFrom(
List.of(new InterestTag(새로운_사용자, 백엔드), new InterestTag(새로운_사용자, 프론트엔드)));

// when
interestTagService.initializeInterestTags(새로운_사용자, tagNames);
final List<InterestTagResponse> actual = interestTagService.findInterestTags(새로운_사용자.getId());
// then
assertThat(actual)
.usingRecursiveComparison()
.isEqualTo(expected);
}

@Test
@DisplayName("사용자 id를 입력으로 받으면 사용자의 관심 태그 리스트를 조회할 수 있다.")
void findInterestTags() {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -2,19 +2,18 @@

import static org.assertj.core.api.Assertions.assertThat;
import static org.assertj.core.api.Assertions.assertThatThrownBy;
import static org.junit.jupiter.api.Assertions.assertAll;
import static org.junit.jupiter.api.Assertions.assertDoesNotThrow;
import static org.junit.jupiter.api.Assertions.assertEquals;

import com.emmsale.activity.application.dto.ActivityResponse;
import com.emmsale.helper.ServiceIntegrationTestHelper;
import com.emmsale.member.application.dto.MemberActivityAddRequest;
import com.emmsale.member.application.dto.MemberActivityInitialRequest;
import com.emmsale.member.domain.Member;
import com.emmsale.member.domain.MemberActivityRepository;
import com.emmsale.member.domain.MemberRepository;
import com.emmsale.member.exception.MemberException;
import com.emmsale.member.exception.MemberExceptionType;
import java.util.List;
import java.util.stream.Collectors;
import org.assertj.core.api.ThrowableAssert.ThrowingCallable;
import org.junit.jupiter.api.DisplayName;
import org.junit.jupiter.api.Test;
Expand All @@ -25,28 +24,36 @@ class MemberActivityCommandServiceTest extends ServiceIntegrationTestHelper {
@Autowired
private MemberActivityCommandService memberActivityCommandService;

@Autowired
private MemberCommandService memberCommandService;

@Autowired
private MemberRepository memberRepository;

@Autowired
private MemberActivityRepository memberActivityRepository;

@Test
@DisplayName("Activity의 id를 통해서, 사용자의 Activity를 등록하고 사용자의 이름을 수정할 수 있다.")
@DisplayName("Activity의 id를 통해서, 사용자의 Activity를 등록할 수 있다.")
void registerActivities() throws Exception {
//given
final List<Long> activityIds = List.of(1L, 2L, 3L);
final long savedMemberId = 1L;
// given
final List<Long> expected = List.of(1L, 2L, 3L);
final long savedMemberId = 3L;

final Member member = memberRepository.findById(savedMemberId).get();
final String updateName = "우르";

final MemberActivityInitialRequest request = new MemberActivityInitialRequest(updateName,
activityIds);
expected);

//when & then
assertAll(
() -> assertDoesNotThrow(
() -> memberActivityCommandService.registerActivities(member, request)),
() -> assertEquals(updateName, member.getName())
);
// when
memberActivityCommandService.registerActivities(member, request);
final List<Long> actual = memberActivityRepository.findAllByMember(member)
.stream()
.map(memberActivity -> memberActivity.getActivity().getId())
.collect(Collectors.toList());
// then
assertThat(actual).usingRecursiveComparison().isEqualTo(expected);
}

@Test
Expand All @@ -63,7 +70,7 @@ void registerActivities_fail() throws Exception {
activityIds);

// when
memberActivityCommandService.registerActivities(member, request);
memberCommandService.initializeMember(member, request);
final ThrowingCallable actual = () -> memberActivityCommandService.registerActivities(member,
request);

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,8 @@
import static org.assertj.core.api.Assertions.assertThat;
import static org.assertj.core.api.Assertions.assertThatThrownBy;
import static org.junit.jupiter.api.Assertions.assertAll;
import static org.junit.jupiter.api.Assertions.assertDoesNotThrow;
import static org.junit.jupiter.api.Assertions.assertEquals;
import static org.mockito.ArgumentMatchers.anyList;
import static org.mockito.ArgumentMatchers.anyString;
import static org.mockito.Mockito.times;
Expand All @@ -13,10 +15,15 @@

import com.emmsale.helper.ServiceIntegrationTestHelper;
import com.emmsale.member.application.dto.DescriptionRequest;
import com.emmsale.member.application.dto.MemberActivityInitialRequest;
import com.emmsale.member.domain.InterestTagRepository;
import com.emmsale.member.domain.Member;
import com.emmsale.member.domain.MemberRepository;
import com.emmsale.member.exception.MemberException;
import com.emmsale.member.exception.MemberExceptionType;
import com.emmsale.tag.domain.Tag;
import com.emmsale.tag.domain.TagRepository;
import java.util.List;
import org.assertj.core.api.ThrowableAssert.ThrowingCallable;
import org.junit.jupiter.api.BeforeEach;
import org.junit.jupiter.api.DisplayName;
Expand All @@ -37,6 +44,34 @@ class MemberCommandServiceTest extends ServiceIntegrationTestHelper {
private MemberCommandService memberCommandService;
@Autowired
private MemberRepository memberRepository;
@Autowired
private InterestTagRepository interestTagRepository;
@Autowired
private TagRepository tagRepository;

@Test
@DisplayName("Activity의 id를 통해서, 사용자의 Activity를 등록하고 사용자의 이름을 수정할 수 있다.")
void registerActivities() throws Exception {
//given
tagRepository.save(new Tag("Backend"));
final List<Long> activityIds = List.of(1L, 2L, 6L);
final long savedMemberId = 1L;

final Member member = memberRepository.findById(savedMemberId).get();
final String updateName = "우르";

final MemberActivityInitialRequest request = new MemberActivityInitialRequest(updateName,
activityIds);

//when & then
assertAll(
() -> assertDoesNotThrow(
Copy link
Collaborator

Choose a reason for hiding this comment

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

요 assertDoesNotThrow 부분은 따로 분리해보면 어떤가요?

저 부분에서 에러가 나지 않는 것을 굳이 assertAll로 감싸고 체크할 필요는 없다고 생각해요.

Copy link
Collaborator Author

Choose a reason for hiding this comment

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

넵 분리해주었습니다~

() -> memberCommandService.initializeMember(member, request)),
() -> assertEquals(updateName, member.getName()),
() -> assertEquals(1,
interestTagRepository.findInterestTagsByMemberId(savedMemberId).size())
);
}

@Nested
@DisplayName("한줄 자기소개를 업데이트한다.")
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -45,7 +45,7 @@ void findOrCreateMemberTest() {
@DisplayName("사용자를 조회하고 존재하지 않으므로 새로 생성하고 생성한 결과를 반환한다.")
void findOrCreateMemberTestWithNewMember() {
//given
final MemberQueryResponse expectResponse = new MemberQueryResponse(3L, false);
final MemberQueryResponse expectResponse = new MemberQueryResponse(4L, false);

final GithubProfileResponse githubProfileFromGithub = new GithubProfileResponse("0", "name",
"username", "https://imageUrl.com");
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -19,7 +19,7 @@ class MemberRepositoryTest extends JpaRepositorySliceTestHelper {
@DisplayName("countMembersById() : 주어진 ids에서 존재하는 members의 개수를 구할 수 있다.")
void test_existsMembersByInIds() throws Exception {
//given
final List<Long> memberIds = List.of(1L, 2L, 3L);
final List<Long> memberIds = List.of(1L, 2L, 4L);

//when
final Long count = memberRepository.countMembersById(memberIds);
Expand All @@ -32,7 +32,7 @@ void test_existsMembersByInIds() throws Exception {
@DisplayName("findAllByIdIn() : 주어진 id들에 속한 member들을 조회할 수 있다.")
void test_findAllByIdIn() throws Exception {
//given
final Set<Long> memberIds = Set.of(1L, 2L, 3L);
final Set<Long> memberIds = Set.of(1L, 2L, 4L);

final List<Member> expected = List.of(
memberRepository.findById(1L).get(),
Expand Down
5 changes: 5 additions & 0 deletions backend/emm-sale/src/test/resources/data-test.sql
Original file line number Diff line number Diff line change
Expand Up @@ -46,6 +46,11 @@ insert into member(id, name, image_url, open_profile_url, github_id, github_user
values (2, 'member2', 'https://imageurl.com', 'https://openprofileurl.com', 2, 'amaran-th22',
CURRENT_TIMESTAMP(),
CURRENT_TIMESTAMP());
insert into member(id, name, image_url, open_profile_url, github_id, github_username, created_at,
Copy link
Collaborator

Choose a reason for hiding this comment

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

혹시 해당 로직은 왜 추가한건지 알 수 있을까요? 저희가 되도록이면 data-test.sql을 안 건들기로 했었어서요

Copy link
Collaborator

Choose a reason for hiding this comment

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

이런 데이터 하나 추가로 변경해야될 테스트 코드도 있는거 같아서요

Copy link
Collaborator Author

Choose a reason for hiding this comment

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

엥 그러네요... MemberFixture를 추가하면 된다는 생각을 못 했었나봅니다,,, 다시 삭제해두겠습니다

updated_at)
values (3, null, 'https://imageurl.com', 'https://openprofileurl.com', 33, 'amaran-th333',
CURRENT_TIMESTAMP(),
CURRENT_TIMESTAMP());

insert into member_activity(id, activity_id, member_id, created_at, updated_at)
values (1, 1, 1, CURRENT_TIMESTAMP(), CURRENT_TIMESTAMP());
Expand Down
Loading