mirror of
https://github.com/rcourtman/Pulse.git
synced 2026-05-19 16:27:37 +00:00
test: Add unit tests for convertDockerServices
Tests cover nil/empty inputs, basic field copying, time fields (CreatedAt/UpdatedAt with nil and zero value handling), update status conversion, endpoint ports, and labels cloning.
This commit is contained in:
parent
c2de40d696
commit
19bc5f7977
1 changed files with 461 additions and 0 deletions
|
|
@ -298,3 +298,464 @@ func TestApplyDockerReportPodmanRuntimeMetadata(t *testing.T) {
|
|||
t.Fatalf("expected docker version fallback to runtime version, got %q", host.DockerVersion)
|
||||
}
|
||||
}
|
||||
|
||||
func TestConvertDockerServices(t *testing.T) {
|
||||
t.Parallel()
|
||||
|
||||
t.Run("nil input returns nil", func(t *testing.T) {
|
||||
t.Parallel()
|
||||
result := convertDockerServices(nil)
|
||||
if result != nil {
|
||||
t.Fatalf("expected nil, got %v", result)
|
||||
}
|
||||
})
|
||||
|
||||
t.Run("empty slice returns nil", func(t *testing.T) {
|
||||
t.Parallel()
|
||||
result := convertDockerServices([]agentsdocker.Service{})
|
||||
if result != nil {
|
||||
t.Fatalf("expected nil, got %v", result)
|
||||
}
|
||||
})
|
||||
|
||||
t.Run("basic fields are copied", func(t *testing.T) {
|
||||
t.Parallel()
|
||||
input := []agentsdocker.Service{{
|
||||
ID: "svc-123",
|
||||
Name: "web",
|
||||
Stack: "mystack",
|
||||
Image: "nginx:latest",
|
||||
Mode: "replicated",
|
||||
DesiredTasks: 3,
|
||||
RunningTasks: 2,
|
||||
CompletedTasks: 1,
|
||||
}}
|
||||
|
||||
result := convertDockerServices(input)
|
||||
if len(result) != 1 {
|
||||
t.Fatalf("expected 1 service, got %d", len(result))
|
||||
}
|
||||
|
||||
svc := result[0]
|
||||
if svc.ID != "svc-123" {
|
||||
t.Errorf("ID = %q, want svc-123", svc.ID)
|
||||
}
|
||||
if svc.Name != "web" {
|
||||
t.Errorf("Name = %q, want web", svc.Name)
|
||||
}
|
||||
if svc.Stack != "mystack" {
|
||||
t.Errorf("Stack = %q, want mystack", svc.Stack)
|
||||
}
|
||||
if svc.Image != "nginx:latest" {
|
||||
t.Errorf("Image = %q, want nginx:latest", svc.Image)
|
||||
}
|
||||
if svc.Mode != "replicated" {
|
||||
t.Errorf("Mode = %q, want replicated", svc.Mode)
|
||||
}
|
||||
if svc.DesiredTasks != 3 {
|
||||
t.Errorf("DesiredTasks = %d, want 3", svc.DesiredTasks)
|
||||
}
|
||||
if svc.RunningTasks != 2 {
|
||||
t.Errorf("RunningTasks = %d, want 2", svc.RunningTasks)
|
||||
}
|
||||
if svc.CompletedTasks != 1 {
|
||||
t.Errorf("CompletedTasks = %d, want 1", svc.CompletedTasks)
|
||||
}
|
||||
})
|
||||
|
||||
t.Run("labels are cloned when present", func(t *testing.T) {
|
||||
t.Parallel()
|
||||
input := []agentsdocker.Service{{
|
||||
ID: "svc-1",
|
||||
Name: "web",
|
||||
Labels: map[string]string{
|
||||
"env": "prod",
|
||||
"version": "1.0",
|
||||
},
|
||||
}}
|
||||
|
||||
result := convertDockerServices(input)
|
||||
if result[0].Labels == nil {
|
||||
t.Fatal("expected labels to be present")
|
||||
}
|
||||
if result[0].Labels["env"] != "prod" {
|
||||
t.Errorf("Labels[env] = %q, want prod", result[0].Labels["env"])
|
||||
}
|
||||
if result[0].Labels["version"] != "1.0" {
|
||||
t.Errorf("Labels[version] = %q, want 1.0", result[0].Labels["version"])
|
||||
}
|
||||
|
||||
// Verify it's a clone, not the same map
|
||||
input[0].Labels["env"] = "modified"
|
||||
if result[0].Labels["env"] == "modified" {
|
||||
t.Error("labels should be cloned, not shared")
|
||||
}
|
||||
})
|
||||
|
||||
t.Run("empty labels are not copied", func(t *testing.T) {
|
||||
t.Parallel()
|
||||
input := []agentsdocker.Service{{
|
||||
ID: "svc-1",
|
||||
Name: "web",
|
||||
Labels: map[string]string{},
|
||||
}}
|
||||
|
||||
result := convertDockerServices(input)
|
||||
if result[0].Labels != nil {
|
||||
t.Errorf("expected nil labels for empty map, got %v", result[0].Labels)
|
||||
}
|
||||
})
|
||||
|
||||
t.Run("nil labels stay nil", func(t *testing.T) {
|
||||
t.Parallel()
|
||||
input := []agentsdocker.Service{{
|
||||
ID: "svc-1",
|
||||
Name: "web",
|
||||
Labels: nil,
|
||||
}}
|
||||
|
||||
result := convertDockerServices(input)
|
||||
if result[0].Labels != nil {
|
||||
t.Errorf("expected nil labels, got %v", result[0].Labels)
|
||||
}
|
||||
})
|
||||
|
||||
t.Run("endpoint ports are converted when present", func(t *testing.T) {
|
||||
t.Parallel()
|
||||
input := []agentsdocker.Service{{
|
||||
ID: "svc-1",
|
||||
Name: "web",
|
||||
EndpointPorts: []agentsdocker.ServicePort{
|
||||
{
|
||||
Name: "http",
|
||||
Protocol: "tcp",
|
||||
TargetPort: 80,
|
||||
PublishedPort: 8080,
|
||||
PublishMode: "ingress",
|
||||
},
|
||||
{
|
||||
Name: "https",
|
||||
Protocol: "tcp",
|
||||
TargetPort: 443,
|
||||
PublishedPort: 8443,
|
||||
PublishMode: "host",
|
||||
},
|
||||
},
|
||||
}}
|
||||
|
||||
result := convertDockerServices(input)
|
||||
if len(result[0].EndpointPorts) != 2 {
|
||||
t.Fatalf("expected 2 ports, got %d", len(result[0].EndpointPorts))
|
||||
}
|
||||
|
||||
port1 := result[0].EndpointPorts[0]
|
||||
if port1.Name != "http" {
|
||||
t.Errorf("port[0].Name = %q, want http", port1.Name)
|
||||
}
|
||||
if port1.Protocol != "tcp" {
|
||||
t.Errorf("port[0].Protocol = %q, want tcp", port1.Protocol)
|
||||
}
|
||||
if port1.TargetPort != 80 {
|
||||
t.Errorf("port[0].TargetPort = %d, want 80", port1.TargetPort)
|
||||
}
|
||||
if port1.PublishedPort != 8080 {
|
||||
t.Errorf("port[0].PublishedPort = %d, want 8080", port1.PublishedPort)
|
||||
}
|
||||
if port1.PublishMode != "ingress" {
|
||||
t.Errorf("port[0].PublishMode = %q, want ingress", port1.PublishMode)
|
||||
}
|
||||
|
||||
port2 := result[0].EndpointPorts[1]
|
||||
if port2.PublishMode != "host" {
|
||||
t.Errorf("port[1].PublishMode = %q, want host", port2.PublishMode)
|
||||
}
|
||||
})
|
||||
|
||||
t.Run("empty endpoint ports are not copied", func(t *testing.T) {
|
||||
t.Parallel()
|
||||
input := []agentsdocker.Service{{
|
||||
ID: "svc-1",
|
||||
Name: "web",
|
||||
EndpointPorts: []agentsdocker.ServicePort{},
|
||||
}}
|
||||
|
||||
result := convertDockerServices(input)
|
||||
if result[0].EndpointPorts != nil {
|
||||
t.Errorf("expected nil endpoint ports for empty slice, got %v", result[0].EndpointPorts)
|
||||
}
|
||||
})
|
||||
|
||||
t.Run("nil endpoint ports stay nil", func(t *testing.T) {
|
||||
t.Parallel()
|
||||
input := []agentsdocker.Service{{
|
||||
ID: "svc-1",
|
||||
Name: "web",
|
||||
EndpointPorts: nil,
|
||||
}}
|
||||
|
||||
result := convertDockerServices(input)
|
||||
if result[0].EndpointPorts != nil {
|
||||
t.Errorf("expected nil endpoint ports, got %v", result[0].EndpointPorts)
|
||||
}
|
||||
})
|
||||
|
||||
t.Run("update status is converted when present", func(t *testing.T) {
|
||||
t.Parallel()
|
||||
completedAt := time.Date(2025, 1, 15, 10, 30, 0, 0, time.UTC)
|
||||
input := []agentsdocker.Service{{
|
||||
ID: "svc-1",
|
||||
Name: "web",
|
||||
UpdateStatus: &agentsdocker.ServiceUpdate{
|
||||
State: "completed",
|
||||
Message: "update succeeded",
|
||||
CompletedAt: &completedAt,
|
||||
},
|
||||
}}
|
||||
|
||||
result := convertDockerServices(input)
|
||||
if result[0].UpdateStatus == nil {
|
||||
t.Fatal("expected update status to be present")
|
||||
}
|
||||
if result[0].UpdateStatus.State != "completed" {
|
||||
t.Errorf("UpdateStatus.State = %q, want completed", result[0].UpdateStatus.State)
|
||||
}
|
||||
if result[0].UpdateStatus.Message != "update succeeded" {
|
||||
t.Errorf("UpdateStatus.Message = %q, want update succeeded", result[0].UpdateStatus.Message)
|
||||
}
|
||||
if result[0].UpdateStatus.CompletedAt == nil {
|
||||
t.Fatal("expected CompletedAt to be set")
|
||||
}
|
||||
if !result[0].UpdateStatus.CompletedAt.Equal(completedAt) {
|
||||
t.Errorf("UpdateStatus.CompletedAt = %v, want %v", result[0].UpdateStatus.CompletedAt, completedAt)
|
||||
}
|
||||
})
|
||||
|
||||
t.Run("update status with nil CompletedAt", func(t *testing.T) {
|
||||
t.Parallel()
|
||||
input := []agentsdocker.Service{{
|
||||
ID: "svc-1",
|
||||
Name: "web",
|
||||
UpdateStatus: &agentsdocker.ServiceUpdate{
|
||||
State: "updating",
|
||||
Message: "in progress",
|
||||
CompletedAt: nil,
|
||||
},
|
||||
}}
|
||||
|
||||
result := convertDockerServices(input)
|
||||
if result[0].UpdateStatus == nil {
|
||||
t.Fatal("expected update status to be present")
|
||||
}
|
||||
if result[0].UpdateStatus.CompletedAt != nil {
|
||||
t.Errorf("expected nil CompletedAt, got %v", result[0].UpdateStatus.CompletedAt)
|
||||
}
|
||||
})
|
||||
|
||||
t.Run("update status with zero CompletedAt", func(t *testing.T) {
|
||||
t.Parallel()
|
||||
zeroTime := time.Time{}
|
||||
input := []agentsdocker.Service{{
|
||||
ID: "svc-1",
|
||||
Name: "web",
|
||||
UpdateStatus: &agentsdocker.ServiceUpdate{
|
||||
State: "updating",
|
||||
CompletedAt: &zeroTime,
|
||||
},
|
||||
}}
|
||||
|
||||
result := convertDockerServices(input)
|
||||
if result[0].UpdateStatus.CompletedAt != nil {
|
||||
t.Errorf("expected nil CompletedAt for zero time, got %v", result[0].UpdateStatus.CompletedAt)
|
||||
}
|
||||
})
|
||||
|
||||
t.Run("nil update status stays nil", func(t *testing.T) {
|
||||
t.Parallel()
|
||||
input := []agentsdocker.Service{{
|
||||
ID: "svc-1",
|
||||
Name: "web",
|
||||
UpdateStatus: nil,
|
||||
}}
|
||||
|
||||
result := convertDockerServices(input)
|
||||
if result[0].UpdateStatus != nil {
|
||||
t.Errorf("expected nil update status, got %v", result[0].UpdateStatus)
|
||||
}
|
||||
})
|
||||
|
||||
t.Run("CreatedAt is copied when valid", func(t *testing.T) {
|
||||
t.Parallel()
|
||||
created := time.Date(2025, 1, 10, 8, 0, 0, 0, time.UTC)
|
||||
input := []agentsdocker.Service{{
|
||||
ID: "svc-1",
|
||||
Name: "web",
|
||||
CreatedAt: &created,
|
||||
}}
|
||||
|
||||
result := convertDockerServices(input)
|
||||
if result[0].CreatedAt == nil {
|
||||
t.Fatal("expected CreatedAt to be set")
|
||||
}
|
||||
if !result[0].CreatedAt.Equal(created) {
|
||||
t.Errorf("CreatedAt = %v, want %v", result[0].CreatedAt, created)
|
||||
}
|
||||
})
|
||||
|
||||
t.Run("nil CreatedAt stays nil", func(t *testing.T) {
|
||||
t.Parallel()
|
||||
input := []agentsdocker.Service{{
|
||||
ID: "svc-1",
|
||||
Name: "web",
|
||||
CreatedAt: nil,
|
||||
}}
|
||||
|
||||
result := convertDockerServices(input)
|
||||
if result[0].CreatedAt != nil {
|
||||
t.Errorf("expected nil CreatedAt, got %v", result[0].CreatedAt)
|
||||
}
|
||||
})
|
||||
|
||||
t.Run("zero CreatedAt is not copied", func(t *testing.T) {
|
||||
t.Parallel()
|
||||
zeroTime := time.Time{}
|
||||
input := []agentsdocker.Service{{
|
||||
ID: "svc-1",
|
||||
Name: "web",
|
||||
CreatedAt: &zeroTime,
|
||||
}}
|
||||
|
||||
result := convertDockerServices(input)
|
||||
if result[0].CreatedAt != nil {
|
||||
t.Errorf("expected nil CreatedAt for zero time, got %v", result[0].CreatedAt)
|
||||
}
|
||||
})
|
||||
|
||||
t.Run("UpdatedAt is copied when valid", func(t *testing.T) {
|
||||
t.Parallel()
|
||||
updated := time.Date(2025, 1, 12, 14, 30, 0, 0, time.UTC)
|
||||
input := []agentsdocker.Service{{
|
||||
ID: "svc-1",
|
||||
Name: "web",
|
||||
UpdatedAt: &updated,
|
||||
}}
|
||||
|
||||
result := convertDockerServices(input)
|
||||
if result[0].UpdatedAt == nil {
|
||||
t.Fatal("expected UpdatedAt to be set")
|
||||
}
|
||||
if !result[0].UpdatedAt.Equal(updated) {
|
||||
t.Errorf("UpdatedAt = %v, want %v", result[0].UpdatedAt, updated)
|
||||
}
|
||||
})
|
||||
|
||||
t.Run("nil UpdatedAt stays nil", func(t *testing.T) {
|
||||
t.Parallel()
|
||||
input := []agentsdocker.Service{{
|
||||
ID: "svc-1",
|
||||
Name: "web",
|
||||
UpdatedAt: nil,
|
||||
}}
|
||||
|
||||
result := convertDockerServices(input)
|
||||
if result[0].UpdatedAt != nil {
|
||||
t.Errorf("expected nil UpdatedAt, got %v", result[0].UpdatedAt)
|
||||
}
|
||||
})
|
||||
|
||||
t.Run("zero UpdatedAt is not copied", func(t *testing.T) {
|
||||
t.Parallel()
|
||||
zeroTime := time.Time{}
|
||||
input := []agentsdocker.Service{{
|
||||
ID: "svc-1",
|
||||
Name: "web",
|
||||
UpdatedAt: &zeroTime,
|
||||
}}
|
||||
|
||||
result := convertDockerServices(input)
|
||||
if result[0].UpdatedAt != nil {
|
||||
t.Errorf("expected nil UpdatedAt for zero time, got %v", result[0].UpdatedAt)
|
||||
}
|
||||
})
|
||||
|
||||
t.Run("multiple services are converted", func(t *testing.T) {
|
||||
t.Parallel()
|
||||
input := []agentsdocker.Service{
|
||||
{ID: "svc-1", Name: "web"},
|
||||
{ID: "svc-2", Name: "api"},
|
||||
{ID: "svc-3", Name: "worker"},
|
||||
}
|
||||
|
||||
result := convertDockerServices(input)
|
||||
if len(result) != 3 {
|
||||
t.Fatalf("expected 3 services, got %d", len(result))
|
||||
}
|
||||
if result[0].ID != "svc-1" {
|
||||
t.Errorf("result[0].ID = %q, want svc-1", result[0].ID)
|
||||
}
|
||||
if result[1].ID != "svc-2" {
|
||||
t.Errorf("result[1].ID = %q, want svc-2", result[1].ID)
|
||||
}
|
||||
if result[2].ID != "svc-3" {
|
||||
t.Errorf("result[2].ID = %q, want svc-3", result[2].ID)
|
||||
}
|
||||
})
|
||||
|
||||
t.Run("full service with all fields", func(t *testing.T) {
|
||||
t.Parallel()
|
||||
created := time.Date(2025, 1, 10, 8, 0, 0, 0, time.UTC)
|
||||
updated := time.Date(2025, 1, 15, 12, 0, 0, 0, time.UTC)
|
||||
completedAt := time.Date(2025, 1, 15, 11, 30, 0, 0, time.UTC)
|
||||
|
||||
input := []agentsdocker.Service{{
|
||||
ID: "svc-full",
|
||||
Name: "fullservice",
|
||||
Stack: "production",
|
||||
Image: "myapp:v2.0",
|
||||
Mode: "global",
|
||||
DesiredTasks: 5,
|
||||
RunningTasks: 5,
|
||||
CompletedTasks: 0,
|
||||
Labels: map[string]string{
|
||||
"com.docker.stack.namespace": "production",
|
||||
},
|
||||
EndpointPorts: []agentsdocker.ServicePort{
|
||||
{Name: "web", Protocol: "tcp", TargetPort: 8080, PublishedPort: 80, PublishMode: "ingress"},
|
||||
},
|
||||
UpdateStatus: &agentsdocker.ServiceUpdate{
|
||||
State: "completed",
|
||||
Message: "rollout complete",
|
||||
CompletedAt: &completedAt,
|
||||
},
|
||||
CreatedAt: &created,
|
||||
UpdatedAt: &updated,
|
||||
}}
|
||||
|
||||
result := convertDockerServices(input)
|
||||
if len(result) != 1 {
|
||||
t.Fatalf("expected 1 service, got %d", len(result))
|
||||
}
|
||||
|
||||
svc := result[0]
|
||||
if svc.ID != "svc-full" {
|
||||
t.Errorf("ID mismatch")
|
||||
}
|
||||
if svc.Mode != "global" {
|
||||
t.Errorf("Mode = %q, want global", svc.Mode)
|
||||
}
|
||||
if svc.Labels["com.docker.stack.namespace"] != "production" {
|
||||
t.Errorf("Labels mismatch")
|
||||
}
|
||||
if len(svc.EndpointPorts) != 1 || svc.EndpointPorts[0].PublishedPort != 80 {
|
||||
t.Errorf("EndpointPorts mismatch")
|
||||
}
|
||||
if svc.UpdateStatus == nil || svc.UpdateStatus.State != "completed" {
|
||||
t.Errorf("UpdateStatus mismatch")
|
||||
}
|
||||
if svc.CreatedAt == nil || !svc.CreatedAt.Equal(created) {
|
||||
t.Errorf("CreatedAt mismatch")
|
||||
}
|
||||
if svc.UpdatedAt == nil || !svc.UpdatedAt.Equal(updated) {
|
||||
t.Errorf("UpdatedAt mismatch")
|
||||
}
|
||||
})
|
||||
}
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue