// createProvidersFromPolicies creates providers from the constraints supplied. func (c *podSecurityPolicyPlugin) createProvidersFromPolicies(psps []*extensions.PodSecurityPolicy, namespace string) ([]psp.Provider, []error) { var ( // collected providers providers []psp.Provider // collected errors to return errs []error ) for _, constraint := range psps { provider, err := psp.NewSimpleProvider(constraint, namespace, c.strategyFactory) if err != nil { errs = append(errs, fmt.Errorf("error creating provider for PSP %s: %v", constraint.Name, err)) continue } providers = append(providers, provider) } return providers, errs }
func TestAssignSecurityContext(t *testing.T) { // psp that will deny privileged container requests and has a default value for a field (uid) psp := restrictivePSP() provider, err := kpsp.NewSimpleProvider(psp, "namespace", kpsp.NewSimpleStrategyFactory()) if err != nil { t.Fatalf("failed to create provider: %v", err) } createContainer := func(priv bool) kapi.Container { return kapi.Container{ SecurityContext: &kapi.SecurityContext{ Privileged: &priv, }, } } // these are set up such that the containers always have a nil uid. If the case should not // validate then the uids should not have been updated by the strategy. If the case should // validate then uids should be set. This is ensuring that we're hanging on to the old SC // as we generate/validate and only updating the original container if the entire pod validates testCases := map[string]struct { pod *kapi.Pod shouldValidate bool expectedUID *int64 }{ "pod and container SC is not changed when invalid": { pod: &kapi.Pod{ Spec: kapi.PodSpec{ SecurityContext: &kapi.PodSecurityContext{}, Containers: []kapi.Container{createContainer(true)}, }, }, shouldValidate: false, }, "must validate all containers": { pod: &kapi.Pod{ Spec: kapi.PodSpec{ // good container and bad container SecurityContext: &kapi.PodSecurityContext{}, Containers: []kapi.Container{createContainer(false), createContainer(true)}, }, }, shouldValidate: false, }, "pod validates": { pod: &kapi.Pod{ Spec: kapi.PodSpec{ SecurityContext: &kapi.PodSecurityContext{}, Containers: []kapi.Container{createContainer(false)}, }, }, shouldValidate: true, }, } for k, v := range testCases { errs := assignSecurityContext(provider, v.pod, nil) if v.shouldValidate && len(errs) > 0 { t.Errorf("%s expected to validate but received errors %v", k, errs) continue } if !v.shouldValidate && len(errs) == 0 { t.Errorf("%s expected validation errors but received none", k) continue } // if we shouldn't have validated ensure that uid is not set on the containers if !v.shouldValidate { for _, c := range v.pod.Spec.Containers { if c.SecurityContext.RunAsUser != nil { t.Errorf("%s had non-nil UID %d. UID should not be set on test cases that don't validate", k, *c.SecurityContext.RunAsUser) } } } // if we validated then the pod sc should be updated now with the defaults from the psp if v.shouldValidate { for _, c := range v.pod.Spec.Containers { if *c.SecurityContext.RunAsUser != 999 { t.Errorf("%s expected uid to be defaulted to 999 but found %v", k, *c.SecurityContext.RunAsUser) } } } } }