TL;DR

Go のモジュールのルートに go.mod と並べて置く、直接・間接の依存モジュールの暗号学的ハッシュを記録したファイル。go コマンドは、ダウンロードしたモジュールをこのハッシュと照らし合わせて、改ざんを検出する。

なぜ必要か

依存モジュールの中身が、前に取得したときから変わっていないことを確かめられる。How Go Mitigates Supply Chain Attacks によると、go.sum が不完全だとエラーになり、go.sum を変えるのは go get と go mod tidy だけなので、依存の変更がコードレビューの対象になる。

仕組み

各行は、空白で区切った 3 つの項目でできている。

  • モジュールパス: ハッシュが属するモジュールの名前
  • バージョン: ハッシュが属するバージョン。/go.mod で終わる行はそのモジュールの go.mod だけのハッシュで、そうでない行はモジュールの .zip に含まれるファイルのハッシュである
  • ハッシュ: アルゴリズム名と base64 でエンコードしたハッシュを : でつないだもの。今使えるのは SHA-256 の h1 だけである

go コマンドは、モジュールの .mod や .zip をモジュールキャッシュにダウンロードするときにハッシュを計算し、go.sum の対応する行と比べる。一致しなければセキュリティエラーを報告し、ダウンロードしたファイルを捨てる。go.sum に行がなければ、チェックサムデータベース(既定は sum.golang.org)でハッシュを確かめてから go.sum に追加する。

MVS では複数のバージョンの go.mod が必要になることがあるので、1 つのモジュールについて複数のバージョンのハッシュが並ぶことがある。不要になった行や足りない行は、go mod tidy で整理できる。

注意点

GOPRIVATE や GONOSUMDB に当てはまる非公開のモジュールや、GOSUMDB=off のときは、チェックサムデータベースで確かめずにハッシュを受け入れる。また、サプライチェーン攻撃に学ぶmoduleの仕組みとセキュリティ対策 によると、go.sum はタイポスクワッティングのように、最初から悪意のあるモジュールを依存に入れてしまう攻撃には無力である。

関連

出典