Repository: beatlabs/patron
Pull request #103 (2019-11-16 07:40:16)

Inject context in service Run()
<!--
Thanks for taking precious time for making a PR.

Before creating a pull request, please make sure:
- Your PR solves one problem for which a issue exist and a solution has been discussed
- You have read the guide for contributing
  - See https://github.com/beatlabs/patron/blob/master/CONTRIBUTING.md
- You signed all your commits (otherwise we won't be able to merge the PR)
  - See https://github.com/beatlabs/patron/blob/master/CONTRIBUTING.md#sign-your-work
- You added unit tests for the new functionality
- You mention in the PR description which issue it is addressing, e.g. "Resolves #123"
-->

## Which problem is this PR solving?
This PR solves #102 issue
<!-- REQUIRED -->

## Short description of the changes
`Run()` signature changes to `Run(ctx context.Context)` in order to pass context into service.
<!-- REQUIRED -->



Patch:
diff --git a/cmd/patron/main.go b/cmd/patron/main.go
index 2d8349fbe..052c53a9a 100644
--- a/cmd/patron/main.go
+++ b/cmd/patron/main.go
@@ -306,6 +306,7 @@ func mainContent(gd *genData) ([]byte, error) {
 	cnt := `package main
 
 import (
+	"context"
 	"fmt"
 	"os"
 	
@@ -342,7 +343,8 @@ func main() {
 		log.Fatalf("failed to create service %v", err)
 	}
 
-	err = srv.Run()
+	ctx := context.Background()
+	err = srv.Run(ctx)
 	if err != nil {
 		log.Fatalf("failed to run service %v", err)
 	}
diff --git a/examples/fifth/main.go b/examples/fifth/main.go
index 1a588104f..8d2bb2fd8 100644
--- a/examples/fifth/main.go
+++ b/examples/fifth/main.go
@@ -1,6 +1,7 @@
 package main
 
 import (
+	"context"
 	"fmt"
 	"os"
 	"time"
@@ -77,7 +78,8 @@ func main() {
 		log.Fatalf("failed to create service: %v", err)
 	}
 
-	err = srv.Run()
+	ctx := context.Background()
+	err = srv.Run(ctx)
 	if err != nil {
 		log.Fatalf("failed to run service: %v", err)
 	}
diff --git a/examples/first/main.go b/examples/first/main.go
index f04b3d5d8..dc84a0dd1 100644
--- a/examples/first/main.go
+++ b/examples/first/main.go
@@ -72,7 +72,8 @@ func main() {
 		log.Fatalf("failed to create service %v", err)
 	}
 
-	err = srv.Run()
+	ctx := context.Background()
+	err = srv.Run(ctx)
 	if err != nil {
 		log.Fatalf("failed to run service %v", err)
 	}
diff --git a/examples/fourth/main.go b/examples/fourth/main.go
index 945c27b57..9f8e66cdb 100644
--- a/examples/fourth/main.go
+++ b/examples/fourth/main.go
@@ -1,6 +1,7 @@
 package main
 
 import (
+	"context"
 	"errors"
 	"fmt"
 	"os"
@@ -122,7 +123,8 @@ func main() {
 		log.Fatalf("failed to create service %v", err)
 	}
 
-	err = srv.Run()
+	ctx := context.Background()
+	err = srv.Run(ctx)
 	if err != nil {
 		log.Fatalf("failed to run service %v", err)
 	}
diff --git a/examples/second/main.go b/examples/second/main.go
index c932e0905..4b745b076 100644
--- a/examples/second/main.go
+++ b/examples/second/main.go
@@ -76,7 +76,8 @@ func main() {
 		log.Fatalf("failed to create service %v", err)
 	}
 
-	err = srv.Run()
+	ctx := context.Background()
+	err = srv.Run(ctx)
 	if err != nil {
 		log.Fatalf("failed to run service %v", err)
 	}
diff --git a/examples/third/main.go b/examples/third/main.go
index 0c133d866..a7ca38957 100644
--- a/examples/third/main.go
+++ b/examples/third/main.go
@@ -1,6 +1,7 @@
 package main
 
 import (
+	"context"
 	"fmt"
 	"os"
 	"time"
@@ -64,7 +65,8 @@ func main() {
 		log.Fatalf("failed to create service %v", err)
 	}
 
-	err = srv.Run()
+	ctx := context.Background()
+	err = srv.Run(ctx)
 	if err != nil {
 		log.Fatalf("failed to run service %v", err)
 	}
diff --git a/service.go b/service.go
index 7927f076f..7aa5b1918 100644
--- a/service.go
+++ b/service.go
@@ -88,21 +88,21 @@ func (s *Service) setupOSSignal() {
 // Run starts up all service components and monitors for errors.
 // If a component returns a error the service is responsible for shutting down
 // all components and terminate itself.
-func (s *Service) Run() error {
+func (s *Service) Run(ctx context.Context) error {
 	defer func() {
 		err := trace.Close()
 		if err != nil {
 			log.Errorf("failed to close trace %v", err)
 		}
 	}()
-	ctx, cnl := context.WithCancel(context.Background())
+	cctx, cnl := context.WithCancel(ctx)
 	chErr := make(chan error, len(s.cps))
 	wg := sync.WaitGroup{}
 	wg.Add(len(s.cps))
 	for _, cp := range s.cps {
 		go func(c Component) {
 			defer wg.Done()
-			chErr <- c.Run(ctx)
+			chErr <- c.Run(cctx)
 		}(cp)
 	}
 


Test patch:
diff --git a/service_test.go b/service_test.go
index f0f2b6b78..a8807ebab 100644
--- a/service_test.go
+++ b/service_test.go
@@ -52,10 +52,11 @@ func TestServer_Run_Shutdown(t *testing.T) {
 	tests := []struct {
 		name    string
 		cp      Component
+		ctx     context.Context
 		wantErr bool
 	}{
-		{name: "success", cp: &testComponent{}, wantErr: false},
-		{name: "failed to run", cp: &testComponent{errorRunning: true}, wantErr: true},
+		{name: "success", cp: &testComponent{}, ctx: context.Background(), wantErr: false},
+		{name: "failed to run", cp: &testComponent{errorRunning: true}, ctx: context.Background(), wantErr: true},
 	}
 	for _, tt := range tests {
 		t.Run(tt.name, func(t *testing.T) {
@@ -63,7 +64,7 @@ func TestServer_Run_Shutdown(t *testing.T) {
 			assert.NoError(t, err)
 			s, err := New("test", "", Components(tt.cp, tt.cp, tt.cp))
 			assert.NoError(t, err)
-			err = s.Run()
+			err = s.Run(tt.ctx)
 			if tt.wantErr {
 				assert.Error(t, err)
 			} else {
@@ -77,13 +78,14 @@ func TestServer_SetupTracing(t *testing.T) {
 	tests := []struct {
 		name string
 		cp   Component
+		ctx  context.Context
 		host string
 		port string
 	}{
-		{name: "success w/ empty tracing vars", cp: &testComponent{}},
-		{name: "success w/ empty tracing host", cp: &testComponent{}, port: "6831"},
-		{name: "success w/ empty tracing port", cp: &testComponent{}, host: "127.0.0.1"},
-		{name: "success", cp: &testComponent{}, host: "127.0.0.1", port: "6831"},
+		{name: "success w/ empty tracing vars", cp: &testComponent{}, ctx: context.Background()},
+		{name: "success w/ empty tracing host", cp: &testComponent{}, ctx: context.Background(), port: "6831"},
+		{name: "success w/ empty tracing port", cp: &testComponent{}, ctx: context.Background(), host: "127.0.0.1"},
+		{name: "success", cp: &testComponent{}, ctx: context.Background(), host: "127.0.0.1", port: "6831"},
 	}
 	for _, tt := range tests {
 		t.Run(tt.name, func(t *testing.T) {
@@ -97,7 +99,7 @@ func TestServer_SetupTracing(t *testing.T) {
 			}
 			s, err := New("test", "", Components(tt.cp, tt.cp, tt.cp))
 			assert.NoError(t, err)
-			err = s.Run()
+			err = s.Run(tt.ctx)
 			assert.NoError(t, err)
 		})
 	}