func()

in pkg/trait/knative_service.go [172:310]


func (t *knativeServiceTrait) getServiceFor(e *Environment) (*serving.Service, error) {
	serviceAnnotations := make(map[string]string)
	if e.Integration.Annotations != nil {
		for k, v := range e.Integration.Annotations {
			serviceAnnotations[k] = v
		}
	}
	// Set Knative rollout
	if t.RolloutDuration != "" {
		serviceAnnotations[knativeServingRolloutDurationAnnotation] = t.RolloutDuration
	}
	if t.Annotations != nil {
		for k, v := range t.Annotations {
			serviceAnnotations[k] = v
		}
	}

	revisionAnnotations := make(map[string]string)
	if e.Integration.Annotations != nil {
		for k, v := range filterTransferableAnnotations(e.Integration.Annotations) {
			revisionAnnotations[k] = v
		}
	}
	// Set Knative auto-scaling
	if t.Class != "" {
		revisionAnnotations[knativeServingClassAnnotation] = t.Class
	}
	if t.Metric != "" {
		revisionAnnotations[knativeServingMetricAnnotation] = t.Metric
	}
	if t.Target != nil {
		revisionAnnotations[knativeServingTargetAnnotation] = strconv.Itoa(*t.Target)
	}
	if t.MinScale != nil && *t.MinScale > 0 {
		revisionAnnotations[knativeServingMinScaleAnnotation] = strconv.Itoa(*t.MinScale)
	}
	if t.MaxScale != nil && *t.MaxScale > 0 {
		revisionAnnotations[knativeServingMaxScaleAnnotation] = strconv.Itoa(*t.MaxScale)
	}

	serviceLabels := map[string]string{
		v1.IntegrationLabel: e.Integration.Name,
		// Make sure the Eventing webhook will select the source resource,
		// in order to inject the sink information.
		// This is necessary for Knative environments, that are configured
		// with SINK_BINDING_SELECTION_MODE=inclusion.
		// See:
		// - https://knative.dev/v1.3-docs/eventing/custom-event-source/sinkbinding/create-a-sinkbinding/#optional-choose-sinkbinding-namespace-selection-behavior
		// - https://github.com/knative/operator/blob/release-1.2/docs/configuration.md#specsinkbindingselectionmode
		"bindings.knative.dev/include": boolean.TrueString,
	}
	if t.Visibility != "" {
		serviceLabels[knativeServingVisibilityLabel] = t.Visibility
	}

	svc := serving.Service{
		TypeMeta: metav1.TypeMeta{
			Kind:       "Service",
			APIVersion: serving.SchemeGroupVersion.String(),
		},
		ObjectMeta: metav1.ObjectMeta{
			Name:        e.Integration.Name,
			Namespace:   e.Integration.Namespace,
			Labels:      serviceLabels,
			Annotations: serviceAnnotations,
		},
		Spec: serving.ServiceSpec{
			ConfigurationSpec: serving.ConfigurationSpec{
				Template: serving.RevisionTemplateSpec{
					ObjectMeta: metav1.ObjectMeta{
						Labels: map[string]string{
							v1.IntegrationLabel: e.Integration.Name,
						},
						Annotations: revisionAnnotations,
					},
					Spec: serving.RevisionSpec{
						PodSpec: corev1.PodSpec{
							ServiceAccountName: e.Integration.Spec.ServiceAccountName,
						},
					},
				},
			},
		},
	}

	if t.TimeoutSeconds != nil {
		svc.Spec.ConfigurationSpec.Template.Spec.TimeoutSeconds = t.TimeoutSeconds
	}
	replicas := e.Integration.Spec.Replicas

	isUpdateRequired := false
	minScale, ok := svc.Spec.Template.Annotations[knativeServingMinScaleAnnotation]
	if ok {
		mnScale, err := strconv.Atoi(minScale)
		if err != nil {
			return nil, err
		}
		if replicas == nil || mnScale != int(*replicas) {
			isUpdateRequired = true
		}
	} else if replicas != nil {
		isUpdateRequired = true
	}

	maxScale, ok := svc.Spec.Template.Annotations[knativeServingMaxScaleAnnotation]
	if ok {
		mxScale, err := strconv.Atoi(maxScale)
		if err != nil {
			return nil, err
		}
		if replicas == nil || mxScale != int(*replicas) {
			isUpdateRequired = true
		}
	} else if replicas != nil {
		isUpdateRequired = true
	}

	//nolint:nestif
	if isUpdateRequired {
		if replicas == nil {
			if t.MinScale != nil && *t.MinScale > 0 {
				svc.Spec.Template.Annotations[knativeServingMinScaleAnnotation] = strconv.Itoa(*t.MinScale)
			} else {
				delete(svc.Spec.Template.Annotations, knativeServingMinScaleAnnotation)
			}
			if t.MaxScale != nil && *t.MaxScale > 0 {
				svc.Spec.Template.Annotations[knativeServingMaxScaleAnnotation] = strconv.Itoa(*t.MaxScale)
			} else {
				delete(svc.Spec.Template.Annotations, knativeServingMaxScaleAnnotation)
			}
		} else {
			scale := strconv.Itoa(int(*replicas))
			svc.Spec.Template.Annotations[knativeServingMinScaleAnnotation] = scale
			svc.Spec.Template.Annotations[knativeServingMaxScaleAnnotation] = scale
		}
	}

	return &svc, nil
}