Ruby procs를 사용하여 RSpec 테스트에서 하드코어 중첩 제거
먼저 평소처럼 컨텍스트에 조건을 중첩하기 시작했습니다. 따라서 테스트는 다음과 같습니다.
context 'when A1' do
let(:a1) {}
it 'R1' do
# ...
end
context 'and B1' do
let(:b1) {}
it 'R1' do
# ...
end
end
context 'and B2' do
let(:b2) {}
it 'R1' do
# ...
end
end
end
context 'when A2' do
let(:a2) {}
it 'R2' do
# ...
end
context 'and B1' do
let(:b1) {}
it 'R3' do
# ...
end
end
context 'and B2' do
let(:b2) {}
it 'R2' do
# ...
end
end
end
제 경우에는 중첩 수준이 한 단계 더 있었기 때문에 코드를 정말 읽을 수 없고 이해하기 어려웠습니다. 여기에서 한 수준을 제거하고 컨텍스트 내용을 정리하여 독자 여러분의 눈을 보호했습니다 :)
보시다시피 반복이 많았기 때문에 가장 먼저 반복 컨텍스트를
shared_context
블록으로 추출하고 테스트 사례를 shared_examples
로 반복하여 코드가 다음과 같이 되었습니다.shared_context 'A1' do
let(:a1) {}
end
shared_context 'A2' do
let(:a2) {}
end
shared_context 'B1' do
let(:b1) {}
end
shared_context 'B2' do
let(:b2) {}
end
shared_examples 'R1' do
it 'R1' do
# ...
end
end
shared_examples 'R2' do
it 'R2' do
# ...
end
end
shared_examples 'R3' do
it 'R3' do
# ...
end
end
context 'A1' do
include_context 'A1'
include_examples 'R1'
context 'B1' do
include_context 'B1'
include_examples 'R1'
end
context 'B2' do
include_context 'B2'
include_examples 'R1'
end
end
context 'A2' do
include_context 'A2'
include_examples 'R2'
context 'B1' do
include_context 'B1'
include_examples 'R3'
end
context 'B2' do
include_context 'B2'
include_examples 'R2'
end
end
좋습니다. 적어도 지금은 테스트 또는 컨텍스트 사례의 세부 정보가 변경될 때마다 모든 위치를 업데이트할 필요가 없습니다.
그러나 중첩으로 인해 테스트는 여전히 읽기 어려울 것이므로 끝없는 중첩 블록을 탐색하는 대신 각 시나리오를 한 줄로 정의하는 것이 멋질 것이라고 생각했습니다.
아래 스 니펫과 같은 것을 상상해보십시오. 중첩된 컨텍스트와 이전 코드 블록의 예제를 번역하여 각 행에서 배열의 마지막 요소가 예상되는
shared_examples
그룹을 정의하고 모든 이전 요소가 shared_context
의 이름이 되도록 변환했습니다. 또 다른:[
['A1', 'R1'],
['A1', 'B1', 'R1'],
['A1', 'B2', 'R1'],
['A2', 'R2'],
['A2', 'B1', 'R3'],
['A2', 'B2', 'R2'],
].each do |scenario|
# ... do some Ruby + rspec magic here
end
훨씬 잘 읽히죠? 전체 솔루션이 어떻게 생겼는지 살펴보겠습니다.
[
['A1', 'R1'],
['A1', 'B1', 'R1'],
['A1', 'B2', 'R1'],
['A2', 'R2'],
['A2', 'B1', 'R3'],
['A2', 'B2', 'R2'],
].each do |scenario|
# All but last element of the array
contexts = scenario[0..-2]
test_example = scenario.last
# Let's prepare a deeply nested set of Procs with all the required nesting to achieve the same result.
# A tricky thing to understand here is that we need to start from the most nested block and go up,
# until the most outer context.
contexts.reverse.inject(proc { include_examples(test_example) }) do |inner, ctx|
proc do
context ctx do
include_context(ctx, &inner)
end
end
end.call
end
나는 이 해결책이 내가 가진 문제에 매우 구체적일 수 있다는 것을 이해하지만 아마도 테스트를 리팩토링하고 가독성을 향상시키는 데 영감을 줄 수 있습니다.
이러한 문제를 처리하는 더 간단하거나 더 나은 방법(Ruby gem? 내장된 RSpec 기능?)을 알고 있다면 댓글이나 비공개 메시지로 알려주세요.
Reference
이 문제에 관하여(Ruby procs를 사용하여 RSpec 테스트에서 하드코어 중첩 제거), 우리는 이곳에서 더 많은 자료를 발견하고 링크를 클릭하여 보았다 https://dev.to/bajena/eliminate-hardcore-nesting-in-your-rspec-tests-by-using-ruby-procs-12l3텍스트를 자유롭게 공유하거나 복사할 수 있습니다.하지만 이 문서의 URL은 참조 URL로 남겨 두십시오.
우수한 개발자 콘텐츠 발견에 전념 (Collection and Share based on the CC Protocol.)