| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449 |
- /*
- Copyright 2020 Docker, Inc.
- Licensed under the Apache License, Version 2.0 (the "License");
- you may not use this file except in compliance with the License.
- You may obtain a copy of the License at
- http://www.apache.org/licenses/LICENSE-2.0
- Unless required by applicable law or agreed to in writing, software
- distributed under the License is distributed on an "AS IS" BASIS,
- WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- See the License for the specific language governing permissions and
- limitations under the License.
- */
- package convert
- import (
- "context"
- "os"
- "testing"
- "github.com/Azure/azure-sdk-for-go/profiles/latest/containerinstance/mgmt/containerinstance"
- "github.com/Azure/go-autorest/autorest/to"
- "github.com/compose-spec/compose-go/types"
- "gotest.tools/v3/assert"
- is "gotest.tools/v3/assert/cmp"
- "github.com/docker/api/containers"
- "github.com/docker/api/context/store"
- )
- var convertCtx = store.AciContext{
- SubscriptionID: "subID",
- ResourceGroup: "rg",
- Location: "eu",
- }
- func TestProjectName(t *testing.T) {
- project := types.Project{
- Name: "TEST",
- }
- containerGroup, err := ToContainerGroup(context.TODO(), convertCtx, project)
- assert.NilError(t, err)
- assert.Equal(t, *containerGroup.Name, "test")
- }
- func TestContainerGroupToContainer(t *testing.T) {
- myContainerGroup := containerinstance.ContainerGroup{
- ContainerGroupProperties: &containerinstance.ContainerGroupProperties{
- IPAddress: &containerinstance.IPAddress{
- Ports: &[]containerinstance.Port{{
- Port: to.Int32Ptr(80),
- }},
- IP: to.StringPtr("42.42.42.42"),
- },
- OsType: "Linux",
- },
- }
- myContainer := containerinstance.Container{
- Name: to.StringPtr("myContainerID"),
- ContainerProperties: &containerinstance.ContainerProperties{
- Image: to.StringPtr("sha256:666"),
- Command: to.StringSlicePtr([]string{"mycommand"}),
- Ports: &[]containerinstance.ContainerPort{{
- Port: to.Int32Ptr(80),
- }},
- EnvironmentVariables: nil,
- InstanceView: &containerinstance.ContainerPropertiesInstanceView{
- RestartCount: nil,
- CurrentState: &containerinstance.ContainerState{
- State: to.StringPtr("Running"),
- },
- },
- Resources: &containerinstance.ResourceRequirements{
- Limits: &containerinstance.ResourceLimits{
- CPU: to.Float64Ptr(3),
- MemoryInGB: to.Float64Ptr(0.1),
- },
- },
- },
- }
- var expectedContainer = containers.Container{
- ID: "myContainerID",
- Status: "Running",
- Image: "sha256:666",
- Command: "mycommand",
- CPULimit: 3,
- MemoryLimit: 107374182,
- Platform: "Linux",
- Ports: []containers.Port{{
- HostPort: uint32(80),
- ContainerPort: uint32(80),
- Protocol: "tcp",
- HostIP: "42.42.42.42",
- }},
- RestartPolicyCondition: "any",
- }
- container := ContainerGroupToContainer("myContainerID", myContainerGroup, myContainer)
- assert.DeepEqual(t, container, expectedContainer)
- }
- func TestComposeContainerGroupToContainerWithDnsSideCarSide(t *testing.T) {
- project := types.Project{
- Services: []types.ServiceConfig{
- {
- Name: "service1",
- Image: "image1",
- },
- {
- Name: "service2",
- Image: "image2",
- },
- },
- }
- group, err := ToContainerGroup(context.TODO(), convertCtx, project)
- assert.NilError(t, err)
- assert.Assert(t, is.Len(*group.Containers, 3))
- assert.Equal(t, *(*group.Containers)[0].Name, "service1")
- assert.Equal(t, *(*group.Containers)[1].Name, "service2")
- assert.Equal(t, *(*group.Containers)[2].Name, ComposeDNSSidecarName)
- assert.DeepEqual(t, *(*group.Containers)[2].Command, []string{"sh", "-c", "echo 127.0.0.1 service1 >> /etc/hosts;echo 127.0.0.1 service2 >> /etc/hosts;sleep infinity"})
- assert.Equal(t, *(*group.Containers)[0].Image, "image1")
- assert.Equal(t, *(*group.Containers)[1].Image, "image2")
- assert.Equal(t, *(*group.Containers)[2].Image, dnsSidecarImage)
- }
- func TestComposeSingleContainerGroupToContainerNoDnsSideCarSide(t *testing.T) {
- project := types.Project{
- Services: []types.ServiceConfig{
- {
- Name: "service1",
- Image: "image1",
- },
- },
- }
- group, err := ToContainerGroup(context.TODO(), convertCtx, project)
- assert.NilError(t, err)
- assert.Assert(t, is.Len(*group.Containers, 1))
- assert.Equal(t, *(*group.Containers)[0].Name, "service1")
- assert.Equal(t, *(*group.Containers)[0].Image, "image1")
- }
- func TestComposeSingleContainerRestartPolicy(t *testing.T) {
- project := types.Project{
- Services: []types.ServiceConfig{
- {
- Name: "service1",
- Image: "image1",
- Deploy: &types.DeployConfig{
- RestartPolicy: &types.RestartPolicy{
- Condition: "on-failure",
- },
- },
- },
- },
- }
- group, err := ToContainerGroup(context.TODO(), convertCtx, project)
- assert.NilError(t, err)
- assert.Assert(t, is.Len(*group.Containers, 1))
- assert.Equal(t, *(*group.Containers)[0].Name, "service1")
- assert.Equal(t, group.RestartPolicy, containerinstance.OnFailure)
- }
- func TestComposeMultiContainerRestartPolicy(t *testing.T) {
- project := types.Project{
- Services: []types.ServiceConfig{
- {
- Name: "service1",
- Image: "image1",
- Deploy: &types.DeployConfig{
- RestartPolicy: &types.RestartPolicy{
- Condition: "on-failure",
- },
- },
- },
- {
- Name: "service2",
- Image: "image2",
- Deploy: &types.DeployConfig{
- RestartPolicy: &types.RestartPolicy{
- Condition: "on-failure",
- },
- },
- },
- },
- }
- group, err := ToContainerGroup(context.TODO(), convertCtx, project)
- assert.NilError(t, err)
- assert.Assert(t, is.Len(*group.Containers, 3))
- assert.Equal(t, *(*group.Containers)[0].Name, "service1")
- assert.Equal(t, group.RestartPolicy, containerinstance.OnFailure)
- assert.Equal(t, *(*group.Containers)[1].Name, "service2")
- assert.Equal(t, group.RestartPolicy, containerinstance.OnFailure)
- }
- func TestComposeInconsistentMultiContainerRestartPolicy(t *testing.T) {
- project := types.Project{
- Services: []types.ServiceConfig{
- {
- Name: "service1",
- Image: "image1",
- Deploy: &types.DeployConfig{
- RestartPolicy: &types.RestartPolicy{
- Condition: "any",
- },
- },
- },
- {
- Name: "service2",
- Image: "image2",
- Deploy: &types.DeployConfig{
- RestartPolicy: &types.RestartPolicy{
- Condition: "on-failure",
- },
- },
- },
- },
- }
- _, err := ToContainerGroup(context.TODO(), convertCtx, project)
- assert.Error(t, err, "ACI integration does not support specifying different restart policies on containers in the same compose application")
- }
- func TestLabelsErrorMessage(t *testing.T) {
- project := types.Project{
- Services: []types.ServiceConfig{
- {
- Name: "service1",
- Image: "image1",
- Labels: map[string]string{
- "label1": "value1",
- },
- },
- },
- }
- _, err := ToContainerGroup(context.TODO(), convertCtx, project)
- assert.Error(t, err, "ACI integration does not support labels in compose applications")
- }
- func TestComposeSingleContainerGroupToContainerDefaultRestartPolicy(t *testing.T) {
- project := types.Project{
- Services: []types.ServiceConfig{
- {
- Name: "service1",
- Image: "image1",
- },
- },
- }
- group, err := ToContainerGroup(context.TODO(), convertCtx, project)
- assert.NilError(t, err)
- assert.Assert(t, is.Len(*group.Containers, 1))
- assert.Equal(t, *(*group.Containers)[0].Name, "service1")
- assert.Equal(t, group.RestartPolicy, containerinstance.Always)
- }
- func TestComposeContainerGroupToContainerMultiplePorts(t *testing.T) {
- project := types.Project{
- Services: []types.ServiceConfig{
- {
- Name: "service1",
- Image: "image1",
- Ports: []types.ServicePortConfig{
- {
- Published: 80,
- Target: 80,
- },
- },
- },
- {
- Name: "service2",
- Image: "image2",
- Ports: []types.ServicePortConfig{
- {
- Published: 8080,
- Target: 8080,
- },
- },
- },
- },
- }
- group, err := ToContainerGroup(context.TODO(), convertCtx, project)
- assert.NilError(t, err)
- assert.Assert(t, is.Len(*group.Containers, 3))
- container1 := (*group.Containers)[0]
- assert.Equal(t, *container1.Name, "service1")
- assert.Equal(t, *container1.Image, "image1")
- assert.Equal(t, *(*container1.Ports)[0].Port, int32(80))
- container2 := (*group.Containers)[1]
- assert.Equal(t, *container2.Name, "service2")
- assert.Equal(t, *container2.Image, "image2")
- assert.Equal(t, *(*container2.Ports)[0].Port, int32(8080))
- groupPorts := *group.IPAddress.Ports
- assert.Assert(t, is.Len(groupPorts, 2))
- assert.Equal(t, *groupPorts[0].Port, int32(80))
- assert.Equal(t, *groupPorts[1].Port, int32(8080))
- }
- func TestComposeContainerGroupToContainerResourceLimits(t *testing.T) {
- _0_1Gb := 0.1 * 1024 * 1024 * 1024
- project := types.Project{
- Services: []types.ServiceConfig{
- {
- Name: "service1",
- Image: "image1",
- Deploy: &types.DeployConfig{
- Resources: types.Resources{
- Limits: &types.Resource{
- NanoCPUs: "0.1",
- MemoryBytes: types.UnitBytes(_0_1Gb),
- },
- },
- },
- },
- },
- }
- group, err := ToContainerGroup(context.TODO(), convertCtx, project)
- assert.NilError(t, err)
- limits := *((*group.Containers)[0]).Resources.Limits
- assert.Equal(t, *limits.CPU, float64(0.1))
- assert.Equal(t, *limits.MemoryInGB, float64(0.1))
- }
- func TestComposeContainerGroupToContainerResourceLimitsDefaults(t *testing.T) {
- project := types.Project{
- Services: []types.ServiceConfig{
- {
- Name: "service1",
- Image: "image1",
- Deploy: &types.DeployConfig{
- Resources: types.Resources{
- Limits: &types.Resource{
- NanoCPUs: "",
- MemoryBytes: 0,
- },
- },
- },
- },
- },
- }
- group, err := ToContainerGroup(context.TODO(), convertCtx, project)
- assert.NilError(t, err)
- limits := *((*group.Containers)[0]).Resources.Limits
- assert.Equal(t, *limits.CPU, float64(1))
- assert.Equal(t, *limits.MemoryInGB, float64(1))
- }
- func TestComposeContainerGroupToContainerenvVar(t *testing.T) {
- err := os.Setenv("key2", "value2")
- assert.NilError(t, err)
- project := types.Project{
- Services: []types.ServiceConfig{
- {
- Name: "service1",
- Image: "image1",
- Environment: types.MappingWithEquals{
- "key1": to.StringPtr("value1"),
- "key2": nil,
- },
- },
- },
- }
- group, err := ToContainerGroup(context.TODO(), convertCtx, project)
- assert.NilError(t, err)
- envVars := *((*group.Containers)[0]).EnvironmentVariables
- assert.Assert(t, is.Len(envVars, 2))
- assert.Assert(t, is.Contains(envVars, containerinstance.EnvironmentVariable{Name: to.StringPtr("key1"), Value: to.StringPtr("value1")}))
- assert.Assert(t, is.Contains(envVars, containerinstance.EnvironmentVariable{Name: to.StringPtr("key2"), Value: to.StringPtr("value2")}))
- }
- func TestConvertToAciRestartPolicyCondition(t *testing.T) {
- assert.Equal(t, toAciRestartPolicy("none"), containerinstance.Never)
- assert.Equal(t, toAciRestartPolicy("always"), containerinstance.Always)
- assert.Equal(t, toAciRestartPolicy("on-failure"), containerinstance.OnFailure)
- assert.Equal(t, toAciRestartPolicy("on-failure:5"), containerinstance.Always)
- }
- func TestConvertToDockerRestartPolicyCondition(t *testing.T) {
- assert.Equal(t, toContainerRestartPolicy(containerinstance.Never), "none")
- assert.Equal(t, toContainerRestartPolicy(containerinstance.Always), "any")
- assert.Equal(t, toContainerRestartPolicy(containerinstance.OnFailure), "on-failure")
- assert.Equal(t, toContainerRestartPolicy(""), "any")
- }
- func TestConvertContainerGroupStatus(t *testing.T) {
- assert.Equal(t, "Running", GetStatus(container(to.StringPtr("Running")), group(to.StringPtr("Started"))))
- assert.Equal(t, "Terminated", GetStatus(container(to.StringPtr("Terminated")), group(to.StringPtr("Stopped"))))
- assert.Equal(t, "Node Stopped", GetStatus(container(nil), group(to.StringPtr("Stopped"))))
- assert.Equal(t, "Node Started", GetStatus(container(nil), group(to.StringPtr("Started"))))
- assert.Equal(t, "Running", GetStatus(container(to.StringPtr("Running")), group(nil)))
- assert.Equal(t, "Unknown", GetStatus(container(nil), group(nil)))
- }
- func container(status *string) containerinstance.Container {
- var state *containerinstance.ContainerState = nil
- if status != nil {
- state = &containerinstance.ContainerState{
- State: status,
- }
- }
- return containerinstance.Container{
- ContainerProperties: &containerinstance.ContainerProperties{
- InstanceView: &containerinstance.ContainerPropertiesInstanceView{
- CurrentState: state,
- },
- },
- }
- }
- func group(status *string) containerinstance.ContainerGroup {
- var view *containerinstance.ContainerGroupPropertiesInstanceView = nil
- if status != nil {
- view = &containerinstance.ContainerGroupPropertiesInstanceView{
- State: status,
- }
- }
- return containerinstance.ContainerGroup{
- ContainerGroupProperties: &containerinstance.ContainerGroupProperties{
- InstanceView: view,
- },
- }
- }
|