github.com/muhammadn/cortex@v1.9.1-0.20220510110439-46bb7000d03d/pkg/cortex/server_service.go (about) 1 package cortex 2 3 import ( 4 "context" 5 "fmt" 6 7 "github.com/go-kit/log/level" 8 "github.com/grafana/dskit/services" 9 "github.com/weaveworks/common/server" 10 11 util_log "github.com/cortexproject/cortex/pkg/util/log" 12 ) 13 14 // NewServerService constructs service from Server component. 15 // servicesToWaitFor is called when server is stopping, and should return all 16 // services that need to terminate before server actually stops. 17 // N.B.: this function is NOT Cortex specific, please let's keep it that way. 18 // Passed server should not react on signals. Early return from Run function is considered to be an error. 19 func NewServerService(serv *server.Server, servicesToWaitFor func() []services.Service) services.Service { 20 serverDone := make(chan error, 1) 21 22 runFn := func(ctx context.Context) error { 23 go func() { 24 defer close(serverDone) 25 serverDone <- serv.Run() 26 }() 27 28 select { 29 case <-ctx.Done(): 30 return nil 31 case err := <-serverDone: 32 if err != nil { 33 return err 34 } 35 return fmt.Errorf("server stopped unexpectedly") 36 } 37 } 38 39 stoppingFn := func(_ error) error { 40 // wait until all modules are done, and then shutdown server. 41 for _, s := range servicesToWaitFor() { 42 _ = s.AwaitTerminated(context.Background()) 43 } 44 45 // shutdown HTTP and gRPC servers (this also unblocks Run) 46 serv.Shutdown() 47 48 // if not closed yet, wait until server stops. 49 <-serverDone 50 level.Info(util_log.Logger).Log("msg", "server stopped") 51 return nil 52 } 53 54 return services.NewBasicService(nil, runFn, stoppingFn) 55 } 56 57 // DisableSignalHandling puts a dummy signal handler 58 func DisableSignalHandling(config *server.Config) { 59 config.SignalHandler = make(ignoreSignalHandler) 60 } 61 62 type ignoreSignalHandler chan struct{} 63 64 func (dh ignoreSignalHandler) Loop() { 65 <-dh 66 } 67 68 func (dh ignoreSignalHandler) Stop() { 69 close(dh) 70 }