//monitorBest monitors for route updates/changes form peer func (self *OfnetBgp) watch() { w := self.bgpServer.Watch(gobgp.WatchBestPath(), gobgp.WatchPeerState(true)) for { select { case ev := <-w.Event(): switch msg := ev.(type) { case *gobgp.WatchEventBestPath: for _, path := range msg.PathList { self.modRib(path) } case *gobgp.WatchEventPeerState: self.peerUpdate(msg) } case <-self.stopWatch: return } } }
func (s *Server) MonitorRib(arg *Table, stream GobgpApi_MonitorRibServer) error { w, err := func() (*server.Watcher, error) { switch arg.Type { case Resource_GLOBAL: return s.bgpServer.Watch(server.WatchBestPath()), nil case Resource_ADJ_IN: if arg.PostPolicy { return s.bgpServer.Watch(server.WatchPostUpdate(false)), nil } return s.bgpServer.Watch(server.WatchUpdate(false)), nil default: return nil, fmt.Errorf("unsupported resource type: %v", arg.Type) } }() if err != nil { return nil } return func() error { defer func() { w.Stop() }() sendPath := func(pathList []*table.Path) error { dsts := make(map[string]*Destination) for _, path := range pathList { if path == nil || (arg.Family != 0 && bgp.RouteFamily(arg.Family) != path.GetRouteFamily()) { continue } if dst, y := dsts[path.GetNlri().String()]; y { dst.Paths = append(dst.Paths, ToPathApi(path)) } else { dsts[path.GetNlri().String()] = &Destination{ Prefix: path.GetNlri().String(), Paths: []*Path{ToPathApi(path)}, } } } for _, dst := range dsts { if err := stream.Send(dst); err != nil { return err } } return nil } for { select { case ev := <-w.Event(): switch msg := ev.(type) { case *server.WatchEventBestPath: if err := sendPath(func() []*table.Path { if len(msg.MultiPathList) > 0 { l := make([]*table.Path, 0) for _, p := range msg.MultiPathList { l = append(l, p...) } return l } else { return msg.PathList } }()); err != nil { return err } case *server.WatchEventUpdate: if err := sendPath(msg.PathList); err != nil { return err } } } } }() }