1
2
3
4
5 package versions_test
6
7 import (
8 "go/ast"
9 "go/parser"
10 "go/token"
11 "go/types"
12 "testing"
13
14 "golang.org/x/tools/internal/testenv"
15 "golang.org/x/tools/internal/versions"
16 )
17
18 func TestIsValid(t *testing.T) {
19
20 for _, x := range []string{
21 "go1.21",
22 "go1.21.2",
23 "go1.21rc",
24 "go1.21rc2",
25 "go0.0",
26 "go1",
27 "go2",
28 "go1.20.0-bigcorp",
29 } {
30 if !versions.IsValid(x) {
31 t.Errorf("expected versions.IsValid(%q) to hold", x)
32 }
33 }
34
35
36 for _, x := range []string{
37 "",
38 "bad",
39 "1.21",
40 "v1.21",
41 "go",
42 "goAA",
43 "go2_3",
44 "go1.BB",
45 "go1.21.",
46 "go1.21.2_2",
47 "go1.21rc_2",
48 "go1.21rc2_",
49 "go1.600+auto",
50 } {
51 if versions.IsValid(x) {
52 t.Errorf("expected versions.IsValid(%q) to not hold", x)
53 }
54 }
55 }
56
57 func TestVersionComparisons(t *testing.T) {
58 for _, item := range []struct {
59 x, y string
60 want int
61 }{
62
63 {"go2", "go2", 0},
64 {"go2", "go1.21.2", +1},
65 {"go2", "go1.21rc2", +1},
66 {"go2", "go1.21rc", +1},
67 {"go2", "go1.21", +1},
68 {"go2", "go1", +1},
69 {"go2", "go0.0", +1},
70 {"go2", "", +1},
71 {"go2", "bad", +1},
72 {"go1.21.2", "go1.21.2", 0},
73 {"go1.21.2", "go1.21rc2", +1},
74 {"go1.21.2", "go1.21rc", +1},
75 {"go1.21.2", "go1.21", +1},
76 {"go1.21.2", "go1", +1},
77 {"go1.21.2", "go0.0", +1},
78 {"go1.21.2", "", +1},
79 {"go1.21.2", "bad", +1},
80 {"go1.21rc2", "go1.21rc2", 0},
81 {"go1.21rc2", "go1.21rc", +1},
82 {"go1.21rc2", "go1.21", +1},
83 {"go1.21rc2", "go1", +1},
84 {"go1.21rc2", "go0.0", +1},
85 {"go1.21rc2", "", +1},
86 {"go1.21rc2", "bad", +1},
87 {"go1.21rc", "go1.21rc", 0},
88 {"go1.21rc", "go1.21", +1},
89 {"go1.21rc", "go1", +1},
90 {"go1.21rc", "go0.0", +1},
91 {"go1.21rc", "", +1},
92 {"go1.21rc", "bad", +1},
93 {"go1.21", "go1.21", 0},
94 {"go1.21", "go1", +1},
95 {"go1.21", "go0.0", +1},
96 {"go1.21", "", +1},
97 {"go1.21", "bad", +1},
98 {"go1", "go1", 0},
99 {"go1", "go0.0", +1},
100 {"go1", "", +1},
101 {"go1", "bad", +1},
102 {"go0.0", "go0.0", 0},
103 {"go0.0", "", +1},
104 {"go0.0", "bad", +1},
105 {"", "", 0},
106 {"", "bad", 0},
107 {"bad", "bad", 0},
108
109 {"go1.20", "go1.20.0-bigcorp", 0},
110 {"go1.21", "go1.21.0-bigcorp", -1},
111 {"go1.21.0", "go1.21.0-bigcorp", 0},
112 {"go1.19rc1", "go1.19", -1},
113 } {
114 got := versions.Compare(item.x, item.y)
115 if got != item.want {
116 t.Errorf("versions.Compare(%q, %q)=%d. expected %d", item.x, item.y, got, item.want)
117 }
118 reverse := versions.Compare(item.y, item.x)
119 if reverse != -got {
120 t.Errorf("versions.Compare(%q, %q)=%d. expected %d", item.y, item.x, reverse, -got)
121 }
122 }
123 }
124
125 func TestLang(t *testing.T) {
126 for _, item := range []struct {
127 x string
128 want string
129 }{
130
131 {"go1.21rc2", "go1.21"},
132 {"go1.21.2", "go1.21"},
133 {"go1.21", "go1.21"},
134 {"go1", "go1"},
135
136 {"bad", ""},
137 {"1.21", ""},
138 } {
139 if got := versions.Lang(item.x); got != item.want {
140 t.Errorf("versions.Lang(%q)=%q. expected %q", item.x, got, item.want)
141 }
142 }
143
144 }
145
146 func TestKnown(t *testing.T) {
147 for _, v := range [...]string{
148 versions.Go1_18,
149 versions.Go1_19,
150 versions.Go1_20,
151 versions.Go1_21,
152 versions.Go1_22,
153 } {
154 if !versions.IsValid(v) {
155 t.Errorf("Expected known version %q to be valid.", v)
156 }
157 if v != versions.Lang(v) {
158 t.Errorf("Expected known version %q == Lang(%q).", v, versions.Lang(v))
159 }
160 }
161 }
162
163 func TestAtLeast(t *testing.T) {
164 for _, item := range [...]struct {
165 v, release string
166 want bool
167 }{
168 {versions.Future, versions.Go1_22, true},
169 {versions.Go1_22, versions.Go1_22, true},
170 {"go1.21", versions.Go1_22, false},
171 {"invalid", versions.Go1_22, false},
172 } {
173 if got := versions.AtLeast(item.v, item.release); got != item.want {
174 t.Errorf("AtLeast(%q, %q)=%v. wanted %v", item.v, item.release, got, item.want)
175 }
176 }
177 }
178
179 func TestBefore(t *testing.T) {
180 for _, item := range [...]struct {
181 v, release string
182 want bool
183 }{
184 {versions.Future, versions.Go1_22, false},
185 {versions.Go1_22, versions.Go1_22, false},
186 {"go1.21", versions.Go1_22, true},
187 {"invalid", versions.Go1_22, true},
188 } {
189 if got := versions.Before(item.v, item.release); got != item.want {
190 t.Errorf("Before(%q, %q)=%v. wanted %v", item.v, item.release, got, item.want)
191 }
192 }
193 }
194
195 func TestFileVersions122(t *testing.T) {
196 testenv.NeedsGo1Point(t, 22)
197
198 const source = `
199 package P
200 `
201 fset := token.NewFileSet()
202 f, err := parser.ParseFile(fset, "hello.go", source, 0)
203 if err != nil {
204 t.Fatal(err)
205 }
206
207 for _, conf := range []types.Config{
208 {GoVersion: versions.Go1_22},
209 {},
210 } {
211 info := &types.Info{}
212 versions.InitFileVersions(info)
213
214 _, err = conf.Check("P", fset, []*ast.File{f}, info)
215 if err != nil {
216 t.Fatal(err)
217 }
218
219 v := versions.FileVersion(info, f)
220 if !versions.AtLeast(v, versions.Go1_22) {
221 t.Errorf("versions.AtLeast(%q, %q) expected to hold", v, versions.Go1_22)
222 }
223
224 if versions.Before(v, versions.Go1_22) {
225 t.Errorf("versions.AtLeast(%q, %q) expected to be false", v, versions.Go1_22)
226 }
227
228 if conf.GoVersion == "" && v != versions.Future {
229 t.Error("Expected the FileVersion to be the Future when conf.GoVersion is unset")
230 }
231 }
232 }
233
234 func TestFileVersions121(t *testing.T) {
235 testenv.SkipAfterGo1Point(t, 21)
236
237
238 v := versions.FileVersion(nil, nil)
239 oneof := map[string]bool{
240 versions.Go1_18: true,
241 versions.Go1_19: true,
242 versions.Go1_20: true,
243 versions.Go1_21: true,
244 }
245 if !oneof[v] {
246 t.Errorf("FileVersion(...)=%q expected to be a known go version <1.22", v)
247 }
248
249 if versions.AtLeast(v, versions.Go1_22) {
250 t.Errorf("versions.AtLeast(%q, %q) expected to be false", v, versions.Go1_22)
251 }
252
253 if !versions.Before(v, versions.Go1_22) {
254 t.Errorf("versions.Before(%q, %q) expected to hold", v, versions.Go1_22)
255 }
256 }
257
View as plain text