From 63e5c29e00be105e77f62f8983bd6f6e588c16d5 Mon Sep 17 00:00:00 2001 From: Sami Tabet Date: Fri, 1 Jun 2018 01:41:22 +0200 Subject: [PATCH] Fix mapping a range of host ports to a single container port Signed-off-by: Sami Tabet --- opts/port.go | 21 +++++++++++++-------- opts/port_test.go | 34 ++++++++++++++++++++++++++++++++++ 2 files changed, 47 insertions(+), 8 deletions(-) diff --git a/opts/port.go b/opts/port.go index 201aefafc8..a4a91b1d5d 100644 --- a/opts/port.go +++ b/opts/port.go @@ -151,17 +151,22 @@ func ConvertPortToPortConfig( if binding.HostIP != "" && binding.HostIP != "0.0.0.0" { logrus.Warnf("ignoring IP-address (%s:%s:%s) service will listen on '0.0.0.0'", binding.HostIP, binding.HostPort, port) } - hostPort, err := strconv.ParseUint(binding.HostPort, 10, 16) + + startHostPort, endHostPort, err := nat.ParsePortRange(binding.HostPort) + if err != nil && binding.HostPort != "" { return nil, fmt.Errorf("invalid hostport binding (%s) for port (%s)", binding.HostPort, port.Port()) } - ports = append(ports, swarm.PortConfig{ - //TODO Name: ? - Protocol: swarm.PortConfigProtocol(strings.ToLower(port.Proto())), - TargetPort: uint32(port.Int()), - PublishedPort: uint32(hostPort), - PublishMode: swarm.PortConfigPublishModeIngress, - }) + + for i := startHostPort; i <= endHostPort; i++ { + ports = append(ports, swarm.PortConfig{ + //TODO Name: ? + Protocol: swarm.PortConfigProtocol(strings.ToLower(port.Proto())), + TargetPort: uint32(port.Int()), + PublishedPort: uint32(i), + PublishMode: swarm.PortConfigPublishModeIngress, + }) + } } return ports, nil } diff --git a/opts/port_test.go b/opts/port_test.go index 7f07a86cfe..5677667b6c 100644 --- a/opts/port_test.go +++ b/opts/port_test.go @@ -96,6 +96,40 @@ func TestPortOptValidSimpleSyntax(t *testing.T) { }, }, }, + { + value: "80-82:8080/udp", + expected: []swarm.PortConfig{ + { + Protocol: "udp", + TargetPort: 8080, + PublishedPort: 80, + PublishMode: swarm.PortConfigPublishModeIngress, + }, + { + Protocol: "udp", + TargetPort: 8080, + PublishedPort: 81, + PublishMode: swarm.PortConfigPublishModeIngress, + }, + { + Protocol: "udp", + TargetPort: 8080, + PublishedPort: 82, + PublishMode: swarm.PortConfigPublishModeIngress, + }, + }, + }, + { + value: "80-80:8080/tcp", + expected: []swarm.PortConfig{ + { + Protocol: "tcp", + TargetPort: 8080, + PublishedPort: 80, + PublishMode: swarm.PortConfigPublishModeIngress, + }, + }, + }, } for _, tc := range testCases { var port PortOpt