diff --git a/applications/rtdt-manager/main.go b/applications/rtdt-manager/main.go index f95d64666e7c90a3ca5e065d2a5208e493ba58b9..967d67c1069b1865e28e07c42232a494b24d884c 100644 --- a/applications/rtdt-manager/main.go +++ b/applications/rtdt-manager/main.go @@ -18,6 +18,10 @@ func main() { var clabConfigName string var benchmark bool var sdnConfigPath string + // The next flag is to disable path checking before applying received events. + //Interface handler in gNMI target is sort of broken and bombards you with events + // Trying to apply them all crashes the handler (? more research needed) + var experimentalMode bool flag.StringVar(&address, "address", "172.100.0.5:55055", "Address of the gosdn controller") flag.StringVar(&address, "a", "172.100.0.5:55055", "Address of the gosdn controller (shorthand)") @@ -29,6 +33,7 @@ func main() { flag.StringVar(&clabConfigName, "c", "data/clab.yaml", "Containerlab file with basic gosdn environment (shorthand)") flag.BoolVar(&benchmark, "benchmark", false, "Run performance tests (measure propagation delay)") flag.BoolVar(&benchmark, "b", false, "Run performance tests (measure propagation delay)") + flag.BoolVar(&experimentalMode, "experimental", false, "Enable experimental mode (spicy!)") flag.StringVar(&sdnConfigPath, "sdnconfig", "applications/rtdt-manager/data/sample_venv_sdnconfig.json", "SdnConfig file (json)") flag.Usage = func() { @@ -37,10 +42,12 @@ func main() { fmt.Println("--password, -p: Password for the user to log into realnet as (Try 'TestPassword')") fmt.Println("--topology, -t: Topology .yaml file with entries for the goSDN environment. Used to generate realnet and twins") fmt.Println("--sdnconfig: Path to the sdnconfig .json file that contains information about network elements and links") + fmt.Println("--experimental: WARNING! Passing this essentially disables paths filtering, trying to apply all changes of events, generally causing breakage because of bugs in gNMI-target") + } flag.Parse() // Register new RtdtManager - rtdtMan := RtdtMan.NewRtdtManager() + rtdtMan := RtdtMan.NewRtdtManager(experimentalMode) if rtdtMan == nil { fmt.Println("Couldn't initialize rtdt-manager, quitting!") return diff --git a/applications/rtdt-manager/rtdt-manager/rtdt-manager.go b/applications/rtdt-manager/rtdt-manager/rtdt-manager.go index 3fcf1e822ce3fbb1dc900e451922771d92f76750..5f6236ed1fa4367aefc86056247dd4b0ea430e60 100644 --- a/applications/rtdt-manager/rtdt-manager/rtdt-manager.go +++ b/applications/rtdt-manager/rtdt-manager/rtdt-manager.go @@ -15,6 +15,7 @@ import ( "time" "code.fbi.h-da.de/danet/gosdn/application-framework/event" + "code.fbi.h-da.de/danet/gosdn/application-framework/registration" clabconfig "code.fbi.h-da.de/danet/gosdn/applications/rtdt-manager/clab-config" "code.fbi.h-da.de/danet/gosdn/applications/rtdt-manager/sdnconfig" @@ -31,16 +32,18 @@ type RtdtManager struct { stopChan chan os.Signal baseClabConfig *clabconfig.ClabConfig benchmark0 bool + experimental bool } // needs to be passed a running realnet VEnv -func NewRtdtManager() *RtdtManager { +func NewRtdtManager(experimental bool) *RtdtManager { rMan := RtdtManager{ realnet: nil, waitGroup: sync.WaitGroup{}, stopChan: make(chan os.Signal, 1), baseClabConfig: nil, benchmark0: false, + experimental: experimental, } signal.Notify(rMan.stopChan, os.Interrupt) fmt.Println("Success: RtdtManager created") @@ -284,7 +287,7 @@ func (r *RtdtManager) Run() error { return nil } if len(r.rtdt_twins) < 1 { - fmt.Println("Warning: You did not start any twins") + fmt.Println("!! Warning: You did not start any twins, you can do so with 'launch-twin'") } // Run until SIGINT, SIGTERM is received @@ -399,9 +402,9 @@ func (r *RtdtManager) InitEventSystem() error { if !r.realnet.EventSystemStarted { fmt.Println("Starting Event System for realnet!") - // realnet_auth := r.realnet.GetAuth() - // ctx := realnet_auth.CreateContextWithAuthorization() - // queueCredentials, err := registration.Register(ctx, realnet_auth.GetAddress(), "basic-interface-monitoring", "SecurePresharedToken") + realnet_auth := r.realnet.GetAuth() + ctx := realnet_auth.CreateContextWithAuthorization() + _, err := registration.Register(ctx, realnet_auth.GetAddress(), "basic-interface-monitoring", "SecurePresharedToken") queueAddress, err := r.realnet.FindQueueAddress() if err != nil { return fmt.Errorf("Error in InitEventSystem(): %w", err) @@ -485,6 +488,16 @@ func (r *RtdtManager) updateMNECallbackTwin(event *event.Event) { } } +func printEvent(event *event.Event) { + + fmt.Println("--------------------------------") + fmt.Println("---------- MNE EVENT -----------") + fmt.Println("EventID: ", event.ID.ID()) + fmt.Println("Event Type: ", event.Type) + fmt.Println("PathsAndValuesMap: ", event.PathsAndValuesMap) + fmt.Println("EntityID", event.EntityID) +} + func (r *RtdtManager) updateMNECallbackRealnet(event *event.Event) { if !r.realnet.SyncBack { return @@ -493,24 +506,17 @@ func (r *RtdtManager) updateMNECallbackRealnet(event *event.Event) { benchmark.Current = benchmark.Benchmark0{} benchmark.Current.StartTimeRealnet = time.Now() } - fmt.Println("--------------------------------") - fmt.Println("---------- MNE EVENT -----------") - fmt.Println("EventID: ", event.ID.ID()) - fmt.Println("Event Type: ", event.Type) - fmt.Println("PathsAndValuesMap: ", event.PathsAndValuesMap) - fmt.Println("EntityID", event.EntityID) - // prefix := "/interfaces/interface[name=" - // prefixHostname := "/system/config/hostname" + prefixInterface := "/interfaces/interface[name=" + prefixHostname := "/system/config/hostname" //realnetClabData := r.realnet.GetClabData() // for i, node := range realnetClabData.Topology.Nodes { // // } - // suffixMTU := "]/config/mtu" + suffixMTU := "]/config/mtu" // Select a twin //TODO: This is where some selection process should happen to select the right twin based on the event var twin *venv.VEnv if len(r.rtdt_twins) > 0 { - fmt.Println("Found twin to apply change to:", r.rtdt_twins[0].Name) twin = r.rtdt_twins[0] // just support one twin for now r.rtdt_twins[0].SyncBack = false // Don't record this in twin } else { @@ -524,8 +530,8 @@ func (r *RtdtManager) updateMNECallbackRealnet(event *event.Event) { // First get hostname of realnet node realnetNode := r.realnet.GetSdnConfig().GetNodeByUUID(event.EntityID.String()) // LINK UP/DOWN - //interfaceRegex := regexp.MustCompile(`/interfaces/interface\[name=([^]]+)]/state/oper-status`) - // regexMatch := interfaceRegex.FindStringSubmatch(path) + interfaceRegex := regexp.MustCompile(`/interfaces/interface\[name=([^]]+)]/state/oper-status`) + regexMatchOperStatus := interfaceRegex.FindStringSubmatch(path) // Get the ID of parallel mne in twin network // parallel nodes are nodes that have the same name in twin and realnet @@ -536,8 +542,45 @@ func (r *RtdtManager) updateMNECallbackRealnet(event *event.Event) { } } - //var err error - twin.SetGnmiPath(path, value, twinEntityID, r.benchmark0) + // If experimental, just call it like this + if r.experimental { + fmt.Println("Found twin to apply change to:", r.rtdt_twins[0].Name) + twin.SetGnmiPath(path, value, twinEntityID, r.benchmark0) + // Else filter it first + } else if strings.HasPrefix(path, prefixInterface) && strings.HasSuffix(path, suffixMTU) { + fmt.Println("--- CHANGE MTU TRIGGERED ---") + printEvent(event) + + fmt.Println("Value of new MTU: ", value) + twin.SetGnmiPath(path, value, twinEntityID, r.benchmark0) + // Set Hostname + } else if strings.HasPrefix(path, prefixHostname) { + + fmt.Println("--- CHANGE HOSTNAME TRIGGERED ---") + printEvent(event) + for _, twin := range r.rtdt_twins { + if twin == nil { + fmt.Println("Encountered nil twin, skipping") + continue + } + fmt.Println("ENTERING SETGNMIPATH, value: ", value, "path:", path) + err := twin.SetGnmiPath(path, value, twinEntityID, r.benchmark0) + if err != nil { + fmt.Println("Callback failed:", err) + return + } + } + } else if regexMatchOperStatus != nil && len(r.rtdt_twins) > 0 { + fmt.Println("Setting interface", regexMatchOperStatus[1], "UP/DOWN") + fmt.Printf("match: %v\n", regexMatchOperStatus) + path := "/interfaces/interface[name=" + regexMatchOperStatus[1] + "]/config/enabled" + if value == "DOWN" { + value = "false" + } else { + value = "true" + } + twin.SetGnmiPath(path, value, twinEntityID, false) + } // Some explicitly supported paths // MTU Change