Skip to content
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

Use goleak to capture goroutine leak #2606

Closed
wants to merge 1 commit into from
Closed

Use goleak to capture goroutine leak #2606

wants to merge 1 commit into from

Conversation

Ashmita152
Copy link
Contributor

Signed-off-by: Ashmita Bohara ashmita.bohara152@gmail.com

Which problem is this PR solving?

This PR uses goleak (https://github.com/uber-go/goleak) to identify goroutine leak as part of unit tests.

Short description of the changes

We are adding a TestMain function for each test package. Goleak provides a way to exclude top functions, hence we are adding TolerantVerifyLeakMain with those exceptions. If this is accepted change, I'll add changes for rest of the test packages too.

Signed-off-by: Ashmita Bohara <ashmita.bohara152@gmail.com>
@Ashmita152 Ashmita152 requested a review from a team as a code owner October 29, 2020 18:20
func TolerantVerifyLeakMain(m *testing.M) {
goleak.VerifyTestMain(m,
// https://github.com/census-instrumentation/opencensus-go/blob/d7677d6af5953e0506ac4c08f349c62b917a443a/stats/view/worker.go#L34
goleak.IgnoreTopFunction("go.opencensus.io/stats/view.(*worker).start"),
Copy link
Member

Choose a reason for hiding this comment

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

where do we even use opencensus?


// TolerantVerifyLeakMain verifies go leaks but excludes the go routines that are
// launched as side effects of some of our dependencies.
func TolerantVerifyLeakMain(m *testing.M) {
Copy link
Member

Choose a reason for hiding this comment

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

This is unfortunate. Seems to indicate that the tests are not closing the resources properly, or the dependencies are not exposing proper clean-up functions.

goleak.IgnoreTopFunction("k8s.io/klog/v2.(*loggingT).flushDaemon"),
goleak.IgnoreTopFunction("k8s.io/klog.(*loggingT).flushDaemon"),
// https://github.com/dgraph-io/badger/blob/v1.5.3/y/watermark.go#L54
goleak.IgnoreTopFunction("github.com/dgraph-io/badger/y.(*WaterMark).process"),
Copy link
Member

Choose a reason for hiding this comment

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

if feels like badger should really have proper clean-ups, maybe we're not invoking them?

)

func TestMain(m *testing.M) {
Copy link
Member

Choose a reason for hiding this comment

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

Manually adding these functions is not a scalable approach, next time someone will surely forget to add one.

I would prefer to have a CI check, similar to make nocover, that will fail if some packages don't have this function (assuming we want to go with checking these leaks).

Copy link
Member

@yurishkuro yurishkuro left a comment

Choose a reason for hiding this comment

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

What is the motivation for using goleak? Does it really help identify issues that are not specific to the tests themselves? E.g. by adding these calls throughout, did you actually run into places where GRs were leaked (not counting external dependencies)?

@codecov
Copy link

codecov bot commented Oct 29, 2020

Codecov Report

Merging #2606 into master will decrease coverage by 0.44%.
The diff coverage is 68.18%.

Impacted file tree graph

@@            Coverage Diff             @@
##           master    #2606      +/-   ##
==========================================
- Coverage   95.31%   94.87%   -0.45%     
==========================================
  Files         208      210       +2     
  Lines        9285     9383      +98     
==========================================
+ Hits         8850     8902      +52     
- Misses        356      402      +46     
  Partials       79       79              
Impacted Files Coverage Δ
pkg/testutils/testutils.go 0.00% <0.00%> (ø)
cmd/anonymizer/app/anonymizer/anonymizer.go 61.25% <100.00%> (ø)
pkg/testutils/logger.go 100.00% <100.00%> (ø)
...lugin/sampling/strategystore/adaptive/processor.go 99.07% <0.00%> (-0.93%) ⬇️
plugin/storage/integration/integration.go 77.90% <0.00%> (+0.55%) ⬆️

Continue to review full report at Codecov.

Legend - Click here to learn more
Δ = absolute <relative> (impact), ø = not affected, ? = missing data
Powered by Codecov. Last update 76b8fba...a50edc3. Read the comment docs.

@Ashmita152
Copy link
Contributor Author

I am very new to golang but I saw goleak is adopted by multiple open-source golang projects like thanos. I just thought it will be good to catch such leaks in unittests. I have no experience with it.
Possibly the issues with badger we noticed as part of this PR when using goleak with badgerexporter test is maybe related to the behaviour noticed in this #2459

@yurishkuro
Copy link
Member

How did you arrive at the exclusion list, by testing packages individually? I would prefer not to have any exclusions and just not enable goleaks for packages that leak, for now.

@Ashmita152
Copy link
Contributor Author

Right, I added that TestMain at each package one by one and when it fails for some package like badgerexporter, it prints the top of the stack which I added to the exclusion list. Sure I will remove that.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants