github.com/sagernet/sing-box@v1.9.0-rc.20/common/badversion/version.go (about)

     1  package badversion
     2  
     3  import (
     4  	"strconv"
     5  	"strings"
     6  
     7  	F "github.com/sagernet/sing/common/format"
     8  )
     9  
    10  type Version struct {
    11  	Major                int
    12  	Minor                int
    13  	Patch                int
    14  	Commit               string
    15  	PreReleaseIdentifier string
    16  	PreReleaseVersion    int
    17  }
    18  
    19  func (v Version) After(anotherVersion Version) bool {
    20  	if v.Major > anotherVersion.Major {
    21  		return true
    22  	} else if v.Major < anotherVersion.Major {
    23  		return false
    24  	}
    25  	if v.Minor > anotherVersion.Minor {
    26  		return true
    27  	} else if v.Minor < anotherVersion.Minor {
    28  		return false
    29  	}
    30  	if v.Patch > anotherVersion.Patch {
    31  		return true
    32  	} else if v.Patch < anotherVersion.Patch {
    33  		return false
    34  	}
    35  	if v.PreReleaseIdentifier == "" && anotherVersion.PreReleaseIdentifier != "" {
    36  		return true
    37  	} else if v.PreReleaseIdentifier != "" && anotherVersion.PreReleaseIdentifier == "" {
    38  		return false
    39  	}
    40  	if v.PreReleaseIdentifier != "" && anotherVersion.PreReleaseIdentifier != "" {
    41  		if v.PreReleaseIdentifier == anotherVersion.PreReleaseIdentifier {
    42  			if v.PreReleaseVersion > anotherVersion.PreReleaseVersion {
    43  				return true
    44  			} else if v.PreReleaseVersion < anotherVersion.PreReleaseVersion {
    45  				return false
    46  			}
    47  		} else if v.PreReleaseIdentifier == "rc" && anotherVersion.PreReleaseIdentifier == "beta" {
    48  			return true
    49  		} else if v.PreReleaseIdentifier == "beta" && anotherVersion.PreReleaseIdentifier == "rc" {
    50  			return false
    51  		} else if v.PreReleaseIdentifier == "beta" && anotherVersion.PreReleaseIdentifier == "alpha" {
    52  			return true
    53  		} else if v.PreReleaseIdentifier == "alpha" && anotherVersion.PreReleaseIdentifier == "beta" {
    54  			return false
    55  		}
    56  	}
    57  	return false
    58  }
    59  
    60  func (v Version) VersionString() string {
    61  	return F.ToString(v.Major, ".", v.Minor, ".", v.Patch)
    62  }
    63  
    64  func (v Version) String() string {
    65  	version := F.ToString(v.Major, ".", v.Minor, ".", v.Patch)
    66  	if v.PreReleaseIdentifier != "" {
    67  		version = F.ToString(version, "-", v.PreReleaseIdentifier, ".", v.PreReleaseVersion)
    68  	}
    69  	return version
    70  }
    71  
    72  func (v Version) BadString() string {
    73  	version := F.ToString(v.Major, ".", v.Minor)
    74  	if v.Patch > 0 {
    75  		version = F.ToString(version, ".", v.Patch)
    76  	}
    77  	if v.PreReleaseIdentifier != "" {
    78  		version = F.ToString(version, "-", v.PreReleaseIdentifier)
    79  		if v.PreReleaseVersion > 0 {
    80  			version = F.ToString(version, v.PreReleaseVersion)
    81  		}
    82  	}
    83  	return version
    84  }
    85  
    86  func Parse(versionName string) (version Version) {
    87  	if strings.HasPrefix(versionName, "v") {
    88  		versionName = versionName[1:]
    89  	}
    90  	if strings.Contains(versionName, "-") {
    91  		parts := strings.Split(versionName, "-")
    92  		versionName = parts[0]
    93  		identifier := parts[1]
    94  		if strings.Contains(identifier, ".") {
    95  			identifierParts := strings.Split(identifier, ".")
    96  			version.PreReleaseIdentifier = identifierParts[0]
    97  			if len(identifierParts) >= 2 {
    98  				version.PreReleaseVersion, _ = strconv.Atoi(identifierParts[1])
    99  			}
   100  		} else {
   101  			if strings.HasPrefix(identifier, "alpha") {
   102  				version.PreReleaseIdentifier = "alpha"
   103  				version.PreReleaseVersion, _ = strconv.Atoi(identifier[5:])
   104  			} else if strings.HasPrefix(identifier, "beta") {
   105  				version.PreReleaseIdentifier = "beta"
   106  				version.PreReleaseVersion, _ = strconv.Atoi(identifier[4:])
   107  			} else {
   108  				version.Commit = identifier
   109  			}
   110  		}
   111  	}
   112  	versionElements := strings.Split(versionName, ".")
   113  	versionLen := len(versionElements)
   114  	if versionLen >= 1 {
   115  		version.Major, _ = strconv.Atoi(versionElements[0])
   116  	}
   117  	if versionLen >= 2 {
   118  		version.Minor, _ = strconv.Atoi(versionElements[1])
   119  	}
   120  	if versionLen >= 3 {
   121  		version.Patch, _ = strconv.Atoi(versionElements[2])
   122  	}
   123  	return
   124  }