From 9ab4ef3a9c7f4076f0f5618e05c452523c704829 Mon Sep 17 00:00:00 2001 From: AhmedGrati <48932084+AhmedGrati@users.noreply.github.com> Date: Wed, 8 Feb 2023 21:46:13 +0100 Subject: [PATCH] Feat: Add hostPort and protocol to containers (#1558) * feat: add the host port to containers * test(unit): add unit tests for host port and protocol * test(functional): add functional tests of host port and protocol * test(functional): add functional tests of host port and protocol for openshift --- pkg/transformer/kubernetes/kubernetes.go | 6 +- pkg/transformer/kubernetes/kubernetes_test.go | 47 ++++++++++ script/test/cmd/tests_new.sh | 8 ++ .../host-port-protocol/docker-compose.yaml | 10 ++ .../host-port-protocol/output-k8s.yaml | 66 ++++++++++++++ .../host-port-protocol/output-os.yaml | 91 +++++++++++++++++++ 6 files changed, 224 insertions(+), 4 deletions(-) create mode 100644 script/test/fixtures/host-port-protocol/docker-compose.yaml create mode 100644 script/test/fixtures/host-port-protocol/output-k8s.yaml create mode 100644 script/test/fixtures/host-port-protocol/output-os.yaml diff --git a/pkg/transformer/kubernetes/kubernetes.go b/pkg/transformer/kubernetes/kubernetes.go index 790c463306..caba2d5c1f 100644 --- a/pkg/transformer/kubernetes/kubernetes.go +++ b/pkg/transformer/kubernetes/kubernetes.go @@ -623,10 +623,8 @@ func ConfigPorts(service kobject.ServiceConfig) []api.ContainerPort { containerPort := api.ContainerPort{ ContainerPort: port.ContainerPort, HostIP: port.HostIP, - } - // If the default is already TCP, no need to include protocol. - if protocol := api.Protocol(port.Protocol); protocol != api.ProtocolTCP { - containerPort.Protocol = protocol + HostPort: port.HostPort, + Protocol: api.Protocol(port.Protocol), } ports = append(ports, containerPort) exist[port.ID()] = true diff --git a/pkg/transformer/kubernetes/kubernetes_test.go b/pkg/transformer/kubernetes/kubernetes_test.go index 0973c91a81..99e9c53ec5 100644 --- a/pkg/transformer/kubernetes/kubernetes_test.go +++ b/pkg/transformer/kubernetes/kubernetes_test.go @@ -84,6 +84,15 @@ func newKomposeObject() kobject.KomposeObject { } } +func newKomposeObjectHostPortProtocolConfig() kobject.ServiceConfig { + return kobject.ServiceConfig{ + Name: "nginx", + ContainerName: "nginx", + Image: "nginx", + Port: []kobject.Ports{{HostPort: 80, Protocol: string(api.ProtocolTCP), ContainerPort: 80}}, + } +} + func equalStringSlice(s1, s2 []string) bool { if len(s1) != len(s2) { return false @@ -938,3 +947,41 @@ func TestCreatePVC(t *testing.T) { t.Errorf("Expected %s returned, got %s", storageClassName, *result.Spec.StorageClassName) } } + +func TestCreateHostPortAndProtocol(t *testing.T) { + groupName := "pod_group" + komposeObject := kobject.KomposeObject{ + ServiceConfigs: map[string]kobject.ServiceConfig{"app": newKomposeObjectHostPortProtocolConfig()}, + } + k := Kubernetes{} + objs, err := k.Transform(komposeObject, kobject.ConvertOptions{ServiceGroupMode: groupName}) + if err != nil { + t.Error(errors.Wrap(err, "k.Transform failed")) + } + for _, obj := range objs { + if deployment, ok := obj.(*appsv1.Deployment); ok { + container := deployment.Spec.Template.Spec.Containers[0] + port := container.Ports[0] + containerPort := port.ContainerPort + hostPort := port.HostPort + protocol := port.Protocol + + expectedPort := komposeObject.ServiceConfigs["app"].Port[0] + expectedContainerPort := expectedPort.ContainerPort + expectedHostPort := expectedPort.HostPort + expectedProtocol := expectedPort.Protocol + + if containerPort != expectedContainerPort { + t.Errorf("Expected container port %v, got %v", expectedContainerPort, containerPort) + } + + if hostPort != expectedHostPort { + t.Errorf("Expected host port %v, got %v", expectedHostPort, hostPort) + } + + if protocol != api.Protocol(expectedProtocol) { + t.Errorf("Expected protocol %v, got %v", expectedProtocol, protocol) + } + } + } +} diff --git a/script/test/cmd/tests_new.sh b/script/test/cmd/tests_new.sh index 92c210087a..09f9cfd963 100755 --- a/script/test/cmd/tests_new.sh +++ b/script/test/cmd/tests_new.sh @@ -216,3 +216,11 @@ convert::expect_success "$os_cmd" "$os_output" k8s_cmd="kompose -f $KOMPOSE_ROOT/script/test/fixtures/single-file-output/docker-compose.yaml convert --stdout --with-kompose-annotation=false" k8s_output="$KOMPOSE_ROOT/script/test/fixtures/single-file-output/output-k8s.yaml" convert::expect_success_and_warning "$k8s_cmd" "$k8s_output" + +# Test host port and protocol feature +k8s_cmd="kompose -f $KOMPOSE_ROOT/script/test/fixtures/host-port-protocol/docker-compose.yaml convert --stdout --with-kompose-annotation=false" +os_cmd="kompose --provider=openshift -f $KOMPOSE_ROOT/script/test/fixtures/host-port-protocol/docker-compose.yaml convert --stdout --with-kompose-annotation=false" +k8s_output="$KOMPOSE_ROOT/script/test/fixtures/host-port-protocol/output-k8s.yaml" +os_output="$KOMPOSE_ROOT/script/test/fixtures/host-port-protocol/output-os.yaml" +convert::expect_success_and_warning "$k8s_cmd" "$k8s_output" +convert::expect_success "$os_cmd" "$os_output" diff --git a/script/test/fixtures/host-port-protocol/docker-compose.yaml b/script/test/fixtures/host-port-protocol/docker-compose.yaml new file mode 100644 index 0000000000..afbf0237f7 --- /dev/null +++ b/script/test/fixtures/host-port-protocol/docker-compose.yaml @@ -0,0 +1,10 @@ +version: "3.3" + +services: + nginx: + ports: + - target: 80 + published: 80 + protocol: tcp + mode: host + image: nginx diff --git a/script/test/fixtures/host-port-protocol/output-k8s.yaml b/script/test/fixtures/host-port-protocol/output-k8s.yaml new file mode 100644 index 0000000000..ae32c02936 --- /dev/null +++ b/script/test/fixtures/host-port-protocol/output-k8s.yaml @@ -0,0 +1,66 @@ +--- +apiVersion: v1 +kind: Service +metadata: + creationTimestamp: null + labels: + io.kompose.service: nginx + name: nginx +spec: + ports: + - name: "80" + port: 80 + targetPort: 80 + selector: + io.kompose.service: nginx +status: + loadBalancer: {} + +--- +apiVersion: apps/v1 +kind: Deployment +metadata: + creationTimestamp: null + labels: + io.kompose.service: nginx + name: nginx +spec: + replicas: 1 + selector: + matchLabels: + io.kompose.service: nginx + strategy: {} + template: + metadata: + creationTimestamp: null + labels: + io.kompose.network/host-port-protocol-default: "true" + io.kompose.service: nginx + spec: + containers: + - image: nginx + name: nginx + ports: + - containerPort: 80 + hostPort: 80 + protocol: TCP + resources: {} + restartPolicy: Always +status: {} + +--- +apiVersion: networking.k8s.io/v1 +kind: NetworkPolicy +metadata: + creationTimestamp: null + name: host-port-protocol-default +spec: + ingress: + - from: + - podSelector: + matchLabels: + io.kompose.network/host-port-protocol-default: "true" + podSelector: + matchLabels: + io.kompose.network/host-port-protocol-default: "true" + diff --git a/script/test/fixtures/host-port-protocol/output-os.yaml b/script/test/fixtures/host-port-protocol/output-os.yaml new file mode 100644 index 0000000000..a83baa0779 --- /dev/null +++ b/script/test/fixtures/host-port-protocol/output-os.yaml @@ -0,0 +1,91 @@ +--- +apiVersion: v1 +kind: Service +metadata: + creationTimestamp: null + labels: + io.kompose.service: nginx + name: nginx +spec: + ports: + - name: "80" + port: 80 + targetPort: 80 + selector: + io.kompose.service: nginx +status: + loadBalancer: {} + +--- +apiVersion: v1 +kind: DeploymentConfig +metadata: + creationTimestamp: null + labels: + io.kompose.service: nginx + name: nginx +spec: + replicas: 1 + selector: + io.kompose.service: nginx + strategy: + resources: {} + template: + metadata: + creationTimestamp: null + labels: + io.kompose.network/host-port-protocol-default: "true" + io.kompose.service: nginx + spec: + containers: + - image: ' ' + name: nginx + ports: + - containerPort: 80 + hostPort: 80 + protocol: TCP + resources: {} + restartPolicy: Always + test: false + triggers: + - type: ConfigChange + - imageChangeParams: + automatic: true + containerNames: + - nginx + from: + kind: ImageStreamTag + name: nginx:latest + type: ImageChange +status: + availableReplicas: 0 + latestVersion: 0 + observedGeneration: 0 + replicas: 0 + unavailableReplicas: 0 + updatedReplicas: 0 + +--- +apiVersion: v1 +kind: ImageStream +metadata: + creationTimestamp: null + labels: + io.kompose.service: nginx + name: nginx +spec: + lookupPolicy: + local: false + tags: + - annotations: null + from: + kind: DockerImage + name: nginx + generation: null + importPolicy: {} + name: latest + referencePolicy: + type: "" +status: + dockerImageRepository: "" +