mirror of
https://github.com/go-acme/lego.git
synced 2026-01-25 05:06:16 +00:00
namecheap: add experimental proxy support (#2715)
This commit is contained in:
committed by
GitHub
parent
b338263c96
commit
a8226a6713
@@ -216,11 +216,7 @@ linters:
|
||||
text: load is a global variable
|
||||
linters:
|
||||
- gochecknoglobals
|
||||
- path: providers/dns/([\d\w]+/)*[\d\w]+_test.go
|
||||
text: envTest is a global variable
|
||||
linters:
|
||||
- gochecknoglobals
|
||||
- path: providers/http/([\d\w]+/)*[\d\w]+_test.go
|
||||
- path: providers/(dns|http)/([\d\w]+/)*[\d\w]+_test.go
|
||||
text: envTest is a global variable
|
||||
linters:
|
||||
- gochecknoglobals
|
||||
@@ -228,6 +224,10 @@ linters:
|
||||
text: testCases is a global variable
|
||||
linters:
|
||||
- gochecknoglobals
|
||||
- path: providers/dns/namecheap/transport.go
|
||||
text: (envProxyOnce|envProxyFuncValue) is a global variable
|
||||
linters:
|
||||
- gochecknoglobals
|
||||
- path: providers/dns/acmedns/mock_test.go
|
||||
text: egTestAccount is a global variable
|
||||
linters:
|
||||
|
||||
@@ -91,6 +91,9 @@ func (d *DumpTransport) RoundTrip(h *http.Request) (*http.Response, error) {
|
||||
_, _ = fmt.Fprintln(d.writer, d.redact(data))
|
||||
|
||||
resp, err := d.rt.RoundTrip(h)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
data, _ = httputil.DumpResponse(resp, true)
|
||||
|
||||
|
||||
@@ -76,7 +76,8 @@ func NewDefaultConfig() *Config {
|
||||
PropagationTimeout: env.GetOrDefaultSecond(EnvPropagationTimeout, time.Hour),
|
||||
PollingInterval: env.GetOrDefaultSecond(EnvPollingInterval, 15*time.Second),
|
||||
HTTPClient: &http.Client{
|
||||
Timeout: env.GetOrDefaultSecond(EnvHTTPTimeout, time.Minute),
|
||||
Timeout: env.GetOrDefaultSecond(EnvHTTPTimeout, time.Minute),
|
||||
Transport: defaultTransport(envNamespace),
|
||||
},
|
||||
}
|
||||
}
|
||||
|
||||
71
providers/dns/namecheap/transport.go
Normal file
71
providers/dns/namecheap/transport.go
Normal file
@@ -0,0 +1,71 @@
|
||||
package namecheap
|
||||
|
||||
import (
|
||||
"net/http"
|
||||
"net/url"
|
||||
"strings"
|
||||
"sync"
|
||||
|
||||
"github.com/go-acme/lego/v4/platform/config/env"
|
||||
"golang.org/x/net/http/httpproxy"
|
||||
)
|
||||
|
||||
const (
|
||||
envHTTPProxy = "HTTP_PROXY"
|
||||
envHTTPProxyLower = "http_proxy"
|
||||
envHTTPSProxy = "HTTPS_PROXY"
|
||||
envHTTPSProxyLower = "https_proxy"
|
||||
envNoProxy = "NO_PROXY"
|
||||
envNoProxyLower = "no_proxy"
|
||||
envRequestMethod = "REQUEST_METHOD"
|
||||
)
|
||||
|
||||
// Allows lazy loading of the proxy.
|
||||
var (
|
||||
envProxyOnce sync.Once
|
||||
envProxyFuncValue func(*url.URL) (*url.URL, error)
|
||||
)
|
||||
|
||||
func defaultTransport(namespace string) http.RoundTripper {
|
||||
tr, ok := http.DefaultTransport.(*http.Transport)
|
||||
if !ok {
|
||||
return nil
|
||||
}
|
||||
|
||||
clone := tr.Clone()
|
||||
clone.Proxy = proxyFromEnvironment(namespace)
|
||||
|
||||
return clone
|
||||
}
|
||||
|
||||
// Inspired by:
|
||||
// - https://pkg.go.dev/net/http#ProxyFromEnvironment
|
||||
// - https://pkg.go.dev/golang.org/x/net/http/httpproxy#FromEnvironment
|
||||
func envProxyFunc(namespace string) func(*url.URL) (*url.URL, error) {
|
||||
envProxyOnce.Do(func() {
|
||||
cfg := &httpproxy.Config{
|
||||
HTTPProxy: getEnv(namespace, envHTTPProxy, envHTTPProxyLower),
|
||||
HTTPSProxy: getEnv(namespace, envHTTPSProxy, envHTTPSProxyLower),
|
||||
NoProxy: getEnv(namespace, envNoProxy, envNoProxyLower),
|
||||
CGI: env.GetOneWithFallback(namespace+envRequestMethod, "", env.ParseString, envRequestMethod) != "",
|
||||
}
|
||||
|
||||
envProxyFuncValue = cfg.ProxyFunc()
|
||||
})
|
||||
|
||||
return envProxyFuncValue
|
||||
}
|
||||
|
||||
// Inspired by:
|
||||
// - https://pkg.go.dev/net/http#ProxyFromEnvironment
|
||||
// - https://pkg.go.dev/golang.org/x/net/http/httpproxy#FromEnvironment
|
||||
func proxyFromEnvironment(namespace string) func(req *http.Request) (*url.URL, error) {
|
||||
return func(req *http.Request) (*url.URL, error) {
|
||||
return envProxyFunc(namespace)(req.URL)
|
||||
}
|
||||
}
|
||||
|
||||
func getEnv(namespace, baseEnvName, baseEnvNameLower string) string {
|
||||
return env.GetOneWithFallback(namespace+baseEnvName, "", env.ParseString,
|
||||
strings.ToLower(namespace)+baseEnvNameLower, baseEnvName, baseEnvNameLower)
|
||||
}
|
||||
39
providers/dns/namecheap/transport_test.go
Normal file
39
providers/dns/namecheap/transport_test.go
Normal file
@@ -0,0 +1,39 @@
|
||||
package namecheap
|
||||
|
||||
import (
|
||||
"net/http"
|
||||
"net/http/httptest"
|
||||
"testing"
|
||||
|
||||
"github.com/go-acme/lego/v4/platform/tester/servermock"
|
||||
"github.com/stretchr/testify/assert"
|
||||
"github.com/stretchr/testify/require"
|
||||
)
|
||||
|
||||
func Test_defaultTransport(t *testing.T) {
|
||||
client := servermock.NewBuilder(
|
||||
func(server *httptest.Server) (*http.Client, error) {
|
||||
cl := server.Client()
|
||||
|
||||
t.Setenv("NAMECHEAP_HTTP_PROXY", server.URL)
|
||||
|
||||
cl.Transport = defaultTransport(envNamespace)
|
||||
|
||||
return cl, nil
|
||||
}).
|
||||
Route("/",
|
||||
servermock.Noop().WithStatusCode(http.StatusTeapot)).
|
||||
Build(t)
|
||||
|
||||
req, err := http.NewRequest(http.MethodGet, "http://example.com", nil)
|
||||
require.NoError(t, err)
|
||||
|
||||
resp, err := client.Do(req)
|
||||
require.NoError(t, err)
|
||||
|
||||
t.Cleanup(func() {
|
||||
_ = resp.Body.Close()
|
||||
})
|
||||
|
||||
assert.Equal(t, http.StatusTeapot, resp.StatusCode)
|
||||
}
|
||||
Reference in New Issue
Block a user