-
Notifications
You must be signed in to change notification settings - Fork 5.1k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Detect proper hostname automatically. #1345
Detect proper hostname automatically. #1345
Conversation
4a8390a
to
9cee32c
Compare
Looks like the unit tests are failing on this change... |
provider/marathon.go
Outdated
@@ -526,21 +527,22 @@ func (provider *Marathon) getBackendServer(task marathon.Task, applications []ma | |||
log.Errorf("Unable to get marathon application from task %s", task.AppID) | |||
return "" | |||
} | |||
if len(task.IPAddresses) == 0 { | |||
if application.IPAddressPerTask == nil || provider.ForceTaskHostname { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Can we turn the block into a switch-case statement? Would make things more readable IMHO.
provider/marathon_test.go
Outdated
applications := []struct { | ||
forceTaskHostname bool | ||
applications []marathon.Application | ||
task marathon.Task |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The task seems to be the same for all tests. Please define it in the loop body.
provider/marathon_test.go
Outdated
forceTaskHostname: true, | ||
applications: []marathon.Application{ | ||
{ | ||
ID: "app-with-IP-per-task-config", |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Can we call this something like app-with-hostname-enforced
?
provider/marathon_test.go
Outdated
} | ||
|
||
for _, app := range applications { | ||
provider := &Marathon{} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Please use sub-tests here. You can use the app IDs as descriptions (first parameter to the t.Run()
method).
traefik.sample.toml
Outdated
@@ -586,6 +586,14 @@ | |||
# | |||
# keepAlive = 10 | |||
|
|||
# Force the use of the task's hostname in the backend server address even in a |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think we should be a bit more elaborative here and describe the default behavior. I'm thinking of something like the following:
By default, a task's IP address (as returned by the Marathon API) is used as backend server if an IP-per-task configuration can be found; otherwise, the name of the host running the task is used.
The latter behavior can be enforced by enabling this switch.
Please also copy the description into the docs/toml.md
file.
hey @diegooliveira, any chance to get an update on the PR? Thanks. |
9cee32c
to
1f0d0ee
Compare
@diegooliveira tests are still failing. |
1f0d0ee
to
c0c556b
Compare
@emilevauge it looks like the tests are passing again. Do you think this will be merged in before the next release? |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
A few minor-ish details we need to address.
provider/marathon_test.go
Outdated
} else { | ||
// Compare backends | ||
if !reflect.DeepEqual(actualConfig.Backends, c.expectedBackends) { | ||
expected, _ := json.Marshal(c.expectedBackends) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Using JSON to display differences can be highly misleading: For instance, the serialization sometimes does not distinguish between a nil and an empty slice.
If pointers are involved, please use go-spew.Sdump
.
provider/marathon_test.go
Outdated
@@ -107,7 +110,7 @@ func TestMarathonLoadConfig(t *testing.T) { | |||
"backend-test": { | |||
Servers: map[string]types.Server{ | |||
"server-test": { | |||
URL: "http://127.0.0.1:80", | |||
URL: "http://localhost:80", |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Was there a need to change this?
provider/marathon_test.go
Outdated
"errors" | ||
"reflect" | ||
"testing" | ||
|
||
"fmt" |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Can you sort the imports alphabetically?
provider/marathon_test.go
Outdated
// Compare backends | ||
if !reflect.DeepEqual(actualConfig.Backends, c.expectedBackends) { | ||
t.Fatalf("expected %#v, got %#v", c.expectedBackends, actualConfig.Backends) | ||
t.Run(fmt.Sprintf("Running case: %s", appID), func(t *testing.T) { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I don't think you need the "Running case" prefix: it's clear we run a case when being logged.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Can we parallelize the tests? If so, please call t.Parallel()
here.
provider/marathon_test.go
Outdated
fakeClient.AssertExpectations(t) | ||
if c.expectedNil { | ||
if actualConfig != nil { | ||
t.Fatalf("Should have been nil, got %v", actualConfig) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Please say "config should have been nil, got [...]".
provider/marathon_test.go
Outdated
if !reflect.DeepEqual(actualConfig.Backends, c.expectedBackends) { | ||
expected, _ := json.Marshal(c.expectedBackends) | ||
actual, _ := json.Marshal(actualConfig.Backends) | ||
t.Fatalf("expected\t %s\n, \tgot %s\n", expected, actual) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This should be an t.Errorf
IMHO so that we can still see the frontend assertion even if the backend one fails.
provider/marathon_test.go
Outdated
} | ||
|
||
for _, app := range applications { | ||
t.Run(fmt.Sprintf("running %s", app.application.ID), func(t *testing.T) { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
No "running" here too.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Can we parallelize the tests? If so, please call t.Parallel()
here and do app := app
before the call to t.Run
to capture the loop variable.
provider/marathon_test.go
Outdated
|
||
actual := provider.getBackendServer(task, applications) | ||
if actual != app.expected { | ||
t.Errorf("App %s, expected %q, got %q", task.AppID, app.expected, actual) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
No need to include the app ID in the message: we already get that context by the first parameter to t.Run
.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Please swap the expected / got order: the actual value should go first (for consistency reasons and because that's Go-typical).
Hey @diegooliveira, do you have time for a final update? Would be great to get this feature merged before the code freeze. |
bc4173b
to
a8be80b
Compare
Wanted to make sure this important PR makes it into the upcoming version 1.3 release, so I carried the PR "in-place". Here's what I did:
@diegooliveira I hope all of this is okay with you. |
Fixes #1243. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Unsurprisingly, I approve my own changes. :-)
@containous/traefik please review. |
a8be80b
to
a3c8c99
Compare
a3c8c99
to
6cd18dc
Compare
@timoreimann nice work, sorry for the delay, busy month. The addition of spew was a nice touch. |
cb7f4bd
to
099d605
Compare
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
LGTM.
You must solve conflicts before 😉
The IP-Per-Task feature changed the behavior for clients without this configuration (using the task IP instead of task hostname). This patch make the new behavior available just for Mesos installation with IP-Per-Task enabled. It also make it possible to force the use of task's hostname.
Allows to move specific test cases to dedicated tests for new function.
- Cover error cases. - Use sub-tests.
6cd18dc
to
7eb3051
Compare
The IP-Per-Task feature changed the behavior for clients without this configuration (using the task IP instead of task hostname).
This patch make the new behavior available just for Mesos installation with IP-Per-Task enabled.
It also make it possible to force the use of task's hostname.