func TestValidateContainers(t *testing.T) {
	volumes := util.StringSet{}
	capabilities.SetForTests(capabilities.Capabilities{
		AllowPrivileged: true,
	})

	successCase := []api.Container{
		{Name: "abc", Image: "image"},
		{Name: "123", Image: "image"},
		{Name: "abc-123", Image: "image"},
		{
			Name:  "life-123",
			Image: "image",
			Lifecycle: &api.Lifecycle{
				PreStop: &api.Handler{
					Exec: &api.ExecAction{Command: []string{"ls", "-l"}},
				},
			},
		},
		{Name: "abc-1234", Image: "image", Privileged: true},
	}
	if errs := validateContainers(successCase, volumes); len(errs) != 0 {
		t.Errorf("expected success: %v", errs)
	}

	capabilities.SetForTests(capabilities.Capabilities{
		AllowPrivileged: false,
	})
	errorCases := map[string][]api.Container{
		"zero-length name":     {{Name: "", Image: "image"}},
		"name > 63 characters": {{Name: strings.Repeat("a", 64), Image: "image"}},
		"name not a DNS label": {{Name: "a.b.c", Image: "image"}},
		"name not unique": {
			{Name: "abc", Image: "image"},
			{Name: "abc", Image: "image"},
		},
		"zero-length image": {{Name: "abc", Image: ""}},
		"host port not unique": {
			{Name: "abc", Image: "image", Ports: []api.Port{{ContainerPort: 80, HostPort: 80}}},
			{Name: "def", Image: "image", Ports: []api.Port{{ContainerPort: 81, HostPort: 80}}},
		},
		"invalid env var name": {
			{Name: "abc", Image: "image", Env: []api.EnvVar{{Name: "ev.1"}}},
		},
		"unknown volume name": {
			{Name: "abc", Image: "image", VolumeMounts: []api.VolumeMount{{Name: "anything", MountPath: "/foo"}}},
		},
		"invalid lifecycle, no exec command.": {
			{
				Name:  "life-123",
				Image: "image",
				Lifecycle: &api.Lifecycle{
					PreStop: &api.Handler{
						Exec: &api.ExecAction{},
					},
				},
			},
		},
		"invalid lifecycle, no http path.": {
			{
				Name:  "life-123",
				Image: "image",
				Lifecycle: &api.Lifecycle{
					PreStop: &api.Handler{
						HTTPGet: &api.HTTPGetAction{},
					},
				},
			},
		},
		"invalid lifecycle, no action.": {
			{
				Name:  "life-123",
				Image: "image",
				Lifecycle: &api.Lifecycle{
					PreStop: &api.Handler{},
				},
			},
		},
		"privilege disabled": {
			{Name: "abc", Image: "image", Privileged: true},
		},
	}
	for k, v := range errorCases {
		if errs := validateContainers(v, volumes); len(errs) == 0 {
			t.Errorf("expected failure for %s", k)
		}
	}
}
Beispiel #2
0
func TestExampleObjectSchemas(t *testing.T) {
	cases := map[string]map[string]runtime.Object{
		"../cmd/integration": {
			"v1-controller": &api.ReplicationController{},
		},
		"../examples/guestbook": {
			"frontend-controller":     &api.ReplicationController{},
			"redis-slave-controller":  &api.ReplicationController{},
			"redis-master-controller": &api.ReplicationController{},
			"frontend-service":        &api.Service{},
			"redis-master-service":    &api.Service{},
			"redis-slave-service":     &api.Service{},
		},
		"../examples/guestbook-go": {
			"guestbook-controller":    &api.ReplicationController{},
			"redis-slave-controller":  &api.ReplicationController{},
			"redis-master-controller": &api.ReplicationController{},
			"guestbook-service":       &api.Service{},
			"redis-master-service":    &api.Service{},
			"redis-slave-service":     &api.Service{},
		},
		"../docs/user-guide/walkthrough": {
			"pod-nginx":                 &api.Pod{},
			"pod-nginx-with-label":      &api.Pod{},
			"pod-redis":                 &api.Pod{},
			"pod-with-http-healthcheck": &api.Pod{},
			"service":                   &api.Service{},
			"replication-controller":    &api.ReplicationController{},
			"podtemplate":               &api.PodTemplate{},
		},
		"../docs/user-guide/update-demo": {
			"kitten-rc":   &api.ReplicationController{},
			"nautilus-rc": &api.ReplicationController{},
		},
		"../docs/user-guide/persistent-volumes/volumes": {
			"local-01": &api.PersistentVolume{},
			"local-02": &api.PersistentVolume{},
			"gce":      &api.PersistentVolume{},
			"nfs":      &api.PersistentVolume{},
		},
		"../docs/user-guide/persistent-volumes/claims": {
			"claim-01": &api.PersistentVolumeClaim{},
			"claim-02": &api.PersistentVolumeClaim{},
			"claim-03": &api.PersistentVolumeClaim{},
		},
		"../docs/user-guide/persistent-volumes/simpletest": {
			"namespace": &api.Namespace{},
			"pod":       &api.Pod{},
			"service":   &api.Service{},
		},
		"../examples/iscsi": {
			"iscsi": &api.Pod{},
		},
		"../examples/glusterfs": {
			"glusterfs-pod":       &api.Pod{},
			"glusterfs-endpoints": &api.Endpoints{},
		},
		"../docs/user-guide/liveness": {
			"exec-liveness": &api.Pod{},
			"http-liveness": &api.Pod{},
		},
		"../docs/user-guide": {
			"multi-pod":   nil,
			"pod":         &api.Pod{},
			"replication": &api.ReplicationController{},
		},
		"../examples": {
			"scheduler-policy-config": &schedulerapi.Policy{},
		},
		"../examples/rbd/secret": {
			"ceph-secret": &api.Secret{},
		},
		"../examples/rbd": {
			"rbd":             &api.Pod{},
			"rbd-with-secret": &api.Pod{},
		},
		"../examples/cassandra": {
			"cassandra-controller": &api.ReplicationController{},
			"cassandra-service":    &api.Service{},
			"cassandra":            &api.Pod{},
		},
		"../examples/celery-rabbitmq": {
			"celery-controller":   &api.ReplicationController{},
			"flower-controller":   &api.ReplicationController{},
			"flower-service":      &api.Service{},
			"rabbitmq-controller": &api.ReplicationController{},
			"rabbitmq-service":    &api.Service{},
		},
		"../examples/cluster-dns": {
			"dns-backend-rc":      &api.ReplicationController{},
			"dns-backend-service": &api.Service{},
			"dns-frontend-pod":    &api.Pod{},
			"namespace-dev":       &api.Namespace{},
			"namespace-prod":      &api.Namespace{},
		},
		"../docs/user-guide/downward-api": {
			"dapi-pod": &api.Pod{},
		},
		"../examples/elasticsearch": {
			"apiserver-secret": nil,
			"music-rc":         &api.ReplicationController{},
			"music-service":    &api.Service{},
		},
		"../examples/explorer": {
			"pod": &api.Pod{},
		},
		"../examples/hazelcast": {
			"hazelcast-controller": &api.ReplicationController{},
			"hazelcast-service":    &api.Service{},
		},
		"../docs/admin/namespaces": {
			"namespace-dev":  &api.Namespace{},
			"namespace-prod": &api.Namespace{},
		},
		"../docs/user-guide/limitrange": {
			"invalid-pod": &api.Pod{},
			"limits":      &api.LimitRange{},
			"namespace":   &api.Namespace{},
			"valid-pod":   &api.Pod{},
		},
		"../docs/user-guide/logging-demo": {
			"synthetic_0_25lps": &api.Pod{},
			"synthetic_10lps":   &api.Pod{},
		},
		"../examples/meteor": {
			"meteor-controller": &api.ReplicationController{},
			"meteor-service":    &api.Service{},
			"mongo-pod":         &api.Pod{},
			"mongo-service":     &api.Service{},
		},
		"../examples/mysql-wordpress-pd": {
			"mysql-service":     &api.Service{},
			"mysql":             &api.Pod{},
			"wordpress-service": &api.Service{},
			"wordpress":         &api.Pod{},
		},
		"../examples/nfs": {
			"nfs-server-pod":     &api.Pod{},
			"nfs-server-service": &api.Service{},
			"nfs-web-pod":        &api.Pod{},
		},
		"../docs/user-guide/node-selection": {
			"pod": &api.Pod{},
		},
		"../examples/openshift-origin": {
			"openshift-controller": &api.ReplicationController{},
			"openshift-service":    &api.Service{},
		},
		"../examples/phabricator": {
			"authenticator-controller": &api.ReplicationController{},
			"phabricator-controller":   &api.ReplicationController{},
			"phabricator-service":      &api.Service{},
		},
		"../examples/redis": {
			"redis-controller":          &api.ReplicationController{},
			"redis-master":              &api.Pod{},
			"redis-proxy":               &api.Pod{},
			"redis-sentinel-controller": &api.ReplicationController{},
			"redis-sentinel-service":    &api.Service{},
		},
		"../docs/user-guide/resourcequota": {
			"namespace": &api.Namespace{},
			"limits":    &api.LimitRange{},
			"quota":     &api.ResourceQuota{},
		},
		"../examples/rethinkdb": {
			"admin-pod":      &api.Pod{},
			"admin-service":  &api.Service{},
			"driver-service": &api.Service{},
			"rc":             &api.ReplicationController{},
		},
		"../docs/user-guide/secrets": {
			"secret-pod": &api.Pod{},
			"secret":     &api.Secret{},
		},
		"../examples/spark": {
			"spark-master-service":    &api.Service{},
			"spark-master":            &api.Pod{},
			"spark-worker-controller": &api.ReplicationController{},
			"spark-driver":            &api.Pod{},
		},
		"../examples/storm": {
			"storm-nimbus-service":    &api.Service{},
			"storm-nimbus":            &api.Pod{},
			"storm-worker-controller": &api.ReplicationController{},
			"zookeeper-service":       &api.Service{},
			"zookeeper":               &api.Pod{},
		},
	}

	capabilities.SetForTests(capabilities.Capabilities{
		AllowPrivileged: true,
	})

	for path, expected := range cases {
		tested := 0
		err := walkJSONFiles(path, func(name, path string, data []byte) {
			expectedType, found := expected[name]
			if !found {
				t.Errorf("%s: %s does not have a test case defined", path, name)
				return
			}
			tested++
			if expectedType == nil {
				t.Logf("skipping : %s/%s\n", path, name)
				return
			}
			if name == "scheduler-policy-config" {
				if err := schedulerapilatest.Codec.DecodeInto(data, expectedType); err != nil {
					t.Errorf("%s did not decode correctly: %v\n%s", path, err, string(data))
					return
				}
				//TODO: Add validate method for &schedulerapi.Policy
			} else {
				if err := latest.Codec.DecodeInto(data, expectedType); err != nil {
					t.Errorf("%s did not decode correctly: %v\n%s", path, err, string(data))
					return
				}
				if errors := validateObject(expectedType); len(errors) > 0 {
					t.Errorf("%s did not validate correctly: %v", path, errors)
				}
			}
		})
		if err != nil {
			t.Errorf("Expected no error, Got %v", err)
		}
		if tested != len(expected) {
			t.Errorf("Directory %v: Expected %d examples, Got %d", path, len(expected), tested)
		}
	}
}
Beispiel #3
0
func init() {
	capabilities.SetForTests(capabilities.Capabilities{
		AllowPrivileged: true,
	})
	flag.Set("v", "5")
}