Keyboard shortcuts

Press or to navigate between chapters

Press S or / to search in the book

Press ? to show this help

Press Esc to hide this help

[インデックス 17477] ファイルの概要

このコミットは、Goコマンドラインツール(cmd/go)におけるテストバイナリの扱いに関する変更です。具体的には、go test -coverコマンドでカバレッジ情報を生成する際に、テストバイナリ(pkg.test)を不要にディスクに残さないように修正しています。

コミット

commit 6833d1b43643d8102be45cb6b4ee5912cafed8e7
Author: Rob Pike <r@golang.org>
Date:   Fri Sep 6 15:54:26 2013 +1000

    cmd/go: don't leave test binary around for coverage
    It's not needed to analyze coverage data.
    Fixes #6120
    
    R=golang-dev, adg
    CC=golang-dev
    https://golang.org/cl/13343050

GitHub上でのコミットページへのリンク

https://github.com/golang/go/commit/6833d1b43643d8102be45cb6b4ee5912cafed8e7

元コミット内容

cmd/go: don't leave test binary around for coveragecmd/go: カバレッジのためにテストバイナリを残さない)

It's not needed to analyze coverage data. (カバレッジデータを分析するために必要ないため。)

Fixes #6120 (Issue #6120 を修正)

変更の背景

Goのgo testコマンドは、テストの実行だけでなく、プロファイリング(CPUプロファイル、メモリプロファイルなど)やコードカバレッジの測定機能も提供します。

以前のgo testの挙動では、プロファイル情報を生成するフラグ(例: -cpuprofile, -memprofile)が指定された場合、生成されたプロファイルデータを分析するためにテストバイナリ(pkg.test)がディスク上に残されていました。これは、プロファイルデータがバイナリ内のシンボル情報に依存するため、プロファイルツールが正確な情報を表示するために必要だったからです。

しかし、コードカバレッジ(-coverフラグ)の場合、カバレッジデータはテスト実行時に生成される独立したファイル(通常は.coverprofile)に記録され、その分析にはテストバイナリ自体は直接必要ありませんでした。それにもかかわらず、カバレッジフラグが指定された場合でも、他のプロファイルフラグと同様にテストバイナリが残されてしまうという非効率な挙動がありました。

このコミットは、この非効率性を解消し、カバレッジ測定時においては不要なテストバイナリの残留を防ぐことを目的としています。これは、Issue #6120で報告された問題に対応するものです。

前提知識の解説

Goのgo testコマンド

go testコマンドは、Go言語のパッケージのテストを実行するための主要なツールです。単体テスト、結合テスト、ベンチマークテストなどを実行できます。

Goのプロファイリング

Goには、プログラムのパフォーマンス特性を分析するためのプロファイリングツールが組み込まれています。go testコマンドと連携して、CPU使用率、メモリ割り当て、ブロックプロファイルなどを収集できます。

  • CPUプロファイル (-cpuprofile): プログラムがCPU時間をどこで消費しているかを分析します。
  • メモリプロファイル (-memprofile): プログラムがメモリをどのように割り当て、使用しているかを分析します。
  • ブロックプロファイル (-blockprofile): ゴルーチンが同期プリミティブ(ミューテックス、チャネルなど)でブロックされている時間を分析します。

これらのプロファイルデータは、通常、pprofツールで分析されます。pprofは、プロファイルデータと元のバイナリを組み合わせて、関数ごとのCPU時間やメモリ使用量などを視覚化します。そのため、プロファイル時にはテストバイナリが残される必要がありました。

Goのコードカバレッジ

コードカバレッジは、テストスイートがソースコードのどの部分を実行したかを示す指標です。go test -coverコマンドを使用すると、テスト実行中にカバレッジ情報を収集し、.coverprofileファイルに出力できます。このファイルは、go tool coverコマンドで分析され、HTMLレポートとして視覚化したり、カバレッジ率を計算したりできます。

カバレッジデータは、実行されたコードの行番号やブロック情報に基づいており、プロファイルデータのようにバイナリのシンボル情報に直接依存しません。そのため、カバレッジ分析にはテストバイナリ自体は不要です。

go listコマンドとビルドタグ

go listコマンドは、Goパッケージに関する情報を表示するためのツールです。パッケージの依存関係、ソースファイルのパス、ビルドタグなどの情報をJSON形式などで出力できます。

ビルドタグ (-tags): Goのソースファイルには、// +build tagのようなビルドタグを記述できます。これにより、特定の環境や条件(例: OS、アーキテクチャ、カスタムタグ)でのみコンパイルされるコードを記述できます。go buildgo testコマンドで-tagsフラグを指定することで、これらのタグに基づいてコンパイルするファイルを制御できます。

レース検出器 (-race): Goには、データ競合(data race)を検出するためのレース検出器が組み込まれています。go build -racego test -raceのように-raceフラグを付けてコンパイル・実行することで、並行処理における潜在的なバグを特定できます。レース検出器を有効にすると、コンパイルされるバイナリに特別なインストゥルメンテーションが追加され、実行時にデータ競合を監視します。このインストゥルメンテーションは、追加の依存関係を必要とします。

技術的詳細

このコミットの主要な変更点は、go testコマンドがテストバイナリをディスクに残すかどうかの判断ロジックを修正したことです。

以前は、testC-cフラグ、テストバイナリをコンパイルするだけ)またはtestProfile(プロファイルフラグのいずれか)が真の場合にテストバイナリを残していました。

この変更では、testProfileの代わりにtestNeedBinaryという新しいブール変数testNeedBinaryを導入し、プロファイルフラグが指定された場合にのみtestNeedBinarytrueに設定するようにしました。これにより、カバレッジフラグ(-cover)が指定されてもtestNeedBinaryfalseのままであり、テストバイナリが不要にディスクに残されることがなくなりました。

また、go listコマンドのドキュメント(src/cmd/go/doc.go)に、-raceフラグに関する説明が追加されました。これは、go listがパッケージデータを表示する際に、レース検出器が必要とする依存関係も考慮に入れることを示しています。

コアとなるコードの変更箇所

  1. src/cmd/go/doc.go:

    • go listコマンドのヘルプメッセージに-raceフラグに関する説明が追加されました。
    • go testコマンドのヘルプメッセージにおいて、プロファイルフラグがテストバイナリを残す条件から「カバレッジ」が除外されました。
  2. src/cmd/go/test.go:

    • testNeedBinaryという新しいブール変数がvarブロックに追加されました。
    • テストバイナリをディスクに残す条件がtestC || testProfileからtestC || testNeedBinaryに変更されました。
    • go testコマンドのヘルプメッセージにおいて、プロファイルフラグがテストバイナリを残す条件から「カバレッジ」が除外されました。(doc.goと同様の変更)
  3. src/cmd/go/testflag.go:

    • testFlags関数内で、blockprofile, cpuprofile, memprofileのいずれかのプロファイルフラグが指定された場合に、新しく追加されたtestNeedBinary変数をtrueに設定するロジックが追加されました。

コアとなるコードの解説

src/cmd/go/doc.go

--- a/src/cmd/go/doc.go
+++ b/src/cmd/go/doc.go
@@ -269,7 +269,7 @@ List packages
 
 Usage:
 
-	go list [-e] [-f format] [-json] [-tags 'tag list'] [packages]
+	go list [-e] [-race] [-f format] [-json] [-tags 'tag list'] [packages]
 
 List lists the packages named by the import paths, one per line.
 
@@ -345,6 +345,9 @@ a non-nil Error field; other information may or may not be missing
 The -tags flag specifies a list of build tags, like in the 'go build'
 command.
 
+The -race flag causes the package data to include the dependencies
+required by the race detector.
+
 For more about specifying packages, see 'go help packages'.
 
 
@@ -809,8 +812,8 @@ will compile the test binary and then run it as
 
 	tpkg.test -test.v -test.cpuprofile=prof.out -dir=testdata -update
 
-The test flags that generate profiles also leave the test binary in pkg.test
-for use when analyzing the profiles.
+The test flags that generate profiles (other than for coverage) also
+leave the test binary in pkg.test for use when analyzing the profiles.
 
 Flags not recognized by 'go test' must be placed after any specified packages.
  • go listのUsageに-raceフラグが追加され、その説明として「The -race flag causes the package data to include the dependencies required by the race detector.」(-raceフラグは、パッケージデータにレース検出器が必要とする依存関係を含めるようにします。)が追記されました。これは、go listがパッケージ情報を取得する際に、レース検出器が有効な場合のビルド依存関係も考慮に入れるようになったことを示唆しています。
  • go testのヘルプメッセージにおいて、テストバイナリが残される条件の説明が「The test flags that generate profiles also leave the test binary in pkg.test for use when analyzing the profiles.」から「The test flags that generate profiles (other than for coverage) also leave the test binary in pkg.test for use when analyzing the profiles.」に変更されました。これにより、カバレッジはテストバイナリを残す条件から除外されることが明示されました。

src/cmd/go/test.go

--- a/src/cmd/go/test.go
+++ b/src/cmd/go/test.go
@@ -213,8 +213,8 @@ will compile the test binary and then run it as
 
 	tpkg.test -test.v -test.cpuprofile=prof.out -dir=testdata -update
 
-The test flags that generate profiles also leave the test binary in pkg.test
-for use when analyzing the profiles.
+The test flags that generate profiles (other than for coverage) also
+leave the test binary in pkg.test for use when analyzing the profiles.
 
 Flags not recognized by 'go test' must be placed after any specified packages.
 `,
@@ -272,6 +272,7 @@ var (
 	testCoverPaths   []string   // -coverpkg flag
 	testCoverPkgs    []*Package // -coverpkg flag
 	testProfile      bool       // some profiling flag
+	testNeedBinary   bool       // profile needs to keep binary around
 	testI            bool       // -i flag
 	testV            bool       // -v flag
 	testFiles        []string   // -file flag(s)  TODO: not respected
@@ -728,7 +729,7 @@ func (b *builder) test(p *Package) (buildAction, runAction, printAction *action,
 	a.target = filepath.Join(testDir, testBinary) + exeSuffix
 	pmainAction := a
 
-\tif testC || testProfile {
+\tif testC || testNeedBinary {
 		// -c or profiling flag: create action to copy binary to ./test.out.
 		runAction = &action{
 			f:      (*builder).install,
  • testNeedBinaryという新しいグローバル変数が追加されました。この変数は、プロファイルのためにテストバイナリを保持する必要があるかどうかを示すフラグです。
  • テストバイナリをコピーする条件がtestC || testProfileからtestC || testNeedBinaryに変更されました。これにより、testProfileが真であっても、testNeedBinaryが真でない限りバイナリは残されなくなります。

src/cmd/go/testflag.go

--- a/src/cmd/go/testflag.go
+++ b/src/cmd/go/testflag.go
@@ -181,6 +181,7 @@ func testFlags(args []string) (packageNames, passToTest []string) {
 		\ttestTimeout = value
 		case "blockprofile", "cpuprofile", "memprofile":
 			testProfile = true
+			testNeedBinary = true
 		case "coverpkg":
 			testCover = true
 			if value == "" {
  • testFlags関数内で、blockprofile, cpuprofile, memprofileのいずれかのプロファイルフラグが解析された場合に、testProfiletrueにするだけでなく、新しく追加されたtestNeedBinarytrueに設定するように変更されました。これにより、これらのプロファイルフラグが指定された場合にのみ、testNeedBinarytrueとなり、テストバイナリが残されるようになります。

これらの変更により、go test -coverを実行してもテストバイナリがディスクに残らなくなり、ディスクスペースの節約とクリーンアップの簡素化に貢献します。

関連リンク

参考にした情報源リンク

このコミットは、Goコマンドラインツール(cmd/go)におけるテストバイナリの扱いに関する変更です。具体的には、go test -coverコマンドでカバレッジ情報を生成する際に、テストバイナリ(pkg.test)を不要にディスクに残さないように修正しています。

コミット

commit 6833d1b43643d8102be45cb6b4ee5912cafed8e7
Author: Rob Pike <r@golang.org>
Date:   Fri Sep 6 15:54:26 2013 +1000

    cmd/go: don't leave test binary around for coverage
    It's not needed to analyze coverage data.
    Fixes #6120
    
    R=golang-dev, adg
    CC=golang-dev
    https://golang.org/cl/13343050

GitHub上でのコミットページへのリンク

https://github.com/golang/go/commit/6833d1b43643d8102be45cb6b4ee5912cafed8e7

元コミット内容

cmd/go: don't leave test binary around for coveragecmd/go: カバレッジのためにテストバイナリを残さない)

It's not needed to analyze coverage data. (カバレッジデータを分析するために必要ないため。)

Fixes #6120 (Issue #6120 を修正)

変更の背景

Goのgo testコマンドは、テストの実行だけでなく、プロファイリング(CPUプロファイル、メモリプロファイルなど)やコードカバレッジの測定機能も提供します。

以前のgo testの挙動では、プロファイル情報を生成するフラグ(例: -cpuprofile, -memprofile)が指定された場合、生成されたプロファイルデータを分析するためにテストバイナリ(pkg.test)がディスク上に残されていました。これは、プロファイルデータがバイナリ内のシンボル情報に依存するため、プロファイルツールが正確な情報を表示するために必要だったからです。

しかし、コードカバレッジ(-coverフラグ)の場合、カバレッジデータはテスト実行時に生成される独立したファイル(通常は.coverprofile)に記録され、その分析にはテストバイナリ自体は直接必要ありませんでした。それにもかかわらず、カバレッジフラグが指定された場合でも、他のプロファイルフラグと同様にテストバイナリが残されてしまうという非効率な挙動がありました。

このコミットは、この非効率性を解消し、カバレッジ測定時においては不要なテストバイナリの残留を防ぐことを目的としています。これは、Issue #6120で報告された問題に対応するものです。

前提知識の解説

Goのgo testコマンド

go testコマンドは、Go言語のパッケージのテストを実行するための主要なツールです。単体テスト、結合テスト、ベンチマークテストなどを実行できます。

Goのプロファイリング

Goには、プログラムのパフォーマンス特性を分析するためのプロファイリングツールが組み込まれています。go testコマンドと連携して、CPU使用率、メモリ割り当て、ブロックプロファイルなどを収集できます。

  • CPUプロファイル (-cpuprofile): プログラムがCPU時間をどこで消費しているかを分析します。
  • メモリプロファイル (-memprofile): プログラムがメモリをどのように割り当て、使用しているかを分析します。
  • ブロックプロファイル (-blockprofile): ゴルーチンが同期プリミティブ(ミューテックス、チャネルなど)でブロックされている時間を分析します。

これらのプロファイルデータは、通常、pprofツールで分析されます。pprofは、プロファイルデータと元のバイナリを組み合わせて、関数ごとのCPU時間やメモリ使用量などを視覚化します。そのため、プロファイル時にはテストバイナリが残される必要がありました。

Goのコードカバレッジ

コードカバレッジは、テストスイートがソースコードのどの部分を実行したかを示す指標です。go test -coverコマンドを使用すると、テスト実行中にカバレッジ情報を収集し、.coverprofileファイルに出力できます。このファイルは、go tool coverコマンドで分析され、HTMLレポートとして視覚化したり、カバレッジ率を計算したりできます。

カバレッジデータは、実行されたコードの行番号やブロック情報に基づいており、プロファイルデータのようにバイナリのシンボル情報に直接依存しません。そのため、カバレッジ分析にはテストバイナリ自体は不要です。

go listコマンドとビルドタグ

go listコマンドは、Goパッケージに関する情報を表示するためのツールです。パッケージの依存関係、ソースファイルのパス、ビルドタグなどの情報をJSON形式などで出力できます。

ビルドタグ (-tags): Goのソースファイルには、// +build tagのようなビルドタグを記述できます。これにより、特定の環境や条件(例: OS、アーキテクチャ、カスタムタグ)でのみコンパイルされるコードを記述できます。go buildgo testコマンドで-tagsフラグを指定することで、これらのタグに基づいてコンパイルするファイルを制御できます。

レース検出器 (-race): Goには、データ競合(data race)を検出するためのレース検出器が組み込まれています。go build -racego test -raceのように-raceフラグを付けてコンパイル・実行することで、並行処理における潜在的なバグを特定できます。レース検出器を有効にすると、コンパイルされるバイナリに特別なインストゥルメンテーションが追加され、実行時にデータ競合を監視します。このインストゥルメンテーションは、追加の依存関係を必要とします。

技術的詳細

このコミットの主要な変更点は、go testコマンドがテストバイナリをディスクに残すかどうかの判断ロジックを修正したことです。

以前は、testC-cフラグ、テストバイナリをコンパイルするだけ)またはtestProfile(プロファイルフラグのいずれか)が真の場合にテストバイナリを残していました。

この変更では、testProfileの代わりにtestNeedBinaryという新しいブール変数testNeedBinaryを導入し、プロファイルフラグが指定された場合にのみtestNeedBinarytrueに設定するようにしました。これにより、カバレッジフラグ(-cover)が指定されてもtestNeedBinaryfalseのままであり、テストバイナリが不要にディスクに残されることがなくなりました。

また、go listコマンドのドキュメント(src/cmd/go/doc.go)に、-raceフラグに関する説明が追加されました。これは、go listがパッケージデータを表示する際に、レース検出器が必要とする依存関係も考慮に入れることを示しています。

コアとなるコードの変更箇所

  1. src/cmd/go/doc.go:

    • go listコマンドのヘルプメッセージに-raceフラグに関する説明が追加されました。
    • go testコマンドのヘルプメッセージにおいて、プロファイルフラグがテストバイナリを残す条件から「カバレッジ」が除外されました。
  2. src/cmd/go/test.go:

    • testNeedBinaryという新しいブール変数がvarブロックに追加されました。
    • テストバイナリをディスクに残す条件がtestC || testProfileからtestC || testNeedBinaryに変更されました。
    • go testコマンドのヘルプメッセージにおいて、プロファイルフラグがテストバイナリを残す条件から「カバレッジ」が除外されました。(doc.goと同様の変更)
  3. src/cmd/go/testflag.go:

    • testFlags関数内で、blockprofile, cpuprofile, memprofileのいずれかのプロファイルフラグが指定された場合に、新しく追加されたtestNeedBinary変数をtrueに設定するロジックが追加されました。

コアとなるコードの解説

src/cmd/go/doc.go

--- a/src/cmd/go/doc.go
+++ b/src/cmd/go/doc.go
@@ -269,7 +269,7 @@ List packages
 
 Usage:
 
-	go list [-e] [-f format] [-json] [-tags 'tag list'] [packages]
+	go list [-e] [-race] [-f format] [-json] [-tags 'tag list'] [packages]
 
 List lists the packages named by the import paths, one per line.
 
@@ -345,6 +345,9 @@ a non-nil Error field; other information may or may not be missing
 The -tags flag specifies a list of build tags, like in the 'go build'
 command.
 
+The -race flag causes the package data to include the dependencies
+required by the race detector.
+
 For more about specifying packages, see 'go help packages'.
 
 
@@ -809,8 +812,8 @@ will compile the test binary and then run it as
 
 	tpkg.test -test.v -test.cpuprofile=prof.out -dir=testdata -update
 
-The test flags that generate profiles also leave the test binary in pkg.test
-for use when analyzing the profiles.
+The test flags that generate profiles (other than for coverage) also
+leave the test binary in pkg.test for use when analyzing the profiles.
 
 Flags not recognized by 'go test' must be placed after any specified packages.
  • go listのUsageに-raceフラグが追加され、その説明として「The -race flag causes the package data to include the dependencies required by the race detector.」(-raceフラグは、パッケージデータにレース検出器が必要とする依存関係を含めるようにします。)が追記されました。これは、go listがパッケージ情報を取得する際に、レース検出器が有効な場合のビルド依存関係も考慮に入れるようになったことを示唆しています。
  • go testのヘルプメッセージにおいて、テストバイナリが残される条件の説明が「The test flags that generate profiles also leave the test binary in pkg.test for use when analyzing the profiles.」から「The test flags that generate profiles (other than for coverage) also leave the test binary in pkg.test for use when analyzing the profiles.」に変更されました。これにより、カバレッジはテストバイナリを残す条件から除外されることが明示されました。

src/cmd/go/test.go

--- a/src/cmd/go/test.go
+++ b/src/cmd/go/test.go
@@ -213,8 +213,8 @@ will compile the test binary and then run it as
 
 	tpkg.test -test.v -test.cpuprofile=prof.out -dir=testdata -update
 
-The test flags that generate profiles also leave the test binary in pkg.test
-for use when analyzing the profiles.
+The test flags that generate profiles (other than for coverage) also
+leave the test binary in pkg.test for use when analyzing the profiles.
 
 Flags not recognized by 'go test' must be placed after any specified packages.
 `,
@@ -272,6 +272,7 @@ var (
 	testCoverPaths   []string   // -coverpkg flag
 	testCoverPkgs    []*Package // -coverpkg flag
 	testProfile      bool       // some profiling flag
+	testNeedBinary   bool       // profile needs to keep binary around
 	testI            bool       // -i flag
 	testV            bool       // -v flag
 	testFiles        []string   // -file flag(s)  TODO: not respected
@@ -728,7 +729,7 @@ func (b *builder) test(p *Package) (buildAction, runAction, printAction *action,\
 	a.target = filepath.Join(testDir, testBinary) + exeSuffix
 	pmainAction := a
 
-\tif testC || testProfile {
+\tif testC || testNeedBinary {
 		// -c or profiling flag: create action to copy binary to ./test.out.
 		runAction = &action{
 			f:      (*builder).install,
  • testNeedBinaryという新しいグローバル変数が追加されました。この変数は、プロファイルのためにテストバイナリを保持する必要があるかどうかを示すフラグです。
  • テストバイナリをコピーする条件がtestC || testProfileからtestC || testNeedBinaryに変更されました。これにより、testProfileが真であっても、testNeedBinaryが真でない限りバイナリは残されなくなります。

src/cmd/go/testflag.go

--- a/src/cmd/go/testflag.go
+++ b/src/cmd/go/testflag.go
@@ -181,6 +181,7 @@ func testFlags(args []string) (packageNames, passToTest []string) {
 		\ttestTimeout = value
 		case "blockprofile", "cpuprofile", "memprofile":
 			testProfile = true
+			testNeedBinary = true
 		case "coverpkg":
 			testCover = true
 			if value == "" {
  • testFlags関数内で、blockprofile, cpuprofile, memprofileのいずれかのプロファイルフラグが解析された場合に、testProfiletrueにするだけでなく、新しく追加されたtestNeedBinarytrueに設定するように変更されました。これにより、これらのプロファイルフラグが指定された場合にのみ、testNeedBinarytrueとなり、テストバイナリが残されるようになります。

これらの変更により、go test -coverを実行してもテストバイナリがディスクに残らなくなり、ディスクスペースの節約とクリーンアップの簡素化に貢献します。

関連リンク

参考にした情報源リンク