// Copyright 2017 The Gitea Authors. All rights reserved. // SPDX-License-Identifier: MIT package private import ( "context" "crypto/tls" "fmt" "net" "net/http" "os" "strings" "time" "code.gitea.io/gitea/modules/httplib" "code.gitea.io/gitea/modules/json" "code.gitea.io/gitea/modules/log" "code.gitea.io/gitea/modules/proxyprotocol" "code.gitea.io/gitea/modules/setting" ) // Response is used for internal request response (for user message and error message) type Response struct { Err string `json:"err,omitempty"` // server-side error log message, it won't be exposed to end users UserMsg string `json:"user_msg,omitempty"` // meaningful error message for end users, it will be shown in git client's output. } func getClientIP() string { sshConnEnv := strings.TrimSpace(os.Getenv("SSH_CONNECTION")) if len(sshConnEnv) == 0 { return "127.0.0.1" } return strings.Fields(sshConnEnv)[0] } func newInternalRequest(ctx context.Context, url, method string, body ...any) *httplib.Request { if setting.InternalToken == "" { log.Fatal(`The INTERNAL_TOKEN setting is missing from the configuration file: %q. Ensure you are running in the correct environment or set the correct configuration file with -c.`, setting.CustomConf) } req := httplib.NewRequest(url, method). SetContext(ctx). Header("X-Real-IP", getClientIP()). Header("X-Gitea-Internal-Auth", fmt.Sprintf("Bearer %s", setting.InternalToken)). SetTLSClientConfig(&tls.Config{ InsecureSkipVerify: true, ServerName: setting.Domain, }) if setting.Protocol == setting.HTTPUnix { req.SetTransport(&http.Transport{ DialContext: func(ctx context.Context, _, _ string) (net.Conn, error) { var d net.Dialer conn, err := d.DialContext(ctx, "unix", setting.HTTPAddr) if err != nil { return conn, err } if setting.LocalUseProxyProtocol { if err = proxyprotocol.WriteLocalHeader(conn); err != nil { _ = conn.Close() return nil, err } } return conn, err }, }) } else if setting.LocalUseProxyProtocol { req.SetTransport(&http.Transport{ DialContext: func(ctx context.Context, network, address string) (net.Conn, error) { var d net.Dialer conn, err := d.DialContext(ctx, network, address) if err != nil { return conn, err } if err = proxyprotocol.WriteLocalHeader(conn); err != nil { _ = conn.Close() return nil, err } return conn, err }, }) } if len(body) == 1 { req.Header("Content-Type", "application/json") jsonBytes, _ := json.Marshal(body[0]) req.Body(jsonBytes) } else if len(body) > 1 { log.Fatal("Too many arguments for newInternalRequest") } req.SetTimeout(10*time.Second, 60*time.Second) return req }