浏览代码

Merge pull request #30813 from yongtang/30232-service-ls-ports

Add `PORTS` field for `docker service ls` (`ingress`)
Sebastiaan van Stijn 8 年之前
父节点
当前提交
fe4d7db1ec
共有 3 个文件被更改,包括 93 次插入11 次删除
  1. 21 2
      cli/command/formatter/service.go
  2. 71 9
      cli/command/formatter/service_test.go
  3. 1 0
      docs/reference/commandline/service_ls.md

+ 21 - 2
cli/command/formatter/service.go

@@ -1,6 +1,7 @@
 package formatter
 package formatter
 
 
 import (
 import (
+	"fmt"
 	"strings"
 	"strings"
 	"time"
 	"time"
 
 
@@ -391,7 +392,7 @@ func (ctx *serviceInspectContext) Ports() []swarm.PortConfig {
 }
 }
 
 
 const (
 const (
-	defaultServiceTableFormat = "table {{.ID}}\t{{.Name}}\t{{.Mode}}\t{{.Replicas}}\t{{.Image}}"
+	defaultServiceTableFormat = "table {{.ID}}\t{{.Name}}\t{{.Mode}}\t{{.Replicas}}\t{{.Image}}\t{{.Ports}}"
 
 
 	serviceIDHeader = "ID"
 	serviceIDHeader = "ID"
 	modeHeader      = "MODE"
 	modeHeader      = "MODE"
@@ -410,7 +411,7 @@ func NewServiceListFormat(source string, quiet bool) Format {
 		if quiet {
 		if quiet {
 			return `id: {{.ID}}`
 			return `id: {{.ID}}`
 		}
 		}
-		return `id: {{.ID}}\nname: {{.Name}}\nmode: {{.Mode}}\nreplicas: {{.Replicas}}\nimage: {{.Image}}\n`
+		return `id: {{.ID}}\nname: {{.Name}}\nmode: {{.Mode}}\nreplicas: {{.Replicas}}\nimage: {{.Image}}\nports: {{.Ports}}\n`
 	}
 	}
 	return Format(source)
 	return Format(source)
 }
 }
@@ -439,6 +440,7 @@ func ServiceListWrite(ctx Context, services []swarm.Service, info map[string]Ser
 		"Mode":     modeHeader,
 		"Mode":     modeHeader,
 		"Replicas": replicasHeader,
 		"Replicas": replicasHeader,
 		"Image":    imageHeader,
 		"Image":    imageHeader,
+		"Ports":    portsHeader,
 	}
 	}
 	return ctx.Write(&serviceCtx, render)
 	return ctx.Write(&serviceCtx, render)
 }
 }
@@ -483,3 +485,20 @@ func (c *serviceContext) Image() string {
 
 
 	return image
 	return image
 }
 }
+
+func (c *serviceContext) Ports() string {
+	if c.service.Spec.EndpointSpec == nil || c.service.Spec.EndpointSpec.Ports == nil {
+		return ""
+	}
+	ports := []string{}
+	for _, pConfig := range c.service.Spec.EndpointSpec.Ports {
+		if pConfig.PublishMode == swarm.PortConfigPublishModeIngress {
+			ports = append(ports, fmt.Sprintf("*:%d->%d/%s",
+				pConfig.PublishedPort,
+				pConfig.TargetPort,
+				pConfig.Protocol,
+			))
+		}
+	}
+	return strings.Join(ports, ",")
+}

+ 71 - 9
cli/command/formatter/service_test.go

@@ -29,9 +29,9 @@ func TestServiceContextWrite(t *testing.T) {
 		// Table format
 		// Table format
 		{
 		{
 			Context{Format: NewServiceListFormat("table", false)},
 			Context{Format: NewServiceListFormat("table", false)},
-			`ID                  NAME                MODE                REPLICAS            IMAGE
-id_baz              baz                 global              2/4                 
-id_bar              bar                 replicated          2/4                 
+			`ID                  NAME                MODE                REPLICAS            IMAGE               PORTS
+id_baz              baz                 global              2/4                                     *:80->8080/tcp
+id_bar              bar                 replicated          2/4                                     *:80->8080/tcp
 `,
 `,
 		},
 		},
 		{
 		{
@@ -62,12 +62,14 @@ name: baz
 mode: global
 mode: global
 replicas: 2/4
 replicas: 2/4
 image: 
 image: 
+ports: *:80->8080/tcp
 
 
 id: id_bar
 id: id_bar
 name: bar
 name: bar
 mode: replicated
 mode: replicated
 replicas: 2/4
 replicas: 2/4
 image: 
 image: 
+ports: *:80->8080/tcp
 
 
 `,
 `,
 		},
 		},
@@ -88,8 +90,38 @@ bar
 
 
 	for _, testcase := range cases {
 	for _, testcase := range cases {
 		services := []swarm.Service{
 		services := []swarm.Service{
-			{ID: "id_baz", Spec: swarm.ServiceSpec{Annotations: swarm.Annotations{Name: "baz"}}},
-			{ID: "id_bar", Spec: swarm.ServiceSpec{Annotations: swarm.Annotations{Name: "bar"}}},
+			{
+				ID: "id_baz",
+				Spec: swarm.ServiceSpec{
+					Annotations: swarm.Annotations{Name: "baz"},
+					EndpointSpec: &swarm.EndpointSpec{
+						Ports: []swarm.PortConfig{
+							{
+								PublishMode:   "ingress",
+								PublishedPort: 80,
+								TargetPort:    8080,
+								Protocol:      "tcp",
+							},
+						},
+					},
+				},
+			},
+			{
+				ID: "id_bar",
+				Spec: swarm.ServiceSpec{
+					Annotations: swarm.Annotations{Name: "bar"},
+					EndpointSpec: &swarm.EndpointSpec{
+						Ports: []swarm.PortConfig{
+							{
+								PublishMode:   "ingress",
+								PublishedPort: 80,
+								TargetPort:    8080,
+								Protocol:      "tcp",
+							},
+						},
+					},
+				},
+			},
 		}
 		}
 		info := map[string]ServiceListInfo{
 		info := map[string]ServiceListInfo{
 			"id_baz": {
 			"id_baz": {
@@ -114,8 +146,38 @@ bar
 
 
 func TestServiceContextWriteJSON(t *testing.T) {
 func TestServiceContextWriteJSON(t *testing.T) {
 	services := []swarm.Service{
 	services := []swarm.Service{
-		{ID: "id_baz", Spec: swarm.ServiceSpec{Annotations: swarm.Annotations{Name: "baz"}}},
-		{ID: "id_bar", Spec: swarm.ServiceSpec{Annotations: swarm.Annotations{Name: "bar"}}},
+		{
+			ID: "id_baz",
+			Spec: swarm.ServiceSpec{
+				Annotations: swarm.Annotations{Name: "baz"},
+				EndpointSpec: &swarm.EndpointSpec{
+					Ports: []swarm.PortConfig{
+						{
+							PublishMode:   "ingress",
+							PublishedPort: 80,
+							TargetPort:    8080,
+							Protocol:      "tcp",
+						},
+					},
+				},
+			},
+		},
+		{
+			ID: "id_bar",
+			Spec: swarm.ServiceSpec{
+				Annotations: swarm.Annotations{Name: "bar"},
+				EndpointSpec: &swarm.EndpointSpec{
+					Ports: []swarm.PortConfig{
+						{
+							PublishMode:   "ingress",
+							PublishedPort: 80,
+							TargetPort:    8080,
+							Protocol:      "tcp",
+						},
+					},
+				},
+			},
+		},
 	}
 	}
 	info := map[string]ServiceListInfo{
 	info := map[string]ServiceListInfo{
 		"id_baz": {
 		"id_baz": {
@@ -128,8 +190,8 @@ func TestServiceContextWriteJSON(t *testing.T) {
 		},
 		},
 	}
 	}
 	expectedJSONs := []map[string]interface{}{
 	expectedJSONs := []map[string]interface{}{
-		{"ID": "id_baz", "Name": "baz", "Mode": "global", "Replicas": "2/4", "Image": ""},
-		{"ID": "id_bar", "Name": "bar", "Mode": "replicated", "Replicas": "2/4", "Image": ""},
+		{"ID": "id_baz", "Name": "baz", "Mode": "global", "Replicas": "2/4", "Image": "", "Ports": "*:80->8080/tcp"},
+		{"ID": "id_bar", "Name": "bar", "Mode": "replicated", "Replicas": "2/4", "Image": "", "Ports": "*:80->8080/tcp"},
 	}
 	}
 
 
 	out := bytes.NewBufferString("")
 	out := bytes.NewBufferString("")

+ 1 - 0
docs/reference/commandline/service_ls.md

@@ -137,6 +137,7 @@ Placeholder | Description
 `.Mode`     | Service mode (replicated, global)
 `.Mode`     | Service mode (replicated, global)
 `.Replicas` | Service replicas
 `.Replicas` | Service replicas
 `.Image`    | Service image
 `.Image`    | Service image
+`.Ports`    | Service ports published in ingress mode
 
 
 When using the `--format` option, the `service ls` command will either
 When using the `--format` option, the `service ls` command will either
 output the data exactly as the template declares or, when using the
 output the data exactly as the template declares or, when using the