Skip to content

Remove pkg/testutil/assert in favor of testify#32614

Merged
dnephin merged 1 commit intomoby:masterfrom
aaronlehmann:testify
Apr 17, 2017
Merged

Remove pkg/testutil/assert in favor of testify#32614
dnephin merged 1 commit intomoby:masterfrom
aaronlehmann:testify

Conversation

@aaronlehmann
Copy link
Copy Markdown

@aaronlehmann aaronlehmann commented Apr 13, 2017

I noticed that we're using a homegrown package for assertions. The
functions are extremely similar to testify, but with enough slight
differences to be confusing (for example, Equal takes its arguments in a
different order). We already vendor testify, and it's used in a few
places by tests.

I also found some problems with pkg/testutil/assert. For example, the
NotNil function seems to be broken. It checks the argument against
nil, which only works for an interface. If you pass in a nil map or
slice, the equality check will fail.

In the interest of avoiding NIH, I'm proposing replacing
pkg/testutil/assert with testify. The test code looks almost the same,
but we avoid the confusion of having two similar but slightly different
assertion packages, and having to maintain our own package instead of
using a commonly-used one.

In the process, I found a few places where the tests should halt if an
assertion fails, so I've made those cases (that I noticed) use require
instead of assert, and I've vendored the require package from
testify alongside the already-present assert package.

cc @dnephin @vdemeester

@dnephin
Copy link
Copy Markdown
Member

dnephin commented Apr 13, 2017

SGTM

The functions are extremely similar to testify

By design! So that someday we could do exactly this. At the time pkg/testutil/assert was added we weren't using testify yet.

testify/assert also has an additional features that makes it easier to use with tabletests. The assertions accept an additional arg that you can pass a string which describes the test. It makes it a lot easier to find the failing case in a table of tests.

@dnephin
Copy link
Copy Markdown
Member

dnephin commented Apr 14, 2017

I think the only thing missing from testify is a single line assert.Error() statement. The testify one only takes an error, so you have to write this:

require.Error(t, err)
assert.Contains(t, err.Error(), expectedError)

The problem is that I think this encourages people to skip checking the error message and only check that there is some error.

Maybe we could leave testutils/assert for a couple helpers and just change their implementation to use testify?

@aaronlehmann
Copy link
Copy Markdown
Author

You can do require.Error(t, err, expectedError) with testify. I have this in many places in the PR.

The difference between testify and testutil/assert is that it checks for an exact match on the error message (which arguably is a good thing to encourage in tests). If you want to check for a substring, it does take an extra line.

I only encountered one place where this came up. If it turns out to be generally useful, I'm fine with having a helper function to do it in a single line (perhaps in testutil/helpers?)

@dnephin
Copy link
Copy Markdown
Member

dnephin commented Apr 14, 2017

Ah, so there is require.EqualError(), I might try submitting a PR for require.ErrorContains()

@aaronlehmann
Copy link
Copy Markdown
Author

Ah, yes, you need to use EqualError for that behavior.

Most of the places in this PR unintentionally dropped the error string checking. I'll either add the helper or update tests to check for full error strings where appropriate.

@vieux
Copy link
Copy Markdown
Contributor

vieux commented Apr 14, 2017

SGTM

@aaronlehmann
Copy link
Copy Markdown
Author

Updated the PR to restore error substring checking. Will work on converting cli tomorrow.

@vieux
Copy link
Copy Markdown
Contributor

vieux commented Apr 14, 2017

@aaronlehmann at least on powerpc, tests are related

@aaronlehmann
Copy link
Copy Markdown
Author

Missed a git add :). Will fix tomorrow.

I noticed that we're using a homegrown package for assertions. The
functions are extremely similar to testify, but with enough slight
differences to be confusing (for example, Equal takes its arguments in a
different order). We already vendor testify, and it's used in a few
places by tests.

I also found some problems with pkg/testutil/assert. For example, the
NotNil function seems to be broken. It checks the argument against
"nil", which only works for an interface. If you pass in a nil map or
slice, the equality check will fail.

In the interest of avoiding NIH, I'm proposing replacing
pkg/testutil/assert with testify. The test code looks almost the same,
but we avoid the confusion of having two similar but slightly different
assertion packages, and having to maintain our own package instead of
using a commonly-used one.

In the process, I found a few places where the tests should halt if an
assertion fails, so I've made those cases (that I noticed) use "require"
instead of "assert", and I've vendored the "require" package from
testify alongside the already-present "assert" package.

Signed-off-by: Aaron Lehmann <[email protected]>
@aaronlehmann aaronlehmann changed the title [WIP] Remove pkg/testutil/assert in favor of testify Remove pkg/testutil/assert in favor of testify Apr 14, 2017
@aaronlehmann
Copy link
Copy Markdown
Author

Updated the PR to fully replace testutil/assert.

@unclejack
Copy link
Copy Markdown
Contributor

Wasn't testify horribly broken? I recall testify was rejected a while ago as well.

@unclejack
Copy link
Copy Markdown
Contributor

I believe @icecrime has looked into this the last time testify was being discussed.

@aaronlehmann
Copy link
Copy Markdown
Author

How is it broken? Why is it better to have our own reimplementation?

@unclejack
Copy link
Copy Markdown
Contributor

@aaronlehmann: I'm not saying we should have our own implementation. It's just that I recall there were objections to using testify. Some issues were brought up related to some bugs in testify. I'll look this up on the tracker and post here.

@unclejack
Copy link
Copy Markdown
Contributor

unclejack commented Apr 14, 2017

@aaronlehmann: #10610 (comment) was the issue where some problems related to testify were brought up. I haven't used that code in a few years and I haven't checked if it's in a better condition since. My concern was mostly related to avoiding the package(s) if they have bugs/code quality issues. I don't have a strong opinion beyond that.

@aaronlehmann
Copy link
Copy Markdown
Author

That PR seems to be a bug fix opened by @icecrime. It was merged more than two years ago.

I don't have a particular attachment to testify, though we use it in swarmkit and haven't encountered any bugs. However, I'm troubled that we've implemented our own assert package that's subtly incompatible. I'd strongly recommend we switch to testify unless anyone knows of outstanding bugs or quality issues.

@vieux
Copy link
Copy Markdown
Contributor

vieux commented Apr 16, 2017

as @aaronlehmann said, it seems like the issue in testify has been fixed upstream. I don't see a reason to not merge this one. LGTM

Copy link
Copy Markdown
Member

@vdemeester vdemeester left a comment

Choose a reason for hiding this comment

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

LGTM 👼

Copy link
Copy Markdown
Member

@dnephin dnephin left a comment

Choose a reason for hiding this comment

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

LGTM

assert.Equal(t, expected, b.image)
assert.Equal(t, expected, b.from.ImageID())
assert.Len(t, b.buildArgs.GetAllAllowed(), 0)
assert.Len(t, b.buildArgs.GetAllMeta(), 1)
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

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

I think this is a good example of an inconsistency in the design of testify.
assert.Len(), assert.Contains(), and assert.EqualError() have actual as the first arg, and expected as the second.

The args for assert.Equal(t, expected, actual) are in the opposite order. They should have been assert.Equal(t, actual, expected) to be consistent with the other assertions.

However I don't think that's enough of a reason to keep our own implementation.

@tonistiigi
Copy link
Copy Markdown
Member

LGTM

@dnephin dnephin merged commit 1eec7b5 into moby:master Apr 17, 2017
dnephin added a commit to dnephin/docker that referenced this pull request Apr 17, 2017
Remove pkg/testutil/assert in favor of testify
Sign up for free to 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.

8 participants