internal/frontend: update to latest vulndb client

There have been some changes to the vulndb entry format.

For golang/go#48223

Change-Id: I60eef20863f0d968d90e97638c06e48d9a7af2d1
Reviewed-on: https://go-review.googlesource.com/c/pkgsite/+/348380
Trust: Jonathan Amsterdam <jba@google.com>
Run-TryBot: Jonathan Amsterdam <jba@google.com>
Reviewed-by: Julie Qiu <julie@golang.org>
diff --git a/go.mod b/go.mod
index a9af1fe..482009d 100644
--- a/go.mod
+++ b/go.mod
@@ -45,7 +45,7 @@
 	golang.org/x/sync v0.0.0-20200625203802-6e8e738ad208
 	golang.org/x/text v0.3.6
 	golang.org/x/tools v0.0.0-20200915173823-2db8f0ff891c
-	golang.org/x/vulndb v0.0.0-20210812203154-5d84be3c9e14
+	golang.org/x/vulndb v0.0.0-20210903204307-a74bfd4ac7eb
 	google.golang.org/api v0.32.0
 	google.golang.org/genproto v0.0.0-20200923140941-5646d36feee1
 	google.golang.org/grpc v1.32.0
diff --git a/go.sum b/go.sum
index e5bf98a..e0c26ea 100644
--- a/go.sum
+++ b/go.sum
@@ -888,8 +888,8 @@
 golang.org/x/tools v0.0.0-20200904185747-39188db58858/go.mod h1:Cj7w3i3Rnn0Xh82ur9kSqwfTHTeVxaDqrfMjpcNT6bE=
 golang.org/x/tools v0.0.0-20200915173823-2db8f0ff891c h1:AQsh/7arPVFDBraQa8x7GoVnwnGg1kM7J2ySI0kF5WU=
 golang.org/x/tools v0.0.0-20200915173823-2db8f0ff891c/go.mod h1:z6u4i615ZeAfBE4XtMziQW1fSVJXACjjbWkB/mvPzlU=
-golang.org/x/vulndb v0.0.0-20210812203154-5d84be3c9e14 h1:fGz1pt31Ygv69LkbU9kkWMChI2ZPUeZ/IzqEce/NA7s=
-golang.org/x/vulndb v0.0.0-20210812203154-5d84be3c9e14/go.mod h1:xh7j0yEDggyETQM2RIfHFmzOcnAwzHg8j8heomkN1Dc=
+golang.org/x/vulndb v0.0.0-20210903204307-a74bfd4ac7eb h1:TfKhb4m4Pq73s62wVmqPze7qSN3JtdRYTzNQJm4c5nk=
+golang.org/x/vulndb v0.0.0-20210903204307-a74bfd4ac7eb/go.mod h1:xh7j0yEDggyETQM2RIfHFmzOcnAwzHg8j8heomkN1Dc=
 golang.org/x/xerrors v0.0.0-20190410155217-1f06c39b4373/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
 golang.org/x/xerrors v0.0.0-20190513163551-3ee3066db522/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
 golang.org/x/xerrors v0.0.0-20190717185122-a985d3407aa7/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
diff --git a/internal/frontend/server.go b/internal/frontend/server.go
index c94edeb..9336720 100644
--- a/internal/frontend/server.go
+++ b/internal/frontend/server.go
@@ -33,7 +33,6 @@
 	"golang.org/x/pkgsite/internal/static"
 	"golang.org/x/pkgsite/internal/version"
 	vulndbc "golang.org/x/vulndb/client"
-	"golang.org/x/vulndb/osv"
 )
 
 // Server can be installed to serve the go discovery frontend.
@@ -99,7 +98,7 @@
 		serveStats:           scfg.ServeStats,
 		reportingClient:      scfg.ReportingClient,
 		fileMux:              http.NewServeMux(),
-		getVulnEntries:       func(m string) ([]*osv.Entry, error) { return scfg.VulndbClient.Get([]string{m}) },
+		getVulnEntries:       scfg.VulndbClient.Get,
 	}
 	errorPageBytes, err := s.renderErrorPage(context.Background(), http.StatusInternalServerError, "error", nil)
 	if err != nil {
diff --git a/internal/frontend/versions_test.go b/internal/frontend/versions_test.go
index 8283136..d6908da 100644
--- a/internal/frontend/versions_test.go
+++ b/internal/frontend/versions_test.go
@@ -89,15 +89,15 @@
 		}
 	}
 
+	vulnFixedVersion := "1.2.3"
 	vulnEntry := &osv.Entry{
 		Details: "vuln",
-		Affects: osv.Affects{
+		Affected: []osv.Affected{{
 			Ranges: []osv.AffectsRange{{
-				Type:       osv.TypeSemver,
-				Introduced: "1.2.0",
-				Fixed:      "1.2.3",
+				Type:   osv.TypeSemver,
+				Events: []osv.RangeEvent{{Introduced: "1.2.0"}, {Fixed: vulnFixedVersion}},
 			}},
-		},
+		}},
 	}
 	getVulnEntries := func(m string) ([]*osv.Entry, error) {
 		if m == modulePath1 {
@@ -144,7 +144,7 @@
 						vl := makeList(v1Path, modulePath1, "v1", []string{"v1.3.0", "v1.2.3", "v1.2.1"}, false)
 						vl.Versions[2].Vulns = []Vuln{{
 							Details:      vulnEntry.Details,
-							FixedVersion: "v" + vulnEntry.Affects.Ranges[0].Fixed,
+							FixedVersion: "v" + vulnFixedVersion,
 						}}
 						return vl
 					}(),
diff --git a/internal/frontend/vulns.go b/internal/frontend/vulns.go
index 66b18b7..157c4b6 100644
--- a/internal/frontend/vulns.go
+++ b/internal/frontend/vulns.go
@@ -25,7 +25,7 @@
 // The getVulnEntries function should retrieve all entries for the given module path.
 // It is passed to facilitate testing.
 func Vulns(modulePath, version, packagePath string, getVulnEntries vulnEntriesFunc) (_ []Vuln, err error) {
-	defer derrors.Wrap(&err, "Vulns(%q, %q)", modulePath, version)
+	defer derrors.Wrap(&err, "Vulns(%q, %q, %q)", modulePath, version, packagePath)
 
 	// Get all the vulns for this module.
 	entries, err := getVulnEntries(modulePath)
@@ -36,20 +36,37 @@
 	// package at this version.
 	var vulns []Vuln
 	for _, e := range entries {
-		if (packagePath == "" || e.Package.Name == packagePath) && e.Affects.AffectsSemver(version) {
-			// Choose the latest fixed version, if any.
-			var fixed string
-			for _, r := range e.Affects.Ranges {
-				if r.Fixed != "" && (fixed == "" || semver.Compare(r.Fixed, fixed) > 0) {
-					fixed = r.Fixed
-				}
-			}
-			vulns = append(vulns, Vuln{
-				Details: e.Details,
-				// TODO(golang/go#48223): handle stdlib versions
-				FixedVersion: "v" + fixed,
-			})
+		if vuln, ok := entryVuln(e, packagePath, version); ok {
+			vulns = append(vulns, vuln)
 		}
 	}
 	return vulns, nil
 }
+
+func entryVuln(e *osv.Entry, packagePath, version string) (Vuln, bool) {
+	for _, a := range e.Affected {
+		if (packagePath == "" || a.Package.Name == packagePath) && a.Ranges.AffectsSemver(version) {
+			// Choose the latest fixed version, if any.
+			var fixed string
+			for _, r := range a.Ranges {
+				if r.Type == osv.TypeGit {
+					continue
+				}
+				for _, re := range r.Events {
+					if re.Fixed != "" && (fixed == "" || semver.Compare(re.Fixed, fixed) > 0) {
+						fixed = re.Fixed
+					}
+				}
+			}
+			if fixed != "" {
+				fixed = "v" + fixed
+			}
+			return Vuln{
+				Details: e.Details,
+				// TODO(golang/go#48223): handle stdlib versions
+				FixedVersion: fixed,
+			}, true
+		}
+	}
+	return Vuln{}, false
+}
diff --git a/internal/frontend/vulns_test.go b/internal/frontend/vulns_test.go
index f82e2a5..791b09f 100644
--- a/internal/frontend/vulns_test.go
+++ b/internal/frontend/vulns_test.go
@@ -14,15 +14,16 @@
 
 func TestVulns(t *testing.T) {
 	e := osv.Entry{
-		Package: osv.Package{Name: "bad.com"},
 		Details: "bad",
-		Affects: osv.Affects{
+		Affected: []osv.Affected{{
+			Package: osv.Package{Name: "bad.com"},
 			Ranges: []osv.AffectsRange{{
-				Type:  osv.TypeSemver,
-				Fixed: "1.2.3",
+				Type:   osv.TypeSemver,
+				Events: []osv.RangeEvent{{Introduced: "0"}, {Fixed: "1.2.3"}},
 			}},
-		},
+		}},
 	}
+
 	get := func(modulePath string) ([]*osv.Entry, error) {
 		switch modulePath {
 		case "good.com":
@@ -52,4 +53,12 @@
 	if diff := cmp.Diff(want, got); diff != "" {
 		t.Errorf("mismatch (-want, +got):\n%s", diff)
 	}
+
+	got, err = Vulns("bad.com", "v1.3.0", "bad.com", get)
+	if err != nil {
+		t.Fatal(err)
+	}
+	if got != nil {
+		t.Errorf("got %v, want nil", got)
+	}
 }