server.go (2218B)
1 package server 2 3 import ( 4 "context" 5 "fmt" 6 "net/http" 7 "runtime/debug" 8 9 "code.dwrz.net/src/pkg/log" 10 ) 11 12 type Server struct { 13 cfg *Config 14 log *log.Logger 15 http *http.Server 16 https *http.Server 17 } 18 19 func (s *Server) Serve() { 20 if s.http != nil { 21 s.log.Debug.Printf("serving http") 22 23 go func() { 24 if msg := recover(); msg != nil { 25 s.log.Error.Printf( 26 "panic: %v:\n%s\n", msg, debug.Stack(), 27 ) 28 } 29 30 s.serveHTTP() 31 }() 32 } 33 if s.https != nil { 34 s.log.Debug.Printf("serving https") 35 36 go func() { 37 if msg := recover(); msg != nil { 38 s.log.Error.Printf( 39 "panic: %v:\n%s\n", msg, debug.Stack(), 40 ) 41 } 42 43 s.serveHTTPS() 44 }() 45 46 } 47 48 s.log.Debug.Printf("server ready") 49 } 50 51 func (s *Server) serveHTTP() { 52 s.log.Debug.Printf("starting http server (%s)", s.http.Addr) 53 54 if err := s.http.ListenAndServe(); err != http.ErrServerClosed { 55 s.log.Error.Fatalf( 56 "failed to listen and serve: %v", err, 57 ) 58 } 59 } 60 61 func (s *Server) serveHTTPS() { 62 s.log.Debug.Printf("starting https server (%s)", s.https.Addr) 63 64 if err := s.https.ListenAndServeTLS( 65 "", "", 66 ); err != http.ErrServerClosed { 67 s.log.Error.Fatalf( 68 "failed to listen and serve: %v", err, 69 ) 70 } 71 } 72 73 func (s *Server) Shutdown() error { 74 s.log.Debug.Printf("shutting down server") 75 76 ctxShutdown, cancel := context.WithTimeout( 77 context.Background(), s.cfg.Timeouts.Shutdown, 78 ) 79 defer cancel() 80 81 var httpShutdownErr, httpsShutdownErr error 82 if s.http != nil { 83 s.http.SetKeepAlivesEnabled(false) 84 85 if err := s.http.Shutdown(ctxShutdown); err != nil { 86 httpShutdownErr = err 87 } 88 } 89 if s.https != nil { 90 s.https.SetKeepAlivesEnabled(false) 91 92 if err := s.https.Shutdown(ctxShutdown); err != nil { 93 httpsShutdownErr = err 94 } 95 } 96 97 switch { 98 case httpShutdownErr != nil && httpsShutdownErr != nil: 99 return fmt.Errorf( 100 "failed to shut down http and https servers: %v, %v", 101 httpShutdownErr, httpsShutdownErr, 102 ) 103 case httpShutdownErr != nil: 104 return fmt.Errorf( 105 "failed to shut down http server: %v", httpShutdownErr, 106 ) 107 case httpsShutdownErr != nil: 108 return fmt.Errorf( 109 "failed to shut down https server: %v", 110 httpsShutdownErr, 111 ) 112 default: 113 s.log.Debug.Printf("server shutdown") 114 115 return nil 116 } 117 }