Skip to content

Commit

Permalink
Added more tests for DenyPublicServices
Browse files Browse the repository at this point in the history
  • Loading branch information
elithrar committed Jun 25, 2019
1 parent 36ca3a5 commit 4196009
Show file tree
Hide file tree
Showing 3 changed files with 142 additions and 120 deletions.
35 changes: 26 additions & 9 deletions admit_funcs.go
Original file line number Diff line number Diff line change
Expand Up @@ -61,35 +61,52 @@ func DenyPublicServices(admissionReview *admission.AdmissionReview) (*admission.
// allowed := false
//
// kind := admissionReview.Request.Kind.Kind
// name := admissionReview.Request.Name
// // name := admissionReview.Request.Name
// resp := &admission.AdmissionResponse{
// Allowed: allowed,
// }
//
// if kind == "Pod" {
// pod := core.Pod{}
// if err := json.Unmarshal(admissionReview.Request.Object.Raw, pod); err != nil {
// if err := json.Unmarshal(admissionReview.Request.Object.Raw, &pod); err != nil {
// return nil, err
// }
//
// annotations := pod.ObjectMeta.Annotations
// missing := map[string]string{}
// for requiredKey, requiredVal := range requiredAnnotations {
// if actualVal, ok := annotations[requiredKey]; ok {
// if actualVal != requiredVal {
// return nil, fmt.Errorf("the submitted %s (name: %s) is missing required annotations: %#v", kind, name, requiredAnnotations)
// if meta.HasAnnotation(pod.ObjectMeta, requiredKey) {
// if annotations[requiredKey] != requiredVal {
// resp.Allowed = false
// // Required value does not match
// // Add to "missing" list to report back on
// }
// } else {
// return nil, fmt.Errorf("the submitted %s (name: %s) is missing required annotations: %#v", kind, name, requiredAnnotations)
// // Has key & matching value
// }
// // does not have key at all
// // add to "missing" list to report back on
// }
//
// allowed = true
// if len(missing) == 0 {
// resp.Allowed = true
// }
//
// // for requiredKey, requiredVal := range requiredAnnotations {
// // if actualVal, ok := annotations[requiredKey]; ok {
// // if actualVal != requiredVal {
// // return nil, fmt.Errorf("the submitted %s (name: %s) is missing required annotations: %#v", kind, name, requiredAnnotations)
// // }
// // } else {
// // return nil, fmt.Errorf("the submitted %s (name: %s) is missing required annotations: %#v", kind, name, requiredAnnotations)
// // }
// // }
// } else {
// allowed = true
// resp.Allowed = true
// }
//
// return resp, nil
// }
//
// return admitFunc
// }
//
116 changes: 116 additions & 0 deletions admit_funcs_test.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,116 @@
package admissioncontrol

import (
"testing"

admission "k8s.io/api/admission/v1beta1"
meta "k8s.io/apimachinery/pkg/apis/meta/v1"
)

func TestDenyPublicServices(t *testing.T) {
var denyTests = []struct {
testName string
kind meta.GroupVersionKind
rawObject []byte
expectedMessage string
shouldAllow bool
}{
{
testName: "Reject Ingress",
kind: meta.GroupVersionKind{
Group: "extensions",
Kind: "Ingress",
Version: "v1beta1",
},
rawObject: nil,
expectedMessage: "Ingress objects cannot be deployed to this cluster",
shouldAllow: false,
},
// TODO(silverlock): Fix the rawObject parts of these tests - need to determine how we can provide a raw k8s object.
// Similar tests here: https://github.com/kubernetes/apimachinery/blob/961b39a1baa06f6c52bdd048a809b9f5b47f1337/pkg/test/apis_meta_v1_unstructed_unstructure_test.go#L451
//
{
testName: "Reject Public Service",
kind: meta.GroupVersionKind{
Group: "",
Kind: "Service",
Version: "v1",
},
rawObject: []byte(`{"kind":"Service","apiVersion":"v1","metadata":{"name":"hello-service","namespace":"default","annotations":{}},"spec":{"ports":[{"protocol":"TCP","port":8000,"targetPort":8080,"nodePort":31433}],"selector":{"app":"hello-app"},"type":"LoadBalancer","externalTrafficPolicy":"Cluster"}}`),
expectedMessage: "Service objects of type: LoadBalancer without an internal-only annotation cannot be deployed to this cluster",
shouldAllow: false,
},
{
testName: "Allow Annotated Private Service",
kind: meta.GroupVersionKind{
Group: "",
Kind: "Service",
Version: "v1",
},
rawObject: []byte(`{"kind":"Service","apiVersion":"v1","metadata":{"name":"hello-service","namespace":"default","annotations":{"cloud.google.com/load-balancer-type": "Internal"}},"spec":{"ports":[{"protocol":"TCP","port":8000,"targetPort":8080,"nodePort":31433}],"selector":{"app":"hello-app"},"type":"LoadBalancer","externalTrafficPolicy":"Cluster"}}`),
expectedMessage: "",
shouldAllow: true,
},
{
testName: "Reject Incorrectly Annotated Private Service",
kind: meta.GroupVersionKind{
Group: "",
Kind: "Service",
Version: "v1",
},
rawObject: []byte(`{"kind":"Service","apiVersion":"v1","metadata":{"name":"hello-service","namespace":"default","annotations":{"cloud.google.com/load-balancer-type": ""}},"spec":{"ports":[{"protocol":"TCP","port":8000,"targetPort":8080,"nodePort":31433}],"selector":{"app":"hello-app"},"type":"LoadBalancer","externalTrafficPolicy":"Cluster"}}`),
expectedMessage: "Service objects of type: LoadBalancer without an internal-only annotation cannot be deployed to this cluster",
shouldAllow: false,
},
{
testName: "Allow Pods",
kind: meta.GroupVersionKind{
Group: "",
Kind: "Pod",
Version: "v1",
},
rawObject: nil,
expectedMessage: "",
shouldAllow: true,
},
{
testName: "Allow Deployments",
kind: meta.GroupVersionKind{
Group: "apps",
Kind: "Deployment",
Version: "v1",
},
rawObject: nil,
expectedMessage: "",
shouldAllow: true,
},
}

for _, tt := range denyTests {
t.Run(tt.testName, func(t *testing.T) {
incomingReview := admission.AdmissionReview{
Request: &admission.AdmissionRequest{},
}
incomingReview.Request.Kind = tt.kind
incomingReview.Request.Object.Raw = tt.rawObject

resp, err := DenyPublicServices(&incomingReview)
if err != nil {
if tt.expectedMessage != err.Error() {
t.Fatalf("error message does not match: got %q - expected %q", err.Error(), tt.expectedMessage)
}

if tt.shouldAllow {
t.Fatalf("incorrectly rejected admission for %s (kind: %v): %s", tt.testName, tt.kind, err.Error())
}

t.Logf("correctly rejected admission for %s (kind: %v): %s", tt.testName, tt.kind, err.Error())
return
}

if resp.Allowed != tt.shouldAllow {
t.Fatalf("incorrectly allowed admission for %s (kind: %v): %s", tt.testName, tt.kind, resp.String())
}
})
}
}
111 changes: 0 additions & 111 deletions handler_test.go

This file was deleted.

0 comments on commit 4196009

Please sign in to comment.