version.go

v1.4.3
Doc Versions Source
1
package git
2
3
import (
4
	"fmt"
5
6
	"golang.org/x/mod/module"
7
	"golang.org/x/mod/semver"
8
)
9
10
// ResolvedVersion holds the canonical version string and the git revision to use.
11
type ResolvedVersion struct {
12
	Version string // canonical semver (tag or pseudo-version)
13
	GitRev  string // git revision to pass to git commands (tag name or full hash)
14
}
15
16
// ResolveVersion determines the canonical version and git revision for a version query.
17
// It handles:
18
//   - Tagged versions: v1.0.0 -> use as-is
19
//   - Pseudo-versions: v0.0.0-20240101120000-abcdef123456 -> extract commit hash
20
//   - Raw commits/branches: abcdef123456 or main -> resolve to pseudo-version
21
func ResolveVersion(repoPath, query string) (*ResolvedVersion, error) {
22
	// Case 1: tagged semver version (not a pseudo-version).
23
	if semver.IsValid(query) && !module.IsPseudoVersion(query) {
24
		return &ResolvedVersion{Version: query, GitRev: query}, nil
25
	}
26
27
	// Case 2: pseudo-version — extract the commit hash.
28
	if module.IsPseudoVersion(query) {
29
		rev, err := module.PseudoVersionRev(query)
30
		if err != nil {
31
			return nil, err
32
		}
33
34
		return &ResolvedVersion{Version: query, GitRev: rev}, nil
35
	}
36
37
	// Case 3: raw ref (commit hash, branch name, etc.) — build a pseudo-version.
38
	hash, commitTime, err := CommitInfo(repoPath, query)
39
	if err != nil {
40
		return nil, fmt.Errorf("resolve ref %q: %w", query, err)
41
	}
42
43
	shortHash := hash[:12]
44
	older := LatestTag(repoPath, hash)
45
46
	pv := module.PseudoVersion("v0", older, commitTime, shortHash)
47
48
	return &ResolvedVersion{Version: pv, GitRev: hash}, nil
49
}
50

Source Files