Go 언어로 테스트하기위한 적절한 패키지 이름 지정


103

Go 내에서 몇 가지 다른 테스트 패키지 명명 전략을 보았고 각각의 장단점과 사용해야하는 것을 알고 싶었습니다.

전략 1 :

파일 이름 : github.com/user/myfunc.go

package myfunc

테스트 파일 이름 : github.com/user/myfunc_test.go

package myfunc

예제는 bzip2 를 참조하십시오 .

전략 2 :

파일 이름 : github.com/user/myfunc.go

package myfunc

테스트 파일 이름 : github.com/user/myfunc_test.go

package myfunc_test

import (
    "github.com/user/myfunc"
)

예는 와이어 를 참조하십시오 .

전략 3 :

파일 이름 : github.com/user/myfunc.go

package myfunc

테스트 파일 이름 : github.com/user/myfunc_test.go

package myfunc_test

import (
    . "myfunc"
)

예는 문자열 을 참조하십시오 .

Go 표준 라이브러리는 전략 1과 2를 혼합하여 사용하는 것 같습니다. 세 가지 중 어느 것을 사용해야합니까? package *_test내 패키지 비공개 메서드를 테스트 할 수 없다는 의미로 내 테스트 패키지에 추가하는 것은 고통 스럽지만 내가 알지 못하는 숨겨진 이점이있을 수 있습니까?


9
이 질문은 다양한 의견을 낳을 것입니다. 개인 메서드를 테스트 할 필요가 없습니다. 다른 개발자가 사용할 패키지의 인터페이스를 테스트하려고합니다. 테스트가 실패하면 개인 메서드를 살펴 봐야한다는 것을 알 수 있습니다.
Brenden 2013

2
전략 2 의 [wire] ( github.com/btcsuite/btcd/blob/master/wire/msgtx_test.go ) 예제는 실제로 이제 전략 1의 예제이기도합니다 ...
durp

답변:


133

나열한 세 가지 전략의 근본적인 차이점은 테스트 코드가 테스트중인 코드와 동일한 패키지에 있는지 여부입니다. 사용에 대한 결정 package myfunc또는 package myfunc_test테스트 파일을 수행할지 여부에 따라 화이트 박스 또는 블랙 박스 테스트를.

프로젝트에서 두 가지 방법을 모두 사용하는 것은 잘못된 것이 아닙니다. 예를 들어 myfunc_whitebox_test.gomyfunx_blackbox_test.go.

테스트 코드 패키지 비교

  • 블랙 박스 테스트 :를 사용 package myfunc_test하면 내 보낸 식별자 만 사용 됩니다 .
  • 화이트 박스 테스트 :package myfunc 내 보내지 않은 식별자에 액세스 할 수 있도록 사용 합니다. 내 보내지 않은 변수, 함수 및 메서드에 액세스해야하는 단위 테스트에 적합합니다.

문제에 나열된 전략 비교

  • 전략 1 : 파일 myfunc_test.go사용 package myfunc—이 경우의 테스트 코드 는이 예제에 있는 myfunc_test.go에서 테스트중인 코드와 동일한 패키지에 있습니다.myfunc.gomyfunc
  • 전략 2 : 파일 myfunc_test.go사용 package myfunc_test—이 경우에있는 테스트 코드는 myfunc_test.go"별도의 패키지로 컴파일 된 다음 메인 테스트 바이너리와 연결 및 실행됩니다." [출처 : test.go 소스 코드의 58 ~ 59 행 ]
  • 전략 3 : 파일 에서 점 표기법을 myfunc_test.go사용 package myfunc_test하지만 가져 오기 myfunc— 전략 2의 변형이지만 점 표기법을 사용하여 myfunc.

1
전략 1을 사용하면 _test.go테스트중인 패키지 와 별도의 파일도 보관 됩니다 (전략 2와 동일한 동작). 이것은 github.com/golang/go/issues/15315
Kevin Deenanauth 2016 년

강력한 패키지 사용 전략 3을 보았지만 요점이 무엇인지 이해할 수 없습니까?
PickBoy apr

1
패키지를 분기하고 변경 한 후 이제 테스트가 모두 분기 된 패키지 대신 원본 저장소를 가져 오려고합니다. 전략 3에서는 '.'를 참조하기 때문에 "github.com/original/link"를 "github.com/my/fork"로 변경할 필요가 없습니다. 대신.
nmarley

1
@KevinDeenanauth 이것은 나를 놀랐습니다. 나는 단지를 발견했을 때 나는 함정을 발견했다고 생각 _test.go비와 _test포함 된 패키지 이름 func init()테스트를 위해 일부 글로벌 패키지 변수를 변경하는합니다. 내가 틀렸어.
Zyl

1
@nmarley는 .포크 문제를 해결하지 않습니다. 상대적 수입이 아닙니다. "현재 패키지로"식별자를 가져옵니다.
qaisjp

19

테스트 범위에 따라 다릅니다. 내 보낸 API를 통해 패키지를 사용하고 있는지 확인하려면 고급 테스트 (통합, 승인 등)를 별도의 패키지에 배치해야합니다.

테스트해야하는 내부가 많은 대형 패키지가있는 경우 테스트에 동일한 패키지를 사용하십시오. 그러나 이는 테스트가 비공개 상태에 액세스하도록 초대하는 것이 아닙니다. 그것은 리팩토링을 악몽으로 만들 것입니다. 이동 중에 구조체를 작성할 때 종종 인터페이스를 구현합니다. 모든 도우미 메서드 / 함수를 개별적으로 호출하는 것이 아니라 테스트에서 호출하는 인터페이스 메서드입니다.


13

가능하면 전략 1을 사용해야합니다. 특수 foo_test패키지 이름을 사용하여 가져 오기주기를 피할 수 있지만 대부분의 경우 동일한 메커니즘으로 표준 라이브러리를 테스트 할 수 있습니다. 예를 들어 패키지가에 종속되어 strings있으므로 전략 1로 테스트 할 수 없습니다 . 말했듯이 전략 2 또는 3에서는 패키지의 개인 식별자에 액세스 할 수 없으므로 필요하지 않는 한 일반적으로 사용하지 않는 것이 좋습니다.testingstrings


10
미덕이 아닌 테스트에서 개인 식별자에 액세스하지 못하는 이유는 무엇입니까?
jub0bs

3
좋은 테스트 사례에 따르면 코드 아티팩트에 대한 내부 구현 세부 정보를 테스트하지 않습니다. 아들의 일을 인 코드 냄새는
제라르 리마

0

Golang CodeReviewCommentsimport . 에서 추가하고 싶은 중요한 메모 :

import .양식은 순환 종속성 으로 인해 테스트중인 패키지의 일부가 될 수없는 테스트에서 유용 할 수 있습니다 .

package foo_test

import (
    "bar/testutil" // also imports "foo"
    . "foo"
)

이 경우 테스트 파일은 foo bar/testutil를 가져 오는를 사용하기 때문에 패키지 foo에있을 수 없습니다 . 그래서 우리는 'import.'를 사용합니다. 파일이 아닌 경우에도 foo 패키지의 일부인 것처럼 가장하는 형식입니다.

이 경우를 제외하고는import . 프로그램에서 사용하지 마십시오 . Quux와 같은 이름이 현재 패키지 또는 가져온 패키지에서 최상위 식별자인지 명확하지 않기 때문에 프로그램을 읽기가 훨씬 더 어려워집니다.

당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.