Skip to content

Don't attempt to remove unsupported resources on older daemon - #277

Merged
vdemeester merged 1 commit into
docker:masterfrom
thaJeztah:dont-remove-what-isnt-there
Jul 12, 2017
Merged

Don't attempt to remove unsupported resources on older daemon#277
vdemeester merged 1 commit into
docker:masterfrom
thaJeztah:dont-remove-what-isnt-there

Conversation

@thaJeztah

Copy link
Copy Markdown
Member

When running docker stack rm <some stack> against an older daemon, a warning was printed for "configs" being ignored;

WARNING: ignoring "configs" (requires API version 1.30, but the Docker daemon API version is 1.26)

Given that an old daemon cannot have configs, there should not be a need to warn, or attempt to remove these resources.

This patch removes the warning, and skips removing configs.

A check if secrets are supported by the daemon is also added, given that this would result in an error when attempted against an older (pre 1.13) daemon.

There is one situation where this could lead to secrets or configs being left behind; if the client is connecting to a daemon that does support secrets, configs, but the API version is overridden using DOCKER_API_VERSION, no warning is printed, and secrets and configs are not attempted to be removed.

Given that DOCKER_API_VERSION is regarded a feature for debugging / "power users", it should be ok to ignore this.

ping @dnephin@vdemeester@briantd

@codecov-io

codecov-io commented Jul 1, 2017

Copy link
Copy Markdown

Codecov Report

Merging #277 into master will increase coverage by 0.01%.
The diff coverage is 66.66%.

@@ Coverage Diff @@## master #277 +/- ##
=========================================
+ Coverage 48.68% 48.7% +0.01% 
=========================================
Files 186 186 Lines 12416 12413 -3 =========================================
+ Hits 6045 6046 +1 + Misses 5996 5995 -1 + Partials 375 372 -3

@thaJeztah

Copy link
Copy Markdown
MemberAuthor

Actually, I realised this is what we had originally in #182, but I failed to see that we only called these endpoints on removal, not in other cases 😓

Comment threadcli/command/stack/remove.go Outdated
errs []string
secrets []swarm.Secret
configs []swarm.Config
)

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is a minor nit, but I think it's generally better to keep variable declarations closer to the code where they are used. It makes it easier to see the scope of the variable and to refactor the code later.

So these could move to immediately before the if versions... check for each

Copy link
Copy Markdown
MemberAuthor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Updated; was thinking that declaring the variables inside the loop was bad, but reading up, Go is smart enough to handle that 👍

Comment threadcli/command/stack/remove.go Outdated
configs []swarm.Config
)

version, err := client.ServerVersion(ctx)

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I missed this in the earlier PR. I think we should already have version stored, we shouldn't need to make another API call.

It's available from cli.Client().ClientVersion(). The name is misleading, but this version was already set from the server version.

Copy link
Copy Markdown
MemberAuthor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Ok, so I tried using this, but ran into issues. the ClientVersion() is returning cli.version

cli.version is only set by NegotiateAPIVersionPing(), and NewClient(), both of which are not used for our fakeClient.

I decided to use the "old" approach for now, but we should look into this, as it's only an issue for testing

Perhaps you have a trick up your sleeve to make it work though 😄

Comment threadcli/command/stack/remove.go Outdated
if versions.GreaterThanOrEqualTo(version.APIVersion, "1.25") {
hasError = removeSecrets(ctx, dockerCli, secrets) || hasError
}
if versions.GreaterThanOrEqualTo(version.APIVersion, "1.30") {

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

These two conditions aren't necessary because removeSecrets() and removeConfigs() iterate over the array, so it's already a no-op if they are empty.

@thaJeztah
thaJeztahforce-pushed the dont-remove-what-isnt-there branch 2 times, most recently from 813ae2f to 87cb17aCompareJuly 5, 2017 03:58
@thaJeztah

Copy link
Copy Markdown
MemberAuthor

@dnephin@vdemeester updated PTAL

@dnephin

Copy link
Copy Markdown
Contributor

test failures

@thaJeztah
thaJeztahforce-pushed the dont-remove-what-isnt-there branch from 87cb17a to ac5093cCompareJuly 10, 2017 23:28
@thaJeztah

Copy link
Copy Markdown
MemberAuthor

Tests are passing again, see my comments above 👍

Comment threadcli/command/stack/remove.go Outdated
client := dockerCli.Client()
ctx := context.Background()

version, err := client.ServerVersion(ctx)

@dnephindnephinJul 11, 2017

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

~You can set ClientVersion() to the version you want like this:~~

&fakeClient{
Client: client.NewClient("http://example.com", apiVersion, nil, nil),
...
}

Edit: Or an even better option would be to add ClientVersion() and version string to fakeClient{} and have it return that version.

Copy link
Copy Markdown
MemberAuthor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think I tried adding version and ClientVersion() to fakeClient{}, but it didn't satisfy the Interface. Hm, let me check, perhaps I didn't

Copy link
Copy Markdown
MemberAuthor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Oh, I know what I did 🤦‍♂️ - yes this works, thanks! Adding some additional test-cases for different versions now

@thaJeztah
thaJeztahforce-pushed the dont-remove-what-isnt-there branch from ac5093c to 2863ee2CompareJuly 11, 2017 17:27
When running `docker stack rm <some stack>` against an older daemon,
a warning was printed for "configs" being ignored;
WARNING: ignoring "configs" (requires API version 1.30, but the Docker daemon API version is 1.26)
Given that an old daemon cannot _have_ configs, there should not be
a need to warn, or _attempt_ to remove these resources.
This patch removes the warning, and skips fetching (and removing)
configs.
A check if _secrets_ are supported by the daemon is also added,
given that this would result in an error when attempted against
an older (pre 1.13) daemon.
There is one situation where this could lead to secrets or
configs being left behind; if the client is connecting to a
daemon that _does_ support secrets, configs, but the API version
is overridden using `DOCKER_API_VERSION`, no warning is printed,
and secrets and configs are not attempted to be removed.
Given that `DOCKER_API_VERSION` is regarded a feature for
debugging / "power users", it should be ok to ignore this.
Signed-off-by: Sebastiaan van Stijn <github@gone.nl>
@thaJeztah
thaJeztahforce-pushed the dont-remove-what-isnt-there branch from 2863ee2 to 2429f15CompareJuly 11, 2017 17:29

@dnephindnephin left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM

assert.NoError(t, cmd.Execute())
assert.Equal(t, allServiceIDs, cli.removedServices)
assert.Equal(t, allNetworkIDs, cli.removedNetworks)
assert.Nil(t, cli.removedSecrets)

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I generally prefer to make these separate test cases instead of inline comments. It's never really clear where an inline comment ends. With a separate test function the scope is obvious.

Any shared setup can be moved into a helper function to remove the duplication, which also helps make the test more readable.

This is a minor style thing, so not blocking.

@vdemeestervdemeester left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM 🐸
Agreeing with @dnephin on the separate tests though 👼

@thaJeztah

Copy link
Copy Markdown
MemberAuthor

yes; at first was doubting to make it a test-table, or separate tests, but kept it like this; I can update if you want, or do a follow up. If we want this into 17.06.1, perhaps a follow up

@vdemeester

Copy link
Copy Markdown
Collaborator

@thaJeztah counting on you for the follow-up 👼 🤗

@vdemeester
vdemeester merged commit 87345ed into docker:masterJul 12, 2017
@GordonTheTurtleGordonTheTurtle added this to the 17.07.0 milestone Jul 12, 2017
@thaJeztah
thaJeztah deleted the dont-remove-what-isnt-there branch August 1, 2017 14:00
Sign up for freeto join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.

5 participants

@thaJeztah@codecov-io@dnephin@vdemeester@GordonTheTurtle