Set default Jenkins master pod resources requirements, this closes #4

This commit is contained in:
Tomasz Sęk 2019-01-15 12:04:50 +01:00
parent ae31901022
commit 8c4fa92ec5
No known key found for this signature in database
GPG Key ID: DC356D23F6A644D0
9 changed files with 80 additions and 31 deletions

View File

@ -142,7 +142,7 @@ test: ## Runs the go tests
.PHONY: e2e
CURRENT_DIRECTORY := $(shell pwd)
e2e: ## Runs e2e tests
e2e: build docker-build ## Runs e2e tests
@echo "+ $@"
@echo "Docker image: $(REPO):$(GITCOMMIT)"
cp deploy/service_account.yaml deploy/namespace-init.yaml

View File

@ -50,8 +50,6 @@ Run e2e tests with minikube:
```bash
make start-minikube
eval $(minikube docker-env)
make build
make docker-build
make e2e
```

View File

@ -315,7 +315,8 @@ func (r *ReconcileJenkinsBaseConfiguration) createJenkinsMasterPod(meta metav1.O
if currentJenkinsMasterPod != nil &&
!reflect.DeepEqual(r.jenkins.Spec.Master.Resources, currentJenkinsMasterPod.Spec.Containers[0].Resources) {
r.logger.Info(fmt.Sprintf("Jenkins pod resources have changed to '%+v', recreating pod", r.jenkins.Spec.Master.Resources))
r.logger.Info(fmt.Sprintf("Jenkins pod resources have changed, actual '%+v' required '%+v' - recreating pod",
currentJenkinsMasterPod.Spec.Containers[0].Resources, r.jenkins.Spec.Master.Resources))
recreatePod = true
}

View File

@ -13,6 +13,7 @@ import (
"github.com/go-logr/logr"
corev1 "k8s.io/api/core/v1"
"k8s.io/apimachinery/pkg/api/errors"
"k8s.io/apimachinery/pkg/api/resource"
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
"k8s.io/apimachinery/pkg/runtime"
"sigs.k8s.io/controller-runtime/pkg/client"
@ -116,7 +117,7 @@ func (r *ReconcileJenkins) reconcile(request reconcile.Request, logger logr.Logg
return reconcile.Result{}, err
}
err = r.setDefaults(jenkins)
err = r.setDefaults(jenkins, logger)
if err != nil {
return reconcile.Result{}, err
}
@ -180,9 +181,33 @@ func (r *ReconcileJenkins) buildLogger(jenkinsName string) logr.Logger {
return log.Log.WithValues("cr", jenkinsName)
}
func (r *ReconcileJenkins) setDefaults(jenkins *virtuslabv1alpha1.Jenkins) error {
func (r *ReconcileJenkins) setDefaults(jenkins *virtuslabv1alpha1.Jenkins, logger logr.Logger) error {
changed := false
if len(jenkins.Spec.Master.Plugins) == 0 {
logger.Info("Setting default base plugins in CR")
changed = true
jenkins.Spec.Master.Plugins = plugin.BasePlugins()
}
_, requestCPUSet := jenkins.Spec.Master.Resources.Requests[corev1.ResourceCPU]
_, requestMemporySet := jenkins.Spec.Master.Resources.Requests[corev1.ResourceMemory]
_, limitCPUSet := jenkins.Spec.Master.Resources.Limits[corev1.ResourceCPU]
_, limitMemporySet := jenkins.Spec.Master.Resources.Limits[corev1.ResourceMemory]
if !limitCPUSet || !limitMemporySet || !requestCPUSet || !requestMemporySet {
logger.Info("Setting default Jenkins master pod resource requirements in CR")
changed = true
jenkins.Spec.Master.Resources = corev1.ResourceRequirements{
Requests: corev1.ResourceList{
corev1.ResourceCPU: resource.MustParse("1"),
corev1.ResourceMemory: resource.MustParse("500Mi"),
},
Limits: corev1.ResourceList{
corev1.ResourceCPU: resource.MustParse("1500m"),
corev1.ResourceMemory: resource.MustParse("3Gi"),
},
}
}
if changed {
return r.client.Update(context.TODO(), jenkins)
}
return nil

View File

@ -1,6 +1,7 @@
package e2e
import (
"context"
"reflect"
"testing"
@ -8,6 +9,10 @@ import (
"github.com/VirtusLab/jenkins-operator/pkg/controller/jenkins/plugin"
"github.com/bndr/gojenkins"
framework "github.com/operator-framework/operator-sdk/pkg/test"
corev1 "k8s.io/api/core/v1"
"k8s.io/apimachinery/pkg/api/resource"
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
)
func TestBaseConfiguration(t *testing.T) {
@ -17,6 +22,7 @@ func TestBaseConfiguration(t *testing.T) {
defer ctx.Cleanup()
jenkins := createJenkinsCR(t, namespace)
createDefaultLimitsForContainersInNamespace(t, namespace)
waitForJenkinsBaseConfigurationToComplete(t, jenkins)
verifyJenkinsMasterPodAttributes(t, jenkins)
@ -24,8 +30,38 @@ func TestBaseConfiguration(t *testing.T) {
verifyBasePlugins(t, jenkinsClient)
}
func createDefaultLimitsForContainersInNamespace(t *testing.T, namespace string) {
limitRange := &corev1.LimitRange{
ObjectMeta: metav1.ObjectMeta{
Name: "e2e",
Namespace: namespace,
},
Spec: corev1.LimitRangeSpec{
Limits: []corev1.LimitRangeItem{
{
Type: corev1.LimitTypeContainer,
DefaultRequest: map[corev1.ResourceName]resource.Quantity{
corev1.ResourceCPU: resource.MustParse("1"),
corev1.ResourceMemory: resource.MustParse("1Gi"),
},
Default: map[corev1.ResourceName]resource.Quantity{
corev1.ResourceCPU: resource.MustParse("4"),
corev1.ResourceMemory: resource.MustParse("4Gi"),
},
},
},
},
}
t.Logf("LimitRange %+v", *limitRange)
if err := framework.Global.Client.Create(context.TODO(), limitRange, nil); err != nil {
t.Fatal(err)
}
}
func verifyJenkinsMasterPodAttributes(t *testing.T, jenkins *virtuslabv1alpha1.Jenkins) {
jenkinsPod := getJenkinsMasterPod(t, jenkins)
jenkins = getJenkins(t, jenkins.Namespace, jenkins.Name)
for key, value := range jenkins.Spec.Master.Annotations {
if jenkinsPod.ObjectMeta.Annotations[key] != value {

View File

@ -13,13 +13,21 @@ import (
"github.com/bndr/gojenkins"
framework "github.com/operator-framework/operator-sdk/pkg/test"
"k8s.io/api/core/v1"
corev1 "k8s.io/api/core/v1"
"k8s.io/apimachinery/pkg/api/resource"
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
"k8s.io/apimachinery/pkg/labels"
"k8s.io/apimachinery/pkg/types"
)
func getJenkins(t *testing.T, namespace, name string) *virtuslabv1alpha1.Jenkins {
jenkins := &virtuslabv1alpha1.Jenkins{}
namespaceName := types.NamespacedName{Namespace: namespace, Name: name}
if err := framework.Global.Client.Get(context.TODO(), namespaceName, jenkins); err != nil {
t.Fatal(err)
}
return jenkins
}
func getJenkinsMasterPod(t *testing.T, jenkins *virtuslabv1alpha1.Jenkins) *v1.Pod {
lo := metav1.ListOptions{
LabelSelector: labels.SelectorFromSet(resources.BuildResourceLabels(jenkins)).String(),
@ -77,16 +85,6 @@ func createJenkinsCR(t *testing.T, namespace string) *virtuslabv1alpha1.Jenkins
Master: virtuslabv1alpha1.JenkinsMaster{
Image: "jenkins/jenkins",
Annotations: map[string]string{"test": "label"},
Resources: corev1.ResourceRequirements{
Requests: corev1.ResourceList{
corev1.ResourceCPU: resource.MustParse("300m"),
corev1.ResourceMemory: resource.MustParse("500Mi"),
},
Limits: corev1.ResourceList{
corev1.ResourceCPU: resource.MustParse("2"),
corev1.ResourceMemory: resource.MustParse("2Gi"),
},
},
},
},
}
@ -109,16 +107,6 @@ func createJenkinsCRWithSeedJob(t *testing.T, namespace string) *virtuslabv1alph
Master: virtuslabv1alpha1.JenkinsMaster{
Image: "jenkins/jenkins",
Annotations: map[string]string{"test": "label"},
Resources: corev1.ResourceRequirements{
Requests: corev1.ResourceList{
corev1.ResourceCPU: resource.MustParse("300m"),
corev1.ResourceMemory: resource.MustParse("500Mi"),
},
Limits: corev1.ResourceList{
corev1.ResourceCPU: resource.MustParse("2"),
corev1.ResourceMemory: resource.MustParse("2Gi"),
},
},
},
//TODO(bantoniak) add seed job with private key
SeedJobs: []virtuslabv1alpha1.SeedJob{

View File

@ -5,6 +5,7 @@ import (
"github.com/VirtusLab/jenkins-operator/pkg/apis"
virtuslabv1alpha1 "github.com/VirtusLab/jenkins-operator/pkg/apis/virtuslab/v1alpha1"
"github.com/VirtusLab/jenkins-operator/pkg/controller/jenkins/constants"
f "github.com/operator-framework/operator-sdk/pkg/test"
framework "github.com/operator-framework/operator-sdk/pkg/test"
@ -13,7 +14,7 @@ import (
)
const (
jenkinsOperatorDeploymentName = "jenkins-operator"
jenkinsOperatorDeploymentName = constants.OperatorName
)
func TestMain(m *testing.M) {

View File

@ -32,6 +32,6 @@ func checkBaseConfigurationCompleteTimeIsNotSet(t *testing.T, jenkins *virtuslab
t.Fatal(err)
}
if jenkinsStatus.Status.BaseConfigurationCompletedTime != nil {
t.Fatalf("Status.BaseConfigurationCompletedTime is set after restart of pod, status %+v", jenkinsStatus.Status)
t.Fatalf("Status.BaseConfigurationCompletedTime is set after pod restart, status %+v", jenkinsStatus.Status)
}
}

View File

@ -44,7 +44,7 @@ func verifyJenkinsSeedJobs(t *testing.T, client *gojenkins.Jenkins, jenkins *vir
seedJobName := "jenkins-operator-configure-seed-job"
t.Logf("Attempting to verify if seed job has been created '%v'", seedJobName)
seedJob, err := client.GetJob(seedJobName)
assert.NoError(t, err, )
assert.NoError(t, err)
assert.NotNil(t, seedJob)
build, err = seedJob.GetLastSuccessfulBuild()