]> ruderich.org/simon Gitweb - safcm/safcm.git/blob - cmd/safcm/config/groups_test.go
ccf096897859dd775b71a86f72919d8c597d87dc
[safcm/safcm.git] / cmd / safcm / config / groups_test.go
1 // Copyright (C) 2021  Simon Ruderich
2 //
3 // This program is free software: you can redistribute it and/or modify
4 // it under the terms of the GNU General Public License as published by
5 // the Free Software Foundation, either version 3 of the License, or
6 // (at your option) any later version.
7 //
8 // This program is distributed in the hope that it will be useful,
9 // but WITHOUT ANY WARRANTY; without even the implied warranty of
10 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
11 // GNU General Public License for more details.
12 //
13 // You should have received a copy of the GNU General Public License
14 // along with this program.  If not, see <http://www.gnu.org/licenses/>.
15
16 package config
17
18 import (
19         "fmt"
20         "os"
21         "reflect"
22         "testing"
23
24         "github.com/google/go-cmp/cmp"
25 )
26
27 func TestLoadGroups(t *testing.T) {
28         cwd, err := os.Getwd()
29         if err != nil {
30                 t.Fatal(err)
31         }
32         defer os.Chdir(cwd)
33
34         err = os.Chdir("../testdata/project")
35         if err != nil {
36                 t.Fatal(err)
37         }
38         hosts, err := LoadHosts()
39         if err != nil {
40                 t.Fatal(err)
41         }
42         err = os.Chdir(cwd)
43         if err != nil {
44                 t.Fatal(err)
45         }
46
47         tests := []struct {
48                 path   string
49                 cfg    *Config
50                 hosts  *Hosts
51                 exp    map[string][]string
52                 expErr error
53         }{
54
55                 {
56                         "../testdata/project",
57                         &Config{
58                                 GroupOrder: []string{
59                                         "detected_linux",
60                                         "detected_freebsd",
61                                 },
62                         },
63                         hosts,
64                         map[string][]string{
65                                 "group": {
66                                         "detected_linux",
67                                         "detected_freebsd",
68                                         "host1.example.org",
69                                 },
70                                 "group:remove": {
71                                         "host2",
72                                         "detected_mips",
73                                 },
74                                 "group2": {
75                                         "all",
76                                 },
77                                 "group2:remove": {
78                                         "remove",
79                                 },
80                                 "all_except_some": {
81                                         "all",
82                                 },
83                                 "all_except_some:remove": {
84                                         "host1.example.org",
85                                         "group2",
86                                 },
87                                 "remove": {
88                                         "host1.example.org",
89                                         "host2",
90                                         "host3.example.net",
91                                 },
92                                 "remove:remove": {
93                                         "host2",
94                                 },
95                         },
96                         nil,
97                 },
98
99                 {
100                         "../testdata/project",
101                         &Config{
102                                 GroupOrder: []string{
103                                         "detected_freebsd",
104                                         "does-not-exist",
105                                 },
106                         },
107                         hosts,
108                         nil,
109                         fmt.Errorf("config.yaml: group_order: group \"does-not-exist\" does not exist"),
110                 },
111                 {
112                         "../testdata/project",
113                         &Config{
114                                 GroupOrder: []string{
115                                         "detected_freebsd",
116                                         "special:group",
117                                 },
118                         },
119                         hosts,
120                         nil,
121                         fmt.Errorf("config.yaml: group_order: invalid group name \"special:group\""),
122                 },
123                 {
124                         "../testdata/project",
125                         &Config{
126                                 GroupOrder: []string{
127                                         "detected_freebsd",
128                                         "group:remove",
129                                 },
130                         },
131                         hosts,
132                         nil,
133                         fmt.Errorf("config.yaml: group_order: invalid group name \"group:remove\""),
134                 },
135
136                 {
137                         "../testdata/group-invalid-all",
138                         &Config{},
139                         hosts,
140                         nil,
141                         fmt.Errorf("groups.yaml: group \"all\": conflict with pre-defined group \"all\""),
142                 },
143                 {
144                         "../testdata/group-invalid-all-remove",
145                         &Config{},
146                         hosts,
147                         nil,
148                         fmt.Errorf("groups.yaml: group \"all:remove\": conflict with pre-defined group \"all:remove\""),
149                 },
150                 {
151                         "../testdata/group-invalid-conflict",
152                         &Config{},
153                         hosts,
154                         nil,
155                         fmt.Errorf("groups.yaml: group \"host2\": conflict with existing host"),
156                 },
157                 {
158                         "../testdata/group-invalid-detected",
159                         &Config{},
160                         &Hosts{},
161                         nil,
162                         fmt.Errorf("groups.yaml: group \"detected_linux\": name must not start with \"detected\" (reserved for detected groups)"),
163                 },
164                 {
165                         "../testdata/group-invalid-member",
166                         &Config{},
167                         &Hosts{},
168                         nil,
169                         fmt.Errorf("groups.yaml: group \"group1\": member \"special:member\" must not contain \":\""),
170                 },
171                 {
172                         "../testdata/group-invalid-missing",
173                         &Config{},
174                         &Hosts{},
175                         nil,
176                         fmt.Errorf("groups.yaml: group \"1group2\": group \"does-not-exist\" not found"),
177                 },
178                 {
179                         "../testdata/group-invalid-name",
180                         &Config{},
181                         &Hosts{},
182                         nil,
183                         fmt.Errorf("groups.yaml: group \"invalid.group.name\": name contains invalid characters (must match ^[a-z0-9_-]+$)"),
184                 },
185         }
186
187         for _, tc := range tests {
188                 err := os.Chdir(tc.path)
189                 if err != nil {
190                         t.Fatal(err)
191                 }
192
193                 res, err := LoadGroups(tc.cfg, tc.hosts)
194
195                 if !reflect.DeepEqual(tc.exp, res) {
196                         t.Errorf("%s: res: %s", tc.path,
197                                 cmp.Diff(tc.exp, res))
198                 }
199                 // Ugly but the simplest way to compare errors (including nil)
200                 if fmt.Sprintf("%s", err) != fmt.Sprintf("%s", tc.expErr) {
201                         t.Errorf("%s: err = %#v, want %#v",
202                                 tc.path, err, tc.expErr)
203                 }
204
205                 err = os.Chdir(cwd)
206                 if err != nil {
207                         t.Fatal(err)
208                 }
209         }
210 }
211
212 func TestResolveHostGroups(t *testing.T) {
213         cwd, err := os.Getwd()
214         if err != nil {
215                 t.Fatal(err)
216         }
217         defer os.Chdir(cwd)
218
219         err = os.Chdir("../testdata/project")
220         if err != nil {
221                 t.Fatal(err)
222         }
223         allHosts, err := LoadHosts()
224         if err != nil {
225                 t.Fatal(err)
226         }
227         allGroups, err := LoadGroups(&Config{}, allHosts)
228         if err != nil {
229                 t.Fatal(err)
230         }
231
232         tests := []struct {
233                 name     string
234                 host     string
235                 detected []string
236                 exp      []string
237                 expErr   error
238         }{
239
240                 {
241                         "host1",
242                         "host1.example.org",
243                         nil,
244                         []string{
245                                 "all",
246                                 "group",
247                                 "host1.example.org",
248                                 "remove",
249                         },
250                         nil,
251                 },
252                 {
253                         "host2",
254                         "host2",
255                         nil,
256                         []string{
257                                 "all",
258                                 "group2",
259                                 "host2",
260                         },
261                         nil,
262                 },
263                 {
264                         "host3",
265                         "host3.example.net",
266                         nil,
267                         []string{
268                                 "all",
269                                 "all_except_some",
270                                 "host3.example.net",
271                                 "remove",
272                         },
273                         nil,
274                 },
275                 {
276                         "unknown host",
277                         "unknown",
278                         nil,
279                         []string{
280                                 "all",
281                                 "group2",
282                                 "unknown",
283                         },
284                         nil,
285                 },
286
287                 {
288                         "host1, detected_mips",
289                         "host1.example.org",
290                         []string{
291                                 "detected_mips",
292                         },
293                         []string{
294                                 "all",
295                                 "detected_mips",
296                                 "host1.example.org",
297                                 "remove",
298                         },
299                         nil,
300                 },
301                 {
302                         "host2, detected_linux",
303                         "host2",
304                         []string{
305                                 "detected_linux",
306                         },
307                         []string{
308                                 "all",
309                                 "detected_linux",
310                                 "group2",
311                                 "host2",
312                         },
313                         nil,
314                 },
315         }
316
317         for _, tc := range tests {
318                 res, err := ResolveHostGroups(tc.host, allGroups, tc.detected)
319                 if !reflect.DeepEqual(tc.exp, res) {
320                         t.Errorf("%s: res: %s", tc.name,
321                                 cmp.Diff(tc.exp, res))
322                 }
323                 // Ugly but the simplest way to compare errors (including nil)
324                 if fmt.Sprintf("%s", err) != fmt.Sprintf("%s", tc.expErr) {
325                         t.Errorf("%s: err = %#v, want %#v",
326                                 tc.name, err, tc.expErr)
327                 }
328         }
329 }