Consume podspec patch directly on executor/builder mounts (#2661)

Signed-off-by: Sanket Sudake <sanketsudake@gmail.com>

Signed-off-by: Sanket Sudake <sanketsudake@gmail.com>
This commit is contained in:
Sanket Sudake
2022-12-08 11:38:57 +05:30
committed by GitHub
parent 4dde3c9520
commit 985d94b5b8
12 changed files with 79 additions and 105 deletions
@@ -4,6 +4,6 @@ kind: ConfigMap
metadata: metadata:
name: builder-podspec-patch name: builder-podspec-patch
data: data:
spec: | builder-podspec-patch.yaml: |
{{- toYaml .Values.builderPodSpec.podSpec | nindent 4 }} {{- toYaml .Values.builderPodSpec.podSpec | nindent 4 }}
{{- end -}} {{- end -}}
@@ -44,7 +44,7 @@ spec:
- name: FISSION_FUNCTION_NAMESPACE - name: FISSION_FUNCTION_NAMESPACE
value: "{{ .Values.functionNamespace }}" value: "{{ .Values.functionNamespace }}"
- name: FISSION_DEFAULT_NAMESPACE - name: FISSION_DEFAULT_NAMESPACE
value: "{{ .Values.defaultNamespace }}" value: "{{ .Values.defaultNamespace }}"
- name: ENABLE_ISTIO - name: ENABLE_ISTIO
value: "{{ .Values.enableIstio }}" value: "{{ .Values.enableIstio }}"
- name: FETCHER_MINCPU - name: FETCHER_MINCPU
@@ -61,8 +61,15 @@ spec:
value: {{ .Values.pprof.enabled | quote }} value: {{ .Values.pprof.enabled | quote }}
- name: HELM_RELEASE_NAME - name: HELM_RELEASE_NAME
value: {{ .Release.Name | quote }} value: {{ .Release.Name | quote }}
{{- include "fission-resource-namespace.envs" . | indent 8 }} {{- include "fission-resource-namespace.envs" . | indent 8 }}
{{- include "opentelemtry.envs" . | indent 8 }} {{- include "opentelemtry.envs" . | indent 8 }}
{{- if .Values.builderPodSpec.enabled }}
volumeMounts:
- name: builder-podspec-patch-volume
mountPath: /etc/fission/builder-podspec-patch.yaml
subPath: builder-podspec-patch.yaml
readOnly: true
{{- end }}
ports: ports:
- containerPort: 8080 - containerPort: 8080
name: metrics name: metrics
@@ -75,11 +82,17 @@ spec:
terminationMessagePolicy: {{ .Values.terminationMessagePolicy }} terminationMessagePolicy: {{ .Values.terminationMessagePolicy }}
{{- end }} {{- end }}
serviceAccountName: fission-buildermgr serviceAccountName: fission-buildermgr
{{- if .Values.builderPodSpec.enabled }}
volumes:
- name: builder-podspec-patch-volume
configMap:
name: builder-podspec-patch
{{- end }}
{{- if .Values.priorityClassName }} {{- if .Values.priorityClassName }}
priorityClassName: {{ .Values.priorityClassName }} priorityClassName: {{ .Values.priorityClassName }}
{{- end }} {{- end }}
{{- with .Values.imagePullSecrets }} {{- with .Values.imagePullSecrets }}
imagePullSecrets: imagePullSecrets:
{{- toYaml . | nindent 8 }} {{- toYaml . | nindent 8 }}
{{- end }} {{- end }}
{{- if .Values.extraCoreComponentPodConfig }} {{- if .Values.extraCoreComponentPodConfig }}
@@ -4,6 +4,6 @@ kind: ConfigMap
metadata: metadata:
name: runtime-podspec-patch name: runtime-podspec-patch
data: data:
spec: | runtime-podspec-patch.yaml: |
{{- toYaml .Values.runtimePodSpec.podSpec | nindent 4 }} {{- toYaml .Values.runtimePodSpec.podSpec | nindent 4 }}
{{- end -}} {{- end -}}
@@ -42,7 +42,7 @@ spec:
- name: FISSION_FUNCTION_NAMESPACE - name: FISSION_FUNCTION_NAMESPACE
value: "{{ .Values.functionNamespace }}" value: "{{ .Values.functionNamespace }}"
- name: FISSION_DEFAULT_NAMESPACE - name: FISSION_DEFAULT_NAMESPACE
value: "{{ .Values.defaultNamespace }}" value: "{{ .Values.defaultNamespace }}"
- name: RUNTIME_IMAGE_PULL_POLICY - name: RUNTIME_IMAGE_PULL_POLICY
value: "{{ .Values.pullPolicy }}" value: "{{ .Values.pullPolicy }}"
- name: ADOPT_EXISTING_RESOURCES - name: ADOPT_EXISTING_RESOURCES
@@ -96,6 +96,13 @@ spec:
port: 8888 port: 8888
initialDelaySeconds: 35 initialDelaySeconds: 35
periodSeconds: 5 periodSeconds: 5
{{- if .Values.runtimePodSpec.enabled }}
volumeMounts:
- name: runtime-podspec-patch-volume
mountPath: /etc/fission/runtime-podspec-patch.yaml
subPath: runtime-podspec-patch.yaml
readOnly: true
{{- end }}
ports: ports:
- containerPort: 8080 - containerPort: 8080
name: metrics name: metrics
@@ -116,13 +123,19 @@ spec:
terminationMessagePolicy: {{ .Values.terminationMessagePolicy }} terminationMessagePolicy: {{ .Values.terminationMessagePolicy }}
{{- end }} {{- end }}
serviceAccountName: fission-executor serviceAccountName: fission-executor
{{- if .Values.runtimePodSpec.enabled }}
volumes:
- name: runtime-podspec-patch-volume
configMap:
name: runtime-podspec-patch
{{- end }}
{{- if .Values.executor.priorityClassName }} {{- if .Values.executor.priorityClassName }}
priorityClassName: {{ .Values.executor.priorityClassName }} priorityClassName: {{ .Values.executor.priorityClassName }}
{{- else if .Values.priorityClassName }} {{- else if .Values.priorityClassName }}
priorityClassName: {{ .Values.priorityClassName }} priorityClassName: {{ .Values.priorityClassName }}
{{- end }} {{- end }}
{{- with .Values.imagePullSecrets }} {{- with .Values.imagePullSecrets }}
imagePullSecrets: imagePullSecrets:
{{- toYaml . | nindent 8 }} {{- toYaml . | nindent 8 }}
{{- end }} {{- end }}
{{- if .Values.extraCoreComponentPodConfig }} {{- if .Values.extraCoreComponentPodConfig }}
+1 -1
View File
@@ -16,6 +16,7 @@ require (
github.com/go-git/go-git/v5 v5.4.2 github.com/go-git/go-git/v5 v5.4.2
github.com/go-openapi/spec v0.20.7 github.com/go-openapi/spec v0.20.7
github.com/golang-jwt/jwt/v4 v4.4.2 github.com/golang-jwt/jwt/v4 v4.4.2
github.com/google/go-cmp v0.5.9
github.com/gorilla/mux v1.8.0 github.com/gorilla/mux v1.8.0
github.com/graymeta/stow v0.2.8 github.com/graymeta/stow v0.2.8
github.com/hashicorp/go-multierror v1.1.1 github.com/hashicorp/go-multierror v1.1.1
@@ -108,7 +109,6 @@ require (
github.com/golang/protobuf v1.5.2 // indirect github.com/golang/protobuf v1.5.2 // indirect
github.com/golang/snappy v0.0.4 // indirect github.com/golang/snappy v0.0.4 // indirect
github.com/google/gnostic v0.5.7-v3refs // indirect github.com/google/gnostic v0.5.7-v3refs // indirect
github.com/google/go-cmp v0.5.9 // indirect
github.com/google/gofuzz v1.1.0 // indirect github.com/google/gofuzz v1.1.0 // indirect
github.com/google/uuid v1.3.0 // indirect github.com/google/uuid v1.3.0 // indirect
github.com/gotestyourself/gotestyourself v2.2.0+incompatible // indirect github.com/gotestyourself/gotestyourself v2.2.0+incompatible // indirect
+2 -2
View File
@@ -67,8 +67,8 @@ const (
) )
const ( const (
RuntimePodSpecConfigmap = "runtime-podspec-patch" RuntimePodSpecPath = "/etc/fission/runtime-podspec-patch.yaml"
BuilderPodSpecConfigmap = "builder-podspec-patch" BuilderPodSpecPath = "/etc/fission/builder-podspec-patch.yaml"
) )
const ( const (
+2 -9
View File
@@ -22,7 +22,6 @@ import (
"github.com/pkg/errors" "github.com/pkg/errors"
"go.uber.org/zap" "go.uber.org/zap"
apiv1 "k8s.io/api/core/v1"
fv1 "github.com/fission/fission/pkg/apis/core/v1" fv1 "github.com/fission/fission/pkg/apis/core/v1"
"github.com/fission/fission/pkg/crd" "github.com/fission/fission/pkg/crd"
@@ -50,15 +49,9 @@ func Start(ctx context.Context, logger *zap.Logger, storageSvcUrl string) error
return errors.Wrap(err, "error making fetcher config") return errors.Wrap(err, "error making fetcher config")
} }
var podSpecPatch *apiv1.PodSpec podSpecPatch, err := util.GetSpecFromConfigMap(fv1.BuilderPodSpecPath)
namespace, err := utils.GetCurrentNamespace()
if err != nil { if err != nil {
logger.Warn("Current namespace not found %v", zap.Error(err)) logger.Warn("error reading data for pod spec patch", zap.String("path", fv1.BuilderPodSpecPath), zap.Error(err))
} else {
podSpecPatch, err = util.GetSpecFromConfigMap(ctx, kubernetesClient, fv1.BuilderPodSpecConfigmap, namespace)
if err != nil {
logger.Warn("Either configmap is not found or error reading data %v", zap.Error(err))
}
} }
envWatcher := makeEnvironmentWatcher(ctx, bmLogger, fissionClient, kubernetesClient, fetcherConfig, podSpecPatch) envWatcher := makeEnvironmentWatcher(ctx, bmLogger, fissionClient, kubernetesClient, fetcherConfig, podSpecPatch)
+2 -9
View File
@@ -28,7 +28,6 @@ import (
"github.com/dchest/uniuri" "github.com/dchest/uniuri"
"github.com/pkg/errors" "github.com/pkg/errors"
"go.uber.org/zap" "go.uber.org/zap"
apiv1 "k8s.io/api/core/v1"
k8sCache "k8s.io/client-go/tools/cache" k8sCache "k8s.io/client-go/tools/cache"
fv1 "github.com/fission/fission/pkg/apis/core/v1" fv1 "github.com/fission/fission/pkg/apis/core/v1"
@@ -271,15 +270,9 @@ func StartExecutor(ctx context.Context, logger *zap.Logger, port int) error {
executorInstanceID := strings.ToLower(uniuri.NewLen(8)) executorInstanceID := strings.ToLower(uniuri.NewLen(8))
var podSpecPatch *apiv1.PodSpec podSpecPatch, err := util.GetSpecFromConfigMap(fv1.RuntimePodSpecPath)
namespace, err := utils.GetCurrentNamespace()
if err != nil { if err != nil {
logger.Warn("Current namespace not found %s", zap.Error(err)) logger.Warn("error reading data for pod spec patch", zap.String("path", fv1.RuntimePodSpecPath), zap.Error(err))
} else {
podSpecPatch, err = util.GetSpecFromConfigMap(ctx, kubernetesClient, fv1.RuntimePodSpecConfigmap, namespace)
if err != nil {
logger.Warn("Either configmap is not found or error reading data %v", zap.Error(err))
}
} }
logger.Info("Starting executor", zap.String("instanceID", executorInstanceID)) logger.Info("Starting executor", zap.String("instanceID", executorInstanceID))
@@ -18,7 +18,6 @@ import (
k8sCache "k8s.io/client-go/tools/cache" k8sCache "k8s.io/client-go/tools/cache"
fv1 "github.com/fission/fission/pkg/apis/core/v1" fv1 "github.com/fission/fission/pkg/apis/core/v1"
"github.com/fission/fission/pkg/executor/util"
fetcherConfig "github.com/fission/fission/pkg/fetcher/config" fetcherConfig "github.com/fission/fission/pkg/fetcher/config"
fClient "github.com/fission/fission/pkg/generated/clientset/versioned/fake" fClient "github.com/fission/fission/pkg/generated/clientset/versioned/fake"
genInformer "github.com/fission/fission/pkg/generated/informers/externalversions" genInformer "github.com/fission/fission/pkg/generated/informers/externalversions"
@@ -65,23 +64,13 @@ func TestRefreshFuncPods(t *testing.T) {
ctx, cancel := context.WithCancel(context.Background()) ctx, cancel := context.WithCancel(context.Background())
defer cancel() defer cancel()
err = BuildConfigMap(ctx, kubernetesClient, functionNamespace, fv1.RuntimePodSpecConfigmap, map[string]string{})
if err != nil {
t.Fatalf("Error building configmap: %s", err)
}
podSpecPatch, err := util.GetSpecFromConfigMap(ctx, kubernetesClient, fv1.RuntimePodSpecConfigmap, functionNamespace)
if err != nil {
t.Fatalf("Error creating pod spec: %s", err)
}
fetcherConfig, err := fetcherConfig.MakeFetcherConfig("/userfunc") fetcherConfig, err := fetcherConfig.MakeFetcherConfig("/userfunc")
if err != nil { if err != nil {
t.Fatalf("Error creating fetcher config: %s", err) t.Fatalf("Error creating fetcher config: %s", err)
} }
executor, err := MakeNewDeploy(ctx, logger, fissionClient, kubernetesClient, fetcherConfig, "test", executor, err := MakeNewDeploy(ctx, logger, fissionClient, kubernetesClient, fetcherConfig, "test",
funcInformer, envInformer, ndmInformerFactory, podSpecPatch) funcInformer, envInformer, ndmInformerFactory, nil)
if err != nil { if err != nil {
t.Fatalf("new deploy manager creation failed: %s", err) t.Fatalf("new deploy manager creation failed: %s", err)
} }
+7 -10
View File
@@ -20,6 +20,7 @@ import (
"context" "context"
"errors" "errors"
"fmt" "fmt"
"os"
"strings" "strings"
"sync" "sync"
"time" "time"
@@ -119,18 +120,14 @@ func ConvertConfigSecrets(ctx context.Context, fn *fv1.Function, kc kubernetes.I
return envFromSources, nil return envFromSources, nil
} }
func GetSpecFromConfigMap(ctx context.Context, kubeClient kubernetes.Interface, cm string, cmns string) (*apiv1.PodSpec, error) { func GetSpecFromConfigMap(filePath string) (*apiv1.PodSpec, error) {
content, err := os.ReadFile(filePath)
podSpecPatch, err := kubeClient.CoreV1().ConfigMaps(cmns).Get(ctx, cm, metav1.GetOptions{})
if err != nil { if err != nil {
return nil, err return nil, fmt.Errorf("error reading YAML file %s: %w", filePath, err)
} }
additionalSpec := &apiv1.PodSpec{}
var additionalSpec apiv1.PodSpec err = yaml.UnmarshalStrict(content, &additionalSpec)
return additionalSpec, err
err = yaml.Unmarshal([]byte(podSpecPatch.Data["spec"]), &additionalSpec)
return &additionalSpec, err
} }
func GetObjectReaperInterval(logger *zap.Logger, executorType fv1.ExecutorType, defaultReaperInterval uint) uint { func GetObjectReaperInterval(logger *zap.Logger, executorType fv1.ExecutorType, defaultReaperInterval uint) uint {
+31 -44
View File
@@ -17,57 +17,45 @@ limitations under the License.
package util package util
import ( import (
"context"
"fmt" "fmt"
"os" "os"
"reflect" "reflect"
"testing" "testing"
apiv1 "k8s.io/api/core/v1" "github.com/google/go-cmp/cmp"
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
"k8s.io/client-go/kubernetes/fake"
fv1 "github.com/fission/fission/pkg/apis/core/v1" fv1 "github.com/fission/fission/pkg/apis/core/v1"
"github.com/fission/fission/pkg/utils/loggerfactory" "github.com/fission/fission/pkg/utils/loggerfactory"
apiv1 "k8s.io/api/core/v1"
) )
func TestGetSpecFromConfigMap(t *testing.T) { func TestGetSpecFromConfigMap(t *testing.T) {
runtimePodSpecPath := "runtime-podspec-patch.yaml"
kubeClient := fake.NewSimpleClientset() tempDir := t.TempDir()
var permissionNum int64 = 10001
var runAsNonRoot bool = true
configMapData := make(map[string]string, 0)
specPatch := ` specPatch := `
securityContext: securityContext:
fsGroup: 10001 fsGroup: 10001
runAsGroup: 10001 runAsGroup: 10001
runAsNonRoot: true runAsNonRoot: true
runAsUser: 10001` runAsUser: 10001`
err := os.WriteFile(tempDir+"/"+runtimePodSpecPath, []byte(specPatch), 0644)
configMapData["spec"] = specPatch
testConfigMap := apiv1.ConfigMap{
TypeMeta: metav1.TypeMeta{
Kind: "ConfigMap",
APIVersion: "v1",
},
ObjectMeta: metav1.ObjectMeta{
Name: "test-config-map",
Namespace: "fission",
},
Data: configMapData,
}
ctx, cancel := context.WithCancel(context.Background())
defer cancel()
configmap, err := kubeClient.CoreV1().ConfigMaps("fission").Create(ctx, &testConfigMap, metav1.CreateOptions{})
if err != nil { if err != nil {
t.Errorf("Error creating configmap %v", err) t.Errorf("Error writing to file %s", err)
}
specPatch2 := `
securityContext2:
securityContext:
fsGroup: "invalida_input"
runAsGroup: 10001
runAsNonRoot: true
runAsUser: 10001`
err = os.WriteFile(tempDir+"/"+runtimePodSpecPath+"2", []byte(specPatch2), 0644)
if err != nil {
t.Errorf("Error writing to file %s", err)
} }
t.Logf("Configmap: %v", configmap.Data) var permissionNum int64 = 10001
var runAsNonRoot bool = true
testSpecPatch := apiv1.PodSpec{ testSpecPatch := apiv1.PodSpec{
SecurityContext: &apiv1.PodSecurityContext{ SecurityContext: &apiv1.PodSecurityContext{
@@ -79,42 +67,41 @@ securityContext:
} }
tests := []struct { tests := []struct {
name string name string
cm string path string
cmns string
want *apiv1.PodSpec want *apiv1.PodSpec
wantErr bool wantErr bool
}{ }{
{ {
name: "Configmap exists", name: "File exists with valid data",
cm: "test-config-map", path: tempDir + "/" + runtimePodSpecPath,
cmns: "fission",
want: &testSpecPatch, want: &testSpecPatch,
wantErr: false, wantErr: false,
}, },
{ {
name: "Configmap does not exists", name: "File with invalid data",
cm: "wrongname", path: tempDir + "/" + runtimePodSpecPath + "2",
cmns: "fission",
want: nil, want: nil,
wantErr: true, wantErr: true,
}, },
{ {
name: "Wrong namespace", name: "File does not exist",
cm: "test-config-map", path: tempDir + "/" + "notexist",
cmns: "fissio",
want: nil, want: nil,
wantErr: true, wantErr: true,
}, },
} }
for _, tt := range tests { for _, tt := range tests {
t.Run(tt.name, func(t *testing.T) { t.Run(tt.name, func(t *testing.T) {
got, err := GetSpecFromConfigMap(ctx, kubeClient, tt.cm, tt.cmns) got, err := GetSpecFromConfigMap(tt.path)
if (err != nil) != tt.wantErr { if (err != nil) != tt.wantErr {
t.Errorf("GetSpecFromConfigMap() error = %v, wantErr %v", err, tt.wantErr) t.Errorf("GetSpecFromConfigMap() error = %v, wantErr %v", err, tt.wantErr)
return return
} }
if err != nil {
return
}
if !reflect.DeepEqual(got, tt.want) { if !reflect.DeepEqual(got, tt.want) {
t.Errorf("GetSpecFromConfigMap() got = %v, want %v", got, tt.want) t.Errorf("GetSpecFromConfigMap() diff = %s", cmp.Diff(tt.want, got))
} }
}) })
} }
-11
View File
@@ -216,17 +216,6 @@ func IsZip(filename string) (bool, error) {
return archiver.DefaultZip.Match(f) return archiver.DefaultZip.Match(f)
} }
// GetCurrentNamespace returns Kubernetes namespace of current Pod
func GetCurrentNamespace() (string, error) {
// This file contains the namespace and can be found in each container.
body, err := os.ReadFile("/var/run/secrets/kubernetes.io/serviceaccount/namespace")
if err != nil {
return "", err
}
return string(body), nil
}
func GetStringValueFromEnv(envVar string) (string, error) { func GetStringValueFromEnv(envVar string) (string, error) {
v := os.Getenv(envVar) v := os.Getenv(envVar)
if v == "" { if v == "" {