k8s.io/kubernetes@v1.29.3/pkg/registry/core/componentstatus/validator.go (about) 1 /* 2 Copyright 2014 The Kubernetes Authors. 3 4 Licensed under the Apache License, Version 2.0 (the "License"); 5 you may not use this file except in compliance with the License. 6 You may obtain a copy of the License at 7 8 http://www.apache.org/licenses/LICENSE-2.0 9 10 Unless required by applicable law or agreed to in writing, software 11 distributed under the License is distributed on an "AS IS" BASIS, 12 WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 See the License for the specific language governing permissions and 14 limitations under the License. 15 */ 16 17 package componentstatus 18 19 import ( 20 "context" 21 "crypto/tls" 22 "fmt" 23 "sync" 24 "time" 25 26 utilnet "k8s.io/apimachinery/pkg/util/net" 27 "k8s.io/apiserver/pkg/storage/storagebackend" 28 "k8s.io/apiserver/pkg/storage/storagebackend/factory" 29 "k8s.io/kubernetes/pkg/probe" 30 httpprober "k8s.io/kubernetes/pkg/probe/http" 31 ) 32 33 const ( 34 probeTimeOut = 20 * time.Second 35 ) 36 37 type ValidatorFn func([]byte) error 38 39 type Server interface { 40 DoServerCheck() (probe.Result, string, error) 41 } 42 43 type HttpServer struct { 44 Addr string 45 Port int 46 Path string 47 EnableHTTPS bool 48 TLSConfig *tls.Config 49 Validate ValidatorFn 50 Prober httpprober.Prober 51 Once sync.Once 52 } 53 54 type ServerStatus struct { 55 // +optional 56 Component string `json:"component,omitempty"` 57 // +optional 58 Health string `json:"health,omitempty"` 59 // +optional 60 HealthCode probe.Result `json:"healthCode,omitempty"` 61 // +optional 62 Msg string `json:"msg,omitempty"` 63 // +optional 64 Err string `json:"err,omitempty"` 65 } 66 67 func (server *HttpServer) DoServerCheck() (probe.Result, string, error) { 68 // setup the prober 69 server.Once.Do(func() { 70 if server.Prober != nil { 71 return 72 } 73 const followNonLocalRedirects = true 74 server.Prober = httpprober.NewWithTLSConfig(server.TLSConfig, followNonLocalRedirects) 75 }) 76 77 scheme := "http" 78 if server.EnableHTTPS { 79 scheme = "https" 80 } 81 url := utilnet.FormatURL(scheme, server.Addr, server.Port, server.Path) 82 83 req, err := httpprober.NewProbeRequest(url, nil) 84 if err != nil { 85 return probe.Unknown, "", fmt.Errorf("failed to construct probe request: %w", err) 86 } 87 result, data, err := server.Prober.Probe(req, probeTimeOut) 88 89 if err != nil { 90 return probe.Unknown, "", err 91 } 92 if result == probe.Failure { 93 return probe.Failure, data, err 94 } 95 if server.Validate != nil { 96 if err := server.Validate([]byte(data)); err != nil { 97 return probe.Failure, data, err 98 } 99 } 100 return result, data, nil 101 } 102 103 type EtcdServer struct { 104 storagebackend.Config 105 } 106 107 func (server *EtcdServer) DoServerCheck() (probe.Result, string, error) { 108 prober, err := factory.CreateProber(server.Config) 109 if err != nil { 110 return probe.Failure, "", err 111 } 112 defer prober.Close() 113 114 ctx, cancel := context.WithTimeout(context.Background(), probeTimeOut) 115 defer cancel() 116 err = prober.Probe(ctx) 117 if err != nil { 118 return probe.Failure, "", err 119 } 120 return probe.Success, "ok", err 121 }