github.com/grafana/pyroscope@v1.18.0/pkg/frontend/vcs/source/golang/golang.go (about)

     1  package golang
     2  
     3  import (
     4  	"path/filepath"
     5  	"strings"
     6  
     7  	"github.com/grafana/regexp"
     8  )
     9  
    10  const (
    11  	vendorPath = "vendor/"
    12  	stdLocal   = "/usr/local/go/src/"
    13  	stdGoRoot  = "$GOROOT/src/"
    14  )
    15  
    16  var (
    17  	stdLibRegex        = regexp.MustCompile(`.*?\/go\/.*?(?P<version>(0|[1-9]\d*)\.(0|[1-9]\d*)\.(0|[1-9]\d*)(?:-((?:0|[1-9]\d*|\d*[a-zA-Z-][0-9a-zA-Z-]*)(?:\.(?:0|[1-9]\d*|\d*[a-zA-Z-][0-9a-zA-Z-]*))*))?(?:\+([0-9a-zA-Z-]+(?:\.[0-9a-zA-Z-]+)*))?).*?\/src\/(?P<path>.*)`)
    18  	toolchainGoVersion = regexp.MustCompile(`-go(?P<version>[0-9]+\.[0-9]+(?:\.[0-9]+)?(?:rc[0-9]+|beta[0-9]+)?)(?:\.|-)`)
    19  )
    20  
    21  // IsStandardLibraryPath returns the cleaned path of the standard library package and a potential version if detected
    22  func IsStandardLibraryPath(path string) (string, string, bool) {
    23  	if len(path) == 0 {
    24  		return "", "", false
    25  	}
    26  
    27  	// match toolchain go mod paths
    28  	if modFile, ok := ParseModuleFromPath(path); ok && modFile.Path == "golang.org/toolchain" {
    29  		// figure out version
    30  		matches := toolchainGoVersion.FindStringSubmatch(modFile.Version.Version)
    31  		if len(matches) > 1 {
    32  			return strings.TrimPrefix(modFile.FilePath, "src/"), matches[1], true
    33  		}
    34  	}
    35  
    36  	if stdLibRegex.MatchString(path) {
    37  		matches := stdLibRegex.FindStringSubmatch(path)
    38  		version := matches[stdLibRegex.SubexpIndex("version")]
    39  		path = matches[stdLibRegex.SubexpIndex("path")]
    40  		return path, version, true
    41  	}
    42  
    43  	path = strings.TrimPrefix(path, stdLocal)
    44  	path = strings.TrimPrefix(path, stdGoRoot)
    45  	fileName := filepath.Base(path)
    46  	packageName := strings.TrimSuffix(path, "/"+fileName)
    47  	isStdVendor := strings.HasPrefix(packageName, vendorPath)
    48  
    49  	if _, isStd := StandardPackages[packageName]; !isStdVendor && !isStd {
    50  		return "", "", false
    51  	}
    52  	return path, "", true
    53  }
    54  
    55  // VendorRelativePath returns the relative path of the given path
    56  // if it is a vendor path.
    57  // For example:
    58  // /drone/src/vendor/google.golang.org/protobuf/proto/merge.go -> /vendor/google.golang.org/protobuf/proto/merge.go
    59  func VendorRelativePath(path string) (string, bool) {
    60  	idx := strings.Index(path, "/"+vendorPath)
    61  	if idx < 0 {
    62  		return "", false
    63  	}
    64  	return path[idx:], true
    65  }