묻고 답해요
141만명의 커뮤니티!! 함께 토론해봐요.
인프런 TOP Writers
-
미해결Practical Testing: 실용적인 테스트 가이드
OrderRepositoryTest에서 단위테스트가 가능한가요?
@SpringBootTest class OrderRepositoryTest { @Autowired private OrderRepository orderRepository; @Autowired private ProductRepository productRepository; @DisplayName("해당 날짜의 모든 결제 내역을 조회한다.") @Test void findAllByDate() { // given LocalDateTime time1 = LocalDateTime.of(2024, 5, 11, 10, 0); LocalDateTime time2 = LocalDateTime.of(2024, 5, 10, 10, 0); Product product1 = createProduct("001"); Product product2 = createProduct("002"); Product product3 = createProduct("003"); Product product4 = createProduct("004"); productRepository.saveAll(List.of(product1, product2, product3, product4)); Order order1 = Order.builder() .products(List.of(product1, product2)) .now(time1) .build(); Order order2 = Order.builder() .products(List.of(product3, product4)) .now(time2) .build(); orderRepository.saveAll(List.of(order1, order2)); // when LocalDate findDate = LocalDate.of(2024, 5, 11); List<Order> findOrders = orderRepository.findAllByDate( findDate.atStartOfDay(), findDate.plusDays(1).atStartOfDay(), OrderStatus.INIT ); // then Assertions.assertThat(findOrders).hasSize(1); } private static Product createProduct(String number){ return Product.builder() .productNumber(number) .productType(ProductType.HAND_MADE) .sellingType(ProductSellingType.SELLING) .name("test") .price(1000) .build(); } } OrderRepositoryTest에서 매서드 테스트를 할 때, Order와 Product는 1대다 다대1로 연관관계 매핑되어 있는 상태인데, 그러면 위와 같이 작성할 경우, productRepository와 관련된 코드가 들어가니, 단위테스트가 깨지는거 아닌가요? 이럴때 어떻게 해야하나요?
-
미해결따라하며 배우는 리액트 A-Z[19버전 반영]
검색어 입력 후 초기화하는 방법 궁금합니다!
안녕하세요. 강의 수강 중에 추가적으로 구현하고 싶은 기능이 있는데 어떻게 해야할지 모르겠어서.. 질문 남깁니다. 검색창에 검색어를 입력하면 SearchPage에 관련 영화 포스터들이 나오고 그 중에 하나를 클릭해서 영화 상세 페이지(DetailPage)로 이동했을 때 검색창을 초기화하고 싶은데 어떻게 해야 하는지 궁금합니다.
-
미해결Practical Testing: 실용적인 테스트 가이드
강의에서 나온 Service 레이어 테스트에 대해서 질문이 있습니당
강사님은 classicist를 지향한다고 했는데, classicist의 단위 테스트는 데이터베이스와 같은 공유 의존성을 테스트 대역(mock)으로 대체해야 한다는 것으로 알고 있는데 유연한 사고(?)로 classist를 지향하지만 통합 테스트로 단위를 확인하는 것을 좋아한다 정도로 정리하면 좋을까요? 아니면 H2를 사용했으니 테스트 대역을 운영환경보단 빠른 환경으로 교체했으니 여전히 단위 테스트라고 생각을 하시는 걸까요?service 레이어를 통합 테스트로 안 짜는 팀에서 classicist를 지향한다면 DB에 대한 의존성을 어떻게 대체하는지 간단한 예제라도 보여주실 수 있을까요? ㅠ
-
미해결Practical Testing: 실용적인 테스트 가이드
Mock과 Stub의 차이가 아직 잘 구분되지 않습니다.
개인적으로 Mock은 상태를 (내가 작성한 값을) 반환하는 것, Stub은 상태가 (내가 작성한 구현대로) 반환되는 것이라고 정의를 내리고 있습니다. 이와 같은 표현으로 차이를 이해하고 있어도 괜찮을까요?아니면 좀 더 명확한 표현이 있을까요? Mock 객체에 우리가 원하는 행위를 정의(Stubbing)하면,그 객체는 이제 Mock 객체라고 해야하나요 아니면 Stub 객체라고 해야하나요? 아래 코드를 보고 Mock 객체인 mailSendClient의 send 메서드에 대한 Stubbing이 이루어졌다. 라고 하면 맞는 표현인가요?@ExtendWith(MockitoExtension.class) class MailServiceTest { @Mock private MailSendClient mailSendClient; @Mock private MailSendHistoryRepository mailSendHistoryRepository; @InjectMocks private MailService mailService; @DisplayName("메일 전송 테스트") @Test void sendMail() { // given when(mailSendClient.send(anyString(), anyString(), anyString(), anyString())) .thenReturn(true); // when boolean result = mailService.sendMail("", "", "", ""); // then assertThat(result).isTrue(); // verify(mailSendHistoryRepository, times(1)) // .save(any(MailSendHistory.class)); } } mailSendClient는 Mocking하더라도 상태검증을 할 수도 있고, Stubbing하더라도 행위검증을 할 수도 있지 않나요?이 둘의 차이는 Mockist와 Classicist의 차이이지, Mock과 Stub의 차이라고 할 수 없지 않을까요?
-
미해결Practical Testing: 실용적인 테스트 가이드
@SpringBootTest 여러 개 사용 시 데이터 남아있는지 여부 문의
안녕하세요. 프로젝트 내에서 통합 테스트를 위해서 @SpringBootTest를 사용한 여러 테스트 코드를 작성하였습니다.예를 들어 아래와 같이 별개의 2개 테스트 코드에는 각각 school table의 값을 생성 및 조회하는 코드가 들어있습니다.@SpringBootTest @Transactional class aTest { // JPA 사용해서 school Table의 data 생성/조회 } --------------------- @SpringBootTest @Transactional class bTest { // JPA 사용해서 school Table의 data 생성/조회 } 위와 같이 테스트 코드를 작성하고 aTest.java 에서 school table에 3개의 데이터를 넣은 경우, bTest.java 에서 school 테이블의 값을 읽었을 때, aTest.java에서 넣은 값은 지워지는 것인지요? 아니면 그대로 남아 bTest.java 에서 조회가 가능한 것인지요?@Transactional이 들어가 있는 경우 데이터가 rollback 되는 것으로 알고 있어서, bTest.java에서 읽었을 때는 빈 테이블이 있을 것으로 예상했는데, 테스트를 해보면 School table의 id 값(자동 증가하는 값)이 bTest.java에서 처음 읽었을 때 4로 보이는 현상이 있어서 질문을 드립니다.
-
미해결스프링부트 JUnit 테스트 - 시큐리티를 활용한 Bank 애플리케이션
테스트 방식에 관해서 질문이 있어요
안녕하세요 강사님 강의 듣고 많이 배우고 있습니다.다름이 아니라 테스트 방식에 질문이 있어서 문의 드립니다.현재 테스트는 서비스 코드를 먼저 짜고 테스트를 진행하는데테스트 방식에는 테스트 코드를 먼저 짜고 서비스 코드를 만들어가는 형식도 있더라구요..둘 차이점이 혹시 있을까요..
-
미해결Practical Testing: 실용적인 테스트 가이드
강사님 유효성 검증의 분리에 대해 궁금한점이 있습니다.
학습 관련 질문을 남겨주세요. 어떤 부분이 고민인지, 무엇이 문제인지 상세히 작성하면 더 좋아요!먼저 유사한 질문이 있었는지 검색해 보세요.서로 예의를 지키며 존중하는 문화를 만들어가요. 저희만의 서비스에 특화된 비즈니스 검증로직은 따로 서비스나 도메인에서 분리해서 검증하라고 하셨는데, 정확히 이해가 가지 않아서 좀더 질문 드립니다.예를 들어, 패스워드 검증 로직이 있다고 하면, 저희만의 서비스는 패스워드 검증을( 영문,특문 혼합 8자이상)이라고 정했을때, 컨트롤러의 요청 부분에서는 @NotBlank를 처리하고, 서비스나 도메인에서 위의 패스워드 검증 로직을 진행하라는 말씀인가요??
-
미해결따라하며 배우는 리액트 A-Z[19버전 반영]
Banner.css에 대해서
강사님은 내부적으로 Banner.css에 대한 내용을 복붙하셨는데,강의 영상에서 Banner.css 내에 소스가 다표기가 되지 않아서동일하게 진행하기 어려운 것 같습니다.
-
미해결Practical Testing: 실용적인 테스트 가이드
환경별 DB 분리 질문있습니다.
안녕하세요.application.yml에서 local, test로 환경을 나누어서 h2 db를 통해 테스트 코드를 만들어보고있습니다.나중에 운영 서버나 릴리즈 서버같은곳에 빌드, 배포할때도 테스트를 진행해야 할텐데 DB 주소를 어떻게 설정하는게 좋을까요? 각각 실제로 사용할 DB의 주소를 적어놓을텐데 빌드하면서 테스트를 진행하면 해당 DB의 테이블과 데이터를 건드리게 될거란 생각이 들어서요..테스트용 resources로 yml을 따로 작성해서 해야할까요?
-
미해결Java/Spring 테스트를 추가하고 싶은 개발자들의 오답노트
실습 1부 레파지토리 커버리지
안녕하세요.강사님은 UserEntitiy 부분이 100%가 나오는데 저는 똑같이 따라해도 UserEntitiy 부분은 테스트 커버리지가 0%로 나옵니다. 제 코드는 practice-part-1의 feat: initialize toy project 버전입니다.강의만 따라가면 다른 분들도 이렇게 나오시나요? 아니면 제가 뭘 놓친 걸까요?practice-part-1 브랜치 보아도 제 코드랑 크게 다른 부분은 없는 것 같은데 왜 커버리지가 다른지 궁금합니다..!
-
미해결실전! 스프링부트 상품-주문 API 개발로 알아보는 TDD
실무 Asserta 사용여부가 궁금합니다.
안녕하세요 강의를보다가 validation 검사를Assert Class를 활용하여 하고 계시던데실무에서도 자주 쓰는 문법인지 궁금합니다.
-
해결됨모든 개발자의 실무를 위한 올인원 기본기 클래스
코드 github
실전프로젝트에서 사용한 코드를 볼수있는 github 주소가있을까요?? 제가 못찾는건가요 ㅠㅠ
-
미해결모든 개발자의 실무를 위한 올인원 기본기 클래스
alembic, dto 위치
안녕하세요!! alembic 을 적용할때는 infrastructure - database - alembic 폴더 이런식으로 구조짜면되는건가요?? 또 dto 는 어디에 위치해야하나요? dto, domain entity, orm entity 모두 필요한거아닌가요?!?! 강의에 dto 가 없어서 헷갈려서 질문드립니다...!! 혹시 domain entity 를 dto 개념으로 사용하신건가요??
-
미해결Do It! 장고+부트스트랩: 파이썬 웹개발의 정석
구글 로그인 오류 .
강의와 동일하게 진행을 했음에도 불구하고 오류가 계속 나옵니다 . 어떻게 해야할지 구글링을 해보아도 답을 찾기 힘들어 질문합니다 해결방법을 알려주시면 정말 감사하겠습니다.
-
미해결Do It! 장고+부트스트랩: 파이썬 웹개발의 정석
makemigrations 을 했는데 aws lightsail에서
makemigrations을 했는데 no changes detected가 나왔습니다 근데 docker-compose logs를 하면 db 오류가 계속 나옵니다 이런 경우에는 어떻게 하여야 하죠? 사진 첨부가 안되서 직접 복붙하겠습니다 FROM "blog_post" ORDER BY "blog_post"."id" DESC LIMIT 3db_1 | 2024-04-01 12:29:31.263 UTC [47] ERROR: relation "blog_post" does not exist at character 256db_1 | 2024-04-01 12:29:31.263 UTC [47] STATEMENT: SELECT "blog_post"."id", "blog_post"."title", "blog_post"."content", "blog_post"."hook_text", "blog_post"."author_id", "blog_post"."category_id", "blog_post"."head_image", "blog_post"."file_upload", "blog_post"."created_at", "blog_post"."updated_at" FROM "blog_post" ORDER BY "blog_post"."id" DESC LIMIT 3db_1 | 2024-04-01 12:29:31.264 UTC [47] ERROR: relation "blog_post" does not exist at character 256db_1 | 2024-04-01 12:29:31.264 UTC [47] STATEMENT: SELECT "blog_post"."id", "blog_post"."title", "blog_post"."content", "blog_post"."hook_text", "blog_post"."author_id", "blog_post"."category_id", "blog_post"."head_image", "blog_post"."file_upload", "blog_post"."created_at", "blog_post"."updated_at" FROM "blog_post" ORDER BY "blog_post"."id" DESC LIMIT 3db_1 | 2024-04-01 12:29:31.265 UTC [47] ERROR: relation "blog_post" does not exist at character 256db_1 | 2024-04-01 12:29:31.265 UTC [47] STATEMENT: SELECT "blog_post"."id", "blog_post"."title", "blog_post"."content", "blog_post"."hook_text", "blog_post"."author_id", "blog_post"."category_id", "blog_post"."head_image", "blog_post"."file_upload", "blog_post"."created_at", "blog_post"."updated_at" FROM "blog_post" ORDER BY "blog_post"."id" DESC LIMIT 3db_1 | 2024-04-01 12:29:31.265 UTC [47] ERROR: relation "blog_post" does not exist at character 256db_1 | 2024-04-01 12:29:31.265 UTC [47] STATEMENT: SELECT "blog_post"."id", "blog_post"."title", "blog_post"."content", "blog_post"."hook_text", "blog_post"."author_id", "blog_post"."category_id", "blog_post"."head_image", "blog_post"."file_upload", "blog_post"."created_at", "blog_post"."updated_at" FROM "blog_post" ORDER BY "blog_post"."id" DESC LIMIT 3db_1 | 2024-04-01 12:29:31.266 UTC [47] ERROR: relation "blog_post" does not exist at character 256db_1 | 2024-04-01 12:29:31.266 UTC [47] STATEMENT: SELECT "blog_post"."id", "blog_post"."title", "blog_post"."content", "blog_post"."hook_text", "blog_post"."author_id", "blog_post"."category_id", "blog_post"."head_image", "blog_post"."file_upload", "blog_post"."created_at", "blog_post"."updated_at" FROM "blog_post" ORDER BY "blog_post"."id" DESC LIMIT 3db_1 | 2024-04-01 12:29:31.266 UTC [47] ERROR: relation "blog_post" does not exist at character 256db_1 | 2024-04-01 12:29:31.266 UTC [47] STATEMENT: SELECT "blog_post"."id", "blog_post"."title", "blog_post"."content", "blog_post"."hook_text", "blog_post"."author_id", "blog_post"."category_id", "blog_post"."head_image", "blog_post"."file_upload", "blog_post"."created_at", "blog_post"."updated_at" FROM "blog_post" ORDER BY "blog_post"."id" DESC LIMIT 3db_1 | 2024-04-01 12:29:31.267 UTC [47] ERROR: relation "blog_post" does not exist at character 256db_1 | 2024-04-01 12:29:31.267 UTC [47] STATEMENT: SELECT "blog_post"."id", "blog_post"."title", "blog_post"."content", "blog_post"."hook_text", "blog_post"."author_id", "blog_post"."category_id", "blog_post"."head_image", "blog_post"."file_upload", "blog_post"."created_at", "blog_post"."updated_at" FROM "blog_post" ORDER BY "blog_post"."id" DESC LIMIT 3web_1 | [2024-04-01 12:20:00 +0000] [1] [INFO] Starting gunicorn 21.2.0web_1 | [2024-04-01 12:20:00 +0000] [1] [INFO] Listening at: http://0.0.0.0:8000 (1)web_1 | [2024-04-01 12:20:00 +0000] [1] [INFO] Using worker: syncweb_1 | [2024-04-01 12:20:00 +0000] [7] [INFO] Booting worker with pid: 7[ec2-user@ip-172-26-12-132 django_giyeon]$ docker-compose exec web python manage.py makemigrationsNo changes detected
-
미해결Practical Testing: 실용적인 테스트 가이드
이 강의 주제를 듣다가.. 외부 시스템
학습 관련 질문을 남겨주세요. 어떤 부분이 고민인지, 무엇이 문제인지 상세히 작성하면 더 좋아요!먼저 유사한 질문이 있었는지 검색해 보세요.서로 예의를 지키며 존중하는 문화를 만들어가요. 제가 테스트 코드를 수행 도중에 맞닥뜨린 고민이 있었습니다.보통 메일과 같은 외부시스템(AWS)를 사용하게 되면, 그 해당 외부시스템의 key값과, secret값이 필요해서 application.yml 에 해당 key값과 secret값을 환경 변수로 설정해서, @Value 애노테이션을 통해서 설정 클래스를 만드는데, 이때테스트 코드를 만들게 되면 application-test.yml과 같은 테스트 전용 yml 파일을 만들어서 테스트 환경을 실행시키도록 하게 되는데, 강사님은 이럴때 어떻게 처리하시는지 궁금합니다. application-test 파일에 설정을 안하게 되면 런타임시 에러가 발생하게 되어, 실행시 에러가 나는데. 외부 시스템은 Mocking 처리하도록 하니. 테스트용 임시로 임의값을 key, secret 값으로 설정하면 되는건지 궁금하네요 진짜 좋은 강의 감사합니다 ^^ ㅎㅎ
-
미해결Java/Spring 테스트를 추가하고 싶은 개발자들의 오답노트
페이징 기능은 어떻게 테스트 하시나요?
안녕하세요. 강사님 강의듣고나서 새로운 시각이 열리게 된 것 같아서 요새 개발을 재밌게 배우고 있습니다. 감사합니다.배경public interface PostJpaRepository extends JpaRepository<PostEntity, Long> { @Query(value = "select new store.ppingpong.board.post.dto.PostWithWriter(p.id, p.title, p.postType, u.userInfo.nickname, p.createdAt) " + "from PostEntity p " + "join UserEntity u on p.userId = u.id " + "where p.forumId = :forumId", countQuery = "select count(p) from PostEntity p where p.forumId = :forumId") Page<PostWithWriter> findPostAndUsernameByForumId(@Param("forumId") String forumId, Pageable pageable); }(Post는 User의 id를 필드로 가지고 있고 Forum을 조회 시, forumId와 같은 Post리스트를 페이징처리하면서, User의 name필드 정보가 필요해서 다음과 같은 쿼리를 작성한 상황입니다.)페이징 기능이 필요해서, 제일 먼저 생각난게 spring data jpa에서 제공하는 페이징기능이었습니다.그런데, 테스트코드를 작성하려보니 뭔가 잘못된 것 같다고 느꼈습니다.문제상황@Override public Page<PostWithWriter> findByForumId(String forumId, Integer listNum, Pageable pageable) { List<Post> list = data.stream() .filter(post -> post.getForumId().equals(forumId)) .toList(); FakePage<Post> posts = new FakePage<>(list, pageable.getPageNumber(), pageable.getPageSize(), list.size()); posts.stream() .map() // ??? return null; }FakePostRepository를 작성하던 중 Page를 상속받은 FakePage를 구현 후, "스트림으로 PostWithWriter dto에 넣어줘야겠다" 라고 생각할 때였습니다.위 상황에서는 Post를 받는 정적 팩토리 메서드를 만들면 될 것 같긴했습니다. 그러나, 테스트코드를 위해서 메인코드를 수정해야하는 상황이 좀 이상하다고 생각했습니다.질문일단 제가 이 상황에서 드는 다양한 생각은dto는 단순히 전달목적이니 코드수정이 들어가도 상관없다.jpa의 페이징기능을 포기하고 Comparator를 구현해서 직접 정렬한다.페이징 기능에 한해서 Mock 프레임워크 기능을 이용한다. 물론 지금은 서비스가 단순히 repository를 호출하는거라 테스트 할 의미가 적은 것 같지만, 나중에 위 같은 상황에서의 대처가 궁금해서 질문올립니다.강사님의 답변을 듣고 싶습니다. 감사합니다!
-
미해결실전! 스프링부트 상품-주문 API 개발로 알아보는 TDD
테스트 코드 내의 지역변수를 final로 선언하는 이유가 궁금합니다.
테스트 코드 내에서 인텔리제이 자동 필드선언 기능 사용시 저는 따로 상수키워드가 붙지 않는데. 선생님께서는 final이 자동으로 붙는 것 자체도 신기하지만 그 이유가 궁금합니다.
-
미해결Do It! 장고+부트스트랩: 파이썬 웹개발의 정석
안녕하세요 강사님,
AWS light sail을 이용하여 배포까지 3월 초에 완료하였습니다.웹사이트는 잘 작동하였고 너무 기뻐 친구들에게도 자랑을 하였습니다. 그렇게 웹사이트가 잘 작동되고 있었는데 갑자기 어느순간부터 도메인을 치면 오류가 납니다. 제 웹사이트 링크는giyeons.com 입니다. 구글링을 해보니 aws에 문제가 없었다가 갑자기 생긴것 같은데 제가 aws는 강사님이 하라는데로 따라하기만 하고 추가로 다른 공부를 하진 않아서 어디를 어떻게 수정해야 하는지 감이 안잡힙니다. (제가 아마존 라이트세일 결제 카드를 배포후 2주 후에 잃어버려서 기존 카드를 해지를 하고 aws에 새로운 카드를 등록시켰는데 이것이 문제가 될 수도 있나요?)새로운 카드를 이미 등록은 하였는데 계속 오류가 나는것을 보아하니 카드의 문제가 아닌것 같습니다.
-
미해결Practical Testing: 실용적인 테스트 가이드
Order.class 에대하여
학습 관련 질문을 남겨주세요. 어떤 부분이 고민인지, 무엇이 문제인지 상세히 작성하면 더 좋아요!먼저 유사한 질문이 있었는지 검색해 보세요.서로 예의를 지키며 존중하는 문화를 만들어가요. 강의 듣다가 궁금한 점이 생겨서 질문을 작성합니다!Order 클래스는 @Entity 어노테이션이 붙어있는 도메인 객체인데 여기에 어떤 로직? 이라고 해야 하나요? List<OrderProduct> 를 바로 넣어주는 것이 아니고 List<Product>를 받아서 값을 뽑아서 new OrderProduct 로 생성하거나, calculateTotalPrice() 같은 메서드를 작성해도 괜찮은가요? (현업에서도 많이 쓰이는 방법인가요? 뭔가 따로 service로 빼도 괜찮지 않을까 라는 생각이 들었습니다. )전에 간단한 토이 프로젝트를 할 때 cascade = CascadeType.ALL 가 아닌 cascade = CascadeType.REMOVE 로 설정하고 Order을 생성한 후 OrderProduct를 수동으로 생성했었는데 CascadeType.ALL 이 더 범용적으로 많이 쓰는 방법인지테스트 코드 작성법을 배우려고 듣게 되었는데 뭔가 라이브 코딩을 따라가면서 전반적으로? 많이 배우고 있어서 좋아요! ㅎㅎ 좋은 강의 감사합니다.