Skip to content

Commit

Permalink
temp reconcile merged service and deployment
Browse files Browse the repository at this point in the history
Signed-off-by: Karol Szwaj <karol.szwaj@gmail.com>
  • Loading branch information
cnvergence committed Oct 13, 2023
1 parent 3d370dd commit ee1fbab
Show file tree
Hide file tree
Showing 5 changed files with 67 additions and 15 deletions.
6 changes: 3 additions & 3 deletions internal/infrastructure/kubernetes/proxy/resource.go
Original file line number Diff line number Diff line change
Expand Up @@ -57,8 +57,8 @@ func ExpectedResourceHashedName(name string) string {
return fmt.Sprintf("%s-%s", config.EnvoyPrefix, hashedName)
}

// ExpectedServiceHashedName returns expected service name with max length of 15 characters.
func ExpectedServiceHashedName(name string) string {
// ExpectedContainerPortHashedName returns expected service name with max length of 15 characters.
func ExpectedContainerPortHashedName(name string) string {
if len(name) > 15 {
hashedName := providerutils.HashString(name)
listenerName := strings.Split(name, "-")
Expand Down Expand Up @@ -114,7 +114,7 @@ func expectedProxyContainers(infra *ir.ProxyInfra, deploymentConfig *egv1a1.Kube
return nil, fmt.Errorf("invalid protocol %q", p.Protocol)
}
port := corev1.ContainerPort{
Name: ExpectedServiceHashedName(p.Name),
Name: ExpectedContainerPortHashedName(p.Name),
ContainerPort: p.ContainerPort,
Protocol: protocol,
}
Expand Down
15 changes: 11 additions & 4 deletions internal/provider/kubernetes/controller.go
Original file line number Diff line number Diff line change
Expand Up @@ -403,16 +403,20 @@ func (r *gatewayAPIReconciler) statusUpdateForGateway(ctx context.Context, gtw *
if r.statusUpdater == nil {
return
}

var merged bool
res, _ := r.resources.GatewayAPIResources.Load(string(gtw.Spec.GatewayClassName))
if res.EnvoyProxy != nil && res.EnvoyProxy.Spec.MergeGateways != nil && *res.EnvoyProxy.Spec.MergeGateways {
merged = true
}
// Get deployment
deploy, err := r.envoyDeploymentForGateway(ctx, gtw)
deploy, err := r.envoyDeploymentForGateway(ctx, gtw, merged)
if err != nil {
r.log.Info("failed to get Deployment for gateway",
"namespace", gtw.Namespace, "name", gtw.Name)
}

// Get service
svc, err := r.envoyServiceForGateway(ctx, gtw)
svc, err := r.envoyServiceForGateway(ctx, gtw, merged)
if err != nil {
r.log.Info("failed to get Service for gateway",
"namespace", gtw.Namespace, "name", gtw.Name)
Expand Down Expand Up @@ -1317,7 +1321,10 @@ func (r *gatewayAPIReconciler) watchResources(ctx context.Context, mgr manager.M
}

// Watch Gateway CRUDs and reconcile affected GatewayClass.
gPredicates := []predicate.Predicate{predicate.NewPredicateFuncs(r.validateGatewayForReconcile)}
gPredicates := []predicate.Predicate{
predicate.NewPredicateFuncs(r.validateGatewayForReconcile),
predicate.GenerationChangedPredicate{},
}
if len(r.namespaceLabels) != 0 {
gPredicates = append(gPredicates, predicate.NewPredicateFuncs(r.hasMatchingNamespaceLabels))
}
Expand Down
12 changes: 10 additions & 2 deletions internal/provider/kubernetes/helpers.go
Original file line number Diff line number Diff line change
Expand Up @@ -197,12 +197,20 @@ func refsSecret(ref *gwapiv1b1.SecretObjectReference) bool {
(ref.Kind == nil || *ref.Kind == gatewayapi.KindSecret)
}

func infraServiceName(gateway *gwapiv1b1.Gateway) string {
func infraServiceName(gateway *gwapiv1b1.Gateway, merged bool) string {
if merged {
infraName := utils.GetHashedName(string(gateway.Spec.GatewayClassName))
return fmt.Sprintf("%s-%s", config.EnvoyPrefix, infraName)
}
infraName := utils.GetHashedName(fmt.Sprintf("%s/%s", gateway.Namespace, gateway.Name))
return fmt.Sprintf("%s-%s", config.EnvoyPrefix, infraName)
}

func infraDeploymentName(gateway *gwapiv1b1.Gateway) string {
func infraDeploymentName(gateway *gwapiv1b1.Gateway, merged bool) string {
if merged {
infraName := utils.GetHashedName(string(gateway.Spec.GatewayClassName))
return fmt.Sprintf("%s-%s", config.EnvoyPrefix, infraName)
}
infraName := utils.GetHashedName(fmt.Sprintf("%s/%s", gateway.Namespace, gateway.Name))
return fmt.Sprintf("%s-%s", config.EnvoyPrefix, infraName)
}
Expand Down
47 changes: 42 additions & 5 deletions internal/provider/kubernetes/predicates.go
Original file line number Diff line number Diff line change
Expand Up @@ -168,7 +168,20 @@ func (r *gatewayAPIReconciler) validateServiceForReconcile(obj client.Object) bo
r.log.Info("unexpected object type, bypassing reconciliation", "object", obj)
return false
}
labels := svc.GetLabels()
gclass, ok := labels[gatewayapi.OwningGatewayClassLabel]
if ok {
gtw := r.findGateways(ctx, gclass)
if len(gtw.Items) != 0 {
for _, gw := range gtw.Items {
gw := gw
r.statusUpdateForGateway(ctx, &gw)
}
}

nsName := utils.NamespacedName(svc)
return r.isRouteReferencingBackend(&nsName)
}
// Check if the Service belongs to a Gateway, if so, update the Gateway status.
gtw := r.findOwningGateway(ctx, svc.GetLabels())
if gtw != nil {
Expand All @@ -180,6 +193,19 @@ func (r *gatewayAPIReconciler) validateServiceForReconcile(obj client.Object) bo
return r.isRouteReferencingBackend(&nsName)
}

// findGateways attempts finds a GatewayList using accepted GatewayClass name.
func (r *gatewayAPIReconciler) findGateways(ctx context.Context, class string) *gwapiv1b1.GatewayList {
gatewayList := &gwapiv1b1.GatewayList{}
if err := r.client.List(ctx, gatewayList, &client.ListOptions{
FieldSelector: fields.OneTermEqualSelector(classGatewayIndex, class),
}); err != nil {
r.log.Info("no associated Gateways found for GatewayClass", "name", class)
return nil
}

return gatewayList
}

// validateServiceImportForReconcile tries finding the owning Gateway of the ServiceImport
// if it exists, finds the Gateway's Deployment, and further updates the Gateway
// status Ready condition. All Services are pushed for reconciliation.
Expand Down Expand Up @@ -286,7 +312,18 @@ func (r *gatewayAPIReconciler) validateDeploymentForReconcile(obj client.Object)
r.log.Info("unexpected object type, bypassing reconciliation", "object", obj)
return false
}

labels := deployment.GetLabels()
gclass, ok := labels[gatewayapi.OwningGatewayClassLabel]
if ok {
gtw := r.findGateways(ctx, gclass)
if len(gtw.Items) != 0 {
for _, gw := range gtw.Items {
gw := gw
r.statusUpdateForGateway(ctx, &gw)
}
}
return false
}
// Only deployments in the configured namespace should be reconciled.
if deployment.Namespace == r.namespace {
// Check if the deployment belongs to a Gateway, if so, update the Gateway status.
Expand Down Expand Up @@ -374,10 +411,10 @@ func (r *gatewayAPIReconciler) filterHTTPRoutesByNamespaceLabels(httpRoutes []gw
}

// envoyDeploymentForGateway returns the Envoy Deployment, returning nil if the Deployment doesn't exist.
func (r *gatewayAPIReconciler) envoyDeploymentForGateway(ctx context.Context, gateway *gwapiv1b1.Gateway) (*appsv1.Deployment, error) {
func (r *gatewayAPIReconciler) envoyDeploymentForGateway(ctx context.Context, gateway *gwapiv1b1.Gateway, merged bool) (*appsv1.Deployment, error) {
key := types.NamespacedName{
Namespace: r.namespace,
Name: infraDeploymentName(gateway),
Name: infraDeploymentName(gateway, merged),
}
deployment := new(appsv1.Deployment)
if err := r.client.Get(ctx, key, deployment); err != nil {
Expand All @@ -390,10 +427,10 @@ func (r *gatewayAPIReconciler) envoyDeploymentForGateway(ctx context.Context, ga
}

// envoyServiceForGateway returns the Envoy service, returning nil if the service doesn't exist.
func (r *gatewayAPIReconciler) envoyServiceForGateway(ctx context.Context, gateway *gwapiv1b1.Gateway) (*corev1.Service, error) {
func (r *gatewayAPIReconciler) envoyServiceForGateway(ctx context.Context, gateway *gwapiv1b1.Gateway, merged bool) (*corev1.Service, error) {
key := types.NamespacedName{
Namespace: r.namespace,
Name: infraServiceName(gateway),
Name: infraServiceName(gateway, merged),
}
svc := new(corev1.Service)
if err := r.client.Get(ctx, key, svc); err != nil {
Expand Down
2 changes: 1 addition & 1 deletion internal/provider/kubernetes/predicates_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -334,7 +334,7 @@ func TestValidateServiceForReconcile(t *testing.T) {
configs: []client.Object{
test.GetGatewayClass("test-gc", v1alpha1.GatewayControllerName),
sampleGateway,
test.GetGatewayDeployment(types.NamespacedName{Name: infraDeploymentName(sampleGateway)}, nil),
test.GetGatewayDeployment(types.NamespacedName{Name: infraDeploymentName(sampleGateway, false)}, nil),
},
service: test.GetService(types.NamespacedName{Name: "service"}, map[string]string{
gatewayapi.OwningGatewayNameLabel: "scheduled-status-test",
Expand Down

0 comments on commit ee1fbab

Please sign in to comment.