묻고 답해요
141만명의 커뮤니티!! 함께 토론해봐요.
인프런 TOP Writers
-
미해결Practical Testing: 실용적인 테스트 가이드
createOrder 변경
학습 관련 질문을 남겨주세요. 어떤 부분이 고민인지, 무엇이 문제인지 상세히 작성하면 더 좋아요!먼저 유사한 질문이 있었는지 검색해 보세요.서로 예의를 지키며 존중하는 문화를 만들어가요. 안녕하세요 강의를 듣다가 의문점이 생겨 질문드립니다.createOrder의 test를 구현하기 위해 LocalTime을 인자로 받게 변경했는데 결국 test를 위해 비지니스 로직을 수정을 하는 과정이 너무 짜치는데 다른 방법은 없을까요? 강의 뒤쪽에 나오는 걸까요?
-
해결됨Practical Testing: 실용적인 테스트 가이드
"테스트 케이스 세분화하기" 강의 화면이 안나옵니다
다른 강의는 잘 나오는데 테스트 케이스 세분화하기 강의만 화면이 까맣게 나옵니다. 저만 그럴까요?Arc 브라우저에서 수강하다가 크롬 브라우저에서도 확인해봤는데 똑같이 화면이 안나옵니다. UPDATE 1: "테스트 케이스 세분화하기" 부터 화면이 안나오는 것 같네요.UPDATE 2: 크롬에서 하드웨어 가속 기능을 끄니까 정상적으로 화면이 나옵니다. 왜 기능을 꺼야하는건지 이유를 알고 싶긴하네요.
-
미해결Practical Testing: 실용적인 테스트 가이드
컨트롤러 테스트 시 POST시 Mockito.when() 처리에서 질문드립니다.
안녕하세요 제가 좀 더 응용해서 post 요청 시에 Mockito.when()과 접목시킨 테스트를 진행해봣는데 이 과정에서 질문이 있어 질문 드립니다. 예시 코드는 다음과 같습니다.void signUpTest() throws Exception { //given var memberResponse = new MemberResponse(MEMBER_ID, MEMBER_EMAIL); var signUpRequest = new SignUpRequest(MEMBER_EMAIL, "password"); //when when(memberFacadeService.signUp(signUpRequest)) .thenReturn(memberResponse); //then mockMvc.perform( post("/api/v1/members/signUp") .content(OBJECT_MAPPER.writeValueAsString(signUpRequest)) .contentType(MediaType.APPLICATION_JSON) ) .andDo(print()) .andExpect(status().isOk()) .andExpect(jsonPath("$.id").value(MEMBER_ID)) .andExpect(jsonPath("$.email").value(MEMBER_EMAIL)); }이 코드 시에 문제가 발생합니다. 문제는 java.lang.AssertionError: No value at JSON path "$.id"이거입니다. 근데, 이 코드를 아래와 같이 바꾸면 에러가 발생하지 않습니다.void signUpTest() throws Exception { //given var memberResponse = new MemberResponse(MEMBER_ID, MEMBER_EMAIL); var signUpRequest = new SignUpRequest(MEMBER_EMAIL, "password"); //when when(memberFacadeService.signUp(any(SignUpRequest.class))) .thenReturn(memberResponse); //then mockMvc.perform( post("/api/v1/members/signUp") .content(objectMapper.writeValueAsString(signUpRequest)) .contentType(MediaType.APPLICATION_JSON) ) .andDo(print()) .andExpect(status().isOk()) .andExpect(jsonPath("$.id").value(MEMBER_ID)) .andExpect(jsonPath("$.email").value(MEMBER_EMAIL)); }위와 아래의 차이는 requestBody에 들어가는 SignUpRequest 클래스를 mockBean처리 된 memberFacadeService의 when 처리 시에 해당 클래스를 any()로 처리하나 안처리하나의 차이입니다. 제가 예상하기에는 mockMvc에서 .content(objectMapper.writeValueAsString(signUpRequest)) 로 이렇게 처리했기 때문에 해당 로직에 들어가는 memberFacadeService 클래스의 signUp 매개변수로 들어가는 SignUpRequest가 제가 위에서 선언한 signUpRequest와 다르기 때문에 발생하는 문제라고 생각합니다. 이 이해가 맞는지에 대한 질문과 post요청에서는 다 이렇게 any()처리를 해야되는지 궁금합니다.
-
해결됨Java/Spring 테스트를 추가하고 싶은 개발자들의 오답노트
테스트 메서드 마다 Environment variables 설정이 불편...
강의시나리오 대로 진행하다보니 살짝 불편한 부분이 있어서..(어쩜 중간에 코멘트가 있었는데 놓친것일 수도..)서비스 설정 중 메일발송 설정 정보를 실행속성으로 구성하는데테스트도 동일하게 구성하다보니(test-application.properties )Intellij >Edit Configurations > JUnit 실행인스턴스 별 Environment variables 를 설정해줘야 실행이 되는듯 합니다. 테스트 메서드를 만들때마다 실행인스턴스를 설정해야하는게 불편해서 그냥 메일발송 설정을 test-application.properties 에 하드코딩하고 진행해봅니다.(혹시.. 다른 더 스마트한 방법이 있을까? Intellij ? spring?) [확인1]'테스트 추가하기: h2를 이용한 repository 테스트' 강의 1:16초를 보면 git에서 받은 application.properties 파일과 강의의 소스가 다른것 으로 보입니다. Environment variables 에서 설정한 속성이 없어서 해당 강의에서는 불편함 없이 진행된 것 으로 이해했습니다. [확인2] 그런데'토이 프로젝트 살펴보기' 강의 7:42 에 확인되는 설정정보는 git 소스와 동일하것으로 확인됩니다. 강의를 훑어볼때는 그냥 넘어갔는데, 따라하며 보니 눈에 밟히는게 좀 있네요. 제가 놓친부분이라면 양해 바라며, 시나리오 상 연결부분이 필요한 내용이면 코멘트 부탁드립니다. 저와 같이 길잃은 양들을 살펴주소서~[git 설정파일]
-
미해결Practical Testing: 실용적인 테스트 가이드
테스트할 때 Auditing 없이 원하는 날짜를 설정할 수 잇을까요?
공부삼아서 과제 프로젝트에 테스트를 도입하다가 궁금한 게 잇어서 질문드립니다. 거래내역 조회를 구현할 때 2024-05-30 같은 거래가 발생할 날짜는 auditing, @CreatedAt 통해 저장된 createdAt에서 가져오도록 구현했습니다. (디자인과 달리, 최근 거래일수록 위로 오도록 변경되었습니다) 구현이 끝난 뒤, 테스트할 때 createAt을 임의로 변경하기 위해 BaseEntity의 private를 protected, 그리고 createdAt을 변경하는 메서드를 추가햇습니다. (이게 맞는 접근인지는 잘 모르겟네요... 할 때에도 이렇게 해도 되나? 라는 의문이 계속 들엇습니다...)@DisplayName("유저의 계좌 내역을 불러올 수 있다.") @Test void getUserStatements() { // given (6/5 18:00) LocalDateTime now = LocalDateTime.of(2024, 6, 5, 18, 0, 0); User u1 = User.of("test1", "id1", "pw"); User u2 = User.of("test2", "id2", "pw"); List<User> users = userRepository.saveAll(List.of(u1, u2)); User loginUser = users.get(0); User notLoginUser = users.get(1); Account a1 = Account.of("111-222-3333", 1000, loginUser); Account a2 = Account.of("111-222-3334", 2000, notLoginUser); List<Account> accounts = accountRepository.saveAll(List.of(a1, a2)); Account loginUserAccount = accounts.get(0); Account notLoginUserAccount = accounts.get(1); // 자신 계좌로 입금 (조회 대상), 6/5 발생 Statement s1 = createStatementForTest(loginUserAccount, loginUserAccount, 100, DEPOSIT); // 자신 계좌에서 출금 (조회 대상), 6/6 발생 Statement s2 = createStatementForTest(loginUserAccount, loginUserAccount, 200, WITHDRAW); // 자신 계좌에서 타 계좌로 이체 (조회 대상), 6/7 발생 Statement s3 = createStatementForTest(loginUserAccount, notLoginUserAccount, 300, TRANSFER); // 타 계좌에서 자신 계좌로 이체 (조회 대상), 6/8 발생 Statement s4 = createStatementForTest(notLoginUserAccount, loginUserAccount, 400, TRANSFER); // 타 계좌에서 타 계좌로 출금 (조회 대상 X), 6/9 발생 Statement s5 = createStatementForTest(notLoginUserAccount, notLoginUserAccount, 50000, WITHDRAW); statementRepository.saveAll(List.of(s1, s2, s3, s4, s5)); // when StatementResponse userStatement = statementService.getUserStatements(loginUser); // then assertThat(userStatement.getStatementInfos()).as("거래 이력을 조회할 수 있다.").hasSize(4) .extracting("amount", "type") .containsExactly( tuple(400, "이체"), tuple(-300, "이체"), tuple(-200, "출금"), tuple(100, "입금") ); assertThat(userStatement.getBalance()).as("계좌 잔액을 조회할 수 있다.").isEqualTo(1000); }(위 테스트 코드는 시간 설정 및 검증 코드를 제거한 테스트입니다.) 위 메서드와 plusDays() 통해 시간 설정 후, extracting에 "date" (createdAt에 yyyy-MM-dd를 적용시켜 String 형태로 저장) 를 추가해서 확인했을 때에는 의도한 대로 2024-06-08, 2024-06-07, 2024-06-06, 2024-06-05가 아닌, 전부 테스트를 실행한 시간으로(2024-06-05) 나오는 걸 확인했습니다. 일단은 date를 검증하는 로직을 빼고 테스트를 통과시켰고, postman에서 입금/출금/이체 등 실시 후 조회했을 때에도 의도한 대로 최근 거래가 위로 오도록, 날짜 형식도 의도한 대로 나온 것도 볼 수 있었습니다. 하지만 이 date를 postman이 아닌, auditing 없이 임의로 날짜를 설정한 후 테스트해 확인해보고 싶은데, 이 경우에는 어떻게 하면 될까요? auditing 잇는 상태로도 가능하다면 알려주시면 감사하겟습니다! 아래는 BaseEntity와 거래 내역을 저장하는 Statement Entity 코드입니다@Getter @MappedSuperclass @EntityListeners(AuditingEntityListener.class) public abstract class BaseEntity{ @CreatedDate private LocalDateTime createdDate; }import jakarta.persistence.*; import lombok.AccessLevel; import lombok.Builder; import lombok.Getter; import lombok.NoArgsConstructor; import java.time.LocalDate; import java.time.LocalDateTime; import static jakarta.persistence.EnumType.*; @Entity @Getter @NoArgsConstructor(access = AccessLevel.PROTECTED) public class Statement extends BaseEntity{ @Id @GeneratedValue(strategy= GenerationType.IDENTITY) private Long id; @ManyToOne(fetch = FetchType.LAZY) @JoinColumn(name="from_account") private Account from; @ManyToOne(fetch = FetchType.LAZY) @JoinColumn(name="to_account") private Account to; private int amount; @Enumerated(STRING) private TransactionType type; @Builder private Statement(Account from, Account to, int amount, transactionType type) { this.from = from; this.to = to; this.amount = amount; this.type = type; } public static Statement of(Account from, Account to, int amount, transactionType type){ return Statement.builder() .from(from) .to(to) .amount(amount) .type(type) .build(); } } 긴 글 읽어주셔서 감사합니다~
-
미해결더 자바, 애플리케이션을 테스트하는 다양한 방법
질문있습니다.
현재 스프링부트는 3.x버전대인데..버전대 맞춰서 예제나 소스코드를 변경해야할까요?..강의버전대는 2.1? 버전으로 알고있습니다..(지원하지 않은 코드가 있을경우)아울러 9월 이후로 답변주시지 않으신것같은데..질문이나 답변은 더 이상 안하시는것일까요?
-
미해결Java/Spring 테스트를 추가하고 싶은 개발자들의 오답노트
CertificationService의 테스트에서 FakerMailSender를 이용하는 부분에서 질문이 있습니다.
해당 방식은 FakerMailSender에 결국 테스트 의존성이생기게 된다고 생각하는데요.현재 코드는 단순해서 개발자가 테스트 코드 수정시 확인할 부분이 없지만, 추후 객체의 구조가 변경되거나, 규칙이 추가 - 변경된다면 모든 테스트 코드의 요구사항에 맞도록 Faker객체의 구현 내용도 함께 변경되어야 할것같습니다. 하지만 항상 모든 테스트의 요구사항을 알기는 쉽지만은 않을것같은데요.이러한 불편함을 극복하기 위한 방법이 있을까요?
-
미해결실무에 바로 적용하는 프런트엔드 테스트 - 1부. 테스트 기초: 단위・통합 테스트
이 작업 영역에서 아직 발견된 테스트가 없습니다.
다른 분들도 겪은 문제인데 0.2.42 버전으로 다운그레이드 하려고해도 지원하지 않는 버전이라고 나오네요. npm run test 는 잘 실행되는거 같습니다. 혹시 해당 이슈 해결방법 알 수 있을까요 .. 아니면 그냥 npm run test 로 진행해도 상관없을까요
-
미해결실무에 바로 적용하는 프런트엔드 테스트 - 1부. 테스트 기초: 단위・통합 테스트
vitest 실행시 테스트 실행에서 출력을 기록하지 않았습니다
결과가 저렇게나오는데 yarn test 실행하면 로그가 정상적으로 출력됩니다 이유가뭘까요?
-
해결됨Practical Testing: 실용적인 테스트 가이드
jpaRepository 에서 update 메서드 테스트 질문 드립니다.
jpaRepository에서 update 관련 메서드를 테스트하던 중 고민이 생겼습니다.update로 변경한 결과가 DB가 아닌, 영속성 컨텍스트에만 반영이 되어서 수정된 값을 확인하기 위해 find()메서드로 저장된 객체를 불러오면 수정한 것과 다른 원본 결과가 출력됩니다.이 문제를 해결하기 위해 두 가지 방법을 생각해보았습니다.하나는 @Modifying 애노테이션에 clearAutomatically = true 라는 옵션을 달아주는 방법이었는데, 이 방식은 테스트를 위해 프로덕션 코드를 수정하기도 하고 성능에 문제가 발생해서 제외하였고다른 하나는 테스트 코드에 EntityManager를 이용해 강제로 flush()와 clear()를 이용해 영속성 컨텍스트를 비워주도록 하는 방법이었습니다. 이 방식도 테스트 코드가 깔끔하지 않고 더 jpa에 종속적이게 되는 것 같아서 마음에 들진 않는데 강사님은 어떤 방식으로 해결하셨는지 궁금합니다!
-
미해결Java/Spring 테스트를 추가하고 싶은 개발자들의 오답노트
토이프로젝트 실행시 이메일 설정 부분에서 앱비밀번호 항목이 보이지 않습니다.
계정차이일 수 있겠지만, 해결방법을 찾을 수 있을까 하여 문의드립니다. 제 구글 계정은 앱비밀번호 항목이 없습니다. 혹시 다른 방법이 없을까요?
-
미해결Java/Spring 테스트를 추가하고 싶은 개발자들의 오답노트
변경감지
도메인 모델을 추가하고 그 도메인 모델 내부에서 작업을 처리하기 때문에 변경 감지 (dirty checking) 의 기능을 사용하지 못하게 되는 거 같은데요! 이 부분은 어느정도 포기를 하는걸까요?
-
미해결실무에 바로 적용하는 프런트엔드 테스트 - 1부. 테스트 기초: 단위・통합 테스트
질문 있습니다.
안녕하세요. 강의 내용 중 정확히 이해하지 못하고 있는 것이 있어서 질문 드립니다.강의 중 로그인 버튼 같이 간단한 동작만 있는 컴포넌트는 그 자체를 테스트 하는 것이 아니라, 통합 테스트로 상태에 따른 동작을 검증하는 것이 더 효율적이고 정확한 테스트가 된다. 라고 하셨습니다.또한 이런 컴포넌트는 스토리북과 같은 도구를 사용하여 스타일이나 레이아우싱 틀어지지 않는지 확인하는 것이 더 중요하다. 라고 말씀 하셨습니다.이 뜻은 통합 테스트를 스토리북과 같은 도구와 함께 하라는 것이 아니라, 통합 테스트로 상태에 따른 동작을 검증하고, 그 안에 있는 각각의 컴포넌트들은 스토리북 안에서 스타일과 레이아웃이 틀어지지 않는지 확인하라는 것일까요?아니면 스토리북을 통해 네비게이션 같은 컴포넌트를 만들고 그 단위로 통합 테스트를 하란 말씀이실까요??궁금합니다. 강의 너무 잘 듣고 있습니다. 정말 감사합니다!
-
미해결스프링부트 JUnit 테스트 - 시큐리티를 활용한 Bank 애플리케이션
Dummy 클래스 위치에 대한 질문
현재 "회원가입 서비스 코드 리팩토링"까지 봤는데 Dummy는 테스트 단에서만 쓰이는 것으로 보입니다. 그러면 더미 클래스를 main.config.dummy가 아닌 test.dummy에 작성하는 것이 의미가 분명하고 추후 개발 및 배포에서도 용이한 것 아닌지 의문이 들어 질문 드립니다! config에 작성한 이유와 test에 작성하지 않은 이유가 궁금합니다.!
-
미해결실전! 스프링부트 상품-주문 API 개발로 알아보는 TDD
이 방법이 TDD가 맞나요?
안녕하세요! 강의를 드는 중 의아한 부분이 있는데요.제가 알고, 공부했던 TDD 와는 달라서 좀 의문이네요.제가 아는 TDD는 Red - Green - Refactor 사이클을 통해 테스트 코드를 작성하면서 자연스럽게 프로덕트 코드가 생성되는 방법입니다. 그 과정은 매우 세밀하고, 정말 짧은 주기로 테스트를 돌려봐야하죠. 강의에서는 프로덕트 코드를 테스트 파일에 작성하는 것으로 밖에 안 보이고 POJO 상품등록하는 로직이 완성될 때까지 테스트를 단 한 번 돌려본다는 게 의아하네요. 테스트 파일에 아무런 테스트 없이 내부 클래스로 프로덕트 코드를 작성하고 다 만들어지면 그 클래스를 옮기는 게 TDD가 맞나요? 이 정도 TDD라면 프로덕트 코드 먼저 만들고 단위 테스트 작성하는 것과 별반 차이가 없다고 느껴져요.제가 순수 자바로만 TDD를 공부했기 때문에 스프링 부트에서 어떻게 하는 지 모르는 걸 수도 있는데, TDD 근간이 달라지는 것 같아 정말 순수하게 궁금합니다.
-
미해결Practical Testing: 실용적인 테스트 가이드
access token의 경우 테스트 코드에서 어떻게 처리해야되나요?
안녕하세요. 현재 강의 잘 수강하고 있습니다.현재 거의 모든 controller에서 access token을 받아서 사용하고 있습니다.토큰의 경우 만료시간 등이 있는데 테스트 코드에서 어떻게 처리되는지 궁금합니다.저 같은 경우는 spring security 사용하지 않고, 직접 API로 Token을 발급하였습니다.예시라던지 레퍼런스가 있다면 공유 좀 부탁드려요~감사합니다.
-
미해결따라하며 배우는 리액트 A-Z[19버전 반영]
CSS
영화 상세페이지 구현에서 className으로 modal_poster-img를 주니까 다른 곳에 있던 css가 적용되는데 위에 import하지 않아도 가능한건가요??
-
미해결실전! 스프링부트 상품-주문 API 개발로 알아보는 TDD
POJO로 개발했는데 비즈니스 로직을 로깅해야 할 경우, 어떻게 해야 할까요?
강의 잘 듣고 있습니다! 강의 들으면서 문득 궁금한 점이 생겼는데요. POJO로 개발했는데, 도메인 클래스 내의 비즈니스 로직을 로깅을 해야하는 경우가 실무에서 많을까요? 만약, 그런 경우가 있다면, 어떻게 해야 할지 궁금합니다. 공통된 패턴이 있다면, AOP를 사용해볼 수 있을 것 같은데, 그렇지 않은 경우, 어쩔 수 없이 도메인 모델이 로깅 프레임워크에 의존하지 않나 라는 생각이 들어서요. 로깅하고 싶은게 클래스의 메서드의 매개변수와 리턴값이 아닌 내부 로직 함수일 경우가 특히 궁금합니다. 혹시, 이런 경우는 실무에서 잘 발생하지 않아 알 필요가 없을까요?
-
미해결쉬운 모바일 테스트 자동화 시작하기 : Appium Studio
iOS 단말 연결 및 에뮬레이터 실행 방법 문의드립니다.
iOS 단말 연결하는 방법도 Android 와 동일한 방법으로 설정해보면 되는 걸까요?만약 iOS 연결 방식이 다르다면, 어떻게 설정을 하면 될까요??
-
미해결2시간으로 끝내는 프론트엔드 테스트 기본기
[공유] cy.visit() failed trying to load;
위 화면처럼 connect ECONNREFUSED::1:54382등 locahost에 접근할 수 없다고 나오면 cypress.config.ts에서 baseurl 설정해야합니다.(https://parkparkpark.tistory.com/186)import { defineConfig } from "cypress"; export default defineConfig({ e2e: { baseUrl: "http://localhost:3000", setupNodeEvents(on, config) { // implement node event listeners here }, }, });