Skip to content
This repository has been archived by the owner on Mar 15, 2024. It is now read-only.

Internal context for service group #110

Merged
merged 2 commits into from
Jan 16, 2022
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
33 changes: 22 additions & 11 deletions .golangci.yml
Original file line number Diff line number Diff line change
@@ -1,16 +1,27 @@
linters:
enable-all: true
enable-all: false
enable:
- unparam
- whitespace
- unconvert
- bodyclose
- gofmt
- gocritic
- godot
- prealloc
- rowserrcheck
- unconvert
- lll
- cyclop
- gci
- gosec
- prealloc
- revive
- gochecknoglobals
- funlen
disable:
- testpackage
- wrapcheck
- interfacer
- scopelint
- maligned
- paralleltest
- tparallel
- stylecheck
- golint
- exhaustivestruct
- errcheck
- ineffassign

linters-settings:
govet:
Expand Down
15 changes: 9 additions & 6 deletions group/group.go
Original file line number Diff line number Diff line change
Expand Up @@ -95,26 +95,29 @@ func (g *group) Run(ctx context.Context) error {
var (
cnt int
err error
top = ctx
res = make(chan error, len(g.services))
)

// we should add cancel to prevent service freeze
top, cancel := context.WithCancel(ctx)

// run all services
for i := range g.services {
go func(callback Callback) { res <- callback(ctx) }(g.services[i].callback)
go func(callback Callback) { res <- callback(top) }(g.services[i].callback)
}

// wait for context.Done() or error will be received:
select {
case err = <-res:
cnt = 1 // first error received, ignore it in future
case <-ctx.Done():
err = ctx.Err()
top = context.Background()
case <-top.Done():
err = top.Err()
}

cancel()

// prepare graceful context to stop
grace, stop := context.WithTimeout(top, g.shutdown)
grace, stop := context.WithTimeout(context.Background(), g.shutdown)
defer stop()

// we should wait until all services will gracefully stopped
Expand Down
31 changes: 31 additions & 0 deletions group/group_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -46,6 +46,37 @@ func TestNew(t *testing.T) {
})
}

{ // should stop all services when one is failed
ctx, cancel := context.WithCancel(context.Background())
cases = append(cases, testCase{
name: "should stop all services when one is failed",

ctx: ctx,
cancel: cancel,

await: defaultAwait,

shutdown: time.Nanosecond,
expect: errAlways,
services: []service{
{
shutdown: func(ctx context.Context) { <-ctx.Done() },
callback: func(context.Context) error { return errAlways },
},

{
shutdown: func(ctx context.Context) { <-ctx.Done() },
callback: func(ctx context.Context) error {
// should not freeze
<-ctx.Done()

return ctx.Err()
},
},
},
})
}

{ // errored service
ctx, cancel := context.WithCancel(context.Background())
cases = append(cases, testCase{
Expand Down