1
0
Fork 0

Merge branch 'v1.6' into master

This commit is contained in:
Fernandez Ludovic 2018-04-25 08:22:17 +02:00
commit 3b3ca89483
55 changed files with 844 additions and 569 deletions

View file

@ -19,7 +19,7 @@ type Account struct {
const (
// RegistrationURLPathV1Regexp is a regexp which match ACME registration URL in the V1 format
RegistrationURLPathV1Regexp string = `^.*/acme/reg/\d+$`
RegistrationURLPathV1Regexp = `^.*/acme/reg/\d+$`
)
// NewAccount creates an account

View file

@ -330,7 +330,6 @@ func (p *Provider) Provide(configurationChan chan<- types.ConfigMessage, pool *s
safe.Go(func() {
if _, err := p.resolveCertificate(domain, true); err != nil {
log.Errorf("Unable to obtain ACME certificate for domains %q : %v", strings.Join(domain.ToStrArray(), ","), err)
} else {
}
})
}
@ -384,15 +383,6 @@ func (p *Provider) watchCertificate() {
})
}
func (p *Provider) deleteCertificateForDomain(domain types.Domain) {
for k, cert := range p.certificates {
if reflect.DeepEqual(cert.Domain, domain) {
p.certificates = append(p.certificates[:k], p.certificates[k+1:]...)
}
}
p.saveCertificates()
}
func (p *Provider) saveCertificates() {
err := p.Store.SaveCertificates(p.certificates)
if err != nil {

View file

@ -237,19 +237,6 @@ func hasTag(name string, tags []string) bool {
return false
}
func hasTagPrefix(name string, tags []string) bool {
lowerName := strings.ToLower(name)
for _, tag := range tags {
lowerTag := strings.ToLower(tag)
if strings.HasPrefix(lowerTag, lowerName) {
return true
}
}
return false
}
func getTag(name string, tags []string, defaultValue string) string {
lowerName := strings.ToLower(name)

View file

@ -156,17 +156,6 @@ func (p *Provider) getFuncSliceAttribute(name string) func(tags []string) []stri
}
}
// Deprecated
func (p *Provider) getMapAttribute(name string, tags []string) map[string]string {
rawValue := getTag(p.getPrefixedName(name), tags, "")
if len(rawValue) == 0 {
return nil
}
return label.ParseMapValue(p.getPrefixedName(name), rawValue)
}
// Deprecated
func (p *Provider) getFuncIntAttribute(name string, defaultValue int) func(tags []string) int {
return func(tags []string) int {
@ -180,13 +169,6 @@ func (p *Provider) getFuncBoolAttribute(name string, defaultValue bool) func(tag
}
}
// Deprecated
func (p *Provider) getFuncHasAttributePrefix(name string) func(tags []string) bool {
return func(tags []string) bool {
return p.hasAttributePrefix(name, tags)
}
}
// Deprecated
func (p *Provider) getInt64Attribute(name string, tags []string, defaultValue int64) int64 {
rawValue := getTag(p.getPrefixedName(name), tags, "")
@ -244,7 +226,3 @@ func (p *Provider) getBoolAttribute(name string, tags []string, defaultValue boo
}
return value
}
func (p *Provider) hasAttributePrefix(name string, tags []string) bool {
return hasTagPrefix(p.getPrefixedName(name), tags)
}

View file

@ -182,19 +182,20 @@ func (p *Provider) getFrontendRule(container dockerData, segmentLabels map[strin
return value
}
domain := label.GetStringValue(segmentLabels, label.TraefikDomain, p.Domain)
if values, err := label.GetStringMultipleStrict(container.Labels, labelDockerComposeProject, labelDockerComposeService); err == nil {
return "Host:" + getSubDomain(values[labelDockerComposeService]+"."+values[labelDockerComposeProject]) + "." + p.Domain
return "Host:" + getSubDomain(values[labelDockerComposeService]+"."+values[labelDockerComposeProject]) + "." + domain
}
if len(p.Domain) > 0 {
return "Host:" + getSubDomain(container.ServiceName) + "." + p.Domain
if len(domain) > 0 {
return "Host:" + getSubDomain(container.ServiceName) + "." + domain
}
return ""
}
func (p Provider) getIPAddress(container dockerData) string {
if value := label.GetStringValue(container.Labels, labelDockerNetwork, ""); value != "" {
networkSettings := container.NetworkSettings
if networkSettings.Networks != nil {
@ -246,6 +247,8 @@ func (p Provider) getIPAddress(container dockerData) string {
for _, network := range container.NetworkSettings.Networks {
return network.Addr
}
log.Warnf("Unable to find the IP address for the container %q.", container.Name)
return ""
}
@ -314,12 +317,17 @@ func (p *Provider) getServers(containers []dockerData) map[string]types.Server {
var servers map[string]types.Server
for i, container := range containers {
ip := p.getIPAddress(container)
if len(ip) == 0 {
log.Warnf("Unable to find the IP address for the container %q: the server is ignored.", container.Name)
continue
}
if servers == nil {
servers = make(map[string]types.Server)
}
protocol := label.GetStringValue(container.SegmentLabels, label.TraefikProtocol, label.DefaultProtocol)
ip := p.getIPAddress(container)
port := getPort(container)
serverName := "server-" + container.SegmentName + "-" + container.Name

View file

@ -406,6 +406,7 @@ func TestDockerBuildConfiguration(t *testing.T) {
test := test
t.Run(test.desc, func(t *testing.T) {
t.Parallel()
var dockerDataList []dockerData
for _, cont := range test.containers {
dData := parseContainer(cont)
@ -809,15 +810,19 @@ func TestDockerGetFrontendRule(t *testing.T) {
expected: "Host:foo.docker.localhost",
},
{
container: containerJSON(name("bar")),
expected: "Host:bar.docker.localhost",
container: containerJSON(name("foo"),
labels(map[string]string{
label.TraefikDomain: "traefik.localhost",
})),
expected: "Host:foo.traefik.localhost",
},
{
container: containerJSON(labels(map[string]string{
label.TraefikFrontendRule: "Host:foo.bar",
})),
expected: "Host:foo.bar",
}, {
},
{
container: containerJSON(labels(map[string]string{
"com.docker.compose.project": "foo",
"com.docker.compose.service": "bar",
@ -1022,3 +1027,122 @@ func TestDockerGetPort(t *testing.T) {
})
}
}
func TestDockerGetServers(t *testing.T) {
p := &Provider{}
testCases := []struct {
desc string
containers []docker.ContainerJSON
expected map[string]types.Server
}{
{
desc: "no container",
expected: nil,
},
{
desc: "with a simple container",
containers: []docker.ContainerJSON{
containerJSON(
name("test1"),
withNetwork("testnet", ipv4("10.10.10.10")),
ports(nat.PortMap{
"80/tcp": {},
})),
},
expected: map[string]types.Server{
"server-test1": {
URL: "http://10.10.10.10:80",
Weight: 1,
},
},
},
{
desc: "with several containers",
containers: []docker.ContainerJSON{
containerJSON(
name("test1"),
withNetwork("testnet", ipv4("10.10.10.11")),
ports(nat.PortMap{
"80/tcp": {},
})),
containerJSON(
name("test2"),
withNetwork("testnet", ipv4("10.10.10.12")),
ports(nat.PortMap{
"81/tcp": {},
})),
containerJSON(
name("test3"),
withNetwork("testnet", ipv4("10.10.10.13")),
ports(nat.PortMap{
"82/tcp": {},
})),
},
expected: map[string]types.Server{
"server-test1": {
URL: "http://10.10.10.11:80",
Weight: 1,
},
"server-test2": {
URL: "http://10.10.10.12:81",
Weight: 1,
},
"server-test3": {
URL: "http://10.10.10.13:82",
Weight: 1,
},
},
},
{
desc: "ignore one container because no ip address",
containers: []docker.ContainerJSON{
containerJSON(
name("test1"),
withNetwork("testnet", ipv4("")),
ports(nat.PortMap{
"80/tcp": {},
})),
containerJSON(
name("test2"),
withNetwork("testnet", ipv4("10.10.10.12")),
ports(nat.PortMap{
"81/tcp": {},
})),
containerJSON(
name("test3"),
withNetwork("testnet", ipv4("10.10.10.13")),
ports(nat.PortMap{
"82/tcp": {},
})),
},
expected: map[string]types.Server{
"server-test2": {
URL: "http://10.10.10.12:81",
Weight: 1,
},
"server-test3": {
URL: "http://10.10.10.13:82",
Weight: 1,
},
},
},
}
for _, test := range testCases {
test := test
t.Run(test.desc, func(t *testing.T) {
t.Parallel()
var dockerDataList []dockerData
for _, cont := range test.containers {
dData := parseContainer(cont)
dockerDataList = append(dockerDataList, dData)
}
servers := p.getServers(dockerDataList)
assert.Equal(t, test.expected, servers)
})
}
}

View file

@ -561,8 +561,11 @@ func TestSwarmGetFrontendRule(t *testing.T) {
networks: map[string]*docker.NetworkResource{},
},
{
service: swarmService(serviceName("bar")),
expected: "Host:bar.docker.localhost",
service: swarmService(serviceName("foo"),
serviceLabels(map[string]string{
label.TraefikDomain: "traefik.localhost",
})),
expected: "Host:foo.traefik.localhost",
networks: map[string]*docker.NetworkResource{},
},
{

View file

@ -27,12 +27,14 @@ func (p Provider) getFrontendRuleV1(container dockerData) string {
return value
}
domain := label.GetStringValue(container.Labels, label.TraefikDomain, p.Domain)
if values, err := label.GetStringMultipleStrict(container.Labels, labelDockerComposeProject, labelDockerComposeService); err == nil {
return "Host:" + getSubDomain(values[labelDockerComposeService]+"."+values[labelDockerComposeProject]) + "." + p.Domain
return "Host:" + getSubDomain(values[labelDockerComposeService]+"."+values[labelDockerComposeProject]) + "." + domain
}
if len(p.Domain) > 0 {
return "Host:" + getSubDomain(container.ServiceName) + "." + p.Domain
if len(domain) > 0 {
return "Host:" + getSubDomain(container.ServiceName) + "." + domain
}
return ""

View file

@ -752,15 +752,19 @@ func TestDockerGetFrontendRuleV1(t *testing.T) {
expected: "Host:foo.docker.localhost",
},
{
container: containerJSON(name("bar")),
expected: "Host:bar.docker.localhost",
container: containerJSON(name("foo"),
labels(map[string]string{
label.TraefikDomain: "traefik.localhost",
})),
expected: "Host:foo.traefik.localhost",
},
{
container: containerJSON(labels(map[string]string{
label.TraefikFrontendRule: "Host:foo.bar",
})),
expected: "Host:foo.bar",
}, {
},
{
container: containerJSON(labels(map[string]string{
"com.docker.compose.project": "foo",
"com.docker.compose.service": "bar",

View file

@ -527,8 +527,11 @@ func TestSwarmGetFrontendRuleV1(t *testing.T) {
networks: map[string]*docker.NetworkResource{},
},
{
service: swarmService(serviceName("bar")),
expected: "Host:bar.docker.localhost",
service: swarmService(serviceName("foo"),
serviceLabels(map[string]string{
label.TraefikDomain: "traefik.localhost",
})),
expected: "Host:foo.traefik.localhost",
networks: map[string]*docker.NetworkResource{},
},
{

View file

@ -136,12 +136,6 @@ func getFuncServiceIntLabelV1(labelSuffix string, defaultValue int) func(contain
}
}
// Deprecated
func hasStrictServiceLabelV1(serviceLabels map[string]string, labelSuffix string) bool {
value, ok := serviceLabels[labelSuffix]
return ok && len(value) > 0
}
// Deprecated
func getServiceStringValueV1(container dockerData, serviceLabels map[string]string, labelSuffix string, defaultValue string) string {
if value, ok := serviceLabels[labelSuffix]; ok {
@ -150,23 +144,6 @@ func getServiceStringValueV1(container dockerData, serviceLabels map[string]stri
return label.GetStringValue(container.Labels, label.Prefix+labelSuffix, defaultValue)
}
// Deprecated
func getStrictServiceStringValueV1(serviceLabels map[string]string, labelSuffix string, defaultValue string) string {
if value, ok := serviceLabels[labelSuffix]; ok {
return value
}
return defaultValue
}
// Deprecated
func getServiceMapValueV1(container dockerData, serviceLabels map[string]string, serviceName string, labelSuffix string) map[string]string {
if value, ok := serviceLabels[labelSuffix]; ok {
lblName := label.GetServiceLabel(labelSuffix, serviceName)
return label.ParseMapValue(lblName, value)
}
return label.GetMapValue(container.Labels, label.Prefix+labelSuffix)
}
// Deprecated
func getServiceSliceValueV1(container dockerData, serviceLabels map[string]string, labelSuffix string) []string {
if value, ok := serviceLabels[labelSuffix]; ok {
@ -197,17 +174,6 @@ func getServiceIntLabelV1(container dockerData, serviceName string, labelSuffix
return label.GetIntValue(container.Labels, label.Prefix+labelSuffix, defaultValue)
}
// Deprecated
func getServiceInt64ValueV1(container dockerData, serviceLabels map[string]string, labelSuffix string, defaultValue int64) int64 {
if rawValue, ok := serviceLabels[labelSuffix]; ok {
value, err := strconv.ParseInt(rawValue, 10, 64)
if err == nil {
return value
}
}
return label.GetInt64Value(container.Labels, label.Prefix+labelSuffix, defaultValue)
}
// Deprecated
func getServiceLabelsV1(container dockerData, serviceName string) label.SegmentPropertyValues {
return label.ExtractServiceProperties(container.Labels)[serviceName]

View file

@ -405,154 +405,6 @@ func TestDockerGetServiceStringValueV1(t *testing.T) {
}
}
func TestDockerHasStrictServiceLabelV1(t *testing.T) {
testCases := []struct {
desc string
serviceLabels map[string]string
labelSuffix string
expected bool
}{
{
desc: "should return false when service don't have label",
serviceLabels: map[string]string{},
labelSuffix: "",
expected: false,
},
{
desc: "should return true when service have label",
serviceLabels: map[string]string{
"foo": "bar",
},
labelSuffix: "foo",
expected: true,
},
}
for _, test := range testCases {
test := test
t.Run(test.desc, func(t *testing.T) {
t.Parallel()
actual := hasStrictServiceLabelV1(test.serviceLabels, test.labelSuffix)
assert.Equal(t, test.expected, actual)
})
}
}
func TestDockerGetStrictServiceStringValueV1(t *testing.T) {
testCases := []struct {
desc string
serviceLabels map[string]string
labelSuffix string
defaultValue string
expected string
}{
{
desc: "should return a string when the label exists",
serviceLabels: map[string]string{
"foo": "bar",
},
labelSuffix: "foo",
expected: "bar",
},
{
desc: "should return a string when the label exists and value empty",
serviceLabels: map[string]string{
"foo": "",
},
labelSuffix: "foo",
defaultValue: "cube",
expected: "",
},
{
desc: "should return the default value when the label doesn't exist",
serviceLabels: map[string]string{},
labelSuffix: "foo",
defaultValue: "cube",
expected: "cube",
},
}
for _, test := range testCases {
test := test
t.Run(test.desc, func(t *testing.T) {
t.Parallel()
actual := getStrictServiceStringValueV1(test.serviceLabels, test.labelSuffix, test.defaultValue)
assert.Equal(t, test.expected, actual)
})
}
}
func TestDockerGetServiceMapValueV1(t *testing.T) {
testCases := []struct {
desc string
container docker.ContainerJSON
serviceLabels map[string]string
serviceName string
labelSuffix string
expected map[string]string
}{
{
desc: "should return when no labels",
container: containerJSON(
name("test1"),
labels(map[string]string{})),
serviceLabels: map[string]string{},
serviceName: "soo",
labelSuffix: "foo",
expected: nil,
},
{
desc: "should return a map when label exists",
container: containerJSON(
name("test1"),
labels(map[string]string{
"traefik.foo": "bir:fii",
})),
serviceLabels: map[string]string{
"foo": "bar:foo",
},
serviceName: "soo",
labelSuffix: "foo",
expected: map[string]string{
"Bar": "foo",
},
},
{
desc: "should return a map when label exists (fallback to container labels)",
container: containerJSON(
name("test1"),
labels(map[string]string{
"traefik.foo": "bir:fii",
})),
serviceLabels: map[string]string{
"fo": "bar:foo",
},
serviceName: "soo",
labelSuffix: "foo",
expected: map[string]string{
"Bir": "fii",
},
},
}
for _, test := range testCases {
test := test
t.Run(test.desc, func(t *testing.T) {
t.Parallel()
dData := parseContainer(test.container)
actual := getServiceMapValueV1(dData, test.serviceLabels, test.serviceName, test.labelSuffix)
assert.Equal(t, test.expected, actual)
})
}
}
func TestDockerGetServiceSliceValueV1(t *testing.T) {
testCases := []struct {
desc string
@ -672,67 +524,6 @@ func TestDockerGetServiceBoolValueV1(t *testing.T) {
}
}
func TestDockerGetServiceInt64ValueV1(t *testing.T) {
testCases := []struct {
desc string
container docker.ContainerJSON
serviceLabels map[string]string
labelSuffix string
defaultValue int64
expected int64
}{
{
desc: "should return default value when no label",
container: containerJSON(
name("test1"),
labels(map[string]string{})),
serviceLabels: map[string]string{},
labelSuffix: "foo",
defaultValue: 666,
expected: 666,
},
{
desc: "should return a int64 when label",
container: containerJSON(
name("test1"),
labels(map[string]string{
"traefik.foo": "20",
})),
serviceLabels: map[string]string{
"foo": "10",
},
labelSuffix: "foo",
expected: 10,
},
{
desc: "should return a int64 when label (fallback to container labels)",
container: containerJSON(
name("test1"),
labels(map[string]string{
"traefik.foo": "20",
})),
serviceLabels: map[string]string{
"fo": "10",
},
labelSuffix: "foo",
expected: 20,
},
}
for _, test := range testCases {
test := test
t.Run(test.desc, func(t *testing.T) {
t.Parallel()
dData := parseContainer(test.container)
actual := getServiceInt64ValueV1(dData, test.serviceLabels, test.labelSuffix, test.defaultValue)
assert.Equal(t, test.expected, actual)
})
}
}
func TestDockerCheckPortLabelsV1(t *testing.T) {
testCases := []struct {
container docker.ContainerJSON

View file

@ -91,7 +91,9 @@ func (p *Provider) filterInstance(i ecsInstance) bool {
}
func (p *Provider) getFrontendRule(i ecsInstance) string {
defaultRule := "Host:" + strings.ToLower(strings.Replace(i.Name, "_", "-", -1)) + "." + p.Domain
domain := label.GetStringValue(i.TraefikLabels, label.TraefikDomain, p.Domain)
defaultRule := "Host:" + strings.ToLower(strings.Replace(i.Name, "_", "-", -1)) + "." + domain
return label.GetStringValue(i.TraefikLabels, label.TraefikFrontendRule, defaultRule)
}

View file

@ -10,6 +10,16 @@ import (
const testTaskName = "taskID"
func withAppData(app marathon.Application, segmentName string) appData {
segmentProperties := label.ExtractTraefikLabels(stringValueMap(app.Labels))
return appData{
Application: app,
SegmentLabels: segmentProperties[segmentName],
SegmentName: segmentName,
LinkedApps: nil,
}
}
// Functions related to building applications.
func withApplications(apps ...marathon.Application) *marathon.Applications {

View file

@ -210,10 +210,12 @@ func (p *Provider) getFrontendRule(app appData) string {
}
}
domain := label.GetStringValue(app.SegmentLabels, label.TraefikDomain, p.Domain)
if len(app.SegmentName) > 0 {
return "Host:" + strings.ToLower(provider.Normalize(app.SegmentName)) + "." + p.getSubDomain(app.ID) + "." + p.Domain
return "Host:" + strings.ToLower(provider.Normalize(app.SegmentName)) + "." + p.getSubDomain(app.ID) + "." + domain
}
return "Host:" + p.getSubDomain(app.ID) + "." + p.Domain
return "Host:" + p.getSubDomain(app.ID) + "." + domain
}
func getPort(task marathon.Task, app appData) string {
@ -345,6 +347,9 @@ func (p *Provider) getServer(app appData, task marathon.Task) (string, *types.Se
func (p *Provider) getServerHost(task marathon.Task, app appData) (string, error) {
if app.IPAddressPerTask == nil || p.ForceTaskHostname {
if len(task.Host) == 0 {
return "", fmt.Errorf("host is undefined for task %q app %q", task.ID, app.ID)
}
return task.Host, nil
}

View file

@ -1034,7 +1034,7 @@ func TestGetPort(t *testing.T) {
desc string
application marathon.Application
task marathon.Task
serviceName string
segmentName string
expected string
}{
{
@ -1116,23 +1116,23 @@ func TestGetPort(t *testing.T) {
},
{
desc: "multiple task ports with service index available",
application: application(withLabel(label.Prefix+"http.portIndex", "0")),
application: application(withSegmentLabel(label.TraefikPortIndex, "0", "http")),
task: task(taskPorts(80, 443)),
serviceName: "http",
segmentName: "http",
expected: "80",
},
{
desc: "multiple task ports with service port available",
application: application(withLabel(label.Prefix+"https.port", "443")),
application: application(withSegmentLabel(label.TraefikPort, "443", "https")),
task: task(taskPorts(80, 443)),
serviceName: "https",
segmentName: "https",
expected: "443",
},
{
desc: "multiple task ports with services but default port available",
application: application(withLabel(label.Prefix+"http.weight", "100")),
application: application(withSegmentLabel(label.TraefikWeight, "100", "http")),
task: task(taskPorts(80, 443)),
serviceName: "http",
segmentName: "http",
expected: "80",
},
}
@ -1142,7 +1142,7 @@ func TestGetPort(t *testing.T) {
t.Run(test.desc, func(t *testing.T) {
t.Parallel()
actual := getPortV1(test.task, test.application, test.serviceName)
actual := getPort(test.task, withAppData(test.application, test.segmentName))
assert.Equal(t, test.expected, actual)
})
@ -1153,7 +1153,7 @@ func TestGetFrontendRule(t *testing.T) {
testCases := []struct {
desc string
application marathon.Application
serviceName string
segmentName string
expected string
marathonLBCompatibility bool
}{
@ -1163,6 +1163,15 @@ func TestGetFrontendRule(t *testing.T) {
marathonLBCompatibility: true,
expected: "Host:test.marathon.localhost",
},
{
desc: "label domain",
application: application(
appID("test"),
withLabel(label.TraefikDomain, "traefik.localhost"),
),
marathonLBCompatibility: true,
expected: "Host:test.traefik.localhost",
},
{
desc: "HAProxy vhost available and LB compat disabled",
application: application(
@ -1180,7 +1189,6 @@ func TestGetFrontendRule(t *testing.T) {
},
{
desc: "frontend rule available",
application: application(
withLabel(label.TraefikFrontendRule, "Host:foo.bar"),
withLabel("HAPROXY_0_VHOST", "unused"),
@ -1189,9 +1197,9 @@ func TestGetFrontendRule(t *testing.T) {
expected: "Host:foo.bar",
},
{
desc: "service label existing",
desc: "segment label frontend rule",
application: application(withSegmentLabel(label.TraefikFrontendRule, "Host:foo.bar", "app")),
serviceName: "app",
segmentName: "app",
marathonLBCompatibility: true,
expected: "Host:foo.bar",
},
@ -1206,7 +1214,7 @@ func TestGetFrontendRule(t *testing.T) {
MarathonLBCompatibility: test.marathonLBCompatibility,
}
actual := p.getFrontendRuleV1(test.application, test.serviceName)
actual := p.getFrontendRule(withAppData(test.application, test.segmentName))
assert.Equal(t, test.expected, actual)
})
@ -1217,7 +1225,7 @@ func TestGetBackendName(t *testing.T) {
testCases := []struct {
desc string
application marathon.Application
serviceName string
segmentName string
expected string
}{
{
@ -1231,9 +1239,9 @@ func TestGetBackendName(t *testing.T) {
expected: "backendbar",
},
{
desc: "service label existing",
desc: "segment label existing",
application: application(withSegmentLabel(label.TraefikBackend, "bar", "app")),
serviceName: "app",
segmentName: "app",
expected: "backendbar",
},
}
@ -1245,7 +1253,7 @@ func TestGetBackendName(t *testing.T) {
p := &Provider{}
actual := p.getBackendNameV1(test.application, test.serviceName)
actual := p.getBackendName(withAppData(test.application, test.segmentName))
assert.Equal(t, test.expected, actual)
})
@ -1256,7 +1264,7 @@ func TestGetServers(t *testing.T) {
testCases := []struct {
desc string
application marathon.Application
serviceName string
segmentName string
expected map[string]types.Server
}{
{
@ -1304,12 +1312,14 @@ func TestGetServers(t *testing.T) {
for _, test := range testCases {
test := test
t.Run(test.desc, func(t *testing.T) {
t.Parallel()
if test.desc == "should return nil when all hosts are empty" {
t.Run(test.desc, func(t *testing.T) {
t.Parallel()
actual := p.getServersV1(test.application, test.serviceName)
actual := p.getServers(withAppData(test.application, test.segmentName))
assert.Equal(t, test.expected, actual)
})
assert.Equal(t, test.expected, actual)
})
}
}
}

View file

@ -138,10 +138,11 @@ func (p *Provider) getFrontendRuleV1(application marathon.Application, serviceNa
}
}
domain := label.GetStringValue(labels, label.SuffixDomain, p.Domain)
if len(serviceName) > 0 {
return "Host:" + strings.ToLower(provider.Normalize(serviceName)) + "." + p.getSubDomain(application.ID) + "." + p.Domain
return "Host:" + strings.ToLower(provider.Normalize(serviceName)) + "." + p.getSubDomain(application.ID) + "." + domain
}
return "Host:" + p.getSubDomain(application.ID) + "." + p.Domain
return "Host:" + p.getSubDomain(application.ID) + "." + domain
}
// Deprecated

View file

@ -760,3 +760,67 @@ func TestGetStickyV1(t *testing.T) {
})
}
}
func TestGetServersV1(t *testing.T) {
testCases := []struct {
desc string
application marathon.Application
segmentName string
expected map[string]types.Server
}{
{
desc: "should return nil when no task",
application: application(ipAddrPerTask(80)),
expected: nil,
},
{
desc: "should return nil when all hosts are empty",
application: application(
withTasks(
task(ipAddresses("1.1.1.1"), withTaskID("A"), taskPorts(80)),
task(ipAddresses("1.1.1.2"), withTaskID("B"), taskPorts(80)),
task(ipAddresses("1.1.1.3"), withTaskID("C"), taskPorts(80))),
),
expected: nil,
},
{
desc: "with 3 tasks",
application: application(
ipAddrPerTask(80),
withTasks(
task(ipAddresses("1.1.1.1"), withTaskID("A"), taskPorts(80)),
task(ipAddresses("1.1.1.2"), withTaskID("B"), taskPorts(80)),
task(ipAddresses("1.1.1.3"), withTaskID("C"), taskPorts(80))),
),
expected: map[string]types.Server{
"server-A": {
URL: "http://1.1.1.1:80",
Weight: label.DefaultWeight,
},
"server-B": {
URL: "http://1.1.1.2:80",
Weight: label.DefaultWeight,
},
"server-C": {
URL: "http://1.1.1.3:80",
Weight: label.DefaultWeight,
},
},
},
}
p := &Provider{}
for _, test := range testCases {
test := test
if test.desc == "should return nil when all hosts are empty" {
t.Run(test.desc, func(t *testing.T) {
t.Parallel()
actual := p.getServersV1(test.application, test.segmentName)
assert.Equal(t, test.expected, actual)
})
}
}
}

View file

@ -166,7 +166,9 @@ func (p *Provider) getFrontendRule(task taskData) string {
if v := label.GetStringValue(task.TraefikLabels, label.TraefikFrontendRule, ""); len(v) > 0 {
return v
}
return "Host:" + strings.ToLower(strings.Replace(p.getSubDomain(task.DiscoveryInfo.Name), "_", "-", -1)) + "." + p.Domain
domain := label.GetStringValue(task.TraefikLabels, label.TraefikDomain, p.Domain)
return "Host:" + strings.ToLower(strings.Replace(p.getSubDomain(task.DiscoveryInfo.Name), "_", "-", -1)) + "." + domain
}
func (p *Provider) getServers(tasks []taskData) map[string]types.Server {

View file

@ -660,3 +660,50 @@ func TestGetServers(t *testing.T) {
})
}
}
func TestGetFrontendRule(t *testing.T) {
p := Provider{
Domain: "mesos.localhost",
}
testCases := []struct {
desc string
mesosTask taskData
expected string
}{
{
desc: "label missing",
mesosTask: aTaskData("test",
withInfo("foo"),
),
expected: "Host:foo.mesos.localhost",
},
{
desc: "label domain",
mesosTask: aTaskData("test",
withInfo("foo"),
withLabel(label.TraefikDomain, "traefik.localhost"),
),
expected: "Host:foo.traefik.localhost",
},
{
desc: "frontend rule available",
mesosTask: aTaskData("test",
withInfo("foo"),
withLabel(label.TraefikFrontendRule, "Host:foo.bar"),
),
expected: "Host:foo.bar",
},
}
for _, test := range testCases {
test := test
t.Run(test.desc, func(t *testing.T) {
t.Parallel()
rule := p.getFrontendRule(test.mesosTask)
assert.Equal(t, test.expected, rule)
})
}
}

View file

@ -196,7 +196,9 @@ func (p *Provider) getFrontendRuleV1(task state.Task) string {
if v := getStringValueV1(task, label.TraefikFrontendRule, ""); len(v) > 0 {
return v
}
return "Host:" + strings.ToLower(strings.Replace(p.getSubDomain(task.DiscoveryInfo.Name), "_", "-", -1)) + "." + p.Domain
domain := getStringValueV1(task, label.TraefikDomain, p.Domain)
return "Host:" + strings.ToLower(strings.Replace(p.getSubDomain(task.DiscoveryInfo.Name), "_", "-", -1)) + "." + domain
}
// Deprecated

View file

@ -124,7 +124,9 @@ func (p *Provider) serviceFilter(service rancherData) bool {
}
func (p *Provider) getFrontendRule(serviceName string, labels map[string]string) string {
defaultRule := "Host:" + strings.ToLower(strings.Replace(serviceName, "/", ".", -1)) + "." + p.Domain
domain := label.GetStringValue(labels, label.TraefikDomain, p.Domain)
defaultRule := "Host:" + strings.ToLower(strings.Replace(serviceName, "/", ".", -1)) + "." + domain
return label.GetStringValue(labels, label.TraefikFrontendRule, defaultRule)
}
@ -164,6 +166,11 @@ func getServers(service rancherData) map[string]types.Server {
var servers map[string]types.Server
for index, ip := range service.Containers {
if len(ip) == 0 {
log.Warnf("Unable to find the IP address for a container in the service %q: this container is ignored.", service.Name)
continue
}
if servers == nil {
servers = make(map[string]types.Server)
}

View file

@ -729,6 +729,16 @@ func TestProviderGetFrontendRule(t *testing.T) {
},
expected: "Host:foo.rancher.localhost",
},
{
desc: "with domain label",
service: rancherData{
Name: "test-service",
Labels: map[string]string{
label.TraefikDomain: "traefik.localhost",
},
},
expected: "Host:test-service.traefik.localhost",
},
{
desc: "host with /",
service: rancherData{
@ -746,26 +756,6 @@ func TestProviderGetFrontendRule(t *testing.T) {
},
expected: "Host:foo.bar.com",
},
{
desc: "with Path label",
service: rancherData{
Name: "test-service",
Labels: map[string]string{
label.TraefikFrontendRule: "Path:/test",
},
},
expected: "Path:/test",
},
{
desc: "with PathPrefix label",
service: rancherData{
Name: "test-service",
Labels: map[string]string{
label.TraefikFrontendRule: "PathPrefix:/test2",
},
},
expected: "PathPrefix:/test2",
},
}
for _, test := range testCases {
@ -849,6 +839,18 @@ func TestGetServers(t *testing.T) {
},
expected: nil,
},
{
desc: "should return nil when no server IPs",
service: rancherData{
Labels: map[string]string{
label.TraefikWeight: "7",
},
Containers: []string{""},
Health: "healthy",
State: "active",
},
expected: nil,
},
{
desc: "should use default weight when invalid weight value",
service: rancherData{