func()

in internal/controllers/symphony/controller.go [156:218]


func (c *symphonyController) reconcileForward(ctx context.Context, symph *apiv1.Symphony, comps *apiv1.CompositionList) (modified bool, err error) {
	logger := logr.FromContextOrDiscard(ctx)

	for _, variation := range symph.Spec.Variations {
		variation := variation
		comp := &apiv1.Composition{}
		comp.Namespace = symph.Namespace
		comp.GenerateName = variation.Synthesizer.Name + "-"
		comp.Spec.Bindings = getBindings(symph, &variation)
		comp.Spec.Synthesizer = variation.Synthesizer
		comp.Spec.SynthesisEnv = getSynthesisEnv(symph, &variation)
		comp.Labels = variation.Labels
		comp.Annotations = variation.Annotations
		err := controllerutil.SetControllerReference(symph, comp, c.client.Scheme())
		if err != nil {
			return false, fmt.Errorf("setting composition's controller: %w", err)
		}
		logger := logger.WithValues("compositionName", comp.Name, "compositionNamespace", comp.Namespace)

		// Compose missing variations
		idx := slices.IndexFunc(comps.Items, func(existing apiv1.Composition) bool {
			return existing.Spec.Synthesizer.Name == variation.Synthesizer.Name
		})
		if idx == -1 {
			err := c.noCacheClient.List(ctx, comps, client.InNamespace(symph.Namespace))
			if err != nil {
				return false, fmt.Errorf("listing existing compositions without cache: %w", err)
			}
			for _, cur := range comps.Items {
				owner := metav1.GetControllerOf(&cur)
				if owner != nil && owner.UID == symph.UID && cur.Spec.Synthesizer.Name == variation.Synthesizer.Name {
					return false, fmt.Errorf("stale cache - composition already exists")
				}
			}

			err = c.client.Create(ctx, comp)
			if k8serrors.IsForbidden(err) && k8serrors.HasStatusCause(err, corev1.NamespaceTerminatingCause) {
				logger.V(0).Info("skipping composition creation because the namespace is being terminated")
				return false, nil
			}
			if err != nil {
				return false, fmt.Errorf("creating composition: %w", err)
			}
			logger.V(0).Info("created composition for symphony")
			return true, nil
		}

		// Diff and update if needed
		existing := comps.Items[idx]
		if equality.Semantic.DeepEqual(comp.Spec, existing.Spec) && !coalesceMetadata(&variation, &existing) {
			continue // already matches
		}
		existing.Spec = comp.Spec
		err = c.client.Update(ctx, &existing)
		if err != nil {
			return false, fmt.Errorf("updating existing composition: %w", err)
		}
		logger.V(0).Info("updated composition because its variation changed")
		return true, nil
	}

	return false, nil
}