Skip to content

Commit d4f2184

Browse files
authored
Support different build branches (#30)
1 parent 4995cc3 commit d4f2184

16 files changed

+194
-49
lines changed

cmd/generate.go

Lines changed: 19 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -8,24 +8,25 @@ import (
88
"github.com/metal-stack/sonic-configdb-utils/configdb"
99
p "github.com/metal-stack/sonic-configdb-utils/platform"
1010
"github.com/metal-stack/sonic-configdb-utils/values"
11+
v "github.com/metal-stack/sonic-configdb-utils/version"
1112
"github.com/spf13/cobra"
1213
)
1314

1415
var generateCmd = &cobra.Command{
1516
Use: "generate",
1617
Short: "Generate a config_db.json",
1718
RunE: func(cmd *cobra.Command, args []string) error {
19+
inputFile, _ := cmd.Flags().GetString("input-file")
20+
outputFile, _ := cmd.Flags().GetString("output-file")
21+
deviceDir, _ := cmd.Flags().GetString("device-dir")
1822
sonicEnvFile, _ := cmd.Flags().GetString("env-file")
23+
sonicVersionFile, _ := cmd.Flags().GetString("version-file")
24+
1925
env, err := p.GetEnvironment(sonicEnvFile)
2026
if err != nil {
2127
return fmt.Errorf("failed to get environment information:%w", err)
2228
}
2329

24-
platformIdentifier := env.Platform
25-
inputFile, _ := cmd.Flags().GetString("input-file")
26-
outputFile, _ := cmd.Flags().GetString("output-file")
27-
deviceDir, _ := cmd.Flags().GetString("device-dir")
28-
2930
inputBytes, err := os.ReadFile(inputFile)
3031
if err != nil {
3132
fmt.Printf("failed to read input file, %v\n", err)
@@ -38,8 +39,7 @@ var generateCmd = &cobra.Command{
3839
os.Exit(1)
3940
}
4041

41-
platformFile := fmt.Sprintf("%s/%s/platform.json", deviceDir, platformIdentifier)
42-
42+
platformFile := fmt.Sprintf("%s/%s/platform.json", deviceDir, env.Platform)
4343
platformBytes, err := os.ReadFile(platformFile)
4444
if err != nil {
4545
return fmt.Errorf("failed to read platform.json file:%w", err)
@@ -50,7 +50,17 @@ var generateCmd = &cobra.Command{
5050
return fmt.Errorf("failed to parse platform.json:%w", err)
5151
}
5252

53-
configDB, err := configdb.GenerateConfigDB(values, platform, env)
53+
versionBytes, err := os.ReadFile(sonicVersionFile)
54+
if err != nil {
55+
return fmt.Errorf("failed to read version file:%w", err)
56+
}
57+
58+
version, err := v.UnmarshalVersion(versionBytes)
59+
if err != nil {
60+
return fmt.Errorf("failed to parse version file:%w", err)
61+
}
62+
63+
configDB, err := configdb.GenerateConfigDB(values, platform, env, version)
5464
if err != nil {
5565
return fmt.Errorf("failed to generate config:%w", err)
5666
}
@@ -76,4 +86,5 @@ func init() {
7686
generateCmd.Flags().StringP("output-file", "o", "config_db.json", "path to output file")
7787
generateCmd.Flags().String("device-dir", "/usr/share/sonic/device", "directory which holds all device-specific files")
7888
generateCmd.Flags().StringP("env-file", "e", "/etc/sonic/sonic-environment", "sonic-environment file holding platform information")
89+
generateCmd.Flags().StringP("version-file", "v", "/etc/sonic/sonic_version.yaml", "sonic version file")
7990
}

configdb/configdb.go

Lines changed: 54 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -7,9 +7,9 @@ import (
77
"slices"
88
"strconv"
99

10-
"github.com/metal-stack/sonic-configdb-utils/platform"
1110
p "github.com/metal-stack/sonic-configdb-utils/platform"
1211
"github.com/metal-stack/sonic-configdb-utils/values"
12+
v "github.com/metal-stack/sonic-configdb-utils/version"
1313
)
1414

1515
type ConfigDB struct {
@@ -44,7 +44,7 @@ type ConfigDB struct {
4444
VXLANTunnelMap VXLANTunnelMap `json:"VXLAN_TUNNEL_MAP,omitempty"`
4545
}
4646

47-
func GenerateConfigDB(input *values.Values, platform *p.Platform, environment *platform.Environment) (*ConfigDB, error) {
47+
func GenerateConfigDB(input *values.Values, platform *p.Platform, environment *p.Environment, version *v.Version) (*ConfigDB, error) {
4848
if input == nil {
4949
return nil, fmt.Errorf("no input values provided")
5050
}
@@ -66,6 +66,16 @@ func GenerateConfigDB(input *values.Values, platform *p.Platform, environment *p
6666
rules, tables := getACLRulesAndTables(input.SSHSourceranges)
6767
vxlanevpn, vxlanTunnel, vxlanTunnelMap := getVXLAN(input.VTEP, input.LoopbackAddress)
6868

69+
sag, err := getSAG(input.SAG, version)
70+
if err != nil {
71+
return nil, err
72+
}
73+
74+
vlanInterfaces, err := getVLANInterfaces(input.VLANs, version)
75+
if err != nil {
76+
return nil, err
77+
}
78+
6979
configdb := ConfigDB{
7080
ACLRules: rules,
7181
ACLTables: tables,
@@ -74,12 +84,13 @@ func GenerateConfigDB(input *values.Values, platform *p.Platform, environment *p
7484
DNSNameservers: getDNSNameservers(input.Nameservers),
7585
Features: features,
7686
Interfaces: getInterfaces(input.Ports, input.BGPPorts, input.Interconnects),
77-
LLDP: getLLDP(input.LLDPHelloTime),
87+
LLDP: getLLDP(input.LLDPHelloTime, version),
7888
LoopbackInterface: getLoopbackInterface(input.LoopbackAddress),
7989
MCLAGDomains: getMCLAGDomains(input.MCLAG),
8090
MCLAGInterfaces: getMCLAGInterfaces(input.MCLAG),
8191
MCLAGUniqueIPs: getMCLAGUniqueIPs(input.MCLAG),
8292
MgmtInterfaces: getMgmtInterfaces(input.MgmtInterface),
93+
// FIX: some switches don't have an eth0
8394
MgmtPorts: map[string]MgmtPort{
8495
"eth0": {
8596
AdminStatus: AdminStatusUp,
@@ -97,9 +108,9 @@ func GenerateConfigDB(input *values.Values, platform *p.Platform, environment *p
97108
Ports: ports,
98109
PortChannels: getPortChannels(input.PortChannels),
99110
PortChannelMembers: getPortChannelMembers(input.PortChannels.List),
100-
SAG: getSAG(input.SAG),
111+
SAG: sag,
101112
VLANs: getVLANs(input.VLANs),
102-
VLANInterfaces: getVLANInterfaces(input.VLANs),
113+
VLANInterfaces: vlanInterfaces,
103114
VLANMembers: getVLANMembers(input.VLANs),
104115
VLANSubinterfaces: getVLANSubinterfaces(input.VLANSubinterfaces),
105116
VRFs: getVRFs(input.Interconnects, input.Ports, input.VLANs),
@@ -169,7 +180,7 @@ func getACLRulesAndTables(sourceRanges []string) (map[string]ACLRule, map[string
169180
return rules, tables
170181
}
171182

172-
func getDeviceMetadata(input *values.Values, environment *platform.Environment) (*DeviceMetadata, error) {
183+
func getDeviceMetadata(input *values.Values, environment *p.Environment) (*DeviceMetadata, error) {
173184
if environment.Platform == "" {
174185
return nil, fmt.Errorf("no platform identifiert found in environment file")
175186
}
@@ -266,15 +277,28 @@ func getInterfaces(ports values.Ports, bgpPorts []string, interconnects map[stri
266277
return interfaces
267278
}
268279

269-
func getLLDP(interval int) *LLDP {
280+
func getLLDP(interval int, version *v.Version) *LLDP {
270281
if interval < 1 {
271282
return nil
272283
}
273-
return &LLDP{
274-
Global: LLDPGlobal{
275-
HelloTime: fmt.Sprintf("%d", interval),
276-
},
284+
285+
lldp := &LLDP{}
286+
global := LLDPGlobal{
287+
HelloTime: fmt.Sprintf("%d", interval),
288+
}
289+
290+
switch version.Branch {
291+
case string(v.Branch202111):
292+
global202111 := LLDPGlobal202111(global)
293+
lldp.Global202111 = &global202111
294+
case string(v.Branch202211):
295+
global202211 := LLDPGlobal202211(global)
296+
lldp.Global202211 = &global202211
297+
default:
298+
lldp = nil
277299
}
300+
301+
return lldp
278302
}
279303

280304
func getLoopbackInterface(loopback string) map[string]struct{} {
@@ -473,16 +497,20 @@ func getPortsAndBreakouts(ports values.Ports, breakouts map[string]string, platf
473497
return configPorts, configBreakouts, nil
474498
}
475499

476-
func getSAG(sag values.SAG) *SAG {
477-
if sag.MAC == "" {
478-
return nil
500+
func getSAG(sag *values.SAG, version *v.Version) (*SAG, error) {
501+
if version.Branch != string(v.Branch202211) && sag != nil {
502+
return nil, fmt.Errorf("sag configuration only works with sonic versions from the ec202211 branch")
503+
}
504+
505+
if sag == nil || sag.MAC == "" {
506+
return nil, nil
479507
}
480508

481509
return &SAG{
482510
SAGGlobal: SAGGlobal{
483511
GatewayMAC: sag.MAC,
484512
},
485-
}
513+
}, nil
486514
}
487515

488516
func getVLANs(vlans []values.VLAN) map[string]VLAN {
@@ -498,15 +526,23 @@ func getVLANs(vlans []values.VLAN) map[string]VLAN {
498526
return configVLANs
499527
}
500528

501-
func getVLANInterfaces(vlans []values.VLAN) map[string]VLANInterface {
529+
func getVLANInterfaces(vlans []values.VLAN, version *v.Version) (map[string]VLANInterface, error) {
502530
vlanInterfaces := make(map[string]VLANInterface)
503531

504532
for _, vlan := range vlans {
505533
var vlanInterface VLANInterface
506534

535+
if version.Branch != string(v.Branch202211) && vlan.SAG != nil {
536+
return nil, fmt.Errorf("sag only works for sonic builds from branch 202211")
537+
}
538+
var sag string
539+
if vlan.SAG != nil {
540+
sag = strconv.FormatBool(*vlan.SAG)
541+
}
542+
507543
if vlan.VRF != "" {
508544
vlanInterface = VLANInterface{
509-
StaticAnycastGateway: strconv.FormatBool(vlan.SAG),
545+
StaticAnycastGateway: sag,
510546
VRFName: vlan.VRF,
511547
}
512548
}
@@ -518,7 +554,7 @@ func getVLANInterfaces(vlans []values.VLAN) map[string]VLANInterface {
518554
vlanInterfaces["Vlan"+vlan.ID+"|"+vlan.IP] = VLANInterface{}
519555
}
520556

521-
return vlanInterfaces
557+
return vlanInterfaces, nil
522558
}
523559

524560
func getVLANMembers(vlans []values.VLAN) map[string]VLANMember {

configdb/configdb_test.go

Lines changed: 58 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,7 @@ import (
88
"github.com/metal-stack/metal-lib/pkg/testcommon"
99
p "github.com/metal-stack/sonic-configdb-utils/platform"
1010
"github.com/metal-stack/sonic-configdb-utils/values"
11+
v "github.com/metal-stack/sonic-configdb-utils/version"
1112
)
1213

1314
func Test_getInterfaces(t *testing.T) {
@@ -551,3 +552,60 @@ func Test_getVRFs(t *testing.T) {
551552
})
552553
}
553554
}
555+
556+
func Test_getSAG(t *testing.T) {
557+
tests := []struct {
558+
name string
559+
sag *values.SAG
560+
version *v.Version
561+
want *SAG
562+
wantErr bool
563+
}{
564+
{
565+
name: "wrong version",
566+
sag: &values.SAG{},
567+
version: &v.Version{
568+
Branch: string(v.Branch202111),
569+
},
570+
want: nil,
571+
wantErr: true,
572+
},
573+
{
574+
name: "empty mac",
575+
sag: &values.SAG{},
576+
version: &v.Version{
577+
Branch: string(v.Branch202211),
578+
},
579+
want: nil,
580+
wantErr: false,
581+
},
582+
{
583+
name: "valid",
584+
sag: &values.SAG{
585+
MAC: "11:11:11:11:11:11",
586+
},
587+
version: &v.Version{
588+
Branch: string(v.Branch202211),
589+
},
590+
want: &SAG{
591+
SAGGlobal: SAGGlobal{
592+
GatewayMAC: "11:11:11:11:11:11",
593+
},
594+
},
595+
wantErr: false,
596+
},
597+
}
598+
599+
for _, tt := range tests {
600+
t.Run(tt.name, func(t *testing.T) {
601+
got, err := getSAG(tt.sag, tt.version)
602+
if (err != nil) != tt.wantErr {
603+
t.Errorf("getSAG() error = %v, wantErr %v", err, tt.wantErr)
604+
return
605+
}
606+
if diff := cmp.Diff(tt.want, got); diff != "" {
607+
t.Errorf("getSAG() diff = %s", diff)
608+
}
609+
})
610+
}
611+
}

configdb/fields.go

Lines changed: 10 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -84,13 +84,22 @@ const (
8484
)
8585

8686
type LLDP struct {
87-
Global LLDPGlobal `json:"Global"`
87+
Global202111 *LLDPGlobal202111 `json:"Global,omitempty"`
88+
Global202211 *LLDPGlobal202211 `json:"GLOBAL,omitempty"`
8889
}
8990

9091
type LLDPGlobal struct {
92+
HelloTime string
93+
}
94+
95+
type LLDPGlobal202111 struct {
9196
HelloTime string `json:"hello_timer,omitempty"`
9297
}
9398

99+
type LLDPGlobal202211 struct {
100+
HelloTime string `json:"hello_time,omitempty"`
101+
}
102+
94103
type MCLAGDomain struct {
95104
MCLAGSystemID string `json:"mclag_system_id,omitempty"`
96105
PeerIP string `json:"peer_ip,omitempty"`

tests/1/expected.json

Lines changed: 0 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -582,11 +582,6 @@
582582
"PortChannel01|Ethernet4": {},
583583
"PortChannel01|Ethernet5": {}
584584
},
585-
"SAG": {
586-
"GLOBAL": {
587-
"gateway_mac": "bb:bb:bb:bb:bb:bb"
588-
}
589-
},
590585
"VLAN": {
591586
"Vlan4000": {
592587
"dhcp_servers": [
@@ -601,7 +596,6 @@
601596
},
602597
"VLAN_INTERFACE": {
603598
"Vlan4000": {
604-
"static_anycast_gateway": "true",
605599
"vrf_name": "Vrf45"
606600
},
607601
"Vlan4000|10.9.7.0": {},

tests/1/sonic-config.yaml

Lines changed: 0 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -87,9 +87,6 @@ ports:
8787
vrf: VrfInternet
8888
- name: Ethernet120
8989

90-
sag:
91-
mac: bb:bb:bb:bb:bb:bb
92-
9390
ssh_sourceranges:
9491
- 10.1.23.1/30
9592

@@ -99,7 +96,6 @@ vlans:
9996
- 10.9.8.7
10097
- 10.9.8.6
10198
ip: 10.9.7.0
102-
sag: true
10399
tagged_ports:
104100
- PortChannel01
105101
untagged_ports:

tests/1/sonic_version.yaml

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,2 @@
1+
---
2+
branch: 'ec202111'

tests/2/expected.json

Lines changed: 0 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -126,11 +126,6 @@
126126
"vrf_name": "Vrf42"
127127
}
128128
},
129-
"LLDP": {
130-
"Global": {
131-
"hello_timer": "10"
132-
}
133-
},
134129
"LOOPBACK_INTERFACE": {
135130
"Loopback0": {},
136131
"Loopback0|10.7.7.7/32": {}

tests/2/sonic-config.yaml

Lines changed: 0 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -48,8 +48,6 @@ ports:
4848
- name: Ethernet48
4949
vrf: Vrf42
5050

51-
sag: {}
52-
5351
vlans:
5452
- id: 4000
5553
dhcp_servers:

tests/2/sonic_version.yaml

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,2 @@
1+
---
2+
branch: 'unknown-version'

0 commit comments

Comments
 (0)