github.com/caos/orbos@v1.5.14-0.20221103111702-e6cd0cea7ad4/internal/helpers/check.go (about)

     1  package helpers
     2  
     3  import (
     4  	"context"
     5  	"crypto/tls"
     6  	"fmt"
     7  	"net"
     8  	"net/http"
     9  	"strings"
    10  	"time"
    11  
    12  	"github.com/AppsFlyer/go-sundheit/checks"
    13  	"github.com/pires/go-proxyproto"
    14  )
    15  
    16  func Check(protocol string, ip string, port uint16, path string, status int, proxyProdocol bool) (string, error) {
    17  
    18  	ipPort := fmt.Sprintf("%s:%d", ip, port)
    19  	if protocol == "tcp" {
    20  		return check(checks.NewPingCheck("tcp", checks.NewDialPinger("tcp", ipPort), 2*time.Second))
    21  	}
    22  	if path != "" && !strings.HasPrefix(path, "/") {
    23  		path = "/" + path
    24  	}
    25  
    26  	roundTripper := &http.Transport{
    27  		TLSClientConfig: &tls.Config{
    28  			// Insecure health checks are ok
    29  			InsecureSkipVerify: true,
    30  		},
    31  		DisableKeepAlives: true,
    32  	}
    33  
    34  	if proxyProdocol {
    35  		roundTripper.DialContext = func(ctx context.Context, network, addr string) (net.Conn, error) {
    36  
    37  			target := &net.TCPAddr{
    38  				IP:   net.ParseIP(ip),
    39  				Port: int(port),
    40  			}
    41  
    42  			conn, err := net.DialTCP("tcp", nil, target)
    43  			if err != nil {
    44  				return nil, err
    45  			}
    46  
    47  			header := &proxyproto.Header{
    48  				Version:           1,
    49  				Command:           proxyproto.PROXY,
    50  				TransportProtocol: proxyproto.TCPv4,
    51  				SourceAddr: &net.TCPAddr{
    52  					IP:   net.ParseIP("10.1.1.1"),
    53  					Port: 1000,
    54  				},
    55  				DestinationAddr: target,
    56  			}
    57  			if _, err := header.WriteTo(conn); err != nil {
    58  				return nil, err
    59  			}
    60  
    61  			return conn, nil
    62  		}
    63  	}
    64  
    65  	return check(checks.NewHTTPCheck(checks.HTTPCheckConfig{
    66  		CheckName:      "http",
    67  		Timeout:        1 * time.Second,
    68  		URL:            fmt.Sprintf("%s://%s%s", protocol, ipPort, path),
    69  		ExpectedStatus: status,
    70  		Options: []checks.RequestOption{func(r *http.Request) {
    71  			r.Close = true
    72  		}},
    73  		Client: &http.Client{
    74  			Transport: roundTripper,
    75  			CheckRedirect: func(req *http.Request, via []*http.Request) error {
    76  				return http.ErrUseLastResponse
    77  			},
    78  		},
    79  	}))
    80  }
    81  
    82  func check(check checks.Check, err error) (string, error) {
    83  	msg, err := checks.Must(check, err).Execute()
    84  	message, ok := msg.(string)
    85  	if !ok {
    86  		return "", err
    87  	}
    88  	return message, err
    89  }