Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

fix: network status in ForeignCluster resource #2783

Merged
merged 1 commit into from
Oct 25, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
5 changes: 4 additions & 1 deletion apis/core/v1beta1/foreigncluster_types.go
Original file line number Diff line number Diff line change
Expand Up @@ -96,8 +96,11 @@ const (
APIServerStatusCondition ConditionType = "APIServerStatus"

// NETWORKING
// NetworkConfigurationStatusCondition tells whether the network configuration of the peer cluster is present.
NetworkConfigurationStatusCondition ConditionType = "NetworkConfigurationStatus"
// NetworkConnectionStatusCondition shows the network connection status.
NetworkConnectionStatusCondition ConditionType = "NetworkConnectionStatus"
NetworkGatewayPresenceCondition ConditionType = "NetworkGatewayPresence"
// NetworkGatewayServerStatusCondition shows the network gateway server status.
NetworkGatewayServerStatusCondition ConditionType = "NetworkGatewayServerStatus"
// NetworkGatewayClientStatusCondition shows the network gateway client status.
Expand Down Expand Up @@ -139,7 +142,7 @@ const (
// Condition contains details about state of a.
type Condition struct {
// Type of the condition.
// +kubebuilder:validation:Enum="APIServerStatus";"NetworkConnectionStatus";"NetworkGatewayServerStatus";"NetworkGatewayClientStatus";"AuthIdentityControlPlaneStatus";"AuthTenantStatus";"OffloadingVirtualNodeStatus";"OffloadingNodeStatus"
// +kubebuilder:validation:Enum="APIServerStatus";"NetworkConnectionStatus";"NetworkGatewayServerStatus";"NetworkGatewayClientStatus";"NetworkGatewayPresence";"NetworkConfigurationStatus";"AuthIdentityControlPlaneStatus";"AuthTenantStatus";"OffloadingVirtualNodeStatus";"OffloadingNodeStatus"
//
//nolint:lll // ignore long lines given by Kubebuilder marker annotations
Type ConditionType `json:"type"`
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -107,6 +107,8 @@ spec:
- NetworkConnectionStatus
- NetworkGatewayServerStatus
- NetworkGatewayClientStatus
- NetworkGatewayPresence
- NetworkConfigurationStatus
- AuthIdentityControlPlaneStatus
- AuthTenantStatus
- OffloadingVirtualNodeStatus
Expand Down Expand Up @@ -170,6 +172,8 @@ spec:
- NetworkConnectionStatus
- NetworkGatewayServerStatus
- NetworkGatewayClientStatus
- NetworkGatewayPresence
- NetworkConfigurationStatus
- AuthIdentityControlPlaneStatus
- AuthTenantStatus
- OffloadingVirtualNodeStatus
Expand Down Expand Up @@ -231,6 +235,8 @@ spec:
- NetworkConnectionStatus
- NetworkGatewayServerStatus
- NetworkGatewayClientStatus
- NetworkGatewayPresence
- NetworkConfigurationStatus
- AuthIdentityControlPlaneStatus
- AuthTenantStatus
- OffloadingVirtualNodeStatus
Expand Down Expand Up @@ -292,6 +298,8 @@ spec:
- NetworkConnectionStatus
- NetworkGatewayServerStatus
- NetworkGatewayClientStatus
- NetworkGatewayPresence
- NetworkConfigurationStatus
- AuthIdentityControlPlaneStatus
- AuthTenantStatus
- OffloadingVirtualNodeStatus
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,9 @@ const (
connectionErrorReason = "ConnectionError"
connectionErrorMessage = "The network connection with the foreign cluster is in error"

connectionMissingReason = "ConnectionMissing"
connectionMissingMessage = "There is no network connection with the foreign cluster"

gatewaysReadyReason = "GatewaysReady"
gatewaysReadyMessage = "All gateway replicas are ready"

Expand All @@ -33,6 +36,18 @@ const (
gatewaysNotReadyReason = "GatewaysNotReady"
gatewaysNotReadyMessage = "All gateway replicas are not ready"

gatewayMissingReason = "GatewayMissing"
gatewayMissingMessage = "The gateway resource connecting to the foreign cluster is missing"

gatewayPresentReason = "GatewayPresence"
gatewayPresentMessage = "There is a gateway connecting to the foreign cluster"

networkConfigurationPresenceReason = "NetworkConfigurationPresence"
networkConfigurationPresenceMessage = "The network configuration of the peer cluster is present"

networkConfigurationMissingReason = "NetworkConfigurationMissing"
networkConfigurationMissingMessage = "The network configuration for the connection with the foreign cluster is missing"

tenantReadyReason = "TenantReady"
tenantReadyMessage = "The tenant has been successfully configured"

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -170,6 +170,7 @@ func (r *ForeignClusterReconciler) SetupWithManager(mgr ctrl.Manager, workers in

return ctrl.NewControllerManagedBy(mgr).Named(consts.CtrlForeignCluster).
For(&liqov1beta1.ForeignCluster{}, builder.WithPredicates(foreignClusterPredicate)).
Watches(&networkingv1beta1.Configuration{}, handler.EnqueueRequestsFromMapFunc(r.foreignclusterEnqueuer)).
Watches(&networkingv1beta1.Connection{}, handler.EnqueueRequestsFromMapFunc(r.foreignclusterEnqueuer)).
Watches(&networkingv1beta1.GatewayServer{}, handler.EnqueueRequestsFromMapFunc(r.foreignclusterEnqueuer)).
Watches(&networkingv1beta1.GatewayClient{}, handler.EnqueueRequestsFromMapFunc(r.foreignclusterEnqueuer)).
Expand Down
120 changes: 103 additions & 17 deletions pkg/liqo-controller-manager/core/foreigncluster-controller/status.go
Original file line number Diff line number Diff line change
Expand Up @@ -35,6 +35,12 @@ import (
"github.com/liqotech/liqo/pkg/utils/pod"
)

type statusException struct {
liqov1beta1.ConditionStatusType
Reason string
Message string
}

func (r *ForeignClusterReconciler) clearStatusExceptConditions(foreignCluster *liqov1beta1.ForeignCluster) {
foreignCluster.Status = liqov1beta1.ForeignClusterStatus{
Role: liqov1beta1.UnknownRole,
Expand All @@ -56,20 +62,20 @@ func (r *ForeignClusterReconciler) clearStatusExceptConditions(foreignCluster *l
}
}

func (r *ForeignClusterReconciler) handleNetworkingModuleStatus(ctx context.Context,
fc *liqov1beta1.ForeignCluster, moduleEnabled bool) error {
if !moduleEnabled {
clearModule(&fc.Status.Modules.Networking)
return nil
}

func (r *ForeignClusterReconciler) handleConnectionStatus(ctx context.Context,
fc *liqov1beta1.ForeignCluster, statusExceptions map[liqov1beta1.ConditionType]statusException) error {
clusterID := fc.Spec.ClusterID

connection, err := getters.GetConnectionByClusterID(ctx, r.Client, string(clusterID))
switch {
case errors.IsNotFound(err):
klog.V(6).Infof("Connection resource not found for ForeignCluster %q", clusterID)
fcutils.DeleteModuleCondition(&fc.Status.Modules.Networking, liqov1beta1.NetworkConnectionStatusCondition)
statusExceptions[liqov1beta1.NetworkConnectionStatusCondition] = statusException{
ConditionStatusType: liqov1beta1.ConditionStatusNotReady,
Reason: connectionMissingReason,
Message: connectionMissingMessage,
}
case err != nil:
klog.Errorf("an error occurred while getting the Connection resource for the ForeignCluster %q: %s", clusterID, err)
return err
Expand All @@ -90,15 +96,38 @@ func (r *ForeignClusterReconciler) handleNetworkingModuleStatus(ctx context.Cont
connectionErrorReason, connectionErrorMessage)
}
}
return nil
}

func (r *ForeignClusterReconciler) handleGatewaysStatus(ctx context.Context,
fc *liqov1beta1.ForeignCluster, statusExceptions map[liqov1beta1.ConditionType]statusException) error {
clusterID := fc.Spec.ClusterID

gwServer, errServer := getters.GetGatewayServerByClusterID(ctx, r.Client, clusterID)
gwClient, errClient := getters.GetGatewayClientByClusterID(ctx, r.Client, clusterID)

if errors.IsNotFound(errServer) && errors.IsNotFound(errClient) {
klog.V(6).Infof("Both GatewayServer and GatewayClient resources not found for ForeignCluster %q", clusterID)
statusExceptions[liqov1beta1.NetworkGatewayPresenceCondition] = statusException{
ConditionStatusType: liqov1beta1.ConditionStatusNotReady,
Reason: gatewayMissingReason,
Message: gatewayMissingMessage,
}
} else {
statusExceptions[liqov1beta1.NetworkGatewayPresenceCondition] = statusException{
ConditionStatusType: liqov1beta1.ConditionStatusReady,
Reason: gatewayPresentReason,
Message: gatewayPresentMessage,
}
}

gwServer, err := getters.GetGatewayServerByClusterID(ctx, r.Client, clusterID)
switch {
case errors.IsNotFound(err):
case errors.IsNotFound(errServer):
klog.V(6).Infof("GatewayServer resource not found for ForeignCluster %q", clusterID)
fcutils.DeleteModuleCondition(&fc.Status.Modules.Networking, liqov1beta1.NetworkGatewayServerStatusCondition)
case err != nil:
klog.Errorf("an error occurred while getting the GatewayServer resource for the ForeignCluster %q: %s", clusterID, err)
return err
case errServer != nil:
klog.Errorf("an error occurred while getting the GatewayServer resource for the ForeignCluster %q: %s", clusterID, errServer)
return errServer
default:
fcutils.EnableModuleNetworking(fc)
gwDeployment := &appsv1.Deployment{
Expand Down Expand Up @@ -127,14 +156,13 @@ func (r *ForeignClusterReconciler) handleNetworkingModuleStatus(ctx context.Cont
}
}

gwClient, err := getters.GetGatewayClientByClusterID(ctx, r.Client, clusterID)
switch {
case errors.IsNotFound(err):
case errors.IsNotFound(errClient):
klog.V(6).Infof("GatewayClient resource not found for ForeignCluster %q", clusterID)
fcutils.DeleteModuleCondition(&fc.Status.Modules.Networking, liqov1beta1.NetworkGatewayClientStatusCondition)
case err != nil:
klog.Errorf("an error occurred while getting the GatewayClient resource for the ForeignCluster %q: %s", clusterID, err)
return err
case errClient != nil:
klog.Errorf("an error occurred while getting the GatewayClient resource for the ForeignCluster %q: %s", clusterID, errClient)
return errClient
default:
fcutils.EnableModuleNetworking(fc)
gwDeployment := &appsv1.Deployment{
Expand Down Expand Up @@ -166,6 +194,64 @@ func (r *ForeignClusterReconciler) handleNetworkingModuleStatus(ctx context.Cont
return nil
}

func (r *ForeignClusterReconciler) handleNetworkConfigurationStatus(ctx context.Context,
fc *liqov1beta1.ForeignCluster, statusExceptions map[liqov1beta1.ConditionType]statusException) error {
clusterID := fc.Spec.ClusterID
_, err := getters.GetConfigurationByClusterID(ctx, r.Client, clusterID)
switch {
case errors.IsNotFound(err):
klog.V(6).Infof("Configuration resource not found for ForeignCluster %q", clusterID)
fcutils.DeleteModuleCondition(&fc.Status.Modules.Networking, liqov1beta1.NetworkConfigurationStatusCondition)
statusExceptions[liqov1beta1.NetworkConfigurationStatusCondition] = statusException{
ConditionStatusType: liqov1beta1.ConditionStatusNotReady,
Reason: networkConfigurationMissingReason,
Message: networkConfigurationMissingMessage,
}
case err != nil:
klog.Errorf("an error occurred while getting the Configuration resource for the ForeignCluster %q: %s", clusterID, err)
return err
default:
fcutils.EnableModuleNetworking(fc)
fcutils.EnsureModuleCondition(&fc.Status.Modules.Networking,
liqov1beta1.NetworkConfigurationStatusCondition, liqov1beta1.ConditionStatusReady,
networkConfigurationPresenceReason, networkConfigurationPresenceMessage)
}
return nil
}

func (r *ForeignClusterReconciler) handleNetworkingModuleStatus(ctx context.Context,
fc *liqov1beta1.ForeignCluster, moduleEnabled bool) error {
if !moduleEnabled {
clearModule(&fc.Status.Modules.Networking)
return nil
}

statusExceptions := map[liqov1beta1.ConditionType]statusException{}

if err := r.handleNetworkConfigurationStatus(ctx, fc, statusExceptions); err != nil {
return err
}

if err := r.handleGatewaysStatus(ctx, fc, statusExceptions); err != nil {
return err
}

if err := r.handleConnectionStatus(ctx, fc, statusExceptions); err != nil {
return err
}

// Write the exception in the status if the module is enabled
if fc.Status.Modules.Networking.Enabled {
for condition, condDescription := range statusExceptions {
fcutils.EnsureModuleCondition(&fc.Status.Modules.Networking,
condition, condDescription.ConditionStatusType,
condDescription.Reason, condDescription.Message)
}
}

return nil
}

func (r *ForeignClusterReconciler) handleAuthenticationModuleStatus(ctx context.Context,
fc *liqov1beta1.ForeignCluster, moduleEnabled bool, consumer, provider *bool) error {
if !moduleEnabled {
Expand Down