From b6bbcc5641a3b7c925c1e9341b25e449db29431a Mon Sep 17 00:00:00 2001 From: ltsonov Date: Wed, 8 Nov 2023 22:56:13 +0200 Subject: [PATCH] Use semver library to correctly compare agent versions --- cbcontainers/models/agent_version.go | 19 +++++++++++++++++-- .../models/operator_compatibility_test.go | 2 ++ go.mod | 1 + go.sum | 2 ++ 4 files changed, 22 insertions(+), 2 deletions(-) diff --git a/cbcontainers/models/agent_version.go b/cbcontainers/models/agent_version.go index 48c3b44b..011685bb 100644 --- a/cbcontainers/models/agent_version.go +++ b/cbcontainers/models/agent_version.go @@ -1,5 +1,7 @@ package models +import "golang.org/x/mod/semver" + type AgentVersion string const ( @@ -12,12 +14,25 @@ func (v AgentVersion) IsLargerThan(version string) bool { if v == AgentMinVersionNone || v == AgentVersionUnknown { return false } - return string(v) > version + return semver.Compare(normalizeToSemVer(string(v)), normalizeToSemVer(version)) > 0 } func (v AgentVersion) IsLessThan(version string) bool { if v == AgentMaxVersionLatest || v == AgentVersionUnknown { return false } - return string(v) < version + return semver.Compare(normalizeToSemVer(string(v)), normalizeToSemVer(version)) < 0 +} + +func normalizeToSemVer(v string) string { + if v == string(AgentMaxVersionLatest) || v == string(AgentVersionUnknown) || v == string(AgentMinVersionNone) { + return v + } + + // semver requires a leading `v` at the front, so we make sure to have one + if v[0] != 'v' { + return "v" + v + } + // Note: v is not guaranteed to be a valid SemVer here, but it should be passable to the semver library + return v } diff --git a/cbcontainers/models/operator_compatibility_test.go b/cbcontainers/models/operator_compatibility_test.go index 499a8020..080b575f 100644 --- a/cbcontainers/models/operator_compatibility_test.go +++ b/cbcontainers/models/operator_compatibility_test.go @@ -31,6 +31,7 @@ func TestCheckCompatibilityCompatible(t *testing.T) { {min: models.AgentVersion("0.0"), max: models.AgentVersion("2.8"), agent: "0.0"}, {min: models.AgentVersion("0.0"), max: models.AgentVersion("2.8"), agent: "1.0"}, {min: models.AgentVersion("0.0"), max: models.AgentVersion("2.8"), agent: "2.0"}, + {min: models.AgentVersion("2.2.7"), max: models.AgentVersion("3.0"), agent: "2.10"}, } testCheckCompatibility(t, testCases, true) @@ -44,6 +45,7 @@ func TestCheckCompatibilityIncompatible(t *testing.T) { {min: models.AgentVersion("2.7"), max: models.AgentVersion("2.8"), agent: "2.6.9"}, {min: models.AgentMinVersionNone, max: models.AgentVersion("2.8"), agent: "2.9"}, {min: models.AgentVersion("2.7"), max: models.AgentMaxVersionLatest, agent: "2.6"}, + {min: models.AgentVersion("2.10"), max: models.AgentMaxVersionLatest, agent: "2.6"}, } testCheckCompatibility(t, testCases, false) diff --git a/go.mod b/go.mod index abbad6c3..3c8e3c98 100644 --- a/go.mod +++ b/go.mod @@ -9,6 +9,7 @@ require ( github.com/golang/mock v1.6.0 github.com/stretchr/testify v1.8.0 go.uber.org/zap v1.24.0 + golang.org/x/mod v0.6.0 k8s.io/api v0.26.2 k8s.io/apimachinery v0.26.2 k8s.io/client-go v0.26.2 diff --git a/go.sum b/go.sum index 48140b04..ecd624f5 100644 --- a/go.sum +++ b/go.sum @@ -364,6 +364,8 @@ golang.org/x/mod v0.1.1-0.20191107180719-034126e5016b/go.mod h1:QqPTAvyqsEbceGzB golang.org/x/mod v0.2.0/go.mod h1:s0Qsj1ACt9ePp/hMypM3fl4fZqREWJwdYDEqhRiZZUA= golang.org/x/mod v0.3.0/go.mod h1:s0Qsj1ACt9ePp/hMypM3fl4fZqREWJwdYDEqhRiZZUA= golang.org/x/mod v0.4.2/go.mod h1:s0Qsj1ACt9ePp/hMypM3fl4fZqREWJwdYDEqhRiZZUA= +golang.org/x/mod v0.6.0 h1:b9gGHsz9/HhJ3HF5DHQytPpuwocVTChQJK3AvoLRD5I= +golang.org/x/mod v0.6.0/go.mod h1:4mET923SAdbXp2ki8ey+zGs1SLqsuM2Y0uvdZR/fUNI= golang.org/x/net v0.0.0-20180724234803-3673e40ba225/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4= golang.org/x/net v0.0.0-20180826012351-8a410e7b638d/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4= golang.org/x/net v0.0.0-20181114220301-adae6a3d119a/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4=