master
go 674 lines 24.3 KB
Raw
1 // SPDX-License-Identifier: GPL-3.0-or-later
2
3 package ddprofiledefinition
4
5 import (
6 "slices"
7 "strings"
8 )
9
10 type BGPRowKind string
11
12 const (
13 BGPRowKindDevice BGPRowKind = "device"
14 BGPRowKindPeer BGPRowKind = "peer"
15 BGPRowKindPeerFamily BGPRowKind = "peer_family"
16 )
17
18 var validBGPRowKinds = map[BGPRowKind]struct{}{
19 BGPRowKindDevice: {},
20 BGPRowKindPeer: {},
21 BGPRowKindPeerFamily: {},
22 }
23
24 func IsValidBGPRowKind(kind BGPRowKind) bool {
25 _, ok := validBGPRowKinds[kind]
26 return ok
27 }
28
29 type BGPPeerState string
30
31 const (
32 BGPPeerStateNone BGPPeerState = "none"
33 BGPPeerStateIdle BGPPeerState = "idle"
34 BGPPeerStateConnect BGPPeerState = "connect"
35 BGPPeerStateActive BGPPeerState = "active"
36 BGPPeerStateOpenSent BGPPeerState = "opensent"
37 BGPPeerStateOpenConfirm BGPPeerState = "openconfirm"
38 BGPPeerStateEstablished BGPPeerState = "established"
39 )
40
41 var validBGPPeerStates = map[BGPPeerState]struct{}{
42 BGPPeerStateNone: {},
43 BGPPeerStateIdle: {},
44 BGPPeerStateConnect: {},
45 BGPPeerStateActive: {},
46 BGPPeerStateOpenSent: {},
47 BGPPeerStateOpenConfirm: {},
48 BGPPeerStateEstablished: {},
49 }
50
51 var requiredBGPPeerStates = []BGPPeerState{
52 BGPPeerStateIdle,
53 BGPPeerStateConnect,
54 BGPPeerStateActive,
55 BGPPeerStateOpenSent,
56 BGPPeerStateOpenConfirm,
57 BGPPeerStateEstablished,
58 }
59
60 func IsValidBGPPeerState(state BGPPeerState) bool {
61 _, ok := validBGPPeerStates[state]
62 return ok
63 }
64
65 type BGPAddressFamily string
66
67 const (
68 BGPAddressFamilyIPv4 BGPAddressFamily = "ipv4"
69 BGPAddressFamilyIPv6 BGPAddressFamily = "ipv6"
70 BGPAddressFamilyL2VPN BGPAddressFamily = "l2vpn"
71 )
72
73 var validBGPAddressFamilies = map[BGPAddressFamily]struct{}{
74 BGPAddressFamilyIPv4: {},
75 BGPAddressFamilyIPv6: {},
76 BGPAddressFamilyL2VPN: {},
77 }
78
79 func IsValidBGPAddressFamily(family BGPAddressFamily) bool {
80 _, ok := validBGPAddressFamilies[family]
81 return ok
82 }
83
84 type BGPSubsequentAddressFamily string
85
86 const (
87 BGPSubsequentAddressFamilyUnicast BGPSubsequentAddressFamily = "unicast"
88 BGPSubsequentAddressFamilyMulticast BGPSubsequentAddressFamily = "multicast"
89 BGPSubsequentAddressFamilyLabeledUnicast BGPSubsequentAddressFamily = "labeled_unicast"
90 BGPSubsequentAddressFamilyMVPN BGPSubsequentAddressFamily = "mvpn"
91 BGPSubsequentAddressFamilyVPLS BGPSubsequentAddressFamily = "vpls"
92 BGPSubsequentAddressFamilyEVPN BGPSubsequentAddressFamily = "evpn"
93 BGPSubsequentAddressFamilyVPN BGPSubsequentAddressFamily = "vpn"
94 BGPSubsequentAddressFamilyRTFilter BGPSubsequentAddressFamily = "rtfilter"
95 BGPSubsequentAddressFamilyFlow BGPSubsequentAddressFamily = "flow"
96 )
97
98 var validBGPSubsequentAddressFamilies = map[BGPSubsequentAddressFamily]struct{}{
99 BGPSubsequentAddressFamilyUnicast: {},
100 BGPSubsequentAddressFamilyMulticast: {},
101 BGPSubsequentAddressFamilyLabeledUnicast: {},
102 BGPSubsequentAddressFamilyMVPN: {},
103 BGPSubsequentAddressFamilyVPLS: {},
104 BGPSubsequentAddressFamilyEVPN: {},
105 BGPSubsequentAddressFamilyVPN: {},
106 BGPSubsequentAddressFamilyRTFilter: {},
107 BGPSubsequentAddressFamilyFlow: {},
108 }
109
110 func IsValidBGPSubsequentAddressFamily(family BGPSubsequentAddressFamily) bool {
111 _, ok := validBGPSubsequentAddressFamilies[family]
112 return ok
113 }
114
115 type BGPConfig struct {
116 OriginProfileID string `yaml:"-" json:"-"`
117 ID string `yaml:"id,omitempty" json:"id,omitempty"`
118 MIB string `yaml:"MIB,omitempty" json:"MIB,omitempty"`
119 Kind BGPRowKind `yaml:"kind,omitempty" json:"kind,omitempty"`
120 Table SymbolConfig `yaml:"table,omitempty" json:"table"`
121
122 Identity BGPIdentityConfig `yaml:"identity,omitempty" json:"identity"`
123 Descriptors BGPDescriptorsConfig `yaml:"descriptors,omitempty" json:"descriptors"`
124 Admin BGPAdminConfig `yaml:"admin,omitempty" json:"admin"`
125 State BGPStateConfig `yaml:"state,omitempty" json:"state"`
126 Previous BGPStateConfig `yaml:"previous_state,omitempty" json:"previous_state"`
127 Connection BGPConnectionConfig `yaml:"connection,omitempty" json:"connection"`
128 Traffic BGPTrafficConfig `yaml:"traffic,omitempty" json:"traffic"`
129 Transitions BGPTransitionsConfig `yaml:"transitions,omitempty" json:"transitions"`
130 Timers BGPTimersConfig `yaml:"timers,omitempty" json:"timers"`
131 LastError BGPLastErrorConfig `yaml:"last_error,omitempty" json:"last_error"`
132 LastNotify BGPLastNotifyConfig `yaml:"last_notifications,omitempty" json:"last_notifications"`
133 Reasons BGPReasonsConfig `yaml:"reasons,omitempty" json:"reasons"`
134 Restart BGPGracefulRestartConfig `yaml:"graceful_restart,omitempty" json:"graceful_restart"`
135 Routes BGPRoutesConfig `yaml:"routes,omitempty" json:"routes"`
136 RouteLimits BGPRouteLimitsConfig `yaml:"route_limits,omitempty" json:"route_limits"`
137 Device BGPDeviceCountsConfig `yaml:"device_counts,omitempty" json:"device_counts"`
138
139 StaticTags []StaticMetricTagConfig `yaml:"static_tags,omitempty" json:"-"`
140 MetricTags MetricTagConfigList `yaml:"metric_tags,omitempty" json:"metric_tags,omitempty"`
141 }
142
143 func (c BGPConfig) Clone() BGPConfig {
144 return BGPConfig{
145 OriginProfileID: c.OriginProfileID,
146 ID: c.ID,
147 MIB: c.MIB,
148 Kind: c.Kind,
149 Table: c.Table.Clone(),
150 Identity: c.Identity.Clone(),
151 Descriptors: c.Descriptors.Clone(),
152 Admin: c.Admin.Clone(),
153 State: c.State.Clone(),
154 Previous: c.Previous.Clone(),
155 Connection: c.Connection.Clone(),
156 Traffic: c.Traffic.Clone(),
157 Transitions: c.Transitions.Clone(),
158 Timers: c.Timers.Clone(),
159 LastError: c.LastError.Clone(),
160 LastNotify: c.LastNotify.Clone(),
161 Reasons: c.Reasons.Clone(),
162 Restart: c.Restart.Clone(),
163 Routes: c.Routes.Clone(),
164 RouteLimits: c.RouteLimits.Clone(),
165 Device: c.Device.Clone(),
166 StaticTags: slices.Clone(c.StaticTags),
167 MetricTags: cloneSlice(c.MetricTags),
168 }
169 }
170
171 type BGPIdentityConfig struct {
172 RoutingInstance BGPValueConfig `yaml:"routing_instance,omitempty" json:"routing_instance"`
173 Neighbor BGPValueConfig `yaml:"neighbor,omitempty" json:"neighbor"`
174 RemoteAS BGPValueConfig `yaml:"remote_as,omitempty" json:"remote_as"`
175 AddressFamily BGPAddressFamilyValueConfig `yaml:"address_family,omitempty" json:"address_family"`
176 SubsequentAddressFamily BGPSubsequentAddressFamilyValueConfig `yaml:"subsequent_address_family,omitempty" json:"subsequent_address_family"`
177 }
178
179 func (c BGPIdentityConfig) Clone() BGPIdentityConfig {
180 return BGPIdentityConfig{
181 RoutingInstance: c.RoutingInstance.Clone(),
182 Neighbor: c.Neighbor.Clone(),
183 RemoteAS: c.RemoteAS.Clone(),
184 AddressFamily: c.AddressFamily.Clone(),
185 SubsequentAddressFamily: c.SubsequentAddressFamily.Clone(),
186 }
187 }
188
189 type BGPDescriptorsConfig struct {
190 LocalAddress BGPValueConfig `yaml:"local_address,omitempty" json:"local_address"`
191 LocalAS BGPValueConfig `yaml:"local_as,omitempty" json:"local_as"`
192 LocalIdentifier BGPValueConfig `yaml:"local_identifier,omitempty" json:"local_identifier"`
193 PeerIdentifier BGPValueConfig `yaml:"peer_identifier,omitempty" json:"peer_identifier"`
194 PeerType BGPValueConfig `yaml:"peer_type,omitempty" json:"peer_type"`
195 BGPVersion BGPValueConfig `yaml:"bgp_version,omitempty" json:"bgp_version"`
196 Description BGPValueConfig `yaml:"description,omitempty" json:"description"`
197 }
198
199 func (c BGPDescriptorsConfig) Clone() BGPDescriptorsConfig {
200 return BGPDescriptorsConfig{
201 LocalAddress: c.LocalAddress.Clone(),
202 LocalAS: c.LocalAS.Clone(),
203 LocalIdentifier: c.LocalIdentifier.Clone(),
204 PeerIdentifier: c.PeerIdentifier.Clone(),
205 PeerType: c.PeerType.Clone(),
206 BGPVersion: c.BGPVersion.Clone(),
207 Description: c.Description.Clone(),
208 }
209 }
210
211 type BGPStateConfig struct {
212 BGPValueConfig `yaml:",inline" json:",inline"`
213 Partial bool `yaml:"partial,omitempty" json:"partial,omitempty"`
214 PartialStates []BGPPeerState `yaml:"partial_states,omitempty" json:"partial_states,omitempty"`
215 }
216
217 func (c BGPStateConfig) Clone() BGPStateConfig {
218 return BGPStateConfig{
219 BGPValueConfig: c.BGPValueConfig.Clone(),
220 Partial: c.Partial,
221 PartialStates: slices.Clone(c.PartialStates),
222 }
223 }
224
225 type BGPAdminConfig struct {
226 Enabled BGPValueConfig `yaml:"enabled,omitempty" json:"enabled"`
227 }
228
229 func (c BGPAdminConfig) Clone() BGPAdminConfig {
230 return BGPAdminConfig{Enabled: c.Enabled.Clone()}
231 }
232
233 type BGPConnectionConfig struct {
234 EstablishedUptime BGPValueConfig `yaml:"established_uptime,omitempty" json:"established_uptime"`
235 LastReceivedUpdateAge BGPValueConfig `yaml:"last_received_update_age,omitempty" json:"last_received_update_age"`
236 }
237
238 func (c BGPConnectionConfig) Clone() BGPConnectionConfig {
239 return BGPConnectionConfig{
240 EstablishedUptime: c.EstablishedUptime.Clone(),
241 LastReceivedUpdateAge: c.LastReceivedUpdateAge.Clone(),
242 }
243 }
244
245 type BGPDirectionalConfig struct {
246 Received BGPValueConfig `yaml:"received,omitempty" json:"received"`
247 Sent BGPValueConfig `yaml:"sent,omitempty" json:"sent"`
248 }
249
250 func (c BGPDirectionalConfig) Clone() BGPDirectionalConfig {
251 return BGPDirectionalConfig{
252 Received: c.Received.Clone(),
253 Sent: c.Sent.Clone(),
254 }
255 }
256
257 type BGPTrafficConfig struct {
258 Messages BGPDirectionalConfig `yaml:"messages,omitempty" json:"messages"`
259 Updates BGPDirectionalConfig `yaml:"updates,omitempty" json:"updates"`
260 Notifications BGPDirectionalConfig `yaml:"notifications,omitempty" json:"notifications"`
261 RouteRefreshes BGPDirectionalConfig `yaml:"route_refreshes,omitempty" json:"route_refreshes"`
262 Opens BGPDirectionalConfig `yaml:"opens,omitempty" json:"opens"`
263 Keepalives BGPDirectionalConfig `yaml:"keepalives,omitempty" json:"keepalives"`
264 }
265
266 func (c BGPTrafficConfig) Clone() BGPTrafficConfig {
267 return BGPTrafficConfig{
268 Messages: c.Messages.Clone(),
269 Updates: c.Updates.Clone(),
270 Notifications: c.Notifications.Clone(),
271 RouteRefreshes: c.RouteRefreshes.Clone(),
272 Opens: c.Opens.Clone(),
273 Keepalives: c.Keepalives.Clone(),
274 }
275 }
276
277 type BGPTransitionsConfig struct {
278 Established BGPValueConfig `yaml:"established,omitempty" json:"established"`
279 Down BGPValueConfig `yaml:"down,omitempty" json:"down"`
280 Up BGPValueConfig `yaml:"up,omitempty" json:"up"`
281 Flaps BGPValueConfig `yaml:"flaps,omitempty" json:"flaps"`
282 }
283
284 func (c BGPTransitionsConfig) Clone() BGPTransitionsConfig {
285 return BGPTransitionsConfig{
286 Established: c.Established.Clone(),
287 Down: c.Down.Clone(),
288 Up: c.Up.Clone(),
289 Flaps: c.Flaps.Clone(),
290 }
291 }
292
293 type BGPTimersConfig struct {
294 Negotiated BGPTimerPairConfig `yaml:"negotiated,omitempty" json:"negotiated"`
295 Configured BGPTimerPairConfig `yaml:"configured,omitempty" json:"configured"`
296 }
297
298 func (c BGPTimersConfig) Clone() BGPTimersConfig {
299 return BGPTimersConfig{
300 Negotiated: c.Negotiated.Clone(),
301 Configured: c.Configured.Clone(),
302 }
303 }
304
305 type BGPTimerPairConfig struct {
306 ConnectRetry BGPValueConfig `yaml:"connect_retry,omitempty" json:"connect_retry"`
307 HoldTime BGPValueConfig `yaml:"hold_time,omitempty" json:"hold_time"`
308 KeepaliveTime BGPValueConfig `yaml:"keepalive_time,omitempty" json:"keepalive_time"`
309 MinASOriginationInterval BGPValueConfig `yaml:"min_as_origination_interval,omitempty" json:"min_as_origination_interval"`
310 MinRouteAdvertisementInterval BGPValueConfig `yaml:"min_route_advertisement_interval,omitempty" json:"min_route_advertisement_interval"`
311 }
312
313 func (c BGPTimerPairConfig) Clone() BGPTimerPairConfig {
314 return BGPTimerPairConfig{
315 ConnectRetry: c.ConnectRetry.Clone(),
316 HoldTime: c.HoldTime.Clone(),
317 KeepaliveTime: c.KeepaliveTime.Clone(),
318 MinASOriginationInterval: c.MinASOriginationInterval.Clone(),
319 MinRouteAdvertisementInterval: c.MinRouteAdvertisementInterval.Clone(),
320 }
321 }
322
323 type BGPLastErrorConfig struct {
324 Code BGPValueConfig `yaml:"code,omitempty" json:"code"`
325 Subcode BGPValueConfig `yaml:"subcode,omitempty" json:"subcode"`
326 }
327
328 func (c BGPLastErrorConfig) Clone() BGPLastErrorConfig {
329 return BGPLastErrorConfig{
330 Code: c.Code.Clone(),
331 Subcode: c.Subcode.Clone(),
332 }
333 }
334
335 type BGPLastNotificationConfig struct {
336 Code BGPValueConfig `yaml:"code,omitempty" json:"code"`
337 Subcode BGPValueConfig `yaml:"subcode,omitempty" json:"subcode"`
338 Reason BGPValueConfig `yaml:"reason,omitempty" json:"reason"`
339 }
340
341 func (c BGPLastNotificationConfig) Clone() BGPLastNotificationConfig {
342 return BGPLastNotificationConfig{
343 Code: c.Code.Clone(),
344 Subcode: c.Subcode.Clone(),
345 Reason: c.Reason.Clone(),
346 }
347 }
348
349 type BGPLastNotifyConfig struct {
350 Received BGPLastNotificationConfig `yaml:"received,omitempty" json:"received"`
351 Sent BGPLastNotificationConfig `yaml:"sent,omitempty" json:"sent"`
352 }
353
354 func (c BGPLastNotifyConfig) Clone() BGPLastNotifyConfig {
355 return BGPLastNotifyConfig{
356 Received: c.Received.Clone(),
357 Sent: c.Sent.Clone(),
358 }
359 }
360
361 type BGPReasonsConfig struct {
362 LastDown BGPValueConfig `yaml:"last_down,omitempty" json:"last_down"`
363 Unavailability BGPValueConfig `yaml:"unavailability,omitempty" json:"unavailability"`
364 }
365
366 func (c BGPReasonsConfig) Clone() BGPReasonsConfig {
367 return BGPReasonsConfig{
368 LastDown: c.LastDown.Clone(),
369 Unavailability: c.Unavailability.Clone(),
370 }
371 }
372
373 type BGPGracefulRestartConfig struct {
374 State BGPValueConfig `yaml:"state,omitempty" json:"state"`
375 }
376
377 func (c BGPGracefulRestartConfig) Clone() BGPGracefulRestartConfig {
378 return BGPGracefulRestartConfig{State: c.State.Clone()}
379 }
380
381 type BGPRoutesConfig struct {
382 Current BGPRouteCountersConfig `yaml:"current,omitempty" json:"current"`
383 Total BGPRouteCountersConfig `yaml:"total,omitempty" json:"total"`
384 }
385
386 func (c BGPRoutesConfig) Clone() BGPRoutesConfig {
387 return BGPRoutesConfig{
388 Current: c.Current.Clone(),
389 Total: c.Total.Clone(),
390 }
391 }
392
393 type BGPRouteCountersConfig struct {
394 Received BGPValueConfig `yaml:"received,omitempty" json:"received"`
395 Accepted BGPValueConfig `yaml:"accepted,omitempty" json:"accepted"`
396 Rejected BGPValueConfig `yaml:"rejected,omitempty" json:"rejected"`
397 Active BGPValueConfig `yaml:"active,omitempty" json:"active"`
398 Advertised BGPValueConfig `yaml:"advertised,omitempty" json:"advertised"`
399 Suppressed BGPValueConfig `yaml:"suppressed,omitempty" json:"suppressed"`
400 Withdrawn BGPValueConfig `yaml:"withdrawn,omitempty" json:"withdrawn"`
401 }
402
403 func (c BGPRouteCountersConfig) Clone() BGPRouteCountersConfig {
404 return BGPRouteCountersConfig{
405 Received: c.Received.Clone(),
406 Accepted: c.Accepted.Clone(),
407 Rejected: c.Rejected.Clone(),
408 Active: c.Active.Clone(),
409 Advertised: c.Advertised.Clone(),
410 Suppressed: c.Suppressed.Clone(),
411 Withdrawn: c.Withdrawn.Clone(),
412 }
413 }
414
415 type BGPRouteLimitsConfig struct {
416 Limit BGPValueConfig `yaml:"limit,omitempty" json:"limit"`
417 Threshold BGPValueConfig `yaml:"threshold,omitempty" json:"threshold"`
418 ClearThreshold BGPValueConfig `yaml:"clear_threshold,omitempty" json:"clear_threshold"`
419 }
420
421 func (c BGPRouteLimitsConfig) Clone() BGPRouteLimitsConfig {
422 return BGPRouteLimitsConfig{
423 Limit: c.Limit.Clone(),
424 Threshold: c.Threshold.Clone(),
425 ClearThreshold: c.ClearThreshold.Clone(),
426 }
427 }
428
429 type BGPDeviceCountsConfig struct {
430 Peers BGPValueConfig `yaml:"peers,omitempty" json:"peers"`
431 InternalPeers BGPValueConfig `yaml:"ibgp_peers,omitempty" json:"ibgp_peers"`
432 ExternalPeers BGPValueConfig `yaml:"ebgp_peers,omitempty" json:"ebgp_peers"`
433 States BGPPeerStatesConfig `yaml:"states,omitempty" json:"states"`
434 }
435
436 func (c BGPDeviceCountsConfig) Clone() BGPDeviceCountsConfig {
437 return BGPDeviceCountsConfig{
438 Peers: c.Peers.Clone(),
439 InternalPeers: c.InternalPeers.Clone(),
440 ExternalPeers: c.ExternalPeers.Clone(),
441 States: c.States.Clone(),
442 }
443 }
444
445 type BGPPeerStatesConfig struct {
446 Idle BGPValueConfig `yaml:"idle,omitempty" json:"idle"`
447 Connect BGPValueConfig `yaml:"connect,omitempty" json:"connect"`
448 Active BGPValueConfig `yaml:"active,omitempty" json:"active"`
449 OpenSent BGPValueConfig `yaml:"opensent,omitempty" json:"opensent"`
450 OpenConfirm BGPValueConfig `yaml:"openconfirm,omitempty" json:"openconfirm"`
451 Established BGPValueConfig `yaml:"established,omitempty" json:"established"`
452 }
453
454 func (c BGPPeerStatesConfig) Clone() BGPPeerStatesConfig {
455 return BGPPeerStatesConfig{
456 Idle: c.Idle.Clone(),
457 Connect: c.Connect.Clone(),
458 Active: c.Active.Clone(),
459 OpenSent: c.OpenSent.Clone(),
460 OpenConfirm: c.OpenConfirm.Clone(),
461 Established: c.Established.Clone(),
462 }
463 }
464
465 type BGPAddressFamilyValueConfig struct {
466 BGPValueConfig `yaml:",inline" json:",inline"`
467 AllowPrivate bool `yaml:"allow_private,omitempty" json:"allow_private,omitempty"`
468 }
469
470 func (c BGPAddressFamilyValueConfig) Clone() BGPAddressFamilyValueConfig {
471 return BGPAddressFamilyValueConfig{
472 BGPValueConfig: c.BGPValueConfig.Clone(),
473 AllowPrivate: c.AllowPrivate,
474 }
475 }
476
477 type BGPSubsequentAddressFamilyValueConfig struct {
478 BGPValueConfig `yaml:",inline" json:",inline"`
479 AllowPrivate bool `yaml:"allow_private,omitempty" json:"allow_private,omitempty"`
480 }
481
482 func (c BGPSubsequentAddressFamilyValueConfig) Clone() BGPSubsequentAddressFamilyValueConfig {
483 return BGPSubsequentAddressFamilyValueConfig{
484 BGPValueConfig: c.BGPValueConfig.Clone(),
485 AllowPrivate: c.AllowPrivate,
486 }
487 }
488
489 type BGPValueConfig struct {
490 Value string `yaml:"value,omitempty" json:"value,omitempty"`
491 From string `yaml:"from,omitempty" json:"from,omitempty"`
492 Table string `yaml:"table,omitempty" json:"table,omitempty"`
493
494 Index uint `yaml:"index,omitempty" json:"index,omitempty"`
495 IndexFromEnd uint `yaml:"index_from_end,omitempty" json:"index_from_end,omitempty"`
496 IndexTransform []MetricIndexTransform `yaml:"index_transform,omitempty" json:"index_transform,omitempty"`
497
498 Symbol SymbolConfig `yaml:"symbol,omitempty" json:"symbol"`
499 OID string `yaml:"OID,omitempty" json:"OID,omitempty" jsonschema:"-"`
500 Name string `yaml:"name,omitempty" json:"name,omitempty" jsonschema:"-"`
501
502 LookupSymbol SymbolConfigCompat `yaml:"lookup_symbol,omitempty" json:"lookup_symbol"`
503
504 Format string `yaml:"format,omitempty" json:"format,omitempty"`
505 Mapping MappingConfig `yaml:"mapping,omitempty" json:"mapping"`
506 }
507
508 func (c BGPValueConfig) IsSet() bool {
509 return c.Value != "" ||
510 c.From != "" ||
511 c.Table != "" ||
512 c.Index != 0 ||
513 c.IndexFromEnd != 0 ||
514 len(c.IndexTransform) > 0 ||
515 c.Symbol.OID != "" ||
516 c.Symbol.Name != "" ||
517 c.OID != "" ||
518 c.Name != "" ||
519 c.LookupSymbol.OID != "" ||
520 c.LookupSymbol.Name != "" ||
521 c.Format != "" ||
522 c.Mapping.HasItems() ||
523 c.Mapping.Mode != ""
524 }
525
526 func (c BGPValueConfig) Clone() BGPValueConfig {
527 return BGPValueConfig{
528 Value: c.Value,
529 From: c.From,
530 Table: c.Table,
531 Index: c.Index,
532 IndexFromEnd: c.IndexFromEnd,
533 IndexTransform: slices.Clone(c.IndexTransform),
534 Symbol: c.Symbol.Clone(),
535 OID: c.OID,
536 Name: c.Name,
537 LookupSymbol: c.LookupSymbol.Clone(),
538 Format: c.Format,
539 Mapping: c.Mapping.Clone(),
540 }
541 }
542
543 func ForEachBGPSignalValue(row BGPConfig, add func(path string, value BGPValueConfig)) {
544 addValue := func(path string, value BGPValueConfig) {
545 if value.IsSet() {
546 add(path, value)
547 }
548 }
549 addState := func(path string, value BGPStateConfig) {
550 if value.BGPValueConfig.IsSet() {
551 add(path, value.BGPValueConfig)
552 }
553 }
554 addDirectional := func(prefix string, value BGPDirectionalConfig) {
555 addValue(prefix+".received", value.Received)
556 addValue(prefix+".sent", value.Sent)
557 }
558 addTimerPair := func(prefix string, value BGPTimerPairConfig) {
559 addValue(prefix+".connect_retry", value.ConnectRetry)
560 addValue(prefix+".hold_time", value.HoldTime)
561 addValue(prefix+".keepalive_time", value.KeepaliveTime)
562 addValue(prefix+".min_as_origination_interval", value.MinASOriginationInterval)
563 addValue(prefix+".min_route_advertisement_interval", value.MinRouteAdvertisementInterval)
564 }
565 addNotification := func(prefix string, value BGPLastNotificationConfig) {
566 addValue(prefix+".code", value.Code)
567 addValue(prefix+".subcode", value.Subcode)
568 addValue(prefix+".reason", value.Reason)
569 }
570 addRoutes := func(prefix string, value BGPRouteCountersConfig) {
571 addValue(prefix+".received", value.Received)
572 addValue(prefix+".accepted", value.Accepted)
573 addValue(prefix+".rejected", value.Rejected)
574 addValue(prefix+".active", value.Active)
575 addValue(prefix+".advertised", value.Advertised)
576 addValue(prefix+".suppressed", value.Suppressed)
577 addValue(prefix+".withdrawn", value.Withdrawn)
578 }
579
580 addValue("admin.enabled", row.Admin.Enabled)
581 addState("state", row.State)
582 addState("previous_state", row.Previous)
583 addValue("connection.established_uptime", row.Connection.EstablishedUptime)
584 addValue("connection.last_received_update_age", row.Connection.LastReceivedUpdateAge)
585 addDirectional("traffic.messages", row.Traffic.Messages)
586 addDirectional("traffic.updates", row.Traffic.Updates)
587 addDirectional("traffic.notifications", row.Traffic.Notifications)
588 addDirectional("traffic.route_refreshes", row.Traffic.RouteRefreshes)
589 addDirectional("traffic.opens", row.Traffic.Opens)
590 addDirectional("traffic.keepalives", row.Traffic.Keepalives)
591 addValue("transitions.established", row.Transitions.Established)
592 addValue("transitions.down", row.Transitions.Down)
593 addValue("transitions.up", row.Transitions.Up)
594 addValue("transitions.flaps", row.Transitions.Flaps)
595 addTimerPair("timers.negotiated", row.Timers.Negotiated)
596 addTimerPair("timers.configured", row.Timers.Configured)
597 addValue("last_error.code", row.LastError.Code)
598 addValue("last_error.subcode", row.LastError.Subcode)
599 addNotification("last_notifications.received", row.LastNotify.Received)
600 addNotification("last_notifications.sent", row.LastNotify.Sent)
601 addValue("reasons.last_down", row.Reasons.LastDown)
602 addValue("reasons.unavailability", row.Reasons.Unavailability)
603 addValue("graceful_restart.state", row.Restart.State)
604 addRoutes("routes.current", row.Routes.Current)
605 addRoutes("routes.total", row.Routes.Total)
606 addValue("route_limits.limit", row.RouteLimits.Limit)
607 addValue("route_limits.threshold", row.RouteLimits.Threshold)
608 addValue("route_limits.clear_threshold", row.RouteLimits.ClearThreshold)
609 addValue("device_counts.peers", row.Device.Peers)
610 addValue("device_counts.ibgp_peers", row.Device.InternalPeers)
611 addValue("device_counts.ebgp_peers", row.Device.ExternalPeers)
612 addValue("device_counts.states.idle", row.Device.States.Idle)
613 addValue("device_counts.states.connect", row.Device.States.Connect)
614 addValue("device_counts.states.active", row.Device.States.Active)
615 addValue("device_counts.states.opensent", row.Device.States.OpenSent)
616 addValue("device_counts.states.openconfirm", row.Device.States.OpenConfirm)
617 addValue("device_counts.states.established", row.Device.States.Established)
618 }
619
620 func BGPStructuralIdentity(row BGPConfig) string {
621 origin := row.OriginProfileID
622 if origin == "" {
623 origin = "<profile>"
624 }
625 return strings.Join([]string{origin, BGPMergeIdentity(row)}, "|")
626 }
627
628 func BGPMergeIdentity(row BGPConfig) string {
629 if row.Table.OID != "" {
630 parts := []string{"table", string(row.Kind), TrimBGPOID(row.Table.OID)}
631 if row.ID != "" {
632 parts = append(parts, row.ID)
633 }
634 return strings.Join(parts, "|")
635 }
636 if row.ID != "" {
637 return strings.Join([]string{"scalar-group", string(row.Kind), row.ID}, "|")
638 }
639 if oid := firstBGPSignalSourceOID(row); oid != "" {
640 return strings.Join([]string{"scalar", string(row.Kind), TrimBGPOID(oid)}, "|")
641 }
642 return strings.Join([]string{"scalar", string(row.Kind), "<missing-source>"}, "|")
643 }
644
645 func firstBGPSignalSourceOID(row BGPConfig) string {
646 var first string
647 ForEachBGPSignalValue(row, func(_ string, value BGPValueConfig) {
648 if first != "" {
649 return
650 }
651 if oid := BGPValueSourceOID(value); oid != "" {
652 first = oid
653 return
654 }
655 })
656 return first
657 }
658
659 func BGPValueSourceOID(value BGPValueConfig) string {
660 switch {
661 case value.From != "":
662 return value.From
663 case value.Symbol.OID != "":
664 return value.Symbol.OID
665 case value.OID != "":
666 return value.OID
667 default:
668 return ""
669 }
670 }
671
672 func TrimBGPOID(oid string) string {
673 return strings.TrimPrefix(strings.TrimSpace(oid), ".")
674 }