diff --git a/doc/modules.md b/doc/modules.md index 15e24dbc49..42ae25c4ef 100644 --- a/doc/modules.md +++ b/doc/modules.md @@ -276,6 +276,10 @@ list. The `go` command does not fall back to later proxies in response to other 4xx and 5xx errors. This allows a proxy to act as a gatekeeper, for example, by responding with error 403 (Forbidden) for modules not on an approved list. + + The table below specifies queries that a module proxy must respond to. For each path, `$base` is the path portion of a proxy URL,`$module` is a module path, and `$version` is a version. For example, if the proxy URL is @@ -425,12 +429,170 @@ setting `GOPROXY` to `https://example.com/proxy`. ## Authenticating modules + +When deciding whether to trust the source code for a module version just +fetched from a proxy or origin server, the `go` command first consults the +`go.sum` lines in the `go.sum` file of the current module. If the `go.sum` file +does not contain an entry for that module version, then it may consult the +checksum database. + ### go.sum file format ### Checksum database +The checksum database is a global source of `go.sum` lines. The `go` command can +use this in many situations to detect misbehavior by proxies or origin servers. + +The checksum database allows for global consistency and reliability for all +publicly available module versions. It makes untrusted proxies possible since +they can't serve the wrong code without it going unnoticed. It also ensures +that the bits associated with a specific version do not change from one day to +the next, even if the module's author subsequently alters the tags in their +repository. + +The checksum database is served by [sum.golang.org](https://sum.golang.org), +which is run by Google. It is a [Transparent +Log](https://research.swtch.com/tlog) (or “Merkle Tree”) of `go.sum` line +hashes, which is backed by [Trillian](https://github.com/google/trillian). The +main advantage of a Merkle tree is that independent auditors can verify that it +hasn't been tampered with, so it is more trustworthy than a simple database. + +The `go` command interacts with the checksum database using the protocol +originally outlined in [Proposal: Secure the Public Go Module +Ecosystem](https://go.googlesource.com/proposal/+/master/design/25530-sumdb.md#checksum-database). + +The table below specifies queries that the checksum database must respond to. +For each path, `$base` is the path portion of the checksum database URL, +`$module` is a module path, and `$version` is a version. For example, if the +checksum database URL is `https://sum.golang.org`, and the client is requesting +the record for the module `golang.org/x/text` at version `v0.3.2`, the client +would send a `GET` request for +`https://sum.golang.org/lookup/golang.org/x/text@v0.3.2`. + +To avoid ambiguity when serving from case-insensitive file systems, +the `$module` and `$version` elements are +[case-encoded](https://pkg.go.dev/golang.org/x/mod/module#EscapePath) +by replacing every uppercase letter with an exclamation mark followed by the +corresponding lower-case letter. This allows modules `example.com/M` and +`example.com/m` to both be stored on disk, since the former is encoded as +`example.com/!m`. + +Parts of the path surrounded by square brakets, like `[.p/$W]` denote optional +values. + +
Path | +Description | +
---|---|
$base/latest |
+
+ Returns a signed, encoded tree description for the latest log. This
+ signed description is in the form of a
+ note,
+ which is text that has been signed by one or more server keys and can
+ be verified using the server's public key. The tree description
+ provides the size of the tree and the hash of the tree head at that
+ size. This encoding is described in
+
+ golang.org/x/mod/sumdb/tlog#FormatTree .
+ |
+
$base/lookup/$module@$version |
+
+ Returns the log record number for the entry about $module
+ at $version , followed by the data for the record (that is,
+ the go.sum lines for $module at
+ $version ) and a signed, encoded tree description that
+ contains the record.
+ |
+
$base/tile/$H/$L/$K[.p/$W] |
+
+ Returns a [log tile](https://research.swtch.com/tlog#serving_tiles),
+ which is a set of hashes that make up a section of the log. Each tile
+ is defined in a two-dimensional coordinate at tile level
+ $L , $K th from the left, with a tile height of
+ $H . The optional .p/$W suffix indicates a
+ partial log tile with only $W hashes. Clients must fall
+ back to fetching the full tile if a partial tile is not found.
+ |
+
$base/tile/$H/data/$K[.p/$W] |
+
+ Returns the record data for the leaf hashes in
+ /tile/$H/0/$K[.p/$W] (with a literal data path
+ element).
+ |
+