Repository: dundee/gdu
Pull request #136 (2022-04-06 12:56:56)

refactor: SignalGroup instead of chan

coveralls: ## Pull Request Test Coverage Report for [Build 2102901094](https://coveralls.io/builds/48048870)

* **14** of **20**   **(70.0%)**  changed or added relevant lines in **5** files are covered.
* No unchanged relevant lines lost coverage.
* Overall coverage decreased (**-0.2%**) to **96.187%**

---

|  Changes Missing Coverage | Covered Lines | Changed/Added Lines | % |
| :-----|--------------|--------|---: |
| [internal/common/signal.go](https://coveralls.io/builds/48048870/source?filename=internal%2Fcommon%2Fsignal.go#L5) | 0 | 6 | 0.0%
<!-- | **Total:** | **14** | **20** | **70.0%** | -->


|  Totals | [![Coverage Status](https://coveralls.io/builds/48048870/badge)](https://coveralls.io/builds/48048870) |
| :-- | --: |
| Change from base [Build 2096588428](https://coveralls.io/builds/48011923): |  -0.2% |
| Covered Lines: | 2346 |
| Relevant Lines: | 2439 |

---
##### 💛  - [Coveralls](https://coveralls.io)

codecov[bot]: # [Codecov](https://codecov.io/gh/dundee/gdu/pull/136?src=pr&el=h1&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=Daniel+Milde) Report
> Merging [#136](https://codecov.io/gh/dundee/gdu/pull/136?src=pr&el=desc&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=Daniel+Milde) (0765bf7) into [master](https://codecov.io/gh/dundee/gdu/commit/ab4e2fac6d118fe93e8bdbc7bf8e78e5c693d4ff?el=desc&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=Daniel+Milde) (ab4e2fa) will **decrease** coverage by `0.15%`.
> The diff coverage is `77.77%`.

```diff
@@            Coverage Diff             @@
##           master     #136      +/-   ##
==========================================
- Coverage   94.89%   94.74%   -0.16%     
==========================================
  Files          25       26       +1     
  Lines        2391     2396       +5     
==========================================
+ Hits         2269     2270       +1     
- Misses         87       91       +4     
  Partials       35       35              
```


| [Impacted Files](https://codecov.io/gh/dundee/gdu/pull/136?src=pr&el=tree&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=Daniel+Milde) | Coverage Δ | |
|---|---|---|
| [internal/common/signal.go](https://codecov.io/gh/dundee/gdu/pull/136/diff?src=pr&el=tree&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=Daniel+Milde#diff-aW50ZXJuYWwvY29tbW9uL3NpZ25hbC5nbw==) | `0.00% <0.00%> (ø)` | |
| [pkg/analyze/dir.go](https://codecov.io/gh/dundee/gdu/pull/136/diff?src=pr&el=tree&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=Daniel+Milde#diff-cGtnL2FuYWx5emUvZGlyLmdv) | `97.85% <100.00%> (+0.01%)` | :arrow_up: |
| [report/export.go](https://codecov.io/gh/dundee/gdu/pull/136/diff?src=pr&el=tree&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=Daniel+Milde#diff-cmVwb3J0L2V4cG9ydC5nbw==) | `92.40% <100.00%> (ø)` | |
| [stdout/stdout.go](https://codecov.io/gh/dundee/gdu/pull/136/diff?src=pr&el=tree&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=Daniel+Milde#diff-c3Rkb3V0L3N0ZG91dC5nbw==) | `100.00% <100.00%> (ø)` | |
| [tui/progress.go](https://codecov.io/gh/dundee/gdu/pull/136/diff?src=pr&el=tree&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=Daniel+Milde#diff-dHVpL3Byb2dyZXNzLmdv) | `100.00% <100.00%> (ø)` | |

------

[Continue to review full report at Codecov](https://codecov.io/gh/dundee/gdu/pull/136?src=pr&el=continue&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=Daniel+Milde).
> **Legend** - [Click here to learn more](https://docs.codecov.io/docs/codecov-delta?utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=Daniel+Milde)
> `Δ = absolute <relative> (impact)`, `ø = not affected`, `? = missing data`
> Powered by [Codecov](https://codecov.io/gh/dundee/gdu/pull/136?src=pr&el=footer&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=Daniel+Milde). Last update [ab4e2fa...0765bf7](https://codecov.io/gh/dundee/gdu/pull/136?src=pr&el=lastupdated&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=Daniel+Milde). Read the [comment docs](https://docs.codecov.io/docs/pull-request-comments?utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=Daniel+Milde).


Patch:
diff --git a/.tool-versions b/.tool-versions
new file mode 100644
index 0000000..4933a41
--- /dev/null
+++ b/.tool-versions
@@ -0,0 +1,1 @@
+golang 1.18
diff --git a/internal/common/analyze.go b/internal/common/analyze.go
index 4afce7b..152bd5e 100644
--- a/internal/common/analyze.go
+++ b/internal/common/analyze.go
@@ -16,6 +16,6 @@ type ShouldDirBeIgnored func(name, path string) bool
 type Analyzer interface {
 	AnalyzeDir(path string, ignore ShouldDirBeIgnored, constGC bool) fs.Item
 	GetProgressChan() chan CurrentProgress
-	GetDoneChan() chan struct{}
+	GetDone() SignalGroup
 	ResetProgress()
 }
diff --git a/internal/common/signal.go b/internal/common/signal.go
new file mode 100644
index 0000000..448947c
--- /dev/null
+++ b/internal/common/signal.go
@@ -0,0 +1,11 @@
+package common
+
+type SignalGroup chan struct{}
+
+func (s SignalGroup) Wait() {
+	<-s
+}
+
+func (s SignalGroup) Broadcast() {
+	close(s)
+}
diff --git a/pkg/analyze/dir.go b/pkg/analyze/dir.go
index 6ced75e..08c0b43 100644
--- a/pkg/analyze/dir.go
+++ b/pkg/analyze/dir.go
@@ -15,12 +15,13 @@ var concurrencyLimit = make(chan struct{}, 3*runtime.GOMAXPROCS(0))
 
 // ParallelAnalyzer implements Analyzer
 type ParallelAnalyzer struct {
-	progress        *common.CurrentProgress
-	progressChan    chan common.CurrentProgress
-	progressOutChan chan common.CurrentProgress
-	doneChan        chan struct{}
-	wait            *WaitGroup
-	ignoreDir       common.ShouldDirBeIgnored
+	progress         *common.CurrentProgress
+	progressChan     chan common.CurrentProgress
+	progressOutChan  chan common.CurrentProgress
+	progressDoneChan chan struct{}
+	doneChan         common.SignalGroup
+	wait             *WaitGroup
+	ignoreDir        common.ShouldDirBeIgnored
 }
 
 // CreateAnalyzer returns Analyzer
@@ -30,10 +31,11 @@ func CreateAnalyzer() *ParallelAnalyzer {
 			ItemCount: 0,
 			TotalSize: int64(0),
 		},
-		progressChan:    make(chan common.CurrentProgress, 1),
-		progressOutChan: make(chan common.CurrentProgress, 1),
-		doneChan:        make(chan struct{}, 2),
-		wait:            (&WaitGroup{}).Init(),
+		progressChan:     make(chan common.CurrentProgress, 1),
+		progressOutChan:  make(chan common.CurrentProgress, 1),
+		progressDoneChan: make(chan struct{}),
+		doneChan:         make(common.SignalGroup),
+		wait:             (&WaitGroup{}).Init(),
 	}
 }
 
@@ -43,7 +45,7 @@ func (a *ParallelAnalyzer) GetProgressChan() chan common.CurrentProgress {
 }
 
 // GetDoneChan returns channel for checking when analysis is done
-func (a *ParallelAnalyzer) GetDoneChan() chan struct{} {
+func (a *ParallelAnalyzer) GetDone() common.SignalGroup {
 	return a.doneChan
 }
 
@@ -52,7 +54,8 @@ func (a *ParallelAnalyzer) ResetProgress() {
 	a.progress = &common.CurrentProgress{}
 	a.progressChan = make(chan common.CurrentProgress, 1)
 	a.progressOutChan = make(chan common.CurrentProgress, 1)
-	a.doneChan = make(chan struct{}, 2)
+	a.progressDoneChan = make(chan struct{})
+	a.doneChan = make(common.SignalGroup)
 	a.wait = (&WaitGroup{}).Init()
 }
 
@@ -73,9 +76,8 @@ func (a *ParallelAnalyzer) AnalyzeDir(
 	dir.BasePath = filepath.Dir(path)
 	a.wait.Wait()
 
-	a.doneChan <- struct{}{} // finish updateProgress here
-	a.doneChan <- struct{}{} // and there
-	a.doneChan <- struct{}{} // and manageMemoryUsage
+	a.progressDoneChan <- struct{}{}
+	a.doneChan.Broadcast()
 
 	return dir
 }
@@ -166,7 +168,7 @@ func (a *ParallelAnalyzer) processDir(path string) *Dir {
 func (a *ParallelAnalyzer) updateProgress() {
 	for {
 		select {
-		case <-a.doneChan:
+		case <-a.progressDoneChan:
 			return
 		case progress := <-a.progressChan:
 			a.progress.CurrentItemName = progress.CurrentItemName
diff --git a/report/export.go b/report/export.go
index 2d7f576..b56cb51 100644
--- a/report/export.go
+++ b/report/export.go
@@ -147,7 +147,7 @@ func (ui *UI) updateProgress() {
 	progressRunes := []rune(`⠇⠏⠋⠙⠹⠸⠼⠴⠦⠧`)
 
 	progressChan := ui.Analyzer.GetProgressChan()
-	doneChan := ui.Analyzer.GetDoneChan()
+	doneChan := ui.Analyzer.GetDone()
 
 	var progress common.CurrentProgress
 
diff --git a/stdout/stdout.go b/stdout/stdout.go
index 8c2135b..e98fc10 100644
--- a/stdout/stdout.go
+++ b/stdout/stdout.go
@@ -303,7 +303,7 @@ func (ui *UI) updateProgress() {
 	}
 
 	progressChan := ui.Analyzer.GetProgressChan()
-	doneChan := ui.Analyzer.GetDoneChan()
+	doneChan := ui.Analyzer.GetDone()
 
 	var progress common.CurrentProgress
 
diff --git a/tui/progress.go b/tui/progress.go
index 7b11359..137e68d 100644
--- a/tui/progress.go
+++ b/tui/progress.go
@@ -13,7 +13,7 @@ func (ui *UI) updateProgress() {
 	}
 
 	progressChan := ui.Analyzer.GetProgressChan()
-	doneChan := ui.Analyzer.GetDoneChan()
+	doneChan := ui.Analyzer.GetDone()
 
 	var progress common.CurrentProgress
 


Test patch:
diff --git a/internal/testanalyze/analyze.go b/internal/testanalyze/analyze.go
index acc8173..cd61cc7 100644
--- a/internal/testanalyze/analyze.go
+++ b/internal/testanalyze/analyze.go
@@ -71,9 +71,9 @@ func (a *MockedAnalyzer) GetProgressChan() chan common.CurrentProgress {
 }
 
 // GetDoneChan returns always Done
-func (a *MockedAnalyzer) GetDoneChan() chan struct{} {
-	c := make(chan struct{}, 1)
-	defer func() { c <- struct{}{} }()
+func (a *MockedAnalyzer) GetDone() common.SignalGroup {
+	c := make(common.SignalGroup)
+	defer c.Broadcast()
 	return c
 }
 
diff --git a/pkg/analyze/dir_test.go b/pkg/analyze/dir_test.go
index ac512f9..2611b91 100644
--- a/pkg/analyze/dir_test.go
+++ b/pkg/analyze/dir_test.go
@@ -28,7 +28,7 @@ func TestAnalyzeDir(t *testing.T) {
 	progress := <-analyzer.GetProgressChan()
 	assert.GreaterOrEqual(t, progress.TotalSize, int64(0))
 
-	<-analyzer.GetDoneChan()
+	analyzer.GetDone().Wait()
 	analyzer.ResetProgress()
 	dir.UpdateStats(make(fs.HardLinkedItems))
 
@@ -93,7 +93,7 @@ func TestFlags(t *testing.T) {
 	dir := analyzer.AnalyzeDir(
 		"test_dir", func(_, _ string) bool { return false }, false,
 	).(*Dir)
-	<-analyzer.GetDoneChan()
+	analyzer.GetDone().Wait()
 	dir.UpdateStats(make(fs.HardLinkedItems))
 
 	sort.Sort(dir.Files)
@@ -121,7 +121,7 @@ func TestHardlink(t *testing.T) {
 	dir := analyzer.AnalyzeDir(
 		"test_dir", func(_, _ string) bool { return false }, false,
 	).(*Dir)
-	<-analyzer.GetDoneChan()
+	analyzer.GetDone().Wait()
 	dir.UpdateStats(make(fs.HardLinkedItems))
 
 	assert.Equal(t, int64(7+4096*3), dir.Size) // file2 and file3 are counted just once for size
@@ -148,7 +148,7 @@ func TestErr(t *testing.T) {
 	dir := analyzer.AnalyzeDir(
 		"test_dir", func(_, _ string) bool { return false }, false,
 	).(*Dir)
-	<-analyzer.GetDoneChan()
+	analyzer.GetDone().Wait()
 	dir.UpdateStats(make(fs.HardLinkedItems))
 
 	assert.Equal(t, "test_dir", dir.GetName())
@@ -169,6 +169,6 @@ func BenchmarkAnalyzeDir(b *testing.B) {
 	dir := analyzer.AnalyzeDir(
 		"test_dir", func(_, _ string) bool { return false }, false,
 	)
-	<-analyzer.GetDoneChan()
+	analyzer.GetDone().Wait()
 	dir.UpdateStats(make(fs.HardLinkedItems))
 }
diff --git a/tui/tui_test.go b/tui/tui_test.go
index 1812cad..c5bffda 100644
--- a/tui/tui_test.go
+++ b/tui/tui_test.go
@@ -69,8 +69,8 @@ func TestUpdateProgress(t *testing.T) {
 	defer simScreen.Fini()
 
 	ui := CreateUI(app, simScreen, &bytes.Buffer{}, false, false, false, false, false)
-	done := ui.Analyzer.GetDoneChan()
-	done <- struct{}{}
+	done := ui.Analyzer.GetDone()
+	done.Broadcast()
 	ui.updateProgress()
 	assert.True(t, true)
 }