mirror of
https://github.com/netbirdio/netbird.git
synced 2026-10-07 14:09:07 +02:00
onpeeradded optimization part 1
This commit is contained in:
@@ -868,6 +868,7 @@ func normalizeAndSortNetworkMap(networkMap *types.NetworkMap) {
|
|||||||
if peer.Status != nil {
|
if peer.Status != nil {
|
||||||
peer.Status.LastSeen = time.Time{}
|
peer.Status.LastSeen = time.Time{}
|
||||||
}
|
}
|
||||||
|
peer.LastLogin = &time.Time{}
|
||||||
}
|
}
|
||||||
for _, peer := range networkMap.OfflinePeers {
|
for _, peer := range networkMap.OfflinePeers {
|
||||||
if peer.Status != nil {
|
if peer.Status != nil {
|
||||||
|
|||||||
@@ -22,7 +22,6 @@ import (
|
|||||||
)
|
)
|
||||||
|
|
||||||
type NetworkMapCache struct {
|
type NetworkMapCache struct {
|
||||||
// globalAccountRoutes map[route.ID]*route.Route
|
|
||||||
globalRoutes map[route.ID]*route.Route
|
globalRoutes map[route.ID]*route.Route
|
||||||
globalRules map[string]*FirewallRule //ruleId
|
globalRules map[string]*FirewallRule //ruleId
|
||||||
globalRouteRules map[string]*RouteFirewallRule //ruleId
|
globalRouteRules map[string]*RouteFirewallRule //ruleId
|
||||||
@@ -66,7 +65,6 @@ type NetworkMapBuilder struct {
|
|||||||
func NewNetworkMapBuilder(account *Account, validatedPeers map[string]struct{}) *NetworkMapBuilder {
|
func NewNetworkMapBuilder(account *Account, validatedPeers map[string]struct{}) *NetworkMapBuilder {
|
||||||
builder := &NetworkMapBuilder{
|
builder := &NetworkMapBuilder{
|
||||||
cache: &NetworkMapCache{
|
cache: &NetworkMapCache{
|
||||||
// globalAccountRoutes: make(map[route.ID]*route.Route),
|
|
||||||
globalRoutes: make(map[route.ID]*route.Route),
|
globalRoutes: make(map[route.ID]*route.Route),
|
||||||
globalRules: make(map[string]*FirewallRule),
|
globalRules: make(map[string]*FirewallRule),
|
||||||
globalRouteRules: make(map[string]*RouteFirewallRule),
|
globalRouteRules: make(map[string]*RouteFirewallRule),
|
||||||
@@ -119,7 +117,6 @@ func (b *NetworkMapBuilder) buildGlobalIndexes(account *Account) {
|
|||||||
clear(b.cache.peerToGroups)
|
clear(b.cache.peerToGroups)
|
||||||
clear(b.cache.policyToRules)
|
clear(b.cache.policyToRules)
|
||||||
clear(b.cache.groupToPolicies)
|
clear(b.cache.groupToPolicies)
|
||||||
// clear(b.cache.globalAccountRoutes)
|
|
||||||
clear(b.cache.globalRoutes)
|
clear(b.cache.globalRoutes)
|
||||||
clear(b.cache.globalRules)
|
clear(b.cache.globalRules)
|
||||||
clear(b.cache.globalRouteRules)
|
clear(b.cache.globalRouteRules)
|
||||||
@@ -171,8 +168,6 @@ func (b *NetworkMapBuilder) buildGlobalIndexes(account *Account) {
|
|||||||
b.cache.globalResources[resource.ID] = resource
|
b.cache.globalResources[resource.ID] = resource
|
||||||
}
|
}
|
||||||
|
|
||||||
// maps.Copy(b.cache.globalAccountRoutes, account.Routes)
|
|
||||||
|
|
||||||
for _, r := range account.Routes {
|
for _, r := range account.Routes {
|
||||||
if !r.Enabled {
|
if !r.Enabled {
|
||||||
continue
|
continue
|
||||||
@@ -586,7 +581,7 @@ func (b *NetworkMapBuilder) buildPeerRoutesView(account *Account, peerID string)
|
|||||||
b.cache.globalRoutes[rt.ID] = rt
|
b.cache.globalRoutes[rt.ID] = rt
|
||||||
}
|
}
|
||||||
|
|
||||||
routeFirewallRules := account.GetPeerRoutesFirewallRules(ctx, peerID, b.validatedPeers)
|
routeFirewallRules := b.getPeerRoutesFirewallRules(account, peerID, b.validatedPeers)
|
||||||
for _, rule := range routeFirewallRules {
|
for _, rule := range routeFirewallRules {
|
||||||
ruleID := b.generateRouteFirewallRuleID(rule)
|
ruleID := b.generateRouteFirewallRuleID(rule)
|
||||||
view.RouteFirewallRuleIDs = append(view.RouteFirewallRuleIDs, ruleID)
|
view.RouteFirewallRuleIDs = append(view.RouteFirewallRuleIDs, ruleID)
|
||||||
@@ -647,19 +642,183 @@ func (b *NetworkMapBuilder) getRoutingPeerRoutes(peerID string) (enabledRoutes [
|
|||||||
return enabledRoutes, disabledRoutes
|
return enabledRoutes, disabledRoutes
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func (b *NetworkMapBuilder) getPeerRoutesFirewallRules(account *Account, peerID string, validatedPeersMap map[string]struct{}) []*RouteFirewallRule {
|
||||||
|
routesFirewallRules := make([]*RouteFirewallRule, 0)
|
||||||
|
|
||||||
|
enabledRoutes, _ := b.getRoutingPeerRoutes(peerID)
|
||||||
|
for _, route := range enabledRoutes {
|
||||||
|
if len(route.AccessControlGroups) == 0 {
|
||||||
|
defaultPermit := getDefaultPermit(route)
|
||||||
|
routesFirewallRules = append(routesFirewallRules, defaultPermit...)
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
|
||||||
|
distributionPeers := b.getDistributionGroupsPeers(route)
|
||||||
|
|
||||||
|
for _, accessGroup := range route.AccessControlGroups {
|
||||||
|
policies := b.getAllRoutePoliciesFromGroups([]string{accessGroup})
|
||||||
|
|
||||||
|
rules := b.getRouteFirewallRules(peerID, policies, route, validatedPeersMap, distributionPeers, account)
|
||||||
|
routesFirewallRules = append(routesFirewallRules, rules...)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return routesFirewallRules
|
||||||
|
}
|
||||||
|
|
||||||
|
func (b *NetworkMapBuilder) getDistributionGroupsPeers(route *route.Route) map[string]struct{} {
|
||||||
|
distPeers := make(map[string]struct{})
|
||||||
|
for _, id := range route.Groups {
|
||||||
|
groupPeers := b.cache.groupToPeers[id]
|
||||||
|
if groupPeers == nil {
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
|
||||||
|
for _, pID := range groupPeers {
|
||||||
|
distPeers[pID] = struct{}{}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return distPeers
|
||||||
|
}
|
||||||
|
|
||||||
|
func (b *NetworkMapBuilder) getAllRoutePoliciesFromGroups(accessControlGroups []string) []*Policy {
|
||||||
|
routePolicies := make(map[string]*Policy)
|
||||||
|
|
||||||
|
for _, groupID := range accessControlGroups {
|
||||||
|
candidatePolicies := b.cache.groupToPolicies[groupID]
|
||||||
|
|
||||||
|
for _, policy := range candidatePolicies {
|
||||||
|
if _, found := routePolicies[policy.ID]; found {
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
policyRules := b.cache.policyToRules[policy.ID]
|
||||||
|
for _, rule := range policyRules {
|
||||||
|
if slices.Contains(rule.Destinations, groupID) {
|
||||||
|
routePolicies[policy.ID] = policy
|
||||||
|
break
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return maps.Values(routePolicies)
|
||||||
|
}
|
||||||
|
|
||||||
|
func (b *NetworkMapBuilder) getRouteFirewallRules(
|
||||||
|
peerID string, policies []*Policy, route *route.Route, validatedPeersMap map[string]struct{},
|
||||||
|
distributionPeers map[string]struct{}, account *Account,
|
||||||
|
) []*RouteFirewallRule {
|
||||||
|
ctx := context.Background()
|
||||||
|
var fwRules []*RouteFirewallRule
|
||||||
|
for _, policy := range policies {
|
||||||
|
if !policy.Enabled {
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
|
||||||
|
for _, rule := range policy.Rules {
|
||||||
|
if !rule.Enabled {
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
|
||||||
|
rulePeers := b.getRulePeers(rule, policy.SourcePostureChecks, peerID, distributionPeers, validatedPeersMap, account)
|
||||||
|
|
||||||
|
rules := generateRouteFirewallRules(ctx, route, rule, rulePeers, FirewallRuleDirectionIN)
|
||||||
|
fwRules = append(fwRules, rules...)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return fwRules
|
||||||
|
}
|
||||||
|
|
||||||
|
func (b *NetworkMapBuilder) getRulePeers(
|
||||||
|
rule *PolicyRule, postureChecks []string, peerID string, distributionPeers map[string]struct{},
|
||||||
|
validatedPeersMap map[string]struct{}, account *Account,
|
||||||
|
) []*nbpeer.Peer {
|
||||||
|
distPeersWithPolicy := make(map[string]struct{})
|
||||||
|
|
||||||
|
for _, id := range rule.Sources {
|
||||||
|
groupPeers := b.cache.groupToPeers[id]
|
||||||
|
if groupPeers == nil {
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
|
||||||
|
for _, pID := range groupPeers {
|
||||||
|
if pID == peerID {
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
_, distPeer := distributionPeers[pID]
|
||||||
|
_, valid := validatedPeersMap[pID]
|
||||||
|
|
||||||
|
if distPeer && valid && account.validatePostureChecksOnPeer(context.Background(), postureChecks, pID) {
|
||||||
|
distPeersWithPolicy[pID] = struct{}{}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
distributionGroupPeers := make([]*nbpeer.Peer, 0, len(distPeersWithPolicy))
|
||||||
|
for pID := range distPeersWithPolicy {
|
||||||
|
peer := b.cache.globalPeers[pID]
|
||||||
|
if peer == nil {
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
distributionGroupPeers = append(distributionGroupPeers, peer)
|
||||||
|
}
|
||||||
|
return distributionGroupPeers
|
||||||
|
}
|
||||||
|
|
||||||
func (b *NetworkMapBuilder) buildPeerDNSView(account *Account, peerID string) {
|
func (b *NetworkMapBuilder) buildPeerDNSView(account *Account, peerID string) {
|
||||||
dnsManagementStatus := account.getPeerDNSManagementStatus(peerID)
|
peerGroups := b.cache.peerToGroups[peerID]
|
||||||
|
checkGroups := make(map[string]struct{}, len(peerGroups))
|
||||||
|
for _, groupID := range peerGroups {
|
||||||
|
checkGroups[groupID] = struct{}{}
|
||||||
|
}
|
||||||
|
|
||||||
|
dnsManagementStatus := b.getPeerDNSManagementStatus(account, checkGroups)
|
||||||
dnsConfig := &nbdns.Config{
|
dnsConfig := &nbdns.Config{
|
||||||
ServiceEnable: dnsManagementStatus,
|
ServiceEnable: dnsManagementStatus,
|
||||||
}
|
}
|
||||||
|
|
||||||
if dnsManagementStatus {
|
if dnsManagementStatus {
|
||||||
dnsConfig.NameServerGroups = getPeerNSGroups(account, peerID)
|
dnsConfig.NameServerGroups = b.getPeerNSGroups(account, peerID, checkGroups)
|
||||||
}
|
}
|
||||||
|
|
||||||
b.cache.peerDNS[peerID] = dnsConfig
|
b.cache.peerDNS[peerID] = dnsConfig
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func (b *NetworkMapBuilder) getPeerDNSManagementStatus(account *Account, checkGroups map[string]struct{}) bool {
|
||||||
|
|
||||||
|
enabled := true
|
||||||
|
for _, groupID := range account.DNSSettings.DisabledManagementGroups {
|
||||||
|
_, found := checkGroups[groupID]
|
||||||
|
if found {
|
||||||
|
enabled = false
|
||||||
|
break
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return enabled
|
||||||
|
}
|
||||||
|
|
||||||
|
func (b *NetworkMapBuilder) getPeerNSGroups(account *Account, peerID string, checkGroups map[string]struct{}) []*nbdns.NameServerGroup {
|
||||||
|
var peerNSGroups []*nbdns.NameServerGroup
|
||||||
|
|
||||||
|
for _, nsGroup := range account.NameServerGroups {
|
||||||
|
if !nsGroup.Enabled {
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
for _, gID := range nsGroup.Groups {
|
||||||
|
_, found := checkGroups[gID]
|
||||||
|
if found {
|
||||||
|
peer := b.cache.globalPeers[peerID]
|
||||||
|
if !peerIsNameserver(peer, nsGroup) {
|
||||||
|
peerNSGroups = append(peerNSGroups, nsGroup.Copy())
|
||||||
|
break
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return peerNSGroups
|
||||||
|
}
|
||||||
|
|
||||||
func (b *NetworkMapBuilder) UpdateAccountPointer(account *Account) {
|
func (b *NetworkMapBuilder) UpdateAccountPointer(account *Account) {
|
||||||
b.account.Store(account)
|
b.account.Store(account)
|
||||||
}
|
}
|
||||||
@@ -777,10 +936,8 @@ func (b *NetworkMapBuilder) generateRouteFirewallRuleID(rule *RouteFirewallRule)
|
|||||||
|
|
||||||
func (b *NetworkMapBuilder) isPeerInGroups(groupIDs []string, peerGroups []string) bool {
|
func (b *NetworkMapBuilder) isPeerInGroups(groupIDs []string, peerGroups []string) bool {
|
||||||
for _, groupID := range groupIDs {
|
for _, groupID := range groupIDs {
|
||||||
for _, peerGroupID := range peerGroups {
|
if slices.Contains(peerGroups, groupID) {
|
||||||
if groupID == peerGroupID {
|
return true
|
||||||
return true
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return false
|
return false
|
||||||
@@ -814,15 +971,6 @@ func (b *NetworkMapBuilder) isPeerRouter(account *Account, peerID string) bool {
|
|||||||
return false
|
return false
|
||||||
}
|
}
|
||||||
|
|
||||||
func (a *Account) GetNetworkResource(resourceID string) *resourceTypes.NetworkResource {
|
|
||||||
for _, resource := range a.NetworkResources {
|
|
||||||
if resource.ID == resourceID {
|
|
||||||
return resource
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return nil
|
|
||||||
}
|
|
||||||
|
|
||||||
type ViewDelta struct {
|
type ViewDelta struct {
|
||||||
AddedPeerIDs []string
|
AddedPeerIDs []string
|
||||||
RemovedPeerIDs []string
|
RemovedPeerIDs []string
|
||||||
@@ -844,7 +992,7 @@ func (b *NetworkMapBuilder) OnPeerAddedIncremental(peerID string) error {
|
|||||||
|
|
||||||
b.cache.globalPeers[peerID] = peer
|
b.cache.globalPeers[peerID] = peer
|
||||||
|
|
||||||
peerGroups := b.updateGroupIndexesForNewPeer(account, peerID)
|
peerGroups := b.updateIndexesForNewPeer(account, peerID)
|
||||||
|
|
||||||
b.buildPeerACLView(account, peerID)
|
b.buildPeerACLView(account, peerID)
|
||||||
b.buildPeerRoutesView(account, peerID)
|
b.buildPeerRoutesView(account, peerID)
|
||||||
@@ -855,32 +1003,38 @@ func (b *NetworkMapBuilder) OnPeerAddedIncremental(peerID string) error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func (b *NetworkMapBuilder) updateGroupIndexesForNewPeer(account *Account, peerID string) []string {
|
func (b *NetworkMapBuilder) updateIndexesForNewPeer(account *Account, peerID string) []string {
|
||||||
peerGroups := make([]string, 0)
|
peerGroups := make([]string, 0)
|
||||||
|
|
||||||
for groupID, group := range account.Groups {
|
for groupID, group := range account.Groups {
|
||||||
for _, pid := range group.Peers {
|
if slices.Contains(group.Peers, peerID) {
|
||||||
if pid == peerID {
|
if !slices.Contains(b.cache.groupToPeers[groupID], peerID) {
|
||||||
if !slices.Contains(b.cache.groupToPeers[groupID], peerID) {
|
b.cache.groupToPeers[groupID] = append(b.cache.groupToPeers[groupID], peerID)
|
||||||
b.cache.groupToPeers[groupID] = append(b.cache.groupToPeers[groupID], peerID)
|
|
||||||
}
|
|
||||||
peerGroups = append(peerGroups, groupID)
|
|
||||||
break
|
|
||||||
}
|
}
|
||||||
|
peerGroups = append(peerGroups, groupID)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
b.cache.peerToGroups[peerID] = peerGroups
|
b.cache.peerToGroups[peerID] = peerGroups
|
||||||
|
|
||||||
|
for _, r := range account.Routes {
|
||||||
|
if !r.Enabled || b.cache.globalRoutes[r.ID] != nil {
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
for _, groupID := range r.Groups {
|
||||||
|
b.cache.groupToRoutes[groupID] = append(b.cache.groupToRoutes[groupID], r)
|
||||||
|
}
|
||||||
|
b.cache.globalRoutes[r.ID] = r
|
||||||
|
}
|
||||||
|
|
||||||
return peerGroups
|
return peerGroups
|
||||||
}
|
}
|
||||||
|
|
||||||
func (b *NetworkMapBuilder) incrementalUpdateAffectedPeers(account *Account, newPeerID string, peerGroups []string) {
|
func (b *NetworkMapBuilder) incrementalUpdateAffectedPeers(account *Account, newPeerID string, peerGroups []string) {
|
||||||
ctx := context.Background()
|
|
||||||
|
|
||||||
updates := b.calculateIncrementalUpdates(account, newPeerID, peerGroups)
|
updates := b.calculateIncrementalUpdates(account, newPeerID, peerGroups)
|
||||||
|
|
||||||
if b.isPeerRouter(account, newPeerID) {
|
if b.isPeerRouter(account, newPeerID) {
|
||||||
affectedByRoutes := b.findPeersAffectedByNewRouter(ctx, account, newPeerID, peerGroups)
|
affectedByRoutes := b.findPeersAffectedByNewRouter(account, newPeerID, peerGroups)
|
||||||
for affectedPeerID := range affectedByRoutes {
|
for affectedPeerID := range affectedByRoutes {
|
||||||
if affectedPeerID == newPeerID {
|
if affectedPeerID == newPeerID {
|
||||||
continue
|
continue
|
||||||
@@ -901,10 +1055,9 @@ func (b *NetworkMapBuilder) incrementalUpdateAffectedPeers(account *Account, new
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func (b *NetworkMapBuilder) findPeersAffectedByNewRouter(ctx context.Context, account *Account, newRouterID string, routerGroups []string) map[string]struct{} {
|
func (b *NetworkMapBuilder) findPeersAffectedByNewRouter(account *Account, newRouterID string, routerGroups []string) map[string]struct{} {
|
||||||
affected := make(map[string]struct{})
|
affected := make(map[string]struct{})
|
||||||
|
enabledRoutes, _ := b.getRoutingPeerRoutes(newRouterID)
|
||||||
enabledRoutes, _ := account.getRoutingPeerRoutes(ctx, newRouterID)
|
|
||||||
|
|
||||||
for _, route := range enabledRoutes {
|
for _, route := range enabledRoutes {
|
||||||
for _, distGroupID := range route.Groups {
|
for _, distGroupID := range route.Groups {
|
||||||
|
|||||||
Reference in New Issue
Block a user