internal/worker: move cve logic add cve.go

Logic for determining if a CVE is a potential Go vulnerability is moved
to cve.go.

Pure code in motion.

Change-Id: I730a1c46d2604727e06387745734f69e45feb150
Reviewed-on: https://go-review.googlesource.com/c/vuln/+/362238
Trust: Julie Qiu <julie@golang.org>
Run-TryBot: Julie Qiu <julie@golang.org>
TryBot-Result: Go Bot <gobot@golang.org>
Reviewed-by: Jonathan Amsterdam <jba@google.com>
diff --git a/internal/worker/cve.go b/internal/worker/cve.go
new file mode 100644
index 0000000..88faac3
--- /dev/null
+++ b/internal/worker/cve.go
@@ -0,0 +1,131 @@
+// Copyright 2021 The Go Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style
+// license that can be found in the LICENSE file.
+
+package worker
+
+import (
+	"fmt"
+	"log"
+	"net/http"
+	"net/url"
+	"strings"
+
+	"golang.org/x/vuln/internal/cveschema"
+	"golang.org/x/vuln/internal/derrors"
+	"golang.org/x/vuln/internal/report"
+)
+
+const goGitHubRepo = "github.com/golang/go"
+
+// cveToIssue creates a cveRecord from a c *cveschema.CVE.
+func cveToIssue(c *cveschema.CVE) (_ *cve, err error) {
+	defer derrors.Wrap(&err, "cveToIssue(%q)", c.CVEDataMeta.ID)
+	if isPendingCVE(c) {
+		return nil, nil
+	}
+	switch c.DataVersion {
+	case "4.0":
+		return cveToIssueV4(c)
+	default:
+		// TODO(https://golang.org/issue/49289): Add support for v5.0.
+		log.Printf("Unxpected data_version for CVE %q: %q (skipping)", c.CVEDataMeta.ID, c.DataVersion)
+		return nil, nil
+	}
+}
+
+func cveToIssueV4(c *cveschema.CVE) (_ *cve, err error) {
+	mp, err := modulePathFromCVE(c)
+	if err != nil {
+		return nil, err
+	}
+	if mp == "" {
+		return nil, nil
+	}
+	var links report.Links
+	for _, r := range c.References.ReferenceData {
+		if links.Commit == "" && strings.Contains(r.URL, "/commit/") {
+			links.Commit = r.URL
+		} else if links.PR == "" && strings.Contains(r.URL, "/pull/") {
+			links.PR = r.URL
+		} else {
+			links.Context = append(links.Context, r.URL)
+		}
+	}
+	var cwe string
+	for _, pt := range c.Problemtype.ProblemtypeData {
+		for _, d := range pt.Description {
+			if strings.Contains(d.Value, "CWE") {
+				cwe = d.Value
+			}
+		}
+	}
+	r := &cve{
+		CVE:         *c,
+		cwe:         cwe,
+		modulePath:  mp,
+		links:       links,
+		description: description(c),
+	}
+	if mp == goGitHubRepo {
+		r.modulePath = "Standard Library"
+	}
+	return r, nil
+}
+
+// isPendingCVE reports if the CVE is still waiting on information and not
+// ready to be triaged.
+func isPendingCVE(c *cveschema.CVE) bool {
+	return c.CVEDataMeta.STATE == cveschema.StateReserved
+}
+
+var vcsHostsWithThreeElementRepoName = map[string]bool{
+	"bitbucket.org": true,
+	"gitea.com":     true,
+	"gitee.com":     true,
+	"github.com":    true,
+	"gitlab.com":    true,
+	"golang.org":    true,
+}
+
+// modulePathFromCVE returns a Go module path for a CVE, if we can determine
+// what it is.
+func modulePathFromCVE(c *cveschema.CVE) (_ string, err error) {
+	defer derrors.Wrap(&err, "modulePathFromCVE(c)")
+	for _, r := range c.References.ReferenceData {
+		if r.URL == "" {
+			continue
+		}
+		for host := range vcsHostsWithThreeElementRepoName {
+			if !strings.Contains(r.URL, host) {
+				continue
+			}
+			refURL, err := url.Parse(r.URL)
+			if err != nil {
+				return "", fmt.Errorf("url.Parse(%q): %v", r.URL, err)
+			}
+			u := refURL.Host + refURL.Path
+			parts := strings.Split(u, "/")
+			if len(parts) < 3 {
+				continue
+			}
+			mod := strings.Join(parts[0:3], "/")
+			r, err := http.DefaultClient.Get(fmt.Sprintf("https://pkg.go.dev/%s", mod))
+			if err != nil {
+				return "", err
+			}
+			if r.StatusCode == http.StatusOK {
+				return mod, nil
+			}
+		}
+	}
+	return "", nil
+}
+
+func description(c *cveschema.CVE) string {
+	var ds []string
+	for _, d := range c.Description.DescriptionData {
+		ds = append(ds, d.Value)
+	}
+	return strings.Join(ds, "| \n ")
+}
diff --git a/internal/worker/worker.go b/internal/worker/worker.go
index 35be805..8fff940 100644
--- a/internal/worker/worker.go
+++ b/internal/worker/worker.go
@@ -10,8 +10,6 @@
 	"encoding/json"
 	"fmt"
 	"log"
-	"net/http"
-	"net/url"
 	"path"
 	"strings"
 
@@ -20,7 +18,6 @@
 	"github.com/go-git/go-git/v5/plumbing/object"
 	"golang.org/x/vuln/internal/cveschema"
 	"golang.org/x/vuln/internal/derrors"
-	"golang.org/x/vuln/internal/report"
 )
 
 // Run clones the CVEProject/cvelist repository and compares the files to the
@@ -124,117 +121,3 @@
 	}
 	return &c, nil
 }
-
-const goGitHubRepo = "github.com/golang/go"
-
-// cveToIssue creates a cveRecord from a c *cveschema.CVE.
-func cveToIssue(c *cveschema.CVE) (_ *cve, err error) {
-	defer derrors.Wrap(&err, "cveToIssue(%q)", c.CVEDataMeta.ID)
-	if isPendingCVE(c) {
-		return nil, nil
-	}
-	switch c.DataVersion {
-	case "4.0":
-		return cveToIssueV4(c)
-	default:
-		// TODO(https://golang.org/issue/49289): Add support for v5.0.
-		log.Printf("Unxpected data_version for CVE %q: %q (skipping)", c.CVEDataMeta.ID, c.DataVersion)
-		return nil, nil
-	}
-}
-
-func cveToIssueV4(c *cveschema.CVE) (_ *cve, err error) {
-	mp, err := modulePathFromCVE(c)
-	if err != nil {
-		return nil, err
-	}
-	if mp == "" {
-		return nil, nil
-	}
-	var links report.Links
-	for _, r := range c.References.ReferenceData {
-		if links.Commit == "" && strings.Contains(r.URL, "/commit/") {
-			links.Commit = r.URL
-		} else if links.PR == "" && strings.Contains(r.URL, "/pull/") {
-			links.PR = r.URL
-		} else {
-			links.Context = append(links.Context, r.URL)
-		}
-	}
-	var cwe string
-	for _, pt := range c.Problemtype.ProblemtypeData {
-		for _, d := range pt.Description {
-			if strings.Contains(d.Value, "CWE") {
-				cwe = d.Value
-			}
-		}
-	}
-	r := &cve{
-		CVE:         *c,
-		cwe:         cwe,
-		modulePath:  mp,
-		links:       links,
-		description: description(c),
-	}
-	if mp == goGitHubRepo {
-		r.modulePath = "Standard Library"
-	}
-	return r, nil
-}
-
-// isPendingCVE reports if the CVE is still waiting on information and not
-// ready to be triaged.
-func isPendingCVE(c *cveschema.CVE) bool {
-	return c.CVEDataMeta.STATE == cveschema.StateReserved
-}
-
-var vcsHostsWithThreeElementRepoName = map[string]bool{
-	"bitbucket.org": true,
-	"gitea.com":     true,
-	"gitee.com":     true,
-	"github.com":    true,
-	"gitlab.com":    true,
-	"golang.org":    true,
-}
-
-// modulePathFromCVE returns a Go module path for a CVE, if we can determine
-// what it is.
-func modulePathFromCVE(c *cveschema.CVE) (_ string, err error) {
-	defer derrors.Wrap(&err, "modulePathFromCVE(c)")
-	for _, r := range c.References.ReferenceData {
-		if r.URL == "" {
-			continue
-		}
-		for host := range vcsHostsWithThreeElementRepoName {
-			if !strings.Contains(r.URL, host) {
-				continue
-			}
-			refURL, err := url.Parse(r.URL)
-			if err != nil {
-				return "", fmt.Errorf("url.Parse(%q): %v", r.URL, err)
-			}
-			u := refURL.Host + refURL.Path
-			parts := strings.Split(u, "/")
-			if len(parts) < 3 {
-				continue
-			}
-			mod := strings.Join(parts[0:3], "/")
-			r, err := http.DefaultClient.Get(fmt.Sprintf("https://pkg.go.dev/%s", mod))
-			if err != nil {
-				return "", err
-			}
-			if r.StatusCode == http.StatusOK {
-				return mod, nil
-			}
-		}
-	}
-	return "", nil
-}
-
-func description(c *cveschema.CVE) string {
-	var ds []string
-	for _, d := range c.Description.DescriptionData {
-		ds = append(ds, d.Value)
-	}
-	return strings.Join(ds, "| \n ")
-}