server/server.go (176 lines of code) (raw):

/* * Licensed to the Apache Software Foundation (ASF) under one or more * contributor license agreements. See the NOTICE file distributed with * this work for additional information regarding copyright ownership. * The ASF licenses this file to You under the Apache License, Version 2.0 * (the "License"); you may not use this file except in compliance with * the License. You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ package server import ( "context" "crypto/tls" "os" "github.com/apache/servicecomb-service-center/server/middleware" "github.com/apache/servicecomb-service-center/server/resource/disco" "github.com/gofiber/fiber/v2" "github.com/go-chassis/go-chassis/v2" chassisServer "github.com/go-chassis/go-chassis/v2/core/server" "github.com/apache/servicecomb-service-center/datasource" nf "github.com/apache/servicecomb-service-center/pkg/event" "github.com/apache/servicecomb-service-center/pkg/log" "github.com/apache/servicecomb-service-center/pkg/plugin" "github.com/apache/servicecomb-service-center/pkg/signal" "github.com/apache/servicecomb-service-center/server/alarm" "github.com/apache/servicecomb-service-center/server/command" "github.com/apache/servicecomb-service-center/server/config" "github.com/apache/servicecomb-service-center/server/event" "github.com/apache/servicecomb-service-center/server/plugin/security/tlsconf" "github.com/apache/servicecomb-service-center/server/service/grc" "github.com/apache/servicecomb-service-center/server/service/rbac" "github.com/go-chassis/foundation/gopool" ) var sc ServiceCenterServer func Run() { if err := command.ParseConfig(os.Args); err != nil { log.Fatal(err.Error(), err) } sc.Run() } type endpoint struct { Host string Port string } type ServiceCenterServer struct { Endpoint endpoint APIServer *APIServer eventCenter *nf.BusService } func (s *ServiceCenterServer) Run() { s.initialize() s.startServices() s.startChassis() signal.RegisterListener() s.waitForQuit() } func (s *ServiceCenterServer) startChassis() { go func() { mask := make([]string, 0) if !config.GetBool("server.turbo", false) { log.Info("turbo is disabled") mask = append(mask, "rest") } else { app := fiber.New(fiber.Config{}) app.Use(middleware.PrepareContextFor) app.Post("/v4/:project/registry/microservices/:serviceId/instances", disco.FiberRegisterInstance) app.Put("/v4/:project/registry/microservices/:serviceId/instances/:instanceId/heartbeat", disco.FiberSendHeartbeat) app.Get("/v4/:project/registry/instances", disco.FiberFindInstances) chassis.RegisterSchema("rest", app) log.Info("turbo is enabled") } if err := chassis.Run(chassisServer.WithServerMask(mask...)); err != nil { log.Warn(err.Error()) } }() } func (s *ServiceCenterServer) waitForQuit() { err := <-s.APIServer.Err() if err != nil { log.Error("service center catch errors", err) } s.Stop() } func (s *ServiceCenterServer) initialize() { s.initEndpoints() // SSL s.initSSL() // Datasource s.initDatasource() s.APIServer = GetAPIServer() s.eventCenter = event.Center() } func (s *ServiceCenterServer) initEndpoints() { s.Endpoint.Host = config.GetString("server.host", "127.0.0.1", config.WithStandby("httpaddr")) s.Endpoint.Port = config.GetString("server.port", "30100", config.WithStandby("httpport")) } func (s *ServiceCenterServer) initDatasource() { // init datasource kind := config.GetString("registry.kind", "", config.WithStandby("registry_plugin")) tlsConfig, err := getDatasourceTLSConfig() if err != nil { log.Fatal("get datasource tlsConfig failed", err) } if err := datasource.Init(datasource.Options{ Kind: kind, Logger: log.Logger, SslEnabled: config.GetSSL().SslEnabled, TLSConfig: tlsConfig, ConnectedFunc: func() { err := alarm.Clear(alarm.IDBackendConnectionRefuse) if err != nil { log.Error("", err) } }, ErrorFunc: func(err error) { if err == nil { return } err = alarm.Raise(alarm.IDBackendConnectionRefuse, alarm.AdditionalContext("%v", err)) if err != nil { log.Error("", err) } }, EnableCache: config.GetRegistry().EnableCache, InstanceTTL: config.GetRegistry().InstanceTTL, }); err != nil { log.Fatal("init datasource failed", err) } } func getDatasourceTLSConfig() (*tls.Config, error) { if config.GetSSL().SslEnabled { return tlsconf.ClientConfig() } return nil, nil } func (s *ServiceCenterServer) initSSL() { if !config.GetSSL().SslEnabled { return } options := tlsconf.Options{ Dir: config.GetString("ssl.dir", "", config.WithENV("SSL_ROOT")), MinVersion: config.GetString("ssl.minVersion", "TLSv1.2", config.WithStandby("ssl_min_version")), ClientMinVersion: config.GetString("ssl.client.minVersion", "", config.WithStandby("ssl_client_min_version")), VerifyPeer: config.GetInt("ssl.verifyClient", 1, config.WithStandby("ssl_verify_client")) != 0, Ciphers: config.GetString("ssl.ciphers", "", config.WithStandby("ssl_ciphers")), ClientCiphers: config.GetString("ssl.client.ciphers", "", config.WithStandby("ssl_client_ciphers")), } if options.ClientMinVersion == "" { options.ClientMinVersion = options.MinVersion } if options.ClientCiphers == "" { options.ClientCiphers = options.Ciphers } if err := tlsconf.Init(options); err != nil { log.Fatal("init ssl failed", err) } } func (s *ServiceCenterServer) startServices() { // notifications s.eventCenter.Start() // load sc plugins plugin.LoadPlugins() rbac.Init() if err := grc.Init(); err != nil { log.Fatal("init gov failed", err) } // check version if config.GetRegistry().SelfRegister { if err := datasource.GetSCManager().UpgradeVersion(context.Background()); err != nil { os.Exit(1) } } // api service s.startAPIService() } func (s *ServiceCenterServer) startAPIService() { s.APIServer.SetHostPort(s.Endpoint.Host, s.Endpoint.Port) s.APIServer.Start() } func (s *ServiceCenterServer) Stop() { if s.APIServer != nil { s.APIServer.Stop() } if s.eventCenter != nil { s.eventCenter.Stop() } gopool.CloseAndWait() log.Warn("service center stopped") log.Flush() }