[インデックス 16937] ファイルの概要
このコミットは、Go言語の標準ライブラリ net
パッケージにおけるTCPコネクションのSetKeepAlivePeriod
メソッドに対するシンプルなテストケースを追加するものです。具体的には、src/pkg/net/protoconn_test.go
ファイルに1行の変更が加えられ、TCPConn
のSetKeepAlivePeriod
メソッドが呼び出されることを確認しています。
コミット
commit fa673bd872d738a24a61ca8ed09c7c3b88d10682
Author: Mikio Hara <mikioh.mikioh@gmail.com>
Date: Wed Jul 31 12:34:14 2013 +0900
net: add simple SetKeepAlivePeriod call test
R=golang-dev, dave
CC=golang-dev
https://golang.org/cl/12090043
GitHub上でのコミットページへのリンク
https://github.com/golang/go/commit/fa673bd872d738a24a61ca8ed09c7c3b88d10682
元コミット内容
net: add simple SetKeepAlivePeriod call test
R=golang-dev, dave
CC=golang-dev
https://golang.org/cl/12090043
変更の背景
このコミットは、net.TCPConn
に新しく追加された(または既存の)SetKeepAlivePeriod
メソッドが正しく呼び出せることを確認するための、基本的なテストカバレッジを追加することを目的としています。TCP Keep-Alive機能は、アイドル状態のTCP接続がまだ有効であるかを検出し、ネットワークの中間デバイス(NATデバイスやファイアウォールなど)によって接続がサイレントに切断されるのを防ぐために重要です。SetKeepAlivePeriod
は、このKeep-Aliveプローブが送信される間隔を設定するためのメソッドであり、その機能がGoのnet
パッケージで適切に動作することを確認するためのテストが不足していた可能性があります。このテストの追加は、ライブラリの堅牢性と信頼性を高める一環として行われました。
前提知識の解説
TCP Keep-Aliveとは
TCP Keep-Aliveは、TCPプロトコルに組み込まれたメカニズムで、アイドル状態のTCP接続がまだアクティブであるかどうかを定期的に確認するために使用されます。これは、以下のような目的で利用されます。
- デッドコネクションの検出: ネットワークケーブルが抜かれたり、リモートマシンがクラッシュしたりした場合、ローカルのオペレーティングシステムはすぐに接続が失われたことを検出できないことがあります。Keep-Aliveプローブは、このような「ハーフオープン」状態の接続を検出し、リソースの無駄遣いを防ぎます。
- 接続の維持: NATデバイスやファイアウォールは、一定時間アイドル状態の接続を自動的に切断することがあります。Keep-Aliveプローブを定期的に送信することで、接続がアクティブであると見せかけ、これらのデバイスによる切断を防ぎ、長期間にわたる接続を維持できます。
- リソースの解放: サーバー側で多数のアイドル接続が残っていると、ファイルディスクリプタなどのシステムリソースが枯渇する可能性があります。Keep-Aliveは、応答しない接続を早期にクリーンアップし、リソースを解放するのに役立ちます。
Keep-Aliveが有効になっている場合、オペレーティングシステムはアイドル状態の接続に対して小さな(通常はデータを含まない)プローブパケットを定期的に送信します。リモートエンドがこれらのプローブに応答すれば、接続は正常であると見なされます。もし一定回数のプローブが応答なしに終わった場合、オペレーティングシステムはその接続がデッドであると判断し、アプリケーションに通知します。
net.TCPConn.SetKeepAlivePeriod
Go言語のnet
パッケージにおけるnet.TCPConn.SetKeepAlivePeriod(d time.Duration)
メソッドは、TCP Keep-Aliveプローブが送信される間隔(期間)を設定するために使用されます。このメソッドは、Keep-Aliveが有効になっているTCP接続に対してのみ意味を持ちます。通常、このメソッドを呼び出す前に、conn.SetKeepAlive(true)
を呼び出してTCP Keep-Alive機能を有効にする必要があります。
この期間d
は、最初のKeep-Aliveプローブが送信されるまでのアイドル時間、そして多くの場合、その後のプローブ間の間隔にも影響を与えます。オペレーティングシステムによって、この設定の挙動は若干異なる場合があります。例えば、macOSでは主にプローブが送信されるまでのアイドル時間を変更しますが、Linuxではアイドル時間とプローブ間の間隔の両方を変更できます。
このメソッドを使用することで、システム全体のTCP Keep-Alive設定に依存せず、特定の接続に対してよりきめ細やかな制御が可能になります。これは、長期間にわたるTCPセッションを維持する必要があるアプリケーションや、ネットワークロードバランサー(NLB)などのアイドルタイムアウトがある環境で特に重要です。
技術的詳細
Goのnet
パッケージは、クロスプラットフォームなネットワークI/Oインターフェースを提供しており、TCP接続のKeep-Alive設定もその一部です。net.TCPConn.SetKeepAlivePeriod
メソッドは、基盤となるオペレーティングシステムのソケットオプションを操作することで機能します。
具体的には、このメソッドは通常、以下のソケットオプションを設定します。
TCP_KEEPIDLE
: 接続がアイドル状態になってから、最初のKeep-Aliveプローブが送信されるまでの時間(秒単位)。TCP_KEEPINTVL
: Keep-Aliveプローブが失敗した場合に、次のプローブが送信されるまでの間隔(秒単位)。TCP_KEEPCNT
: 接続がデッドであると判断されるまでに、送信されるKeep-Aliveプローブの最大数。
SetKeepAlivePeriod
に渡されるtime.Duration
は、これらのオプションのいずれか、または複数を設定するために使用されます。Go 1.12以降では、net
パッケージはデフォルトで新しいソケットに対してTCP_KEEPIDLE
とTCP_KEEPINTVL
を15秒に設定していますが、SetKeepAlivePeriod
を使用することで、このデフォルト値を上書きし、アプリケーションの要件に合わせて調整することができます。
このコミットでは、SetKeepAlivePeriod
が3 * time.Second
という短い期間で呼び出されています。これは、テストの目的上、Keep-Aliveプローブの動作を迅速に確認するため、または特定のシナリオ(例えば、非常に短いアイドルタイムアウトを持つネットワーク環境)をシミュレートするために行われたと考えられます。
protoconn_test.go
ファイルは、net
パッケージ内のプロトコル固有のコネクション(TCPConnなど)の動作をテストするためのものです。このテストは、TCPConnSpecificMethods
という関数の一部として実行され、TCPConn
の様々なメソッドが期待通りに呼び出せることを検証しています。
コアとなるコードの変更箇所
--- a/src/pkg/net/protoconn_test.go
+++ b/src/pkg/net/protoconn_test.go
@@ -103,6 +103,7 @@ func TestTCPConnSpecificMethods(t *testing.T) {
}\n defer c.Close()\n c.SetKeepAlive(false)\n+\tc.SetKeepAlivePeriod(3 * time.Second)\n \tc.SetLinger(0)\n \tc.SetNoDelay(false)\n \tc.LocalAddr()\n```
## コアとなるコードの解説
変更は`src/pkg/net/protoconn_test.go`ファイルの`TestTCPConnSpecificMethods`関数内で行われています。
追加された行は以下の通りです。
```go
c.SetKeepAlivePeriod(3 * time.Second)
この行は、テスト対象のTCPConn
インスタンスc
に対して、SetKeepAlivePeriod
メソッドを呼び出しています。引数として3 * time.Second
が渡されており、これはKeep-Aliveプローブの期間を3秒に設定することを意味します。
このテストの目的は、SetKeepAlivePeriod
メソッドがエラーなく呼び出され、Goのnet
パッケージがこの機能をサポートしていることを確認することです。このテストは、SetKeepAlive(false)
の直後に呼び出されていますが、これはテストの独立性を保つため、または特定のテストシナリオ(例えば、Keep-Aliveが無効な状態でも期間設定メソッドが呼び出せるか)を検証するためかもしれません。ただし、通常、SetKeepAlivePeriod
が効果を発揮するためにはSetKeepAlive(true)
が呼び出されている必要があります。このテストはあくまで「呼び出しが可能であること」を確認するシンプルなテストであり、機能の完全な検証は別のテストで行われるか、OSレベルでの挙動に依存する可能性があります。
関連リンク
- Go CL 12090043: https://golang.org/cl/12090043
参考にした情報源リンク
- The
net.TCPConn.SetKeepAlivePeriod
method in Go: https://medium.com/@vertexaisearch.cloud.google.com/grounding-api-redirect/AUZIYQEHVtqZIkiwjSZMTLfduz9gdr4SwURDarwR-gQPNHe6257ARhus_u13JuQXPYWnY5LO_zLsFy1cX8byK0WuEHbYmAyOM3SNNoGkQRMZLsOfi1-beMpnm8m2Iqnt3Chx9unEeMh6HXYOlDBW8Nq4hh5VSD_VBE3kj-N05rnyj_7hKQywwpS6Bnkw_93FWLD8M7sroLdZD5xMRBxqjkU= - Go
net
package documentation: https://go.dev/pkg/net/ - Understanding TCP Keep-Alive: https://www.bencane.com/2014/06/02/understanding-tcp-keepalive/
- TCP Keep-Alive on Stack Overflow: https://stackoverflow.com/questions/2241980/what-is-tcp-keepalive
- TCP Keep-Alive on Linux and macOS: https://felixge.de/2014/07/10/tcp-keepalive-on-linux-and-mac-os-x.html
- Go 1.12
net
package changes regarding TCP Keep-Alive: https://github.com/golang/go/issues/27203 - Go 1.12
net
package changes regarding TCP Keep-Alive (another source): https://github.com/golang/go/issues/27203 - Why use TCP Keep-Alive: https://medium.com/@vertexaisearch.cloud.google.com/grounding-api-redirect/AUZIYQHJZyAPsQHp3zr83J0Hs6gzNAimTMaQPfHD0gra2aG_O3BjGLuyr7PBY-0Tjhq8BcFZXCk-0Ll_mqLrqAtgzE9szvScjQBpb9o-JrK_IeV4WliO5t8v2HfXCHwuOoICSMUtYpX42GD1PDbV2UNtoaKJ2CpJ06bh3Z-BuVSORTOlvuetUntG4uhxNGgrdimAh_3X