-
Notifications
You must be signed in to change notification settings - Fork 455
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
[자동차 경주] 조승우 미션 제출합니다. #350
Open
seungineer
wants to merge
63
commits into
woowacourse-precourse:main
Choose a base branch
from
seungineer:seungineer
base: main
Could not load branches
Branch not found: {{ refName }}
Loading
Could not load tags
Nothing to show
Loading
Are you sure you want to change the base?
Some commits from the old base branch may be removed from the timeline,
and old review comments may become outdated.
Open
Changes from all commits
Commits
Show all changes
63 commits
Select commit
Hold shift + click to select a range
6a0f16e
docs(README): 구현 기능 목록 및 스스로 정한 규칙을 추가한다
seungineer e6dff8d
feat(input): 문자열을 입력받는 기능을 추가한다
seungineer 9ccea01
docs(README): 스스로 정한 규칙 및 관련 예시를 추가한다
seungineer c043cc6
feat(game): 입력받은 문자열로 Game 클래스를 생성한다
seungineer 7e10bb0
docs(README): 구현 기능 목록에 자동차 관리 방법 항목을 추가한다
seungineer 39fd236
feat(game): 입력 받은 자동차 이름 문자열을 배열화하는 기능을 추가한다
seungineer 8ffc2a2
feat(game): 자동차 객체를 배열로 관리하는 기능을 추가한다
seungineer 126121b
feat(car): 이름을 입력 받는 자동차 객체를 생성한다
seungineer 6bdef82
refactor(input): inputHandler를 통해 반환되는 값의 type을 변수명에 반영한다
seungineer b7be9bc
feat(game): 반복 횟수 만큼 game Round를 반복하는 기능을 추가한다
seungineer 585ab17
feat(game): Round를 시작하여 자동차의 전진 여부를 결정하는 메서드를 추가한다
seungineer 1385392
feat(game): 전진 가능 여부 판단하는 기능을 추가한다
seungineer e5e76e9
feat(car): 자동차를 전진시키는 기능을 추가한다
seungineer c1b5f97
feat(game): Round 별 결과를 출력하는 기능을 추가한다
seungineer 785e308
feat(game): 최종 우승자를 선정하는 기능을 추가한다
seungineer ec636aa
feat(output): 경주 결과를 출력하는 기능을 추가한다
seungineer ce8aa75
refactor(game): 반복문의 가독성 제고를 위해 JavaScript API로 전환한다
seungineer d59e2c2
feat(validator): 입력 문자열의 형식을 검증하는 기능을 추가한다
seungineer 4e5595e
docs(README): 구현 기능 목록 중 완료된 기능을 표시한다
seungineer b45bbd5
docs(README): 스스로 정한 규칙에 항목을 추가한다
seungineer 8a4c493
fix(validator): 두 개 이상의 이름이 입력되어야 하는 규칙으로 정규 표현식을 수정한다
seungineer 9ed036a
docs(README): 예외 처리 목록을 추가한다
seungineer 2d4b06f
chore(README): 어색한 문장을 다듬는다
seungineer 83c1a37
feat(validator): 이름이 하나만 입력되는 경우를 예외 처리한다
seungineer a135c0a
feat(validator): 이름의 길이가 5를 초과하는 경우를 예외 처리한다
seungineer 71eefb3
feat(validator): 이름 입력 문자열 끝자리에 쉼표(,)가 있는 경우를 예외 처리한다
seungineer f982904
chore(validator): 주석 및 typo를 수정한다
seungineer 89d8241
feat(validator): 시도 횟수 입력이 숫자만 입력되지 않는 경우를 예외 처리한다
seungineer 5d34ca0
feat(validator): 시도 횟수가 0인 경우를 예외 처리한다
seungineer 4428789
feat(validator): 시도 횟수 입력이 0으로 시작하는 경우를 예외 처리한다
seungineer 183a331
docs(README): 예외 처리된 항목을 표시한다
seungineer ee77d42
refactor(validator): 검증 함수를 utils 폴더로 관리한다
seungineer fe7e94e
refactor(game): 주요 클래스를 components 폴더로 분리한다
seungineer cb49aba
refactor(input, game): this를 사용하지 않는 클래스의 메서드를 static으로 변경한다
seungineer 2b7edb3
refactor(validator): 직접 입력된 에러 메시지를 resources 폴더로 분리한다
seungineer 47f4d82
refactor(validator): 직접 입력된 정규표현식을 resources 폴더로 분리한다
seungineer 8d8e68a
refactor(input, output, game): 직접 입력된 문자열을 resources 폴더로 분리한다
seungineer af5b7f1
refactor(game): game 인스턴스의 currentRepeat 속성을 제거한다
seungineer 0df4281
test(input): Input 클래스 테스트를 추가한다
seungineer e3bfcb7
feat(validator): 반복 횟수가 음수, 실수인 경우 예외 처리한다
seungineer aac6af8
chore(test, game): 메시지 의미를 명확히 한다
seungineer 1f7df67
refactor(validator): 에러메시지 변수명을 명확하게 한다
seungineer 82851aa
test(validator): validation 테스트를 추가한다
seungineer c60295c
test(output): output 클래스 테스트를 추가한다
seungineer 8877159
refactor(game): 이동 가능 여부 판단 메서드를 인스턴스 속성에 추가한다
seungineer 6f17af4
test(game): game 클래스 테스트를 추가한다
seungineer e9b6b9c
docs(README): 연산 횟수 관련 예외 처리 항목을 추가한다
seungineer 2641696
feat(validator): 시간 복잡도가 과도한 입력을 예외 처리한다
seungineer 89422de
test(validator): validateTimeComplexity() 메서드 테스트를 추가한다
seungineer 0ae5ab1
docs(README): 예외 처리된 연산 횟수 관련 항목을 표시한다
seungineer 8cfad95
refactor(input, output): 입출력 모듈을 util 폴더로 분리한다
seungineer b915a5d
refactor(game): 중간 결과를 출력하는 기능을 Output.js로 모듈화한다
seungineer c4783e2
test(game): 중간 결과 출력 방식을 변경한다
seungineer 56a4e64
refactor(game): 문자열을 출력하는 기능을 Ouput.js로 모듈화한다
seungineer a7157fd
test(car): Car 클래스 테스트를 추가한다
seungineer 8f968c1
refactor(game): 문자열 parsing 및 Car 객체 할당 기능을 모듈화한다
seungineer 045c0f5
refactor(test): 문자열 parsing 및 Car 객체 할당 테스트 코드를 분리한다
seungineer 2457a41
refactor(game): 게임 라운드를 관리하는 기능을 RoundManager.js로 모듈화한다
seungineer fd8c329
refactor(test): GameTest에서 RoundManager 테스트 코드를 분리한다
seungineer 6f1d8e8
docs(README): 프로그램 실행 gif를 추가한다
seungineer 4c2a14a
docs(README): 폴더 구조 설명을 추가한다
seungineer 4759fe5
docs(README): 입력 예시에 따른 Error 결과 참고 항목을 추가한다
seungineer ac0ce01
fix(validator): 유효한 시간 복잡도 이상인 경우 에러로 처리하도록 수정한다
seungineer File filter
Filter by extension
Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1 +1,133 @@ | ||
# javascript-racingcar-precourse | ||
## 프리코스 2주 차 미션 - 자동차 경주 | ||
<p align='center'> | ||
<img src="./docs/car_demo.gif", width = '240px'> | ||
</p> | ||
|
||
## 스스로 정한 규칙 | ||
- 입력된 이름은 두 개 이상이어야 한다. | ||
- 한 개일 때는 '경주'가 성립하지 않기 때문이다. | ||
- 입력된 이름은 ‘공백을 포함한’ 문자열의 길이가 5 이하인 경우 **해당 문자열이 그대로 이름**이 된다. | ||
- 입력된 공백을 임의로 삭제하지 않는다. | ||
- ex) ` `도 길이가 5인 이름이라고 할 수 있다. | ||
- ex) ` `과 ` `은 길이가 다르기에 서로 다른 이름이다. | ||
- 중복된 이름은 순서대로 출력된다. | ||
- '실행 결과'가 항상 출력되므로 사용자가 분간할 수 있기 때문이다. | ||
- 이동 횟수가 0회인 경우 경주가 이루어지지 않기에 `error` 처리한다. | ||
- 이름의 개수(n) 곱하기 시도 횟수(k)의 값은 $10^7$ 미만이어야 한다. | ||
- 프로그램 연산의 시간 복잡도 $O(n*k)$를 고려한다. | ||
|
||
## 구현 기능 목록 | ||
- [x] 사용자 입력 요청 메시지 출력하기 | ||
- [x] `경주할 자동차 이름을 입력하세요.(이름은 쉼표(,) 기준으로 구분)\n` | ||
- [x] 사용자로부터 n대 자동차의 이름 입력 받기 | ||
- [x] `시도할 횟수는 몇 회인가요?` | ||
- [x] 사용자로부터 이동 횟수(`k`) 입력받기 | ||
- [x] 사용자 입력 검증 하기 | ||
- [x] 한 개의 이름이 문자열의 길이가 5가 넘지 않으며, 쉼표(,)로 구분되는지 검증 | ||
- [x] 시도 횟수 `k`는 1 이상의 정수만 입력 | ||
- [x] 게임 내에서 자동차를 객체로 관리하기 | ||
- [x] `k`회 반복하며 각 자동차에 대해 전진 또는 정지 결정 | ||
- [x] 전진: 0과 9 사이 랜덤한 수 중 4 이상이 추출될 경우 | ||
- [x] 정지: 0과 9 사이 랜덤한 수 중 4 미만이 추출될 경우 | ||
- [x] 반복 회차마다 실행 결과 출력하기 | ||
- [x] 가장 많이 전진한 자동차를 최종 우승자로 선정 _(여러 대일 수 있음)_ 하여 출력하기 | ||
- [x] `최종 우승자 : pobi, jun` | ||
|
||
## 예외 처리 목록 | ||
|
||
### 자동차 이름 | ||
- [x] 아무 것도 입력되지 않는 경우 | ||
- [x] 어떤 이름의 길이가 5 초과인 경우 | ||
- [x] 이름이 2개 미만 입력되는 경우 | ||
- [x] 이름 문자열 끝이 쉼표(,)로 끝나는 경우 | ||
|
||
### 시도 횟수 | ||
- [x] 아무 것도 입력되지 않는 경우 | ||
- [x] 숫자가 아닌 다른 값이 입력된 경우 | ||
- [x] `0`이 입력된 경우 | ||
- [x] `0`으로 시작되는 문자열인 경우 | ||
|
||
### 연산 횟수 | ||
- [x] 이름의 개수와 게임 시도 횟수를 곱한 값이 `1e7`을 초과하는 경우 | ||
|
||
## 입력 예시에 따른 결과 참고 | ||
#### validateNames | ||
- 이름이 하나만 입력되었을 때 예외를 발생시킨다. | ||
- 입력: `"car1"` | ||
- 결과: `[ERROR] 최소 두 개의 이름이 필요합니다.` | ||
|
||
- 이름이 5자를 초과하는 경우 예외를 발생시킨다. | ||
- 입력: `"car1,car5678"` | ||
- 결과: `[ERROR] 이름 길이 초과 (최대 5자)` | ||
|
||
- 이름이 콤마로 끝나는 경우 예외를 발생시킨다. | ||
- 입력: `"car1,car2,"` | ||
- 결과: `[ERROR] 이름 리스트는 콤마로 끝날 수 없습니다.` | ||
|
||
- 이름 중간에 두 개의 쉼표가 포함될 때 예외를 발생시킨다. | ||
- 입력: `"car1,,car2"` | ||
- 결과: `[ERROR] 유효하지 않은 이름 형식입니다.` | ||
|
||
- 이름이 빈 문자열일 때 예외를 발생시킨다. | ||
- 입력: `""` | ||
- 결과: `[ERROR] 빈 문자열은 이름으로 사용할 수 없습니다.` | ||
|
||
#### validateRepetitionString | ||
- 반복 횟수가 숫자가 아닐 때 예외를 발생시킨다. | ||
- 입력: `"abc"` | ||
- 결과: `[ERROR] 반복 횟수는 숫자여야 합니다.` | ||
|
||
- 반복 횟수가 0일 때 예외를 발생시킨다. | ||
- 입력: `"0"` | ||
- 결과: `[ERROR] 반복 횟수는 1 이상이어야 합니다.` | ||
|
||
- 반복 횟수가 0으로 시작하는 경우 예외를 발생시킨다. | ||
- 입력: `"05"` | ||
- 결과: `[ERROR] 반복 횟수는 0으로 시작할 수 없습니다.` | ||
|
||
- 반복 횟수가 빈 문자열일 때 예외를 발생시킨다. | ||
- 입력: `""` | ||
- 결과: `[ERROR] 반복 횟수는 빈 문자열일 수 없습니다.` | ||
|
||
- 반복 횟수가 음수일 때 예외를 발생시킨다. | ||
- 입력: `"-5"` | ||
- 결과: `[ERROR] 반복 횟수는 양수여야 합니다.` | ||
|
||
- 반복 횟수가 소수점을 포함할 때 예외를 발생시킨다. | ||
- 입력: `"3.5"` | ||
- 결과: `[ERROR] 반복 횟수는 정수여야 합니다.` | ||
|
||
#### validateTimeComplexity | ||
- 시간 복잡도가 허용된 한계를 초과할 때 예외를 발생시킨다. | ||
- 입력: `names = "car1,car2", repetitionString = "12345678"` | ||
- 결과: `[ERROR] 허용된 시간 복잡도를 초과했습니다.` | ||
|
||
- 시간 복잡도가 허용된 한계를 초과하지 않을 때 예외가 발생하지 않는다. | ||
- 입력: `names = "car1,car2", repetitionString = "1234567"` | ||
- 결과: 예외 없음 | ||
|
||
## 폴더 구조 | ||
``` | ||
src | ||
┣ components | ||
┃ ┣ Car.js // 자동차 객체 관리 컴포넌트 | ||
┃ ┣ CarAllocator.js // 자동차 할당 및 분배 정보 처리 컴포넌트 | ||
┃ ┣ Game.js // 게임 진행과 상태를 관리하는 컴포넌트 | ||
┃ ┗ RoundManager.js // 게임 라우든 관리 및 진행 순서를 담당하는 컴포넌트 | ||
┣ resources | ||
┃ ┣ Constants.js // App 전반에 사용되는 상수 정의한 파일 | ||
┃ ┣ ErrorMessage.js // Error 발생 시 출력 메시지를 정의한 파일 | ||
┃ ┣ RegularExpression.js // App에서 사용하는 정규표현식을 정의한 파일 | ||
┃ ┗ Rules.js // 게임 관련 규칙을 정의한 파일 | ||
┣ utils | ||
┃ ┣ io | ||
┃ ┃ ┣ Input.js // 사용자 입력을 처리하는 기능을 담은 유틸리티 파일 | ||
┃ ┃ ┗ Output.js // 출력 처리 기능을 담은 유틸리티 파일 | ||
┃ ┗ validation | ||
┃ ┃ ┣ validateNames.js // 자동차 이름 관련 입력 유효성 검사를 수행하는 유틸리티 파일 | ||
┃ ┃ ┣ validateRepetitionString.js // 시도 횟수 입력 유효성 검사를 수행하는 유틸리티 파일 | ||
┃ ┃ ┗ validateTimeComplexity.js // 사용자 입력의 시간 복잡도 검사를 수행하는 유틸리티 파일 | ||
┣ App.js | ||
┗ index.js | ||
``` |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,25 @@ | ||
import Car from '../src/components/Car.js'; | ||
import CarAllocator from '../src/components/CarAllocator.js'; | ||
import Rules from '../src/resources/Rules.js'; | ||
|
||
describe('CarAllocator 클래스 테스트', () => { | ||
describe('parseNames 메서드', () => { | ||
test('이름 문자열을 구분자로 나누어 배열을 반환한다.', () => { | ||
const names = `Woo${Rules.DELIMITER}Wa${Rules.DELIMITER}Han`; | ||
const result = CarAllocator.parseNames(names); | ||
expect(result).toEqual(['Woo', 'Wa', 'Han']); | ||
}); | ||
}); | ||
|
||
describe('allocateCars 메서드', () => { | ||
test('이름 배열을 받아 각 이름에 대한 Car 인스턴스를 생성하여 반환한다.', () => { | ||
const nameList = ['Woo', 'Wa', 'Han']; | ||
const cars = CarAllocator.allocateCars(nameList); | ||
expect(cars).toHaveLength(3); | ||
expect(cars[0]).toBeInstanceOf(Car); | ||
expect(cars[0].name).toBe('Woo'); | ||
expect(cars[1].name).toBe('Wa'); | ||
expect(cars[2].name).toBe('Han'); | ||
}); | ||
}); | ||
}); |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,34 @@ | ||
import Car from '../src/components/Car'; | ||
import Rules from '../src/resources/Rules'; | ||
|
||
describe('Car 클래스 테스트', () => { | ||
describe('생성자', () => { | ||
test('Car 인스턴스를 생성하면 자동차의 이름과 현재 위치가 설정된다.', () => { | ||
const car = new Car('Woo'); | ||
expect(car.name).toBe('Woo'); | ||
expect(car.currentDistance).toBe(Rules.INITIAL_DISTANCE); | ||
}); | ||
}); | ||
|
||
describe('moveForward 메서드', () => { | ||
test('moveForward 메서드를 호출하면 이동 거리가 증가한다.', () => { | ||
const car = new Car('Woo'); | ||
car.moveForward(); | ||
expect(car.currentDistance).toBe( | ||
Rules.INITIAL_DISTANCE + Rules.MOVE_LENGTH, | ||
); | ||
}); | ||
}); | ||
|
||
describe('getStatus 메서드', () => { | ||
test('getStatus 메서드는 현재 이름과 거리를 객체로 반환한다.', () => { | ||
const car = new Car('Woo'); | ||
car.moveForward(); | ||
const status = car.getStatus(); | ||
expect(status).toEqual({ | ||
name: 'Woo', | ||
distance: Rules.INITIAL_DISTANCE + Rules.MOVE_LENGTH, | ||
}); | ||
}); | ||
}); | ||
}); |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,67 @@ | ||
import { Console, Random } from '@woowacourse/mission-utils'; | ||
import Car from '../src/components/Car.js'; | ||
import Rules from '../src/resources/Rules.js'; | ||
import RoundManager from '../src/components/RoundManager.js'; | ||
import { OutputView } from '../src/resources/Constants.js'; | ||
|
||
jest.mock('@woowacourse/mission-utils', () => ({ | ||
Console: { print: jest.fn() }, | ||
Random: { pickNumberInRange: jest.fn() }, | ||
})); | ||
|
||
describe('RoundManager 클래스 테스트', () => { | ||
let cars; | ||
let roundManager; | ||
|
||
beforeEach(() => { | ||
Console.print.mockClear(); | ||
Random.pickNumberInRange.mockClear(); | ||
cars = [new Car('Woo'), new Car('Wa')]; | ||
roundManager = new RoundManager(); | ||
}); | ||
|
||
describe('startRound 메서드', () => { | ||
test('각 Car 인스턴스가 이동할지 여부를 결정한다.', () => { | ||
Random.pickNumberInRange | ||
.mockReturnValueOnce(Rules.THRESHOLD_NUMBER) // Woo 전진 | ||
.mockReturnValueOnce(Rules.THRESHOLD_NUMBER - 1); // Wa 정지 | ||
|
||
roundManager.startRound(cars); | ||
|
||
expect(cars[0].currentDistance).toBe( | ||
Rules.INITIAL_DISTANCE + Rules.MOVE_LENGTH, | ||
); | ||
expect(cars[1].currentDistance).toBe(Rules.INITIAL_DISTANCE); | ||
}); | ||
}); | ||
|
||
describe('getCarsStatuses 메서드', () => { | ||
test('각 자동차의 상태를 반환한다.', () => { | ||
cars[0].moveForward(); | ||
const statuses = roundManager.getCarsStatuses(cars); | ||
|
||
expect(statuses).toEqual([ | ||
{ name: 'Woo', distance: Rules.INITIAL_DISTANCE + Rules.MOVE_LENGTH }, | ||
{ name: 'Wa', distance: Rules.INITIAL_DISTANCE }, | ||
]); | ||
}); | ||
}); | ||
|
||
describe('getWinners 메서드', () => { | ||
test('가장 멀리 간 자동차의 이름을 반환한다.', () => { | ||
cars[0].moveForward(); | ||
cars[0].moveForward(); // Woo가 더 멀리 감 | ||
const winners = roundManager.getWinners(cars); | ||
|
||
expect(winners).toEqual(['Woo']); | ||
}); | ||
|
||
test('가장 멀리 간 자동차가 여러 대일 경우 모두 반환한다.', () => { | ||
cars[0].moveForward(); | ||
cars[1].moveForward(); // Woo와 Wa 모두 같은 거리 이동 | ||
const winners = roundManager.getWinners(cars); | ||
|
||
expect(winners).toEqual(expect.arrayContaining(['Woo', 'Wa'])); | ||
}); | ||
}); | ||
}); |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,98 @@ | ||
import { Console, Random } from '@woowacourse/mission-utils'; | ||
import { OutputView } from '../src/resources/Constants.js'; | ||
import Game from '../src/components/Game.js'; | ||
import Rules from '../src/resources/Rules.js'; | ||
import Output from '../src/utils/io/Output.js'; | ||
import RoundManager from '../src/components/RoundManager.js'; | ||
import CarAllocator from '../src/components/CarAllocator.js'; | ||
|
||
jest.mock('@woowacourse/mission-utils', () => ({ | ||
Console: { print: jest.fn() }, | ||
Random: { pickNumberInRange: jest.fn() }, | ||
})); | ||
|
||
jest.mock('../src/components/CarAllocator'); | ||
jest.mock('../src/components/RoundManager'); | ||
jest.mock('../src/utils/io/Output.js', () => ({ | ||
print: jest.fn(), | ||
printRoundResults: jest.fn(), | ||
})); | ||
|
||
describe('Game 클래스 테스트', () => { | ||
beforeEach(() => { | ||
Console.print.mockClear(); | ||
Random.pickNumberInRange.mockClear(); | ||
CarAllocator.parseNames.mockClear(); | ||
CarAllocator.allocateCars.mockClear(); | ||
RoundManager.prototype.startRound.mockClear(); | ||
RoundManager.prototype.getCarsStatuses.mockClear(); | ||
RoundManager.prototype.getWinners.mockClear(); | ||
Output.print.mockClear(); | ||
Output.printRoundResults.mockClear(); | ||
}); | ||
|
||
describe('play 메서드', () => { | ||
test('게임을 진행하고 결과를 출력한다.', () => { | ||
CarAllocator.parseNames.mockReturnValue(['Woo', 'Wa']); | ||
CarAllocator.allocateCars.mockReturnValue([ | ||
{ name: 'Woo' }, | ||
{ name: 'Wa' }, | ||
]); | ||
|
||
const game = new Game('Woo,Wa', 3); | ||
|
||
Random.pickNumberInRange.mockReturnValue(Rules.THRESHOLD_NUMBER); // Woo, Wa 모두 전진 | ||
|
||
RoundManager.prototype.startRound.mockImplementation(() => {}); | ||
RoundManager.prototype.getCarsStatuses.mockReturnValue([ | ||
{ name: 'Woo', distance: 1 }, | ||
{ name: 'Wa', distance: 1 }, | ||
]); | ||
RoundManager.prototype.getWinners.mockReturnValue(['Woo', 'Wa']); | ||
|
||
const winners = game.play(); | ||
|
||
expect(Output.print).toHaveBeenCalledWith( | ||
OutputView.RESULT_PRINT_BEGINNING, | ||
); | ||
expect(Output.printRoundResults).toHaveBeenCalledTimes(3); | ||
expect(Output.printRoundResults).toHaveBeenCalledWith([ | ||
{ name: 'Woo', distance: 1 }, | ||
{ name: 'Wa', distance: 1 }, | ||
]); | ||
expect(winners).toEqual(expect.arrayContaining(['Woo', 'Wa'])); | ||
}); | ||
}); | ||
|
||
describe('startRound 메서드', () => { | ||
test('각 Car 인스턴스가 이동할지 여부를 결정한다.', () => { | ||
CarAllocator.parseNames.mockReturnValue(['Woo', 'Wa']); | ||
CarAllocator.allocateCars.mockReturnValue([ | ||
{ name: 'Woo' }, | ||
{ name: 'Wa' }, | ||
]); | ||
|
||
const game = new Game('Woo,Wa', 1); | ||
|
||
Random.pickNumberInRange | ||
.mockReturnValueOnce(Rules.THRESHOLD_NUMBER) // Woo 전진 | ||
.mockReturnValueOnce(Rules.THRESHOLD_NUMBER - 1); // Wa 정지 | ||
|
||
RoundManager.prototype.startRound.mockImplementation((cars) => { | ||
cars[0].currentDistance = Rules.INITIAL_DISTANCE + Rules.MOVE_LENGTH; | ||
cars[1].currentDistance = Rules.INITIAL_DISTANCE; | ||
}); | ||
RoundManager.prototype.getCarsStatuses.mockReturnValue([ | ||
{ name: 'Woo', distance: Rules.INITIAL_DISTANCE + Rules.MOVE_LENGTH }, | ||
{ name: 'Wa', distance: Rules.INITIAL_DISTANCE }, | ||
]); | ||
|
||
game.play(); | ||
|
||
expect(Output.printRoundResults).toHaveBeenCalledWith([ | ||
{ name: 'Woo', distance: Rules.INITIAL_DISTANCE + Rules.MOVE_LENGTH }, | ||
{ name: 'Wa', distance: Rules.INITIAL_DISTANCE }, | ||
]); | ||
}); | ||
}); | ||
}); |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,22 @@ | ||
import { Console } from '@woowacourse/mission-utils'; | ||
import Input from '../src/utils/io/Input'; | ||
|
||
describe('Input 클래스 테스트', () => { | ||
beforeAll(() => { | ||
Console.readLineAsync = jest.fn(); | ||
}); | ||
|
||
test('자동차 이름과 게임 반복 횟수를 올바르게 입력받아 반환한다.', async () => { | ||
const mockNames = 'car1,car2,car3'; | ||
const mockRepetition = '5'; | ||
|
||
Console.readLineAsync | ||
.mockResolvedValueOnce(mockNames) | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more.
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. 비동기 함수를 mocking하여 return 변수를 지정할 때, |
||
.mockResolvedValueOnce(mockRepetition); | ||
|
||
const result = await Input.get(); | ||
|
||
expect(result.names).toBe(mockNames); | ||
expect(result.repetitionString).toBe(mockRepetition); | ||
}); | ||
}); |
Oops, something went wrong.
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
import할떄 RULES로 선언하셨으면 상수로 인식하기더 좋을 것 같아요!
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
오! 정말 그런 것 같아요.
변하지 않는 상수라는 뜻이 잘 내포되는 것 같습니당 👍