wafflestudio / seminar-2021

2021 Rookies 세미나
47 stars 110 forks source link

(Django 과제3) tests.py 내부 atomic() 사용 / 2번 문제 정오 확인 #518

Closed footprinthere closed 3 years ago

footprinthere commented 3 years ago

요약

  1. 과제의 1번 문제에서 제공된 test 파일을 실행했더니 TransactionManagementError가 나왔는데, 코드 내부에 atomic() block을 추가해도 될까요?
  2. 과제의 2번에서 test를 작성해야 하는 API 중 POST /api/v1/user/가 포함되어 있는데, 혹시 오타인가요?





문제 내용

1

과제 1번을 수행하기 위해 $ python manage.py test 커맨드로 제공된 test 파일을 실행했더니 test_post_user_중복()에서 아래와 같이 오류가 발생했습니다. image

검색을 해보니 중복된 유저 생성을 시도할 때 IntegrityError가 발생하도록 구현이 되어 있어 이 때문에 오류가 발생한 것 같았습니다. 그래서 test 코드의 해당 부분을 아래와 같이 수정했습니다.

    def test_post_user_중복(self):
        data = self.post_data
        with transaction.atomic():
            response = self.client.post('/api/v1/signup/', data=data)
        self.assertEqual(response.status_code, status.HTTP_409_CONFLICT)    # 중복 회원가입 시도 시 409

        user_count = User.objects.count()
        self.assertEqual(user_count, 1)     # 생성되지 않음

그랬더니 오류가 발생하지 않고 정상적으로 test가 완료되었습니다. 이렇게 수정해도 괜찮을까요? 아니면 다른 해결책을 의도하신 건가요?

2

과제의 2번을 보면 POST /api/v1/user/ API에 대한 test를 작성하라고 되어 있는데, 이는 과제2에서 명시되어 있지 않았던 API인 것 같습니다. 혹시 POST /api/v1/user/participant/를 의미하는 것인가 싶었는데 그건 목록의 아래쪽에 따로 있더군요. 제가 무언가를 놓친 것인지, 아니면 잘못 적으신 것인지 궁금합니다. image

Jhvictor4 commented 3 years ago

2번은 /signup/ 으로 수정해야 합니다. 죄송합니다.

1번은 제가 예시답안 구현을 atomic하게 해서 인지 못하고 있었네요. 아뇨 저기서는 의도한 구현은 없습니다. 해결 정확한 방법으로 해주셨습니다.

이대로 반영해서 코드 최신화 하겠습니다. 감사합니다.

Jhvictor4 commented 3 years ago

@footprinthere 참고하시도록 전달드리면,

signup 과정에서 이제 profile을 고르기 때문에, create 쿼리 하나로는 제대로 된 동작을 이행할 수 없습니다. 만약 유저 생성 후 -> 프로필 생성 과정을 거친다면,

후자에서 에러가 났을 때 이미 생성된 유저도 삭제할 필요가 있습니다. 이를 제대로 구현하려면 transaction 관리를 해주어야 합니다.

다만 세미나에서 다루지 않기도 했고, 에러가 날려면 보통 첫번째 유저 생성 단계에서 걸리기 때문에 없어도 동작은 할 것 같습니다. 성태님 지적해주신것처럼 테스트에 아토믹 설정을 달아주어야 로직은 잘 동작하는 다른 구현들도 테스트해줄 수 있을 것 같긴 합니다만, 없이 돌렸을 때도 돌아가도록 구현해주시면 더욱 좋긴 합니다.

footprinthere commented 3 years ago

아.. 그렇게 구현하는 게 가능하군요. 좀 더 고민해보겠습니다! 감사합니다 :)