From 851494ea8e41f8c71e0760c0e197d8c8d2feedca Mon Sep 17 00:00:00 2001 From: Aaron Paterson Date: Fri, 31 Oct 2025 08:21:56 -0600 Subject: [PATCH 01/51] networks.go with sd and sdgram --- listeners.go | 165 ++++-------------------------------- modules/caddyhttp/server.go | 31 ------- networks.go | 119 ++++++++++++++++++++++++++ networks_nosystemd.go | 29 +++++++ networks_systemd.go | 158 ++++++++++++++++++++++++++++++++++ 5 files changed, 324 insertions(+), 178 deletions(-) create mode 100644 networks.go create mode 100644 networks_nosystemd.go create mode 100644 networks_systemd.go diff --git a/listeners.go b/listeners.go index b673c86e109..de0c9402baf 100644 --- a/listeners.go +++ b/listeners.go @@ -38,10 +38,6 @@ import ( "github.com/caddyserver/caddy/v2/internal" ) -// listenFdsStart is the first file descriptor number for systemd socket activation. -// File descriptors 0, 1, 2 are reserved for stdin, stdout, stderr. -const listenFdsStart = 3 - // NetworkAddress represents one or more network addresses. // It contains the individual components for a parsed network // address of the form accepted by ParseNetworkAddress(). @@ -137,31 +133,29 @@ func (na NetworkAddress) ListenAll(ctx context.Context, config net.ListenConfig) // Listen synchronizes binds to unix domain sockets to avoid race conditions // while an existing socket is unlinked. func (na NetworkAddress) Listen(ctx context.Context, portOffset uint, config net.ListenConfig) (any, error) { - if na.IsUnixNetwork() { - unixSocketsMu.Lock() - defer unixSocketsMu.Unlock() - } + var ( + ln any + err error + ) - // check to see if plugin provides listener - if ln, err := getListenerFromPlugin(ctx, na.Network, na.Host, na.port(), portOffset, config); ln != nil || err != nil { + // check to see if network provides a listener + if ln, err = getListenerFromNetwork(ctx, na.Network, na.Host, na.port(), portOffset, config); ln != nil || err != nil { return ln, err } // create (or reuse) the listener ourselves - return na.listen(ctx, portOffset, config) -} - -func (na NetworkAddress) listen(ctx context.Context, portOffset uint, config net.ListenConfig) (any, error) { var ( - ln any - err error address string unixFileMode fs.FileMode ) + // lock other unix sockets from being bound and // split unix socket addr early so lnKey // is independent of permissions bits if na.IsUnixNetwork() { + unixSocketsMu.Lock() + defer unixSocketsMu.Unlock() + address, unixFileMode, err = internal.SplitUnixSocketPermissionsBits(na.Host) if err != nil { return nil, err @@ -172,7 +166,7 @@ func (na NetworkAddress) listen(ctx context.Context, portOffset uint, config net address = na.JoinHostPort(portOffset) } - if strings.HasPrefix(na.Network, "ip") { + if na.IsIpNetwork() { ln, err = config.ListenPacket(ctx, na.Network, address) } else { if na.IsUnixNetwork() { @@ -220,6 +214,12 @@ func (na NetworkAddress) IsFdNetwork() bool { return IsFdNetwork(na.Network) } +// IsIpNetwork returns true if na.Network starts with +// ip: ip4: or ip6: +func (na NetworkAddress) IsIpNetwork() bool { + return IsIpNetwork(na.Network) +} + // JoinHostPort is like net.JoinHostPort, but where the port // is StartPort + offset. func (na NetworkAddress) JoinHostPort(offset uint) string { @@ -299,74 +299,6 @@ func (na NetworkAddress) String() string { return JoinNetworkAddress(na.Network, na.Host, na.port()) } -// IsUnixNetwork returns true if the netw is a unix network. -func IsUnixNetwork(netw string) bool { - return strings.HasPrefix(netw, "unix") -} - -// IsFdNetwork returns true if the netw is a fd network. -func IsFdNetwork(netw string) bool { - return strings.HasPrefix(netw, "fd") -} - -// getFdByName returns the file descriptor number for the given -// socket name from systemd's LISTEN_FDNAMES environment variable. -// Socket names are provided by systemd via socket activation. -// -// The name can optionally include an index to handle multiple sockets -// with the same name: "web:0" for first, "web:1" for second, etc. -// If no index is specified, defaults to index 0 (first occurrence). -func getFdByName(nameWithIndex string) (int, error) { - if nameWithIndex == "" { - return 0, fmt.Errorf("socket name cannot be empty") - } - - fdNamesStr := os.Getenv("LISTEN_FDNAMES") - if fdNamesStr == "" { - return 0, fmt.Errorf("LISTEN_FDNAMES environment variable not set") - } - - // Parse name and optional index - parts := strings.Split(nameWithIndex, ":") - if len(parts) > 2 { - return 0, fmt.Errorf("invalid socket name format '%s': too many colons", nameWithIndex) - } - - name := parts[0] - targetIndex := 0 - - if len(parts) > 1 { - var err error - targetIndex, err = strconv.Atoi(parts[1]) - if err != nil { - return 0, fmt.Errorf("invalid socket index '%s': %v", parts[1], err) - } - if targetIndex < 0 { - return 0, fmt.Errorf("socket index cannot be negative: %d", targetIndex) - } - } - - // Parse the socket names - names := strings.Split(fdNamesStr, ":") - - // Find the Nth occurrence of the requested name - matchCount := 0 - for i, fdName := range names { - if fdName == name { - if matchCount == targetIndex { - return listenFdsStart + i, nil - } - matchCount++ - } - } - - if matchCount == 0 { - return 0, fmt.Errorf("socket name '%s' not found in LISTEN_FDNAMES", name) - } - - return 0, fmt.Errorf("socket name '%s' found %d times, but index %d requested", name, matchCount, targetIndex) -} - // ParseNetworkAddress parses addr into its individual // components. The input string is expected to be of // the form "network/host:port-range" where any part is @@ -398,27 +330,9 @@ func ParseNetworkAddressWithDefaults(addr, defaultNetwork string, defaultPort ui }, err } if IsFdNetwork(network) { - fdAddr := host - - // Handle named socket activation (fdname/name, fdgramname/name) - if strings.HasPrefix(network, "fdname") || strings.HasPrefix(network, "fdgramname") { - fdNum, err := getFdByName(host) - if err != nil { - return NetworkAddress{}, fmt.Errorf("named socket activation: %v", err) - } - fdAddr = strconv.Itoa(fdNum) - - // Normalize network to standard fd/fdgram - if strings.HasPrefix(network, "fdname") { - network = "fd" - } else { - network = "fdgram" - } - } - return NetworkAddress{ Network: network, - Host: fdAddr, + Host: host, }, nil } var start, end uint64 @@ -713,55 +627,12 @@ func (fcql *fakeCloseQuicListener) Close() error { return nil } -// RegisterNetwork registers a network type with Caddy so that if a listener is -// created for that network type, getListener will be invoked to get the listener. -// This should be called during init() and will panic if the network type is standard -// or reserved, or if it is already registered. EXPERIMENTAL and subject to change. -func RegisterNetwork(network string, getListener ListenerFunc) { - network = strings.TrimSpace(strings.ToLower(network)) - - if network == "tcp" || network == "tcp4" || network == "tcp6" || - network == "udp" || network == "udp4" || network == "udp6" || - network == "unix" || network == "unixpacket" || network == "unixgram" || - strings.HasPrefix(network, "ip:") || strings.HasPrefix(network, "ip4:") || strings.HasPrefix(network, "ip6:") || - network == "fd" || network == "fdgram" { - panic("network type " + network + " is reserved") - } - - if _, ok := networkTypes[strings.ToLower(network)]; ok { - panic("network type " + network + " is already registered") - } - - networkTypes[network] = getListener -} - var unixSocketsMu sync.Mutex -// getListenerFromPlugin returns a listener on the given network and address -// if a plugin has registered the network name. It may return (nil, nil) if -// no plugin can provide a listener. -func getListenerFromPlugin(ctx context.Context, network, host, port string, portOffset uint, config net.ListenConfig) (any, error) { - // get listener from plugin if network type is registered - if getListener, ok := networkTypes[network]; ok { - Log().Debug("getting listener from plugin", zap.String("network", network)) - return getListener(ctx, network, host, port, portOffset, config) - } - - return nil, nil -} - func listenerKey(network, addr string) string { return network + "/" + addr } -// ListenerFunc is a function that can return a listener given a network and address. -// The listeners must be capable of overlapping: with Caddy, new configs are loaded -// before old ones are unloaded, so listeners may overlap briefly if the configs -// both need the same listener. EXPERIMENTAL and subject to change. -type ListenerFunc func(ctx context.Context, network, host, portRange string, portOffset uint, cfg net.ListenConfig) (any, error) - -var networkTypes = map[string]ListenerFunc{} - // ListenerWrapper is a type that wraps a listener // so it can modify the input listener's methods. // Modules that implement this interface are found diff --git a/modules/caddyhttp/server.go b/modules/caddyhttp/server.go index ac30f40286e..d3e654533e1 100644 --- a/modules/caddyhttp/server.go +++ b/modules/caddyhttp/server.go @@ -1124,34 +1124,3 @@ const ( // For tracking the real client IP (affected by trusted_proxy) ClientIPVarKey string = "client_ip" ) - -var networkTypesHTTP3 = map[string]string{ - "unixgram": "unixgram", - "udp": "udp", - "udp4": "udp4", - "udp6": "udp6", - "tcp": "udp", - "tcp4": "udp4", - "tcp6": "udp6", - "fdgram": "fdgram", -} - -// RegisterNetworkHTTP3 registers a mapping from non-HTTP/3 network to HTTP/3 -// network. This should be called during init() and will panic if the network -// type is standard, reserved, or already registered. -// -// EXPERIMENTAL: Subject to change. -func RegisterNetworkHTTP3(originalNetwork, h3Network string) { - if _, ok := networkTypesHTTP3[strings.ToLower(originalNetwork)]; ok { - panic("network type " + originalNetwork + " is already registered") - } - networkTypesHTTP3[originalNetwork] = h3Network -} - -func getHTTP3Network(originalNetwork string) (string, error) { - h3Network, ok := networkTypesHTTP3[strings.ToLower(originalNetwork)] - if !ok { - return "", fmt.Errorf("network '%s' cannot handle HTTP/3 connections", originalNetwork) - } - return h3Network, nil -} diff --git a/networks.go b/networks.go new file mode 100644 index 00000000000..6241fbe4055 --- /dev/null +++ b/networks.go @@ -0,0 +1,119 @@ +// Copyright 2015 Matthew Holt and The Caddy Authors +// +// Licensed 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 caddy + +import ( + "strings" + "context" + "net" + "sync" + "go.uber.org/zap" + "fmt" +) + +// IsUnixNetwork returns true if the netw is a unix network. +func IsUnixNetwork(netw string) bool { + return netw == "unix" || netw == "unixgram" || netw == "unixpacket" +} + +// IsIpNetwork returns true if the netw is an ip network. +func IsIpNetwork(netw string) bool { + return strings.HasPrefix(netw, "ip:") || strings.HasPrefix(netw, "ip4:") || strings.HasPrefix(netw, "ip6:") +} + +// IsFdNetwork returns true if the netw is a fd network. +func IsFdNetwork(netw string) bool { + return netw == "fd" || netw == "fdgram" +} + +// ListenerFunc is a function that can return a listener given a network and address. +// The listeners must be capable of overlapping: with Caddy, new configs are loaded +// before old ones are unloaded, so listeners may overlap briefly if the configs +// both need the same listener. EXPERIMENTAL and subject to change. +type ListenerFunc func(ctx context.Context, network, host, portRange string, portOffset uint, cfg net.ListenConfig) (any, error) + +var networkPlugins = map[string]ListenerFunc{} +var networkPluginsMu sync.RWMutex + +// RegisterNetwork registers a network plugin with Caddy so that if a listener is +// created for that network plugin, getListener will be invoked to get the listener. +// This should be called during init() and will panic if the network type is standard +// or reserved, or if it is already registered. EXPERIMENTAL and subject to change. +func RegisterNetwork(network string, getListener ListenerFunc) { + network = strings.TrimSpace(strings.ToLower(network)) + + if IsReservedNetwork(network) { + panic("network type " + network + " is reserved") + } + + if _, ok := networkPlugins[strings.ToLower(network)]; ok { + panic("network type " + network + " is already registered") + } + + networkPluginsMu.Lock() + defer networkPluginsMu.Unlock() + + networkPlugins[network] = getListener +} + +// getListenerFromPlugin returns a listener on the given network and address +// if a plugin has registered the network name. It may return (nil, nil) if +// no plugin can provide a listener. +func getListenerFromPlugin(ctx context.Context, network, host, port string, portOffset uint, config net.ListenConfig) (any, error) { + networkPluginsMu.RLock() + defer networkPluginsMu.RUnlock() + + // get listener from plugin if network is registered + if getListener, ok := networkPlugins[network]; ok { + Log().Debug("getting listener from plugin", zap.String("network", network)) + return getListener(ctx, network, host, port, portOffset, config) + } + + return nil, nil +} + +var networkHTTP3Plugins = map[string]string{} +var networkHTTP3PluginsMu sync.RWMutex + +// RegisterNetworkHTTP3 registers a mapping from non-HTTP/3 network to HTTP/3 +// network. This should be called during init() and will panic if the network +// type is standard, reserved, or already registered. +// +// EXPERIMENTAL: Subject to change. +func RegisterNetworkHTTP3(originalNetwork, h3Network string) { + if IsReservedNetwork(originalNetwork) { + panic("network type " + originalNetwork + " is reserved") + } + if _, ok := networkHTTP3Plugins[strings.ToLower(originalNetwork)]; ok { + panic("network type " + originalNetwork + " is already registered") + } + + networkHTTP3PluginsMu.Lock() + defer networkHTTP3PluginsMu.Unlock() + + networkHTTP3Plugins[originalNetwork] = h3Network +} + +func getHTTP3Plugin(originalNetwork string) (string, error) { + networkHTTP3PluginsMu.RLock() + defer networkHTTP3PluginsMu.RUnlock() + + h3Network, ok := networkHTTP3Plugins[strings.ToLower(originalNetwork)] + if !ok { + return "", fmt.Errorf("network '%s' cannot handle HTTP/3 connections", originalNetwork) + } + + return h3Network, nil +} diff --git a/networks_nosystemd.go b/networks_nosystemd.go new file mode 100644 index 00000000000..63424800f3d --- /dev/null +++ b/networks_nosystemd.go @@ -0,0 +1,29 @@ +//go:build !linux || nosystemd + +package caddy + +func IsReservedNetwork(network string) bool { + return network == "tcp" || network == "tcp4" || network == "tcp6" || + network == "udp" || network == "udp4" || network == "udp6" || + IsUnixNetwork(network) || + IsIpNetwork(network) || + IsFdNetwork(network) +} + +func getListenerFromNetwork(ctx context.Context, network, host, port string, portOffset uint, config net.ListenConfig) (any, error) { + return getListenerFromPlugin(ctx, network, host, port, portOffset, config) +} + +func getHTTP3Network(originalNetwork string) (string, error) { + switch originalNetwork { + case "unixgram": return "unixgram", nil + case "udp": return "udp", nil + case "udp4": return "udp4", nil + case "udp6": return "udp6", nil + case "tcp": return "udp", nil + case "tcp4": return "udp4", nil + case "tcp6": return "udp6", nil + case "fdgram": return "fdgram", nil + } + return getHTTP3Plugin(originalNetwork) +} diff --git a/networks_systemd.go b/networks_systemd.go new file mode 100644 index 00000000000..4a1ddb2def4 --- /dev/null +++ b/networks_systemd.go @@ -0,0 +1,158 @@ +//go:build linux && !nosystemd + +package caddy + +import ( + "context" + "net" + "sync" + "os" + "errors" + "strconv" + "fmt" + "strings" +) + +func IsSdNetwork(network string) bool { + return network == "sd" || network == "sdgram" +} + +func IsReservedNetwork(network string) bool { + return network == "tcp" || network == "tcp4" || network == "tcp6" || + network == "udp" || network == "udp4" || network == "udp6" || + IsUnixNetwork(network) || + IsIpNetwork(network) || + IsFdNetwork(network) || + IsSdNetwork(network) +} + +var ( + nameToFiles map[string][]int + nameToFilesErr error + nameToFilesMu sync.Mutex +) + +func sdListenFds() (map[string][]int, error) { + nameToFilesMu.Lock() + defer nameToFilesMu.Unlock() + + if nameToFilesErr != nil { + return nil, nameToFilesErr + } + + if nameToFiles != nil { + return nameToFiles, nil + } + + const lnFdsStart = 3 + + lnPid, ok := os.LookupEnv("LISTEN_PID") + if !ok { + nameToFilesErr = errors.New("LISTEN_PID is unset.") + return nil, nameToFilesErr + } + + pid, err := strconv.ParseUint(lnPid, 0, strconv.IntSize) + if err != nil { + nameToFilesErr = err + return nil, nameToFilesErr + } + + if pid != uint64(os.Getpid()) { + nameToFilesErr = fmt.Errorf("LISTEN_PID does not match pid: %d != %d", pid, os.Getpid()) + return nil, nameToFilesErr + } + + lnFds, ok := os.LookupEnv("LISTEN_FDS") + if !ok { + nameToFilesErr = errors.New("LISTEN_FDS is unset.") + return nil, nameToFilesErr + } + + fds, err := strconv.ParseUint(lnFds, 0, strconv.IntSize) + if err != nil { + nameToFilesErr = err + return nil, nameToFilesErr + } + + lnFdnames, ok := os.LookupEnv("LISTEN_FDNAMES") + if !ok { + nameToFilesErr = errors.New("LISTEN_FDNAMES is unset.") + return nil, nameToFilesErr + } + + fdNames := strings.Split(lnFdnames, ":") + if fds != uint64(len(fdNames)) { + nameToFilesErr = fmt.Errorf("LISTEN_FDS does not match LISTEN_FDNAMES length: %d != %d", fds, len(fdNames)) + return nil, nameToFilesErr + } + + nameToFiles = make(map[string][]int, len(fdNames)) + for index, name := range fdNames { + nameToFiles[name] = append(nameToFiles[name], lnFdsStart+index) + } + + return nameToFiles, nil +} + +func getListenerFromNetwork(ctx context.Context, network, host, port string, portOffset uint, config net.ListenConfig) (any, error) { + if IsSdNetwork(network) { + sdLnFds, err := sdListenFds() + if err != nil { + return nil, err + } + + name, index, li := host, portOffset, strings.LastIndex(host, "/") + if li >= 0 { + name = host[:li] + i, err := strconv.ParseUint(host[li+1:], 0, strconv.IntSize) + if err != nil { + return nil, err + } + index += uint(i) + } + + files, ok := sdLnFds[name] + if !ok { + return nil, fmt.Errorf("invalid listen fd name: %s", name) + } + + if uint(len(files)) <= index { + return nil, fmt.Errorf("invalid listen fd index: %d", index) + } + file := files[index] + + var fdNetwork string + switch network { + case "sd": + fdNetwork = "fd" + case "sdgram": + fdNetwork = "fdgram" + default: + return nil, fmt.Errorf("invalid network: %s", network) + } + + na, err := ParseNetworkAddress(JoinNetworkAddress(fdNetwork, strconv.Itoa(file), port)) + if err != nil { + return nil, err + } + + return na.Listen(ctx, portOffset, config) + } + return getListenerFromPlugin(ctx, network, host, port, portOffset, config) +} + +func getHTTP3Network(originalNetwork string) (string, error) { + switch originalNetwork { + case "unixgram": return "unixgram", nil + case "udp": return "udp", nil + case "udp4": return "udp4", nil + case "udp6": return "udp6", nil + case "tcp": return "udp", nil + case "tcp4": return "udp4", nil + case "tcp6": return "udp6", nil + case "fdgram": return "fdgram", nil + case "sdgram": return "sdgram", nil + } + return getHTTP3Plugin(originalNetwork) +} From 8725ffe77021852098b42848e9286ea96f45e115 Mon Sep 17 00:00:00 2001 From: Aaron Paterson Date: Fri, 31 Oct 2025 18:01:58 -0600 Subject: [PATCH 02/51] update tests --- listeners_test.go | 206 ++++++++++++++++++++++++++++++++------------ networks_systemd.go | 102 +++++++++++----------- 2 files changed, 200 insertions(+), 108 deletions(-) diff --git a/listeners_test.go b/listeners_test.go index c2cc255f21f..ce3312b4610 100644 --- a/listeners_test.go +++ b/listeners_test.go @@ -18,6 +18,7 @@ import ( "os" "reflect" "testing" + "strconv" "github.com/caddyserver/caddy/v2/internal" ) @@ -658,6 +659,8 @@ func TestSplitUnixSocketPermissionsBits(t *testing.T) { func TestGetFdByName(t *testing.T) { // Save original environment originalFdNames := os.Getenv("LISTEN_FDNAMES") + originalFds := os.Getenv("LISTEN_FDS") + originalPid := os.Getenv("LISTEN_PID") // Restore environment after test defer func() { @@ -666,121 +669,150 @@ func TestGetFdByName(t *testing.T) { } else { os.Unsetenv("LISTEN_FDNAMES") } + if originalFds != "" { + os.Setenv("LISTEN_FDS", originalFds) + } else { + os.Unsetenv("LISTEN_FDS") + } + if originalPid != "" { + os.Setenv("LISTEN_PID", originalPid) + } else { + os.Unsetenv("LISTEN_PID") + } }() tests := []struct { name string fdNames string + fds string socketName string - expectedFd int + expectedFd uint expectError bool }{ { name: "simple http socket", fdNames: "http", + fds: "1", socketName: "http", expectedFd: 3, }, { name: "multiple different sockets - first", fdNames: "http:https:dns", + fds: "3", socketName: "http", expectedFd: 3, }, { name: "multiple different sockets - second", fdNames: "http:https:dns", + fds: "3", socketName: "https", expectedFd: 4, }, { name: "multiple different sockets - third", fdNames: "http:https:dns", + fds: "3", socketName: "dns", expectedFd: 5, }, { name: "duplicate names - first occurrence (no index)", fdNames: "web:web:api", + fds: "3", socketName: "web", expectedFd: 3, }, { name: "duplicate names - first occurrence (explicit index 0)", fdNames: "web:web:api", - socketName: "web:0", + fds: "3", + socketName: "web/0", expectedFd: 3, }, { name: "duplicate names - second occurrence (index 1)", fdNames: "web:web:api", - socketName: "web:1", + fds: "3", + socketName: "web/1", expectedFd: 4, }, { name: "complex duplicates - first api", fdNames: "web:api:web:api:dns", - socketName: "api:0", + fds: "5", + socketName: "api/0", expectedFd: 4, }, { name: "complex duplicates - second api", fdNames: "web:api:web:api:dns", - socketName: "api:1", + fds: "5", + socketName: "api/1", expectedFd: 6, }, { name: "complex duplicates - first web", fdNames: "web:api:web:api:dns", - socketName: "web:0", + fds: "5", + socketName: "web/0", expectedFd: 3, }, { name: "complex duplicates - second web", fdNames: "web:api:web:api:dns", - socketName: "web:1", + fds: "5", + socketName: "web/1", expectedFd: 5, }, { name: "socket not found", fdNames: "http:https", + fds: "2", socketName: "missing", expectError: true, }, { name: "empty socket name", fdNames: "http", + fds: "1", socketName: "", expectError: true, }, { name: "missing LISTEN_FDNAMES", fdNames: "", + fds: "", socketName: "http", expectError: true, }, { name: "index out of range", fdNames: "web:web", - socketName: "web:2", + fds: "2", + socketName: "web/2", expectError: true, }, { name: "negative index", fdNames: "web", - socketName: "web:-1", + fds: "1", + socketName: "web/-1", expectError: true, }, { name: "invalid index format", fdNames: "web", - socketName: "web:abc", + fds: "1", + socketName: "web/abc", expectError: true, }, { name: "too many colons", fdNames: "web", - socketName: "web:0:extra", + fds: "1", + socketName: "web/0/extra", expectError: true, }, } @@ -794,8 +826,24 @@ func TestGetFdByName(t *testing.T) { os.Unsetenv("LISTEN_FDNAMES") } + if tc.fds != "" { + os.Setenv("LISTEN_FDS", tc.fds) + } else { + os.Unsetenv("LISTEN_FDS") + } + + os.Setenv("LISTEN_PID", strconv.Itoa(os.Getpid())) + // Test the function - fd, err := getFdByName(tc.socketName) + var ( + listenFdsWithNames map[string][]uint + err error + fd uint + ) + listenFdsWithNames, err = sdListenFdsWithNames() + if err == nil { + fd, err = sdListenFd(listenFdsWithNames, tc.socketName, 0) + } if tc.expectError { if err == nil { @@ -817,113 +865,158 @@ func TestGetFdByName(t *testing.T) { func TestParseNetworkAddressFdName(t *testing.T) { // Save and restore environment originalFdNames := os.Getenv("LISTEN_FDNAMES") + originalFds := os.Getenv("LISTEN_FDS") + originalPid := os.Getenv("LISTEN_PID") + defer func() { if originalFdNames != "" { os.Setenv("LISTEN_FDNAMES", originalFdNames) } else { os.Unsetenv("LISTEN_FDNAMES") } + if originalFds != "" { + os.Setenv("LISTEN_FDS", originalFds) + } else { + os.Unsetenv("LISTEN_FDS") + } + if originalPid != "" { + os.Setenv("LISTEN_PID", originalPid) + } else { + os.Unsetenv("LISTEN_PID") + } }() // Set up test environment os.Setenv("LISTEN_FDNAMES", "http:https:dns") + os.Setenv("LISTEN_FDS", "3") + os.Setenv("LISTEN_PID", strconv.Itoa(os.Getpid())) tests := []struct { - input string - expectAddr NetworkAddress - expectErr bool + input string + expectedAddr NetworkAddress + expectedFd uint + expectErr bool }{ { - input: "fdname/http", - expectAddr: NetworkAddress{ - Network: "fd", - Host: "3", + input: "sd/http", + expectedAddr: NetworkAddress{ + Network: "sd", + Host: "http", }, + expectedFd: 3, }, { - input: "fdname/https", - expectAddr: NetworkAddress{ - Network: "fd", - Host: "4", + input: "sd/https", + expectedAddr: NetworkAddress{ + Network: "sd", + Host: "https", }, + expectedFd: 4, }, { - input: "fdname/dns", - expectAddr: NetworkAddress{ - Network: "fd", - Host: "5", + input: "sd/dns", + expectedAddr: NetworkAddress{ + Network: "sd", + Host: "dns", }, + expectedFd: 5, }, { - input: "fdname/http:0", - expectAddr: NetworkAddress{ - Network: "fd", - Host: "3", + input: "sd/http/0", + expectedAddr: NetworkAddress{ + Network: "sd", + Host: "http/0", }, + expectedFd: 3, }, { - input: "fdname/https:0", - expectAddr: NetworkAddress{ - Network: "fd", - Host: "4", + input: "sd/https/0", + expectedAddr: NetworkAddress{ + Network: "sd", + Host: "https/0", }, + expectedFd: 4, }, { - input: "fdgramname/http", - expectAddr: NetworkAddress{ - Network: "fdgram", - Host: "3", + input: "sdgram/http", + expectedAddr: NetworkAddress{ + Network: "sdgram", + Host: "http", }, + expectedFd: 3, }, { - input: "fdgramname/https", - expectAddr: NetworkAddress{ - Network: "fdgram", - Host: "4", + input: "sdgram/https", + expectedAddr: NetworkAddress{ + Network: "sdgram", + Host: "https", }, + expectedFd: 4, }, { - input: "fdgramname/http:0", - expectAddr: NetworkAddress{ - Network: "fdgram", - Host: "3", + input: "sdgram/http/0", + expectedAddr: NetworkAddress{ + Network: "sdgram", + Host: "http/0", }, + expectedFd: 3, }, { - input: "fdname/nonexistent", + input: "sd/nonexistent", expectErr: true, }, { - input: "fdgramname/nonexistent", + input: "sd/nonexistent", expectErr: true, }, { - input: "fdname/http:99", + input: "sd/http/99", expectErr: true, }, { - input: "fdname/invalid:abc", + input: "sd/invalid/abc", expectErr: true, }, // Test that old fd/N syntax still works { input: "fd/7", - expectAddr: NetworkAddress{ + expectedAddr: NetworkAddress{ Network: "fd", Host: "7", }, + expectedFd: 7, }, { input: "fdgram/8", - expectAddr: NetworkAddress{ + expectedAddr: NetworkAddress{ Network: "fdgram", Host: "8", }, + expectedFd: 8, }, } for i, tc := range tests { actualAddr, err := ParseNetworkAddress(tc.input) + var ( + listenFdsWithNames map[string][]uint + fd uint + ) + if err == nil { + switch actualAddr.Network { + case "fd": fallthrough + case "fdgram": + var fd64 uint64 + fd64, err = strconv.ParseUint(actualAddr.Host, 0, strconv.IntSize) + if err == nil { + fd = uint(fd64) + } + case "sd": fallthrough + case "sdgram": + listenFdsWithNames, err = sdListenFdsWithNames() + fd, err = sdListenFd(listenFdsWithNames, actualAddr.Host, 0) + } + } if tc.expectErr && err == nil { t.Errorf("Test %d (%s): Expected error but got none", i, tc.input) @@ -931,8 +1024,11 @@ func TestParseNetworkAddressFdName(t *testing.T) { if !tc.expectErr && err != nil { t.Errorf("Test %d (%s): Expected no error but got: %v", i, tc.input, err) } - if !tc.expectErr && !reflect.DeepEqual(tc.expectAddr, actualAddr) { - t.Errorf("Test %d (%s): Expected %+v but got %+v", i, tc.input, tc.expectAddr, actualAddr) + if !tc.expectErr && !reflect.DeepEqual(tc.expectedAddr, actualAddr) { + t.Errorf("Test %d (%s): Expected %+v but got %+v", i, tc.input, tc.expectedAddr, actualAddr) + } + if !tc.expectErr && fd != tc.expectedFd { + t.Errorf("Expected FD %d but got %d", tc.expectedFd, fd) } } } diff --git a/networks_systemd.go b/networks_systemd.go index 4a1ddb2def4..73f3b0fb07b 100644 --- a/networks_systemd.go +++ b/networks_systemd.go @@ -26,101 +26,97 @@ func IsReservedNetwork(network string) bool { IsSdNetwork(network) } -var ( - nameToFiles map[string][]int - nameToFilesErr error - nameToFilesMu sync.Mutex -) - -func sdListenFds() (map[string][]int, error) { - nameToFilesMu.Lock() - defer nameToFilesMu.Unlock() - - if nameToFilesErr != nil { - return nil, nameToFilesErr - } - - if nameToFiles != nil { - return nameToFiles, nil - } - +func sdListenFdsWithNames() (map[string][]uint, error) { const lnFdsStart = 3 lnPid, ok := os.LookupEnv("LISTEN_PID") if !ok { - nameToFilesErr = errors.New("LISTEN_PID is unset.") - return nil, nameToFilesErr + return nil, errors.New("LISTEN_PID is unset.") } pid, err := strconv.ParseUint(lnPid, 0, strconv.IntSize) if err != nil { - nameToFilesErr = err - return nil, nameToFilesErr + return nil, err } if pid != uint64(os.Getpid()) { - nameToFilesErr = fmt.Errorf("LISTEN_PID does not match pid: %d != %d", pid, os.Getpid()) - return nil, nameToFilesErr + return nil, fmt.Errorf("LISTEN_PID does not match pid: %d != %d", pid, os.Getpid()) } lnFds, ok := os.LookupEnv("LISTEN_FDS") if !ok { - nameToFilesErr = errors.New("LISTEN_FDS is unset.") - return nil, nameToFilesErr + return nil, errors.New("LISTEN_FDS is unset.") } fds, err := strconv.ParseUint(lnFds, 0, strconv.IntSize) if err != nil { - nameToFilesErr = err - return nil, nameToFilesErr + return nil, err } lnFdnames, ok := os.LookupEnv("LISTEN_FDNAMES") if !ok { - nameToFilesErr = errors.New("LISTEN_FDNAMES is unset.") - return nil, nameToFilesErr + return nil, errors.New("LISTEN_FDNAMES is unset.") } fdNames := strings.Split(lnFdnames, ":") if fds != uint64(len(fdNames)) { - nameToFilesErr = fmt.Errorf("LISTEN_FDS does not match LISTEN_FDNAMES length: %d != %d", fds, len(fdNames)) - return nil, nameToFilesErr + return nil, fmt.Errorf("LISTEN_FDS does not match LISTEN_FDNAMES length: %d != %d", fds, len(fdNames)) } - nameToFiles = make(map[string][]int, len(fdNames)) + nameToFiles := make(map[string][]uint, len(fdNames)) for index, name := range fdNames { - nameToFiles[name] = append(nameToFiles[name], lnFdsStart+index) + nameToFiles[name] = append(nameToFiles[name], lnFdsStart+uint(index)) } return nameToFiles, nil } -func getListenerFromNetwork(ctx context.Context, network, host, port string, portOffset uint, config net.ListenConfig) (any, error) { - if IsSdNetwork(network) { - sdLnFds, err := sdListenFds() +func sdListenFd(nameToFiles map[string][]uint, host string, portOffset uint) (uint, error) { + name, index, li := host, portOffset, strings.LastIndex(host, "/") + if li >= 0 { + name = host[:li] + i, err := strconv.ParseUint(host[li+1:], 0, strconv.IntSize) if err != nil { - return nil, err + return 0, err } + index += uint(i) + } - name, index, li := host, portOffset, strings.LastIndex(host, "/") - if li >= 0 { - name = host[:li] - i, err := strconv.ParseUint(host[li+1:], 0, strconv.IntSize) - if err != nil { - return nil, err - } - index += uint(i) + files, ok := nameToFiles[name] + if !ok { + return 0, fmt.Errorf("invalid listen fd name: %s", name) + } + + if uint(len(files)) <= index { + return 0, fmt.Errorf("invalid listen fd index: %d", index) + } + + return files[index], nil +} + +var ( + initNameToFiles map[string][]uint + initNameToFilesErr error + initNameToFilesMu sync.Mutex +) + +func getListenerFromNetwork(ctx context.Context, network, host, port string, portOffset uint, config net.ListenConfig) (any, error) { + if IsSdNetwork(network) { + initNameToFilesMu.Lock() + defer initNameToFilesMu.Unlock() + + if initNameToFiles == nil && initNameToFilesErr == nil { + initNameToFiles, initNameToFilesErr = sdListenFdsWithNames() } - files, ok := sdLnFds[name] - if !ok { - return nil, fmt.Errorf("invalid listen fd name: %s", name) + if initNameToFilesErr != nil { + return nil, initNameToFilesErr } - if uint(len(files)) <= index { - return nil, fmt.Errorf("invalid listen fd index: %d", index) + file, err := sdListenFd(initNameToFiles, host, portOffset) + if err != nil { + return nil, err } - file := files[index] var fdNetwork string switch network { @@ -132,7 +128,7 @@ func getListenerFromNetwork(ctx context.Context, network, host, port string, por return nil, fmt.Errorf("invalid network: %s", network) } - na, err := ParseNetworkAddress(JoinNetworkAddress(fdNetwork, strconv.Itoa(file), port)) + na, err := ParseNetworkAddress(JoinNetworkAddress(fdNetwork, strconv.FormatUint(uint64(file),10), port)) if err != nil { return nil, err } From 659e3081b8029c1b22118f0a22abff8b13d0a220 Mon Sep 17 00:00:00 2001 From: Aaron Paterson Date: Fri, 31 Oct 2025 18:23:20 -0600 Subject: [PATCH 03/51] gofmt --- listeners.go | 4 ++-- listeners_test.go | 32 ++++++++++++++++-------------- modules/logging/filters_test.go | 4 ++-- networks.go | 6 +++--- networks_nosystemd.go | 24 ++++++++++++++-------- networks_systemd.go | 35 +++++++++++++++++++++------------ 6 files changed, 62 insertions(+), 43 deletions(-) diff --git a/listeners.go b/listeners.go index de0c9402baf..6623a57d1d5 100644 --- a/listeners.go +++ b/listeners.go @@ -134,8 +134,8 @@ func (na NetworkAddress) ListenAll(ctx context.Context, config net.ListenConfig) // while an existing socket is unlinked. func (na NetworkAddress) Listen(ctx context.Context, portOffset uint, config net.ListenConfig) (any, error) { var ( - ln any - err error + ln any + err error ) // check to see if network provides a listener diff --git a/listeners_test.go b/listeners_test.go index ce3312b4610..7fd26fdea5a 100644 --- a/listeners_test.go +++ b/listeners_test.go @@ -17,8 +17,8 @@ package caddy import ( "os" "reflect" - "testing" "strconv" + "testing" "github.com/caddyserver/caddy/v2/internal" ) @@ -837,8 +837,8 @@ func TestGetFdByName(t *testing.T) { // Test the function var ( listenFdsWithNames map[string][]uint - err error - fd uint + err error + fd uint ) listenFdsWithNames, err = sdListenFdsWithNames() if err == nil { @@ -1000,21 +1000,23 @@ func TestParseNetworkAddressFdName(t *testing.T) { actualAddr, err := ParseNetworkAddress(tc.input) var ( listenFdsWithNames map[string][]uint - fd uint + fd uint ) if err == nil { switch actualAddr.Network { - case "fd": fallthrough - case "fdgram": - var fd64 uint64 - fd64, err = strconv.ParseUint(actualAddr.Host, 0, strconv.IntSize) - if err == nil { - fd = uint(fd64) - } - case "sd": fallthrough - case "sdgram": - listenFdsWithNames, err = sdListenFdsWithNames() - fd, err = sdListenFd(listenFdsWithNames, actualAddr.Host, 0) + case "fd": + fallthrough + case "fdgram": + var fd64 uint64 + fd64, err = strconv.ParseUint(actualAddr.Host, 0, strconv.IntSize) + if err == nil { + fd = uint(fd64) + } + case "sd": + fallthrough + case "sdgram": + listenFdsWithNames, err = sdListenFdsWithNames() + fd, err = sdListenFd(listenFdsWithNames, actualAddr.Host, 0) } } diff --git a/modules/logging/filters_test.go b/modules/logging/filters_test.go index 42aa297575b..cf35e717827 100644 --- a/modules/logging/filters_test.go +++ b/modules/logging/filters_test.go @@ -404,12 +404,12 @@ func TestMultiRegexpFilterInputSizeLimit(t *testing.T) { // Test with very large input (should be truncated) largeInput := strings.Repeat("test", 300000) // Creates ~1.2MB string out := f.Filter(zapcore.Field{String: largeInput}) - + // The input should be truncated to 1MB and still processed if len(out.String) > 1000000 { t.Fatalf("output string not truncated: length %d", len(out.String)) } - + // Should still contain replacements within the truncated portion if !strings.Contains(out.String, "REPLACED") { t.Fatalf("replacements not applied to truncated input") diff --git a/networks.go b/networks.go index 6241fbe4055..d527c73236b 100644 --- a/networks.go +++ b/networks.go @@ -15,12 +15,12 @@ package caddy import ( - "strings" "context" + "fmt" + "go.uber.org/zap" "net" + "strings" "sync" - "go.uber.org/zap" - "fmt" ) // IsUnixNetwork returns true if the netw is a unix network. diff --git a/networks_nosystemd.go b/networks_nosystemd.go index 63424800f3d..90cfa7f3166 100644 --- a/networks_nosystemd.go +++ b/networks_nosystemd.go @@ -16,14 +16,22 @@ func getListenerFromNetwork(ctx context.Context, network, host, port string, por func getHTTP3Network(originalNetwork string) (string, error) { switch originalNetwork { - case "unixgram": return "unixgram", nil - case "udp": return "udp", nil - case "udp4": return "udp4", nil - case "udp6": return "udp6", nil - case "tcp": return "udp", nil - case "tcp4": return "udp4", nil - case "tcp6": return "udp6", nil - case "fdgram": return "fdgram", nil + case "unixgram": + return "unixgram", nil + case "udp": + return "udp", nil + case "udp4": + return "udp4", nil + case "udp6": + return "udp6", nil + case "tcp": + return "udp", nil + case "tcp4": + return "udp4", nil + case "tcp6": + return "udp6", nil + case "fdgram": + return "fdgram", nil } return getHTTP3Plugin(originalNetwork) } diff --git a/networks_systemd.go b/networks_systemd.go index 73f3b0fb07b..e0c02a05d01 100644 --- a/networks_systemd.go +++ b/networks_systemd.go @@ -4,13 +4,13 @@ package caddy import ( "context" + "errors" + "fmt" "net" - "sync" "os" - "errors" "strconv" - "fmt" "strings" + "sync" ) func IsSdNetwork(network string) bool { @@ -128,7 +128,7 @@ func getListenerFromNetwork(ctx context.Context, network, host, port string, por return nil, fmt.Errorf("invalid network: %s", network) } - na, err := ParseNetworkAddress(JoinNetworkAddress(fdNetwork, strconv.FormatUint(uint64(file),10), port)) + na, err := ParseNetworkAddress(JoinNetworkAddress(fdNetwork, strconv.FormatUint(uint64(file), 10), port)) if err != nil { return nil, err } @@ -140,15 +140,24 @@ func getListenerFromNetwork(ctx context.Context, network, host, port string, por func getHTTP3Network(originalNetwork string) (string, error) { switch originalNetwork { - case "unixgram": return "unixgram", nil - case "udp": return "udp", nil - case "udp4": return "udp4", nil - case "udp6": return "udp6", nil - case "tcp": return "udp", nil - case "tcp4": return "udp4", nil - case "tcp6": return "udp6", nil - case "fdgram": return "fdgram", nil - case "sdgram": return "sdgram", nil + case "unixgram": + return "unixgram", nil + case "udp": + return "udp", nil + case "udp4": + return "udp4", nil + case "udp6": + return "udp6", nil + case "tcp": + return "udp", nil + case "tcp4": + return "udp4", nil + case "tcp6": + return "udp6", nil + case "fdgram": + return "fdgram", nil + case "sdgram": + return "sdgram", nil } return getHTTP3Plugin(originalNetwork) } From c87d9c38deac73d3b87817a5fb7110ff8374c9c0 Mon Sep 17 00:00:00 2001 From: Aaron Paterson Date: Fri, 31 Oct 2025 18:44:07 -0600 Subject: [PATCH 04/51] use caddy package --- modules/caddyhttp/server.go | 2 +- networks_nosystemd.go | 2 +- networks_systemd.go | 2 +- 3 files changed, 3 insertions(+), 3 deletions(-) diff --git a/modules/caddyhttp/server.go b/modules/caddyhttp/server.go index d3e654533e1..a171bf60a30 100644 --- a/modules/caddyhttp/server.go +++ b/modules/caddyhttp/server.go @@ -620,7 +620,7 @@ func (s *Server) findLastRouteWithHostMatcher() int { // not already done, and then uses that server to serve HTTP/3 over // the listener, with Server s as the handler. func (s *Server) serveHTTP3(addr caddy.NetworkAddress, tlsCfg *tls.Config) error { - h3net, err := getHTTP3Network(addr.Network) + h3net, err := caddy.GetHTTP3Network(addr.Network) if err != nil { return fmt.Errorf("starting HTTP/3 QUIC listener: %v", err) } diff --git a/networks_nosystemd.go b/networks_nosystemd.go index 90cfa7f3166..605bf02e511 100644 --- a/networks_nosystemd.go +++ b/networks_nosystemd.go @@ -14,7 +14,7 @@ func getListenerFromNetwork(ctx context.Context, network, host, port string, por return getListenerFromPlugin(ctx, network, host, port, portOffset, config) } -func getHTTP3Network(originalNetwork string) (string, error) { +func GetHTTP3Network(originalNetwork string) (string, error) { switch originalNetwork { case "unixgram": return "unixgram", nil diff --git a/networks_systemd.go b/networks_systemd.go index e0c02a05d01..fd03c1bd446 100644 --- a/networks_systemd.go +++ b/networks_systemd.go @@ -138,7 +138,7 @@ func getListenerFromNetwork(ctx context.Context, network, host, port string, por return getListenerFromPlugin(ctx, network, host, port, portOffset, config) } -func getHTTP3Network(originalNetwork string) (string, error) { +func GetHTTP3Network(originalNetwork string) (string, error) { switch originalNetwork { case "unixgram": return "unixgram", nil From 4c3696238a82e19260a376fd31b6df00b14807f6 Mon Sep 17 00:00:00 2001 From: Aaron Paterson Date: Fri, 31 Oct 2025 18:48:38 -0600 Subject: [PATCH 05/51] fix nosystemd build --- networks_nosystemd.go | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/networks_nosystemd.go b/networks_nosystemd.go index 605bf02e511..f56f79e0525 100644 --- a/networks_nosystemd.go +++ b/networks_nosystemd.go @@ -2,6 +2,11 @@ package caddy +import ( + "context" + "net" +) + func IsReservedNetwork(network string) bool { return network == "tcp" || network == "tcp4" || network == "tcp6" || network == "udp" || network == "udp4" || network == "udp6" || From e5c4b04873e4a577c05fb0ddc22d61a6efc1fc15 Mon Sep 17 00:00:00 2001 From: Aaron Paterson Date: Fri, 31 Oct 2025 18:51:06 -0600 Subject: [PATCH 06/51] gofumpt --- networks.go | 15 ++++++++++----- 1 file changed, 10 insertions(+), 5 deletions(-) diff --git a/networks.go b/networks.go index d527c73236b..f739bc71566 100644 --- a/networks.go +++ b/networks.go @@ -17,10 +17,11 @@ package caddy import ( "context" "fmt" - "go.uber.org/zap" "net" "strings" "sync" + + "go.uber.org/zap" ) // IsUnixNetwork returns true if the netw is a unix network. @@ -44,8 +45,10 @@ func IsFdNetwork(netw string) bool { // both need the same listener. EXPERIMENTAL and subject to change. type ListenerFunc func(ctx context.Context, network, host, portRange string, portOffset uint, cfg net.ListenConfig) (any, error) -var networkPlugins = map[string]ListenerFunc{} -var networkPluginsMu sync.RWMutex +var ( + networkPlugins = map[string]ListenerFunc{} + networkPluginsMu sync.RWMutex +) // RegisterNetwork registers a network plugin with Caddy so that if a listener is // created for that network plugin, getListener will be invoked to get the listener. @@ -84,8 +87,10 @@ func getListenerFromPlugin(ctx context.Context, network, host, port string, port return nil, nil } -var networkHTTP3Plugins = map[string]string{} -var networkHTTP3PluginsMu sync.RWMutex +var ( + networkHTTP3Plugins = map[string]string{} + networkHTTP3PluginsMu sync.RWMutex +) // RegisterNetworkHTTP3 registers a mapping from non-HTTP/3 network to HTTP/3 // network. This should be called during init() and will panic if the network From dfe2fe20367ae72b615286309302c228c8334de0 Mon Sep 17 00:00:00 2001 From: Aaron Paterson Date: Fri, 31 Oct 2025 19:03:52 -0600 Subject: [PATCH 07/51] fix unix+h2c --- networks.go | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/networks.go b/networks.go index f739bc71566..52d5a4a38c4 100644 --- a/networks.go +++ b/networks.go @@ -26,7 +26,7 @@ import ( // IsUnixNetwork returns true if the netw is a unix network. func IsUnixNetwork(netw string) bool { - return netw == "unix" || netw == "unixgram" || netw == "unixpacket" + return netw == "unix" || netw == "unixgram" || netw == "unixpacket" || netw == "unix+h2c" } // IsIpNetwork returns true if the netw is an ip network. From ac84e68c5f2b0c75681c237607fa3968fb16c3b9 Mon Sep 17 00:00:00 2001 From: Aaron Paterson Date: Fri, 31 Oct 2025 19:12:10 -0600 Subject: [PATCH 08/51] separate listeners_test target --- listeners_test.go | 382 ------------------------------------- listeners_test_systemd.go | 390 ++++++++++++++++++++++++++++++++++++++ 2 files changed, 390 insertions(+), 382 deletions(-) create mode 100644 listeners_test_systemd.go diff --git a/listeners_test.go b/listeners_test.go index 7fd26fdea5a..a4cadd3aab1 100644 --- a/listeners_test.go +++ b/listeners_test.go @@ -15,9 +15,7 @@ package caddy import ( - "os" "reflect" - "strconv" "testing" "github.com/caddyserver/caddy/v2/internal" @@ -654,383 +652,3 @@ func TestSplitUnixSocketPermissionsBits(t *testing.T) { } } } - -// TestGetFdByName tests the getFdByName function for systemd socket activation. -func TestGetFdByName(t *testing.T) { - // Save original environment - originalFdNames := os.Getenv("LISTEN_FDNAMES") - originalFds := os.Getenv("LISTEN_FDS") - originalPid := os.Getenv("LISTEN_PID") - - // Restore environment after test - defer func() { - if originalFdNames != "" { - os.Setenv("LISTEN_FDNAMES", originalFdNames) - } else { - os.Unsetenv("LISTEN_FDNAMES") - } - if originalFds != "" { - os.Setenv("LISTEN_FDS", originalFds) - } else { - os.Unsetenv("LISTEN_FDS") - } - if originalPid != "" { - os.Setenv("LISTEN_PID", originalPid) - } else { - os.Unsetenv("LISTEN_PID") - } - }() - - tests := []struct { - name string - fdNames string - fds string - socketName string - expectedFd uint - expectError bool - }{ - { - name: "simple http socket", - fdNames: "http", - fds: "1", - socketName: "http", - expectedFd: 3, - }, - { - name: "multiple different sockets - first", - fdNames: "http:https:dns", - fds: "3", - socketName: "http", - expectedFd: 3, - }, - { - name: "multiple different sockets - second", - fdNames: "http:https:dns", - fds: "3", - socketName: "https", - expectedFd: 4, - }, - { - name: "multiple different sockets - third", - fdNames: "http:https:dns", - fds: "3", - socketName: "dns", - expectedFd: 5, - }, - { - name: "duplicate names - first occurrence (no index)", - fdNames: "web:web:api", - fds: "3", - socketName: "web", - expectedFd: 3, - }, - { - name: "duplicate names - first occurrence (explicit index 0)", - fdNames: "web:web:api", - fds: "3", - socketName: "web/0", - expectedFd: 3, - }, - { - name: "duplicate names - second occurrence (index 1)", - fdNames: "web:web:api", - fds: "3", - socketName: "web/1", - expectedFd: 4, - }, - { - name: "complex duplicates - first api", - fdNames: "web:api:web:api:dns", - fds: "5", - socketName: "api/0", - expectedFd: 4, - }, - { - name: "complex duplicates - second api", - fdNames: "web:api:web:api:dns", - fds: "5", - socketName: "api/1", - expectedFd: 6, - }, - { - name: "complex duplicates - first web", - fdNames: "web:api:web:api:dns", - fds: "5", - socketName: "web/0", - expectedFd: 3, - }, - { - name: "complex duplicates - second web", - fdNames: "web:api:web:api:dns", - fds: "5", - socketName: "web/1", - expectedFd: 5, - }, - { - name: "socket not found", - fdNames: "http:https", - fds: "2", - socketName: "missing", - expectError: true, - }, - { - name: "empty socket name", - fdNames: "http", - fds: "1", - socketName: "", - expectError: true, - }, - { - name: "missing LISTEN_FDNAMES", - fdNames: "", - fds: "", - socketName: "http", - expectError: true, - }, - { - name: "index out of range", - fdNames: "web:web", - fds: "2", - socketName: "web/2", - expectError: true, - }, - { - name: "negative index", - fdNames: "web", - fds: "1", - socketName: "web/-1", - expectError: true, - }, - { - name: "invalid index format", - fdNames: "web", - fds: "1", - socketName: "web/abc", - expectError: true, - }, - { - name: "too many colons", - fdNames: "web", - fds: "1", - socketName: "web/0/extra", - expectError: true, - }, - } - - for _, tc := range tests { - t.Run(tc.name, func(t *testing.T) { - // Set up environment - if tc.fdNames != "" { - os.Setenv("LISTEN_FDNAMES", tc.fdNames) - } else { - os.Unsetenv("LISTEN_FDNAMES") - } - - if tc.fds != "" { - os.Setenv("LISTEN_FDS", tc.fds) - } else { - os.Unsetenv("LISTEN_FDS") - } - - os.Setenv("LISTEN_PID", strconv.Itoa(os.Getpid())) - - // Test the function - var ( - listenFdsWithNames map[string][]uint - err error - fd uint - ) - listenFdsWithNames, err = sdListenFdsWithNames() - if err == nil { - fd, err = sdListenFd(listenFdsWithNames, tc.socketName, 0) - } - - if tc.expectError { - if err == nil { - t.Errorf("Expected error but got none") - } - } else { - if err != nil { - t.Errorf("Expected no error but got: %v", err) - } - if fd != tc.expectedFd { - t.Errorf("Expected FD %d but got %d", tc.expectedFd, fd) - } - } - }) - } -} - -// TestParseNetworkAddressFdName tests parsing of fdname and fdgramname addresses. -func TestParseNetworkAddressFdName(t *testing.T) { - // Save and restore environment - originalFdNames := os.Getenv("LISTEN_FDNAMES") - originalFds := os.Getenv("LISTEN_FDS") - originalPid := os.Getenv("LISTEN_PID") - - defer func() { - if originalFdNames != "" { - os.Setenv("LISTEN_FDNAMES", originalFdNames) - } else { - os.Unsetenv("LISTEN_FDNAMES") - } - if originalFds != "" { - os.Setenv("LISTEN_FDS", originalFds) - } else { - os.Unsetenv("LISTEN_FDS") - } - if originalPid != "" { - os.Setenv("LISTEN_PID", originalPid) - } else { - os.Unsetenv("LISTEN_PID") - } - }() - - // Set up test environment - os.Setenv("LISTEN_FDNAMES", "http:https:dns") - os.Setenv("LISTEN_FDS", "3") - os.Setenv("LISTEN_PID", strconv.Itoa(os.Getpid())) - - tests := []struct { - input string - expectedAddr NetworkAddress - expectedFd uint - expectErr bool - }{ - { - input: "sd/http", - expectedAddr: NetworkAddress{ - Network: "sd", - Host: "http", - }, - expectedFd: 3, - }, - { - input: "sd/https", - expectedAddr: NetworkAddress{ - Network: "sd", - Host: "https", - }, - expectedFd: 4, - }, - { - input: "sd/dns", - expectedAddr: NetworkAddress{ - Network: "sd", - Host: "dns", - }, - expectedFd: 5, - }, - { - input: "sd/http/0", - expectedAddr: NetworkAddress{ - Network: "sd", - Host: "http/0", - }, - expectedFd: 3, - }, - { - input: "sd/https/0", - expectedAddr: NetworkAddress{ - Network: "sd", - Host: "https/0", - }, - expectedFd: 4, - }, - { - input: "sdgram/http", - expectedAddr: NetworkAddress{ - Network: "sdgram", - Host: "http", - }, - expectedFd: 3, - }, - { - input: "sdgram/https", - expectedAddr: NetworkAddress{ - Network: "sdgram", - Host: "https", - }, - expectedFd: 4, - }, - { - input: "sdgram/http/0", - expectedAddr: NetworkAddress{ - Network: "sdgram", - Host: "http/0", - }, - expectedFd: 3, - }, - { - input: "sd/nonexistent", - expectErr: true, - }, - { - input: "sd/nonexistent", - expectErr: true, - }, - { - input: "sd/http/99", - expectErr: true, - }, - { - input: "sd/invalid/abc", - expectErr: true, - }, - // Test that old fd/N syntax still works - { - input: "fd/7", - expectedAddr: NetworkAddress{ - Network: "fd", - Host: "7", - }, - expectedFd: 7, - }, - { - input: "fdgram/8", - expectedAddr: NetworkAddress{ - Network: "fdgram", - Host: "8", - }, - expectedFd: 8, - }, - } - - for i, tc := range tests { - actualAddr, err := ParseNetworkAddress(tc.input) - var ( - listenFdsWithNames map[string][]uint - fd uint - ) - if err == nil { - switch actualAddr.Network { - case "fd": - fallthrough - case "fdgram": - var fd64 uint64 - fd64, err = strconv.ParseUint(actualAddr.Host, 0, strconv.IntSize) - if err == nil { - fd = uint(fd64) - } - case "sd": - fallthrough - case "sdgram": - listenFdsWithNames, err = sdListenFdsWithNames() - fd, err = sdListenFd(listenFdsWithNames, actualAddr.Host, 0) - } - } - - if tc.expectErr && err == nil { - t.Errorf("Test %d (%s): Expected error but got none", i, tc.input) - } - if !tc.expectErr && err != nil { - t.Errorf("Test %d (%s): Expected no error but got: %v", i, tc.input, err) - } - if !tc.expectErr && !reflect.DeepEqual(tc.expectedAddr, actualAddr) { - t.Errorf("Test %d (%s): Expected %+v but got %+v", i, tc.input, tc.expectedAddr, actualAddr) - } - if !tc.expectErr && fd != tc.expectedFd { - t.Errorf("Expected FD %d but got %d", tc.expectedFd, fd) - } - } -} diff --git a/listeners_test_systemd.go b/listeners_test_systemd.go new file mode 100644 index 00000000000..866e922d760 --- /dev/null +++ b/listeners_test_systemd.go @@ -0,0 +1,390 @@ +//go:build linux && !nosystemd + +package caddy + +import ( + "os" + "reflect" + "strconv" + "testing" +) + +// TestSdListenFd tests the sdListenFd function for systemd socket activation. +func TestSdListenFd(t *testing.T) { + // Save original environment + originalFdNames := os.Getenv("LISTEN_FDNAMES") + originalFds := os.Getenv("LISTEN_FDS") + originalPid := os.Getenv("LISTEN_PID") + + // Restore environment after test + defer func() { + if originalFdNames != "" { + os.Setenv("LISTEN_FDNAMES", originalFdNames) + } else { + os.Unsetenv("LISTEN_FDNAMES") + } + if originalFds != "" { + os.Setenv("LISTEN_FDS", originalFds) + } else { + os.Unsetenv("LISTEN_FDS") + } + if originalPid != "" { + os.Setenv("LISTEN_PID", originalPid) + } else { + os.Unsetenv("LISTEN_PID") + } + }() + + tests := []struct { + name string + fdNames string + fds string + socketName string + expectedFd uint + expectError bool + }{ + { + name: "simple http socket", + fdNames: "http", + fds: "1", + socketName: "http", + expectedFd: 3, + }, + { + name: "multiple different sockets - first", + fdNames: "http:https:dns", + fds: "3", + socketName: "http", + expectedFd: 3, + }, + { + name: "multiple different sockets - second", + fdNames: "http:https:dns", + fds: "3", + socketName: "https", + expectedFd: 4, + }, + { + name: "multiple different sockets - third", + fdNames: "http:https:dns", + fds: "3", + socketName: "dns", + expectedFd: 5, + }, + { + name: "duplicate names - first occurrence (no index)", + fdNames: "web:web:api", + fds: "3", + socketName: "web", + expectedFd: 3, + }, + { + name: "duplicate names - first occurrence (explicit index 0)", + fdNames: "web:web:api", + fds: "3", + socketName: "web/0", + expectedFd: 3, + }, + { + name: "duplicate names - second occurrence (index 1)", + fdNames: "web:web:api", + fds: "3", + socketName: "web/1", + expectedFd: 4, + }, + { + name: "complex duplicates - first api", + fdNames: "web:api:web:api:dns", + fds: "5", + socketName: "api/0", + expectedFd: 4, + }, + { + name: "complex duplicates - second api", + fdNames: "web:api:web:api:dns", + fds: "5", + socketName: "api/1", + expectedFd: 6, + }, + { + name: "complex duplicates - first web", + fdNames: "web:api:web:api:dns", + fds: "5", + socketName: "web/0", + expectedFd: 3, + }, + { + name: "complex duplicates - second web", + fdNames: "web:api:web:api:dns", + fds: "5", + socketName: "web/1", + expectedFd: 5, + }, + { + name: "socket not found", + fdNames: "http:https", + fds: "2", + socketName: "missing", + expectError: true, + }, + { + name: "empty socket name", + fdNames: "http", + fds: "1", + socketName: "", + expectError: true, + }, + { + name: "missing LISTEN_FDNAMES", + fdNames: "", + fds: "", + socketName: "http", + expectError: true, + }, + { + name: "index out of range", + fdNames: "web:web", + fds: "2", + socketName: "web/2", + expectError: true, + }, + { + name: "negative index", + fdNames: "web", + fds: "1", + socketName: "web/-1", + expectError: true, + }, + { + name: "invalid index format", + fdNames: "web", + fds: "1", + socketName: "web/abc", + expectError: true, + }, + { + name: "too many colons", + fdNames: "web", + fds: "1", + socketName: "web/0/extra", + expectError: true, + }, + } + + for _, tc := range tests { + t.Run(tc.name, func(t *testing.T) { + // Set up environment + if tc.fdNames != "" { + os.Setenv("LISTEN_FDNAMES", tc.fdNames) + } else { + os.Unsetenv("LISTEN_FDNAMES") + } + + if tc.fds != "" { + os.Setenv("LISTEN_FDS", tc.fds) + } else { + os.Unsetenv("LISTEN_FDS") + } + + os.Setenv("LISTEN_PID", strconv.Itoa(os.Getpid())) + + // Test the function + var ( + listenFdsWithNames map[string][]uint + err error + fd uint + ) + listenFdsWithNames, err = sdListenFdsWithNames() + if err == nil { + fd, err = sdListenFd(listenFdsWithNames, tc.socketName, 0) + } + + if tc.expectError { + if err == nil { + t.Errorf("Expected error but got none") + } + } else { + if err != nil { + t.Errorf("Expected no error but got: %v", err) + } + if fd != tc.expectedFd { + t.Errorf("Expected FD %d but got %d", tc.expectedFd, fd) + } + } + }) + } +} + +// TestParseNetworkAddressSd tests parsing of sd and sdgram addresses. +func TestParseNetworkAddressSd(t *testing.T) { + // Save and restore environment + originalFdNames := os.Getenv("LISTEN_FDNAMES") + originalFds := os.Getenv("LISTEN_FDS") + originalPid := os.Getenv("LISTEN_PID") + + defer func() { + if originalFdNames != "" { + os.Setenv("LISTEN_FDNAMES", originalFdNames) + } else { + os.Unsetenv("LISTEN_FDNAMES") + } + if originalFds != "" { + os.Setenv("LISTEN_FDS", originalFds) + } else { + os.Unsetenv("LISTEN_FDS") + } + if originalPid != "" { + os.Setenv("LISTEN_PID", originalPid) + } else { + os.Unsetenv("LISTEN_PID") + } + }() + + // Set up test environment + os.Setenv("LISTEN_FDNAMES", "http:https:dns") + os.Setenv("LISTEN_FDS", "3") + os.Setenv("LISTEN_PID", strconv.Itoa(os.Getpid())) + + tests := []struct { + input string + expectedAddr NetworkAddress + expectedFd uint + expectErr bool + }{ + { + input: "sd/http", + expectedAddr: NetworkAddress{ + Network: "sd", + Host: "http", + }, + expectedFd: 3, + }, + { + input: "sd/https", + expectedAddr: NetworkAddress{ + Network: "sd", + Host: "https", + }, + expectedFd: 4, + }, + { + input: "sd/dns", + expectedAddr: NetworkAddress{ + Network: "sd", + Host: "dns", + }, + expectedFd: 5, + }, + { + input: "sd/http/0", + expectedAddr: NetworkAddress{ + Network: "sd", + Host: "http/0", + }, + expectedFd: 3, + }, + { + input: "sd/https/0", + expectedAddr: NetworkAddress{ + Network: "sd", + Host: "https/0", + }, + expectedFd: 4, + }, + { + input: "sdgram/http", + expectedAddr: NetworkAddress{ + Network: "sdgram", + Host: "http", + }, + expectedFd: 3, + }, + { + input: "sdgram/https", + expectedAddr: NetworkAddress{ + Network: "sdgram", + Host: "https", + }, + expectedFd: 4, + }, + { + input: "sdgram/http/0", + expectedAddr: NetworkAddress{ + Network: "sdgram", + Host: "http/0", + }, + expectedFd: 3, + }, + { + input: "sd/nonexistent", + expectErr: true, + }, + { + input: "sd/nonexistent", + expectErr: true, + }, + { + input: "sd/http/99", + expectErr: true, + }, + { + input: "sd/invalid/abc", + expectErr: true, + }, + // Test that old fd/N syntax still works + { + input: "fd/7", + expectedAddr: NetworkAddress{ + Network: "fd", + Host: "7", + }, + expectedFd: 7, + }, + { + input: "fdgram/8", + expectedAddr: NetworkAddress{ + Network: "fdgram", + Host: "8", + }, + expectedFd: 8, + }, + } + + for i, tc := range tests { + actualAddr, err := ParseNetworkAddress(tc.input) + var ( + listenFdsWithNames map[string][]uint + fd uint + ) + if err == nil { + switch actualAddr.Network { + case "fd": + fallthrough + case "fdgram": + var fd64 uint64 + fd64, err = strconv.ParseUint(actualAddr.Host, 0, strconv.IntSize) + if err == nil { + fd = uint(fd64) + } + case "sd": + fallthrough + case "sdgram": + listenFdsWithNames, err = sdListenFdsWithNames() + fd, err = sdListenFd(listenFdsWithNames, actualAddr.Host, 0) + } + } + + if tc.expectErr && err == nil { + t.Errorf("Test %d (%s): Expected error but got none", i, tc.input) + } + if !tc.expectErr && err != nil { + t.Errorf("Test %d (%s): Expected no error but got: %v", i, tc.input, err) + } + if !tc.expectErr && !reflect.DeepEqual(tc.expectedAddr, actualAddr) { + t.Errorf("Test %d (%s): Expected %+v but got %+v", i, tc.input, tc.expectedAddr, actualAddr) + } + if !tc.expectErr && fd != tc.expectedFd { + t.Errorf("Expected FD %d but got %d", tc.expectedFd, fd) + } + } +} From be042868d9b1a903c89954a1ceda0acb95262f49 Mon Sep 17 00:00:00 2001 From: Aaron Paterson Date: Fri, 31 Oct 2025 20:23:26 -0600 Subject: [PATCH 09/51] deprecate caddyhttp.RegisterNetworkHTTP3 --- modules/caddyhttp/server.go | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/modules/caddyhttp/server.go b/modules/caddyhttp/server.go index a171bf60a30..7c095fa97a4 100644 --- a/modules/caddyhttp/server.go +++ b/modules/caddyhttp/server.go @@ -1124,3 +1124,8 @@ const ( // For tracking the real client IP (affected by trusted_proxy) ClientIPVarKey string = "client_ip" ) + +// DEPRECATED: moved to caddy.RegisterNetworkHTTP3 +func RegisterNetworkHTTP3(originalNetwork, h3Network string) { + caddy.RegisterNetworkHTTP3(originalNetwork, h3Network) +} From 5ba3608e8902ca78081116f69982e21d9beb343c Mon Sep 17 00:00:00 2001 From: Aaron Paterson Date: Sat, 1 Nov 2025 17:37:06 -0600 Subject: [PATCH 10/51] getSdFd --- listeners_test_systemd.go | 8 ++-- networks_systemd.go | 85 +++++++++++++++++++++++---------------- 2 files changed, 54 insertions(+), 39 deletions(-) diff --git a/listeners_test_systemd.go b/listeners_test_systemd.go index 866e922d760..b393a653f73 100644 --- a/listeners_test_systemd.go +++ b/listeners_test_systemd.go @@ -9,8 +9,8 @@ import ( "testing" ) -// TestSdListenFd tests the sdListenFd function for systemd socket activation. -func TestSdListenFd(t *testing.T) { +// TestGetSdFd tests the getSdFd function for systemd socket activation. +func TestGetSdFd(t *testing.T) { // Save original environment originalFdNames := os.Getenv("LISTEN_FDNAMES") originalFds := os.Getenv("LISTEN_FDS") @@ -196,7 +196,7 @@ func TestSdListenFd(t *testing.T) { ) listenFdsWithNames, err = sdListenFdsWithNames() if err == nil { - fd, err = sdListenFd(listenFdsWithNames, tc.socketName, 0) + fd, err = getSdFd(listenFdsWithNames, tc.socketName, 0) } if tc.expectError { @@ -370,7 +370,7 @@ func TestParseNetworkAddressSd(t *testing.T) { fallthrough case "sdgram": listenFdsWithNames, err = sdListenFdsWithNames() - fd, err = sdListenFd(listenFdsWithNames, actualAddr.Host, 0) + fd, err = getSdFd(listenFdsWithNames, actualAddr.Host, 0) } } diff --git a/networks_systemd.go b/networks_systemd.go index fd03c1bd446..d99f46c87bc 100644 --- a/networks_systemd.go +++ b/networks_systemd.go @@ -26,29 +26,38 @@ func IsReservedNetwork(network string) bool { IsSdNetwork(network) } -func sdListenFdsWithNames() (map[string][]uint, error) { - const lnFdsStart = 3 - +func sdListenFds() (int, error) { lnPid, ok := os.LookupEnv("LISTEN_PID") if !ok { - return nil, errors.New("LISTEN_PID is unset.") + return 0, errors.New("LISTEN_PID is unset.") } - pid, err := strconv.ParseUint(lnPid, 0, strconv.IntSize) + pid, err := strconv.Atoi(lnPid) if err != nil { - return nil, err + return 0, err } - if pid != uint64(os.Getpid()) { - return nil, fmt.Errorf("LISTEN_PID does not match pid: %d != %d", pid, os.Getpid()) + if pid != os.Getpid() { + return 0, fmt.Errorf("LISTEN_PID does not match pid: %d != %d", pid, os.Getpid()) } lnFds, ok := os.LookupEnv("LISTEN_FDS") if !ok { - return nil, errors.New("LISTEN_FDS is unset.") + return 0, errors.New("LISTEN_FDS is unset.") } - fds, err := strconv.ParseUint(lnFds, 0, strconv.IntSize) + fds, err := strconv.Atoi(lnFds) + if err != nil { + return 0, err + } + + return fds, nil +} + +func sdListenFdsWithNames() (map[string][]uint, error) { + const lnFdsStart = 3 + + fds, err := sdListenFds() if err != nil { return nil, err } @@ -59,7 +68,7 @@ func sdListenFdsWithNames() (map[string][]uint, error) { } fdNames := strings.Split(lnFdnames, ":") - if fds != uint64(len(fdNames)) { + if fds != len(fdNames) { return nil, fmt.Errorf("LISTEN_FDS does not match LISTEN_FDNAMES length: %d != %d", fds, len(fdNames)) } @@ -71,7 +80,7 @@ func sdListenFdsWithNames() (map[string][]uint, error) { return nameToFiles, nil } -func sdListenFd(nameToFiles map[string][]uint, host string, portOffset uint) (uint, error) { +func getSdFd(nameToFiles map[string][]uint, host string, portOffset uint) (uint, error) { name, index, li := host, portOffset, strings.LastIndex(host, "/") if li >= 0 { name = host[:li] @@ -100,40 +109,46 @@ var ( initNameToFilesMu sync.Mutex ) -func getListenerFromNetwork(ctx context.Context, network, host, port string, portOffset uint, config net.ListenConfig) (any, error) { - if IsSdNetwork(network) { +func getListenerFromSd(ctx context.Context, network, host, port string, portOffset uint, config net.ListenConfig) (any, error) { + func() { initNameToFilesMu.Lock() defer initNameToFilesMu.Unlock() if initNameToFiles == nil && initNameToFilesErr == nil { initNameToFiles, initNameToFilesErr = sdListenFdsWithNames() } + }() - if initNameToFilesErr != nil { - return nil, initNameToFilesErr - } + if initNameToFilesErr != nil { + return nil, initNameToFilesErr + } - file, err := sdListenFd(initNameToFiles, host, portOffset) - if err != nil { - return nil, err - } + file, err := getSdFd(initNameToFiles, host, portOffset) + if err != nil { + return nil, err + } - var fdNetwork string - switch network { - case "sd": - fdNetwork = "fd" - case "sdgram": - fdNetwork = "fdgram" - default: - return nil, fmt.Errorf("invalid network: %s", network) - } + var fdNetwork string + switch network { + case "sd": + fdNetwork = "fd" + case "sdgram": + fdNetwork = "fdgram" + default: + return nil, fmt.Errorf("invalid network: %s", network) + } - na, err := ParseNetworkAddress(JoinNetworkAddress(fdNetwork, strconv.FormatUint(uint64(file), 10), port)) - if err != nil { - return nil, err - } + na, err := ParseNetworkAddress(JoinNetworkAddress(fdNetwork, strconv.FormatUint(uint64(file), 10), port)) + if err != nil { + return nil, err + } - return na.Listen(ctx, portOffset, config) + return na.Listen(ctx, portOffset, config) +} + +func getListenerFromNetwork(ctx context.Context, network, host, port string, portOffset uint, config net.ListenConfig) (any, error) { + if IsSdNetwork(network) { + return getListenerFromSd(ctx, network, host, port, portOffset, config) } return getListenerFromPlugin(ctx, network, host, port, portOffset, config) } From b596cdd60cdcf0708e91bf76aacd1c4156d36a8d Mon Sep 17 00:00:00 2001 From: Aaron Paterson Date: Tue, 4 Nov 2025 05:05:35 -0700 Subject: [PATCH 11/51] abandon for switch to placeholders --- listeners.go | 17 +++++++--- networks.go | 73 +++++++++++++++++++++++++++++++++++++++++++ networks_nosystemd.go | 15 +++++++++ networks_systemd.go | 16 ++++++++++ test.go | 22 +++++++++++++ 5 files changed, 138 insertions(+), 5 deletions(-) create mode 100644 test.go diff --git a/listeners.go b/listeners.go index 6623a57d1d5..1887ad15a27 100644 --- a/listeners.go +++ b/listeners.go @@ -203,21 +203,28 @@ func (na NetworkAddress) Listen(ctx context.Context, portOffset uint, config net } // IsUnixNetwork returns true if na.Network is -// unix, unixgram, or unixpacket. +// unix, unixgram, unixpacket, or unix+h2c. func (na NetworkAddress) IsUnixNetwork() bool { return IsUnixNetwork(na.Network) } + +// IsIpNetwork returns true if na.Network starts with +// ip: ip4: or ip6: +func (na NetworkAddress) IsIpNetwork() bool { + return IsIpNetwork(na.Network) +} + // IsFdNetwork returns true if na.Network is // fd or fdgram. func (na NetworkAddress) IsFdNetwork() bool { return IsFdNetwork(na.Network) } -// IsIpNetwork returns true if na.Network starts with -// ip: ip4: or ip6: -func (na NetworkAddress) IsIpNetwork() bool { - return IsIpNetwork(na.Network) +// IsIfaceNetwork returns true if na.Network is +// iface, iface4, iface6, ifacegram, ifacegram4, or ifacegram6. +func (na NetworkAddress) IsIfaceNetwork() bool { + return IsIfaceNetwork(na.Network) } // JoinHostPort is like net.JoinHostPort, but where the port diff --git a/networks.go b/networks.go index 52d5a4a38c4..6789e643ce4 100644 --- a/networks.go +++ b/networks.go @@ -18,6 +18,7 @@ import ( "context" "fmt" "net" + "net/netip" "strings" "sync" @@ -39,6 +40,11 @@ func IsFdNetwork(netw string) bool { return netw == "fd" || netw == "fdgram" } +// IsIfaceNetwork returns true if the netw is an iface network. +func IsIfaceNetwork(netw string) bool { + return netw == "iface" || netw == "iface4" || netw == "iface6" || netw == "ifacegram" || netw == "ifacegram4" || netw == "ifacegram6" +} + // ListenerFunc is a function that can return a listener given a network and address. // The listeners must be capable of overlapping: with Caddy, new configs are loaded // before old ones are unloaded, so listeners may overlap briefly if the configs @@ -71,6 +77,73 @@ func RegisterNetwork(network string, getListener ListenerFunc) { networkPlugins[network] = getListener } +func getListenerFromIface(ctx context.Context, network, host, port string, portOffset uint, config net.ListenConfig) (any, error) { + iface, err := net.InterfaceByName(host) + if err != nil { + return nil, err + } + + var ( + addrs []net.Addr + err error + ) + switch network { + case "iface": fallthrough + case "iface4": fallthrough + case "iface6": + unicast, err = iface.Addrs() + if err != nil { + //todo + } else { + addrs = append(addrs, unicast...) + } + case "ifacegram": fallthrough + case "ifacegram4": fallthrough + case "ifacegram6": + multicast, err = iface.MulticastAddrs() + if err != nil { + //todo + } else { + addrs = append(addrs, multicast...) + } + } + if err != nil { + return nil, err + } + + for _, addr := range addrs { + switch addrt := addr.(type) { + case *net.IPAddr: + + case *net.IPNet: + + } + prefix, err := netip.ParsePrefix(addr.String()) + preaddr := prefix.Addr() + if(preaddr.Is4()) { + switch network { + case "iface": fallthrough + case "iface4": fallthrough + case "ifacegram": fallthrough + case "ifacegram4": + //todo + } + } + if(preaddr.Is6()) { + switch network { + case "iface": fallthrough + case "iface6": fallthrough + case "ifacegram": fallthrough + case "ifacegram6": + //todo + } + } + if err != nil { + continue + } + } +} + // getListenerFromPlugin returns a listener on the given network and address // if a plugin has registered the network name. It may return (nil, nil) if // no plugin can provide a listener. diff --git a/networks_nosystemd.go b/networks_nosystemd.go index f56f79e0525..378c088f818 100644 --- a/networks_nosystemd.go +++ b/networks_nosystemd.go @@ -16,6 +16,9 @@ func IsReservedNetwork(network string) bool { } func getListenerFromNetwork(ctx context.Context, network, host, port string, portOffset uint, config net.ListenConfig) (any, error) { + if IsIfaceNetwork(network) { + return getListenerFromIface(ctx, network, host, port, portOffset, config) + } return getListenerFromPlugin(ctx, network, host, port, portOffset, config) } @@ -37,6 +40,18 @@ func GetHTTP3Network(originalNetwork string) (string, error) { return "udp6", nil case "fdgram": return "fdgram", nil + case "ifacegram": + return "ifacegram", nil + case "ifacegram4": + return "ifacegram4", nil + case "ifacegram6": + return "ifacegram6", nil + case "iface": + return "ifacegram", nil + case "iface4": + return "ifacegram4", nil + case "iface6": + return "ifacegram6", nil } return getHTTP3Plugin(originalNetwork) } diff --git a/networks_systemd.go b/networks_systemd.go index d99f46c87bc..801117777f0 100644 --- a/networks_systemd.go +++ b/networks_systemd.go @@ -13,6 +13,7 @@ import ( "sync" ) +// IsFdNetwork returns true if the netw is a sd network. func IsSdNetwork(network string) bool { return network == "sd" || network == "sdgram" } @@ -147,6 +148,9 @@ func getListenerFromSd(ctx context.Context, network, host, port string, portOffs } func getListenerFromNetwork(ctx context.Context, network, host, port string, portOffset uint, config net.ListenConfig) (any, error) { + if IsIfaceNetwork(network) { + return getListenerFromIface(ctx, network, host, port, portOffset, config) + } if IsSdNetwork(network) { return getListenerFromSd(ctx, network, host, port, portOffset, config) } @@ -173,6 +177,18 @@ func GetHTTP3Network(originalNetwork string) (string, error) { return "fdgram", nil case "sdgram": return "sdgram", nil + case "ifacegram": + return "ifacegram", nil + case "ifacegram4": + return "ifacegram4", nil + case "ifacegram6": + return "ifacegram6", nil + case "iface": + return "ifacegram", nil + case "iface4": + return "ifacegram4", nil + case "iface6": + return "ifacegram6", nil } return getHTTP3Plugin(originalNetwork) } diff --git a/test.go b/test.go new file mode 100644 index 00000000000..1b38e7e2b36 --- /dev/null +++ b/test.go @@ -0,0 +1,22 @@ +package main + +import ( + "fmt" + "net" +) + +func main() { + a, _ := net.Interfaces() + for _, ifc := range a { + fmt.Println(ifc) + addrs, err := ifc.Addrs() + fmt.Println(err) + for _, addr := range addrs { + fmt.Println(addr.String()) + // prefix, err := netip.ParsePrefix(addr.String()) + // fmt.Println(err) + // fmt.Println(prefix) + // fmt.Println(prefix.Addr()) + } + } +} From 72119bde4eb4e43f49638ce09df5a742c3152cc5 Mon Sep 17 00:00:00 2001 From: Aaron Paterson Date: Tue, 4 Nov 2025 05:05:53 -0700 Subject: [PATCH 12/51] rm --- test.go | 22 ---------------------- 1 file changed, 22 deletions(-) delete mode 100644 test.go diff --git a/test.go b/test.go deleted file mode 100644 index 1b38e7e2b36..00000000000 --- a/test.go +++ /dev/null @@ -1,22 +0,0 @@ -package main - -import ( - "fmt" - "net" -) - -func main() { - a, _ := net.Interfaces() - for _, ifc := range a { - fmt.Println(ifc) - addrs, err := ifc.Addrs() - fmt.Println(err) - for _, addr := range addrs { - fmt.Println(addr.String()) - // prefix, err := netip.ParsePrefix(addr.String()) - // fmt.Println(err) - // fmt.Println(prefix) - // fmt.Println(prefix.Addr()) - } - } -} From e755ff909ccba14632701aadfbfa8dc1ab872bb4 Mon Sep 17 00:00:00 2001 From: Aaron Paterson Date: Tue, 4 Nov 2025 08:20:03 -0700 Subject: [PATCH 13/51] systemd.listen placeholder --- listen.go | 4 +- listeners.go | 18 +- networks.go | 110 +++------- networks_nosystemd.go | 57 ----- networks_systemd.go | 194 ------------------ replacer.go | 17 +- replacer_nosystemd.go | 8 + replacer_systemd.go | 118 +++++++++++ replacer_test.go | 2 +- ...est_systemd.go => replacer_test_systemd.go | 132 ++++++------ 10 files changed, 231 insertions(+), 429 deletions(-) delete mode 100644 networks_nosystemd.go delete mode 100644 networks_systemd.go create mode 100644 replacer_nosystemd.go create mode 100644 replacer_systemd.go rename listeners_test_systemd.go => replacer_test_systemd.go (73%) diff --git a/listen.go b/listen.go index fba9c3a6ba6..197da156342 100644 --- a/listen.go +++ b/listen.go @@ -37,7 +37,7 @@ func reuseUnixSocket(_, _ string) (any, error) { func listenReusable(ctx context.Context, lnKey string, network, address string, config net.ListenConfig) (any, error) { var socketFile *os.File - fd := slices.Contains([]string{"fd", "fdgram"}, network) + fd := IsFdNetwork(network) if fd { socketFd, err := strconv.ParseUint(address, 0, strconv.IntSize) if err != nil { @@ -49,8 +49,8 @@ func listenReusable(ctx context.Context, lnKey string, network, address string, defer socketFilesMu.Unlock() socketFdWide := uintptr(socketFd) - var ok bool + var ok bool socketFile, ok = socketFiles[socketFdWide] if !ok { diff --git a/listeners.go b/listeners.go index 1887ad15a27..d8d567b5e5e 100644 --- a/listeners.go +++ b/listeners.go @@ -138,8 +138,8 @@ func (na NetworkAddress) Listen(ctx context.Context, portOffset uint, config net err error ) - // check to see if network provides a listener - if ln, err = getListenerFromNetwork(ctx, na.Network, na.Host, na.port(), portOffset, config); ln != nil || err != nil { + // check to see if plugin provides a listener + if ln, err = getListenerFromPlugin(ctx, na.Network, na.Host, na.port(), portOffset, config); ln != nil || err != nil { return ln, err } @@ -161,7 +161,12 @@ func (na NetworkAddress) Listen(ctx context.Context, portOffset uint, config net return nil, err } } else if na.IsFdNetwork() { - address = na.Host + socketFd, err := strconv.ParseUint(na.Host, 0, strconv.IntSize) + if err != nil { + return nil, fmt.Errorf("invalid file descriptor: %v", err) + } + + address = strconv.FormatUint(uint64(uint(socketFd)+portOffset), 10) } else { address = na.JoinHostPort(portOffset) } @@ -208,7 +213,6 @@ func (na NetworkAddress) IsUnixNetwork() bool { return IsUnixNetwork(na.Network) } - // IsIpNetwork returns true if na.Network starts with // ip: ip4: or ip6: func (na NetworkAddress) IsIpNetwork() bool { @@ -221,12 +225,6 @@ func (na NetworkAddress) IsFdNetwork() bool { return IsFdNetwork(na.Network) } -// IsIfaceNetwork returns true if na.Network is -// iface, iface4, iface6, ifacegram, ifacegram4, or ifacegram6. -func (na NetworkAddress) IsIfaceNetwork() bool { - return IsIfaceNetwork(na.Network) -} - // JoinHostPort is like net.JoinHostPort, but where the port // is StartPort + offset. func (na NetworkAddress) JoinHostPort(offset uint) string { diff --git a/networks.go b/networks.go index 6789e643ce4..f66cd6b528c 100644 --- a/networks.go +++ b/networks.go @@ -18,7 +18,6 @@ import ( "context" "fmt" "net" - "net/netip" "strings" "sync" @@ -40,9 +39,12 @@ func IsFdNetwork(netw string) bool { return netw == "fd" || netw == "fdgram" } -// IsIfaceNetwork returns true if the netw is an iface network. -func IsIfaceNetwork(netw string) bool { - return netw == "iface" || netw == "iface4" || netw == "iface6" || netw == "ifacegram" || netw == "ifacegram4" || netw == "ifacegram6" +func IsReservedNetwork(network string) bool { + return network == "tcp" || network == "tcp4" || network == "tcp6" || + network == "udp" || network == "udp4" || network == "udp6" || + IsUnixNetwork(network) || + IsIpNetwork(network) || + IsFdNetwork(network) } // ListenerFunc is a function that can return a listener given a network and address. @@ -77,73 +79,6 @@ func RegisterNetwork(network string, getListener ListenerFunc) { networkPlugins[network] = getListener } -func getListenerFromIface(ctx context.Context, network, host, port string, portOffset uint, config net.ListenConfig) (any, error) { - iface, err := net.InterfaceByName(host) - if err != nil { - return nil, err - } - - var ( - addrs []net.Addr - err error - ) - switch network { - case "iface": fallthrough - case "iface4": fallthrough - case "iface6": - unicast, err = iface.Addrs() - if err != nil { - //todo - } else { - addrs = append(addrs, unicast...) - } - case "ifacegram": fallthrough - case "ifacegram4": fallthrough - case "ifacegram6": - multicast, err = iface.MulticastAddrs() - if err != nil { - //todo - } else { - addrs = append(addrs, multicast...) - } - } - if err != nil { - return nil, err - } - - for _, addr := range addrs { - switch addrt := addr.(type) { - case *net.IPAddr: - - case *net.IPNet: - - } - prefix, err := netip.ParsePrefix(addr.String()) - preaddr := prefix.Addr() - if(preaddr.Is4()) { - switch network { - case "iface": fallthrough - case "iface4": fallthrough - case "ifacegram": fallthrough - case "ifacegram4": - //todo - } - } - if(preaddr.Is6()) { - switch network { - case "iface": fallthrough - case "iface6": fallthrough - case "ifacegram": fallthrough - case "ifacegram6": - //todo - } - } - if err != nil { - continue - } - } -} - // getListenerFromPlugin returns a listener on the given network and address // if a plugin has registered the network name. It may return (nil, nil) if // no plugin can provide a listener. @@ -160,10 +95,7 @@ func getListenerFromPlugin(ctx context.Context, network, host, port string, port return nil, nil } -var ( - networkHTTP3Plugins = map[string]string{} - networkHTTP3PluginsMu sync.RWMutex -) +var networkHTTP3Plugins = map[string]string{} // RegisterNetworkHTTP3 registers a mapping from non-HTTP/3 network to HTTP/3 // network. This should be called during init() and will panic if the network @@ -178,16 +110,10 @@ func RegisterNetworkHTTP3(originalNetwork, h3Network string) { panic("network type " + originalNetwork + " is already registered") } - networkHTTP3PluginsMu.Lock() - defer networkHTTP3PluginsMu.Unlock() - networkHTTP3Plugins[originalNetwork] = h3Network } func getHTTP3Plugin(originalNetwork string) (string, error) { - networkHTTP3PluginsMu.RLock() - defer networkHTTP3PluginsMu.RUnlock() - h3Network, ok := networkHTTP3Plugins[strings.ToLower(originalNetwork)] if !ok { return "", fmt.Errorf("network '%s' cannot handle HTTP/3 connections", originalNetwork) @@ -195,3 +121,25 @@ func getHTTP3Plugin(originalNetwork string) (string, error) { return h3Network, nil } + +func GetHTTP3Network(originalNetwork string) (string, error) { + switch originalNetwork { + case "unixgram": + return "unixgram", nil + case "udp": + return "udp", nil + case "udp4": + return "udp4", nil + case "udp6": + return "udp6", nil + case "tcp": + return "udp", nil + case "tcp4": + return "udp4", nil + case "tcp6": + return "udp6", nil + case "fdgram": + return "fdgram", nil + } + return getHTTP3Plugin(originalNetwork) +} diff --git a/networks_nosystemd.go b/networks_nosystemd.go deleted file mode 100644 index 378c088f818..00000000000 --- a/networks_nosystemd.go +++ /dev/null @@ -1,57 +0,0 @@ -//go:build !linux || nosystemd - -package caddy - -import ( - "context" - "net" -) - -func IsReservedNetwork(network string) bool { - return network == "tcp" || network == "tcp4" || network == "tcp6" || - network == "udp" || network == "udp4" || network == "udp6" || - IsUnixNetwork(network) || - IsIpNetwork(network) || - IsFdNetwork(network) -} - -func getListenerFromNetwork(ctx context.Context, network, host, port string, portOffset uint, config net.ListenConfig) (any, error) { - if IsIfaceNetwork(network) { - return getListenerFromIface(ctx, network, host, port, portOffset, config) - } - return getListenerFromPlugin(ctx, network, host, port, portOffset, config) -} - -func GetHTTP3Network(originalNetwork string) (string, error) { - switch originalNetwork { - case "unixgram": - return "unixgram", nil - case "udp": - return "udp", nil - case "udp4": - return "udp4", nil - case "udp6": - return "udp6", nil - case "tcp": - return "udp", nil - case "tcp4": - return "udp4", nil - case "tcp6": - return "udp6", nil - case "fdgram": - return "fdgram", nil - case "ifacegram": - return "ifacegram", nil - case "ifacegram4": - return "ifacegram4", nil - case "ifacegram6": - return "ifacegram6", nil - case "iface": - return "ifacegram", nil - case "iface4": - return "ifacegram4", nil - case "iface6": - return "ifacegram6", nil - } - return getHTTP3Plugin(originalNetwork) -} diff --git a/networks_systemd.go b/networks_systemd.go deleted file mode 100644 index 801117777f0..00000000000 --- a/networks_systemd.go +++ /dev/null @@ -1,194 +0,0 @@ -//go:build linux && !nosystemd - -package caddy - -import ( - "context" - "errors" - "fmt" - "net" - "os" - "strconv" - "strings" - "sync" -) - -// IsFdNetwork returns true if the netw is a sd network. -func IsSdNetwork(network string) bool { - return network == "sd" || network == "sdgram" -} - -func IsReservedNetwork(network string) bool { - return network == "tcp" || network == "tcp4" || network == "tcp6" || - network == "udp" || network == "udp4" || network == "udp6" || - IsUnixNetwork(network) || - IsIpNetwork(network) || - IsFdNetwork(network) || - IsSdNetwork(network) -} - -func sdListenFds() (int, error) { - lnPid, ok := os.LookupEnv("LISTEN_PID") - if !ok { - return 0, errors.New("LISTEN_PID is unset.") - } - - pid, err := strconv.Atoi(lnPid) - if err != nil { - return 0, err - } - - if pid != os.Getpid() { - return 0, fmt.Errorf("LISTEN_PID does not match pid: %d != %d", pid, os.Getpid()) - } - - lnFds, ok := os.LookupEnv("LISTEN_FDS") - if !ok { - return 0, errors.New("LISTEN_FDS is unset.") - } - - fds, err := strconv.Atoi(lnFds) - if err != nil { - return 0, err - } - - return fds, nil -} - -func sdListenFdsWithNames() (map[string][]uint, error) { - const lnFdsStart = 3 - - fds, err := sdListenFds() - if err != nil { - return nil, err - } - - lnFdnames, ok := os.LookupEnv("LISTEN_FDNAMES") - if !ok { - return nil, errors.New("LISTEN_FDNAMES is unset.") - } - - fdNames := strings.Split(lnFdnames, ":") - if fds != len(fdNames) { - return nil, fmt.Errorf("LISTEN_FDS does not match LISTEN_FDNAMES length: %d != %d", fds, len(fdNames)) - } - - nameToFiles := make(map[string][]uint, len(fdNames)) - for index, name := range fdNames { - nameToFiles[name] = append(nameToFiles[name], lnFdsStart+uint(index)) - } - - return nameToFiles, nil -} - -func getSdFd(nameToFiles map[string][]uint, host string, portOffset uint) (uint, error) { - name, index, li := host, portOffset, strings.LastIndex(host, "/") - if li >= 0 { - name = host[:li] - i, err := strconv.ParseUint(host[li+1:], 0, strconv.IntSize) - if err != nil { - return 0, err - } - index += uint(i) - } - - files, ok := nameToFiles[name] - if !ok { - return 0, fmt.Errorf("invalid listen fd name: %s", name) - } - - if uint(len(files)) <= index { - return 0, fmt.Errorf("invalid listen fd index: %d", index) - } - - return files[index], nil -} - -var ( - initNameToFiles map[string][]uint - initNameToFilesErr error - initNameToFilesMu sync.Mutex -) - -func getListenerFromSd(ctx context.Context, network, host, port string, portOffset uint, config net.ListenConfig) (any, error) { - func() { - initNameToFilesMu.Lock() - defer initNameToFilesMu.Unlock() - - if initNameToFiles == nil && initNameToFilesErr == nil { - initNameToFiles, initNameToFilesErr = sdListenFdsWithNames() - } - }() - - if initNameToFilesErr != nil { - return nil, initNameToFilesErr - } - - file, err := getSdFd(initNameToFiles, host, portOffset) - if err != nil { - return nil, err - } - - var fdNetwork string - switch network { - case "sd": - fdNetwork = "fd" - case "sdgram": - fdNetwork = "fdgram" - default: - return nil, fmt.Errorf("invalid network: %s", network) - } - - na, err := ParseNetworkAddress(JoinNetworkAddress(fdNetwork, strconv.FormatUint(uint64(file), 10), port)) - if err != nil { - return nil, err - } - - return na.Listen(ctx, portOffset, config) -} - -func getListenerFromNetwork(ctx context.Context, network, host, port string, portOffset uint, config net.ListenConfig) (any, error) { - if IsIfaceNetwork(network) { - return getListenerFromIface(ctx, network, host, port, portOffset, config) - } - if IsSdNetwork(network) { - return getListenerFromSd(ctx, network, host, port, portOffset, config) - } - return getListenerFromPlugin(ctx, network, host, port, portOffset, config) -} - -func GetHTTP3Network(originalNetwork string) (string, error) { - switch originalNetwork { - case "unixgram": - return "unixgram", nil - case "udp": - return "udp", nil - case "udp4": - return "udp4", nil - case "udp6": - return "udp6", nil - case "tcp": - return "udp", nil - case "tcp4": - return "udp4", nil - case "tcp6": - return "udp6", nil - case "fdgram": - return "fdgram", nil - case "sdgram": - return "sdgram", nil - case "ifacegram": - return "ifacegram", nil - case "ifacegram4": - return "ifacegram4", nil - case "ifacegram6": - return "ifacegram6", nil - case "iface": - return "ifacegram", nil - case "iface4": - return "ifacegram4", nil - case "iface6": - return "ifacegram6", nil - } - return getHTTP3Plugin(originalNetwork) -} diff --git a/replacer.go b/replacer.go index 1a2aa5771d1..7e5e62d51cf 100644 --- a/replacer.go +++ b/replacer.go @@ -36,16 +36,12 @@ func NewReplacer() *Replacer { static: make(map[string]any), mapMutex: &sync.RWMutex{}, } - rep.providers = []replacementProvider{ - globalDefaultReplacementProvider{}, - fileReplacementProvider{}, - ReplacerFunc(rep.fromStatic), - } + rep.providers = append(globalReplacementProviders, ReplacerFunc(rep.fromStatic)) return rep } // NewEmptyReplacer returns a new Replacer, -// without the global default replacements. +// without the global replacements. func NewEmptyReplacer() *Replacer { rep := &Replacer{ static: make(map[string]any), @@ -360,12 +356,11 @@ func (f fileReplacementProvider) replace(key string) (any, bool) { return string(body), true } -// globalDefaultReplacementProvider handles replacements -// that can be used in any context, such as system variables, -// time, or environment variables. -type globalDefaultReplacementProvider struct{} +// defaultReplacementProvider handles replacements +// such as system variables, time, or environment variables. +type defaultReplacementProvider struct{} -func (f globalDefaultReplacementProvider) replace(key string) (any, bool) { +func (f defaultReplacementProvider) replace(key string) (any, bool) { // check environment variable const envPrefix = "env." if strings.HasPrefix(key, envPrefix) { diff --git a/replacer_nosystemd.go b/replacer_nosystemd.go new file mode 100644 index 00000000000..682d7757bb3 --- /dev/null +++ b/replacer_nosystemd.go @@ -0,0 +1,8 @@ +//go:build !linux || nosystemd + +package caddy + +const globalReplacementProviders = []replacementProvider{ + defaultReplacementProvider{}, + fileReplacementProvider{}, +} diff --git a/replacer_systemd.go b/replacer_systemd.go new file mode 100644 index 00000000000..10971ad03f8 --- /dev/null +++ b/replacer_systemd.go @@ -0,0 +1,118 @@ +//go:build linux && !nosystemd + +package caddy + +import ( + "errors" + "fmt" + "os" + "strconv" + "strings" +) + +func sdListenFds() (int, error) { + lnPid, ok := os.LookupEnv("LISTEN_PID") + if !ok { + return 0, errors.New("LISTEN_PID is unset.") + } + + pid, err := strconv.Atoi(lnPid) + if err != nil { + return 0, err + } + + if pid != os.Getpid() { + return 0, fmt.Errorf("LISTEN_PID does not match pid: %d != %d", pid, os.Getpid()) + } + + lnFds, ok := os.LookupEnv("LISTEN_FDS") + if !ok { + return 0, errors.New("LISTEN_FDS is unset.") + } + + fds, err := strconv.Atoi(lnFds) + if err != nil { + return 0, err + } + + return fds, nil +} + +func sdListenFdsWithNames() (map[string][]uint, error) { + const lnFdsStart = 3 + + fds, err := sdListenFds() + if err != nil { + return nil, err + } + + lnFdnames, ok := os.LookupEnv("LISTEN_FDNAMES") + if !ok { + return nil, errors.New("LISTEN_FDNAMES is unset.") + } + + fdNames := strings.Split(lnFdnames, ":") + if fds != len(fdNames) { + return nil, fmt.Errorf("LISTEN_FDS does not match LISTEN_FDNAMES length: %d != %d", fds, len(fdNames)) + } + + nameToFiles := make(map[string][]uint, len(fdNames)) + for index, name := range fdNames { + nameToFiles[name] = append(nameToFiles[name], lnFdsStart+uint(index)) + } + + return nameToFiles, nil +} + +func getSdListenFd(nameToFiles map[string][]uint, host string) (uint, error) { + name, index, li := host, uint(0), strings.Index(host, ":") + if li >= 0 { + name = host[:li] + i, err := strconv.ParseUint(host[li+1:], 0, strconv.IntSize) + if err != nil { + return 0, err + } + index += uint(i) + } + + files, ok := nameToFiles[name] + if !ok { + return 0, fmt.Errorf("invalid listen fd name: %s", name) + } + + if uint(len(files)) <= index { + return 0, fmt.Errorf("invalid listen fd index: %d", index) + } + + return files[index], nil +} + +var initNameToFiles, initNameToFilesErr = sdListenFdsWithNames() + +// systemdReplacementProvider handles {systemd.*} replacements +type systemdReplacementProvider struct{} + +func (f systemdReplacementProvider) replace(key string) (any, bool) { + // check environment variable + const systemdListenPrefix = "systemd.listen." + if strings.HasPrefix(key, systemdListenPrefix) { + if initNameToFilesErr != nil { + return nil, false + } + fd, err := getSdListenFd(initNameToFiles, key[len(systemdListenPrefix):]) + if err != nil { + return nil, false + } + return fd, true + } + + // TODO const systemdCredsPrefix = "systemd.creds." + + return nil, false +} + +var globalReplacementProviders = []replacementProvider{ + defaultReplacementProvider{}, + fileReplacementProvider{}, + systemdReplacementProvider{}, +} diff --git a/replacer_test.go b/replacer_test.go index 4f20bede30f..a1c4256435f 100644 --- a/replacer_test.go +++ b/replacer_test.go @@ -374,7 +374,7 @@ func TestReplacerMap(t *testing.T) { func TestReplacerNew(t *testing.T) { repl := NewReplacer() - if len(repl.providers) != 3 { + if len(repl.providers) != 4 { t.Errorf("Expected providers length '%v' got length '%v'", 3, len(repl.providers)) } diff --git a/listeners_test_systemd.go b/replacer_test_systemd.go similarity index 73% rename from listeners_test_systemd.go rename to replacer_test_systemd.go index b393a653f73..1623497b769 100644 --- a/listeners_test_systemd.go +++ b/replacer_test_systemd.go @@ -9,8 +9,8 @@ import ( "testing" ) -// TestGetSdFd tests the getSdFd function for systemd socket activation. -func TestGetSdFd(t *testing.T) { +// TestGetSdListenFd tests the getSdListenFd function for systemd socket activation. +func TestGetSdListenFd(t *testing.T) { // Save original environment originalFdNames := os.Getenv("LISTEN_FDNAMES") originalFds := os.Getenv("LISTEN_FDS") @@ -82,42 +82,42 @@ func TestGetSdFd(t *testing.T) { name: "duplicate names - first occurrence (explicit index 0)", fdNames: "web:web:api", fds: "3", - socketName: "web/0", + socketName: "web:0", expectedFd: 3, }, { name: "duplicate names - second occurrence (index 1)", fdNames: "web:web:api", fds: "3", - socketName: "web/1", + socketName: "web:1", expectedFd: 4, }, { name: "complex duplicates - first api", fdNames: "web:api:web:api:dns", fds: "5", - socketName: "api/0", + socketName: "api:0", expectedFd: 4, }, { name: "complex duplicates - second api", fdNames: "web:api:web:api:dns", fds: "5", - socketName: "api/1", + socketName: "api:1", expectedFd: 6, }, { name: "complex duplicates - first web", fdNames: "web:api:web:api:dns", fds: "5", - socketName: "web/0", + socketName: "web:0", expectedFd: 3, }, { name: "complex duplicates - second web", fdNames: "web:api:web:api:dns", fds: "5", - socketName: "web/1", + socketName: "web:1", expectedFd: 5, }, { @@ -145,28 +145,28 @@ func TestGetSdFd(t *testing.T) { name: "index out of range", fdNames: "web:web", fds: "2", - socketName: "web/2", + socketName: "web:2", expectError: true, }, { name: "negative index", fdNames: "web", fds: "1", - socketName: "web/-1", + socketName: "web:-1", expectError: true, }, { name: "invalid index format", fdNames: "web", fds: "1", - socketName: "web/abc", + socketName: "web:abc", expectError: true, }, { name: "too many colons", fdNames: "web", fds: "1", - socketName: "web/0/extra", + socketName: "web:0:extra", expectError: true, }, } @@ -196,7 +196,7 @@ func TestGetSdFd(t *testing.T) { ) listenFdsWithNames, err = sdListenFdsWithNames() if err == nil { - fd, err = getSdFd(listenFdsWithNames, tc.socketName, 0) + fd, err = getSdListenFd(listenFdsWithNames, tc.socketName) } if tc.expectError { @@ -215,8 +215,8 @@ func TestGetSdFd(t *testing.T) { } } -// TestParseNetworkAddressSd tests parsing of sd and sdgram addresses. -func TestParseNetworkAddressSd(t *testing.T) { +// TestParseSystemdListenPlaceholder tests parsing of {systemd.listen.name} placeholders. +func TestParseSystemdListenPlaceholder(t *testing.T) { // Save and restore environment originalFdNames := os.Getenv("LISTEN_FDNAMES") originalFds := os.Getenv("LISTEN_FDS") @@ -252,83 +252,83 @@ func TestParseNetworkAddressSd(t *testing.T) { expectErr bool }{ { - input: "sd/http", + input: "fd/{systemd.listen.http}", expectedAddr: NetworkAddress{ - Network: "sd", - Host: "http", + Network: "fd", + Host: "{systemd.listen.http}", }, expectedFd: 3, }, { - input: "sd/https", + input: "fd/{systemd.listen.https}", expectedAddr: NetworkAddress{ - Network: "sd", - Host: "https", + Network: "fd", + Host: "{systemd.listen.https}", }, expectedFd: 4, }, { - input: "sd/dns", + input: "fd/{systemd.listen.dns}", expectedAddr: NetworkAddress{ - Network: "sd", - Host: "dns", + Network: "fd", + Host: "{systemd.listen.dns}", }, expectedFd: 5, }, { - input: "sd/http/0", + input: "fd/{systemd.listen.http:0}", expectedAddr: NetworkAddress{ - Network: "sd", - Host: "http/0", + Network: "fd", + Host: "{systemd.listen.http:0}", }, expectedFd: 3, }, { - input: "sd/https/0", + input: "fd/{systemd.listen.https:0}", expectedAddr: NetworkAddress{ - Network: "sd", - Host: "https/0", + Network: "fd", + Host: "{systemd.listen.https:0}", }, expectedFd: 4, }, { - input: "sdgram/http", + input: "fdgram/{systemd.listen.http}", expectedAddr: NetworkAddress{ - Network: "sdgram", - Host: "http", + Network: "fdgram", + Host: "{systemd.listen.http}", }, expectedFd: 3, }, { - input: "sdgram/https", + input: "fdgram/{systemd.listen.https}", expectedAddr: NetworkAddress{ - Network: "sdgram", - Host: "https", + Network: "fdgram", + Host: "{systemd.listen.https}", }, expectedFd: 4, }, { - input: "sdgram/http/0", + input: "fdgram/{systemd.listen.http:0}", expectedAddr: NetworkAddress{ - Network: "sdgram", - Host: "http/0", + Network: "fdgram", + Host: "http:0", }, expectedFd: 3, }, { - input: "sd/nonexistent", + input: "fd/{systemd.listen.nonexistent}", expectErr: true, }, { - input: "sd/nonexistent", + input: "fdgram/{systemd.listen.nonexistent}", expectErr: true, }, { - input: "sd/http/99", + input: "fd/{systemd.listen.http:99}", expectErr: true, }, { - input: "sd/invalid/abc", + input: "fd/{systemd.listen.invalid:abc}", expectErr: true, }, // Test that old fd/N syntax still works @@ -352,39 +352,25 @@ func TestParseNetworkAddressSd(t *testing.T) { for i, tc := range tests { actualAddr, err := ParseNetworkAddress(tc.input) - var ( - listenFdsWithNames map[string][]uint - fd uint - ) if err == nil { - switch actualAddr.Network { - case "fd": - fallthrough - case "fdgram": - var fd64 uint64 - fd64, err = strconv.ParseUint(actualAddr.Host, 0, strconv.IntSize) - if err == nil { - fd = uint(fd64) - } - case "sd": - fallthrough - case "sdgram": - listenFdsWithNames, err = sdListenFdsWithNames() - fd, err = getSdFd(listenFdsWithNames, actualAddr.Host, 0) + var fd uint + fdWide, err := strconv.ParseUint(actualAddr.Host, 0, strconv.IntSize) + if err == nil { + fd = uint(fdWide) } - } - if tc.expectErr && err == nil { - t.Errorf("Test %d (%s): Expected error but got none", i, tc.input) - } - if !tc.expectErr && err != nil { - t.Errorf("Test %d (%s): Expected no error but got: %v", i, tc.input, err) - } - if !tc.expectErr && !reflect.DeepEqual(tc.expectedAddr, actualAddr) { - t.Errorf("Test %d (%s): Expected %+v but got %+v", i, tc.input, tc.expectedAddr, actualAddr) - } - if !tc.expectErr && fd != tc.expectedFd { - t.Errorf("Expected FD %d but got %d", tc.expectedFd, fd) + if tc.expectErr && err == nil { + t.Errorf("Test %d (%s): Expected error but got none", i, tc.input) + } + if !tc.expectErr && err != nil { + t.Errorf("Test %d (%s): Expected no error but got: %v", i, tc.input, err) + } + if !tc.expectErr && !reflect.DeepEqual(tc.expectedAddr, actualAddr) { + t.Errorf("Test %d (%s): Expected %+v but got %+v", i, tc.input, tc.expectedAddr, actualAddr) + } + if !tc.expectErr && fd != tc.expectedFd { + t.Errorf("Expected FD %d but got %d", tc.expectedFd, fd) + } } } } From ea28788ac3f65c771f16d53e49bda06ab919ae2e Mon Sep 17 00:00:00 2001 From: Aaron Paterson Date: Tue, 4 Nov 2025 08:32:46 -0700 Subject: [PATCH 14/51] editor did not save --- listen.go | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/listen.go b/listen.go index 197da156342..fba9c3a6ba6 100644 --- a/listen.go +++ b/listen.go @@ -37,7 +37,7 @@ func reuseUnixSocket(_, _ string) (any, error) { func listenReusable(ctx context.Context, lnKey string, network, address string, config net.ListenConfig) (any, error) { var socketFile *os.File - fd := IsFdNetwork(network) + fd := slices.Contains([]string{"fd", "fdgram"}, network) if fd { socketFd, err := strconv.ParseUint(address, 0, strconv.IntSize) if err != nil { @@ -49,8 +49,8 @@ func listenReusable(ctx context.Context, lnKey string, network, address string, defer socketFilesMu.Unlock() socketFdWide := uintptr(socketFd) - var ok bool + socketFile, ok = socketFiles[socketFdWide] if !ok { From 3b5ca2dd083a680a0bb308f5c263a549f6ad0a15 Mon Sep 17 00:00:00 2001 From: Aaron Paterson Date: Tue, 4 Nov 2025 08:36:47 -0700 Subject: [PATCH 15/51] no const on array --- replacer_nosystemd.go | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/replacer_nosystemd.go b/replacer_nosystemd.go index 682d7757bb3..c885e4cb7a7 100644 --- a/replacer_nosystemd.go +++ b/replacer_nosystemd.go @@ -2,7 +2,7 @@ package caddy -const globalReplacementProviders = []replacementProvider{ +var globalReplacementProviders = []replacementProvider{ defaultReplacementProvider{}, fileReplacementProvider{}, } From 9524b388a6b777d7a4f96a3dd0b352d28dccf215 Mon Sep 17 00:00:00 2001 From: Aaron Paterson Date: Tue, 4 Nov 2025 08:47:06 -0700 Subject: [PATCH 16/51] remove provider len test --- replacer_test.go | 4 ---- 1 file changed, 4 deletions(-) diff --git a/replacer_test.go b/replacer_test.go index a1c4256435f..27774935a48 100644 --- a/replacer_test.go +++ b/replacer_test.go @@ -374,10 +374,6 @@ func TestReplacerMap(t *testing.T) { func TestReplacerNew(t *testing.T) { repl := NewReplacer() - if len(repl.providers) != 4 { - t.Errorf("Expected providers length '%v' got length '%v'", 3, len(repl.providers)) - } - // test if default global replacements are added as the first provider hostname, _ := os.Hostname() wd, _ := os.Getwd() From ee76e7a77fc65f62f4041b691ce22c057f4000db Mon Sep 17 00:00:00 2001 From: Aaron Paterson Date: Tue, 4 Nov 2025 08:54:13 -0700 Subject: [PATCH 17/51] lint --- replacer_systemd.go | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/replacer_systemd.go b/replacer_systemd.go index 10971ad03f8..d810861f9b0 100644 --- a/replacer_systemd.go +++ b/replacer_systemd.go @@ -13,7 +13,7 @@ import ( func sdListenFds() (int, error) { lnPid, ok := os.LookupEnv("LISTEN_PID") if !ok { - return 0, errors.New("LISTEN_PID is unset.") + return 0, errors.New("LISTEN_PID is unset") } pid, err := strconv.Atoi(lnPid) @@ -27,7 +27,7 @@ func sdListenFds() (int, error) { lnFds, ok := os.LookupEnv("LISTEN_FDS") if !ok { - return 0, errors.New("LISTEN_FDS is unset.") + return 0, errors.New("LISTEN_FDS is unset") } fds, err := strconv.Atoi(lnFds) @@ -48,7 +48,7 @@ func sdListenFdsWithNames() (map[string][]uint, error) { lnFdnames, ok := os.LookupEnv("LISTEN_FDNAMES") if !ok { - return nil, errors.New("LISTEN_FDNAMES is unset.") + return nil, errors.New("LISTEN_FDNAMES is unset") } fdNames := strings.Split(lnFdnames, ":") From 7c8c7659b31db0c38c95eaea5fc14b88c93ad642 Mon Sep 17 00:00:00 2001 From: Aaron Paterson Date: Tue, 4 Nov 2025 09:35:28 -0700 Subject: [PATCH 18/51] lock not needed in init --- networks.go | 12 +----------- 1 file changed, 1 insertion(+), 11 deletions(-) diff --git a/networks.go b/networks.go index f66cd6b528c..edcdfa48811 100644 --- a/networks.go +++ b/networks.go @@ -19,7 +19,6 @@ import ( "fmt" "net" "strings" - "sync" "go.uber.org/zap" ) @@ -53,10 +52,7 @@ func IsReservedNetwork(network string) bool { // both need the same listener. EXPERIMENTAL and subject to change. type ListenerFunc func(ctx context.Context, network, host, portRange string, portOffset uint, cfg net.ListenConfig) (any, error) -var ( - networkPlugins = map[string]ListenerFunc{} - networkPluginsMu sync.RWMutex -) +var networkPlugins = map[string]ListenerFunc{} // RegisterNetwork registers a network plugin with Caddy so that if a listener is // created for that network plugin, getListener will be invoked to get the listener. @@ -73,9 +69,6 @@ func RegisterNetwork(network string, getListener ListenerFunc) { panic("network type " + network + " is already registered") } - networkPluginsMu.Lock() - defer networkPluginsMu.Unlock() - networkPlugins[network] = getListener } @@ -83,9 +76,6 @@ func RegisterNetwork(network string, getListener ListenerFunc) { // if a plugin has registered the network name. It may return (nil, nil) if // no plugin can provide a listener. func getListenerFromPlugin(ctx context.Context, network, host, port string, portOffset uint, config net.ListenConfig) (any, error) { - networkPluginsMu.RLock() - defer networkPluginsMu.RUnlock() - // get listener from plugin if network is registered if getListener, ok := networkPlugins[network]; ok { Log().Debug("getting listener from plugin", zap.String("network", network)) From 4645077dea4c0173042e4c21324945fffef73071 Mon Sep 17 00:00:00 2001 From: Aaron Paterson Date: Wed, 5 Nov 2025 12:03:47 -0700 Subject: [PATCH 19/51] read addresses from network interfaces --- caddyconfig/httpcaddyfile/addresses.go | 45 ++++++++++++++++++++++---- caddyconfig/httpcaddyfile/builtins.go | 21 ++++++++---- replacer_systemd.go | 11 ++++--- 3 files changed, 59 insertions(+), 18 deletions(-) diff --git a/caddyconfig/httpcaddyfile/addresses.go b/caddyconfig/httpcaddyfile/addresses.go index 1121776d98f..7b661806fc5 100644 --- a/caddyconfig/httpcaddyfile/addresses.go +++ b/caddyconfig/httpcaddyfile/addresses.go @@ -307,21 +307,22 @@ func (st *ServerType) listenersForServerBlockAddress(sblock serverBlock, addr Ad } // the bind directive specifies hosts (and potentially network), and the protocols to serve them with, but is optional - lnCfgVals := make([]addressesWithProtocols, 0, len(sblock.pile["bind"])) + lnCfgVals := make([]bindOptions, 0, len(sblock.pile["bind"])) for _, cfgVal := range sblock.pile["bind"] { - if val, ok := cfgVal.Value.(addressesWithProtocols); ok { + if val, ok := cfgVal.Value.(bindOptions); ok { lnCfgVals = append(lnCfgVals, val) } } if len(lnCfgVals) == 0 { if defaultBindValues, ok := options["default_bind"].([]ConfigValue); ok { for _, defaultBindValue := range defaultBindValues { - lnCfgVals = append(lnCfgVals, defaultBindValue.Value.(addressesWithProtocols)) + lnCfgVals = append(lnCfgVals, defaultBindValue.Value.(bindOptions)) } } else { - lnCfgVals = []addressesWithProtocols{{ - addresses: []string{""}, - protocols: nil, + lnCfgVals = []bindOptions{{ + addresses: []string{""}, + interfaces: nil, + protocols: nil, }} } } @@ -329,6 +330,32 @@ func (st *ServerType) listenersForServerBlockAddress(sblock serverBlock, addr Ad // use a map to prevent duplication listeners := map[string]map[string]struct{}{} for _, lnCfgVal := range lnCfgVals { + addresses := []string{} + addresses = append(addresses, lnCfgVal.addresses...) + for _, lnIface := range lnCfgVal.interfaces { + lnNetw, lnDevice, _, err := caddy.SplitNetworkAddress(lnIface) + if err != nil { + return nil, fmt.Errorf("splitting listener interface: %v", err) + } + iface, err := net.InterfaceByName(lnDevice) + if err != nil || iface == nil { + return nil, fmt.Errorf("querying listener interface: %v", err) + } + ifaceAddrs, err := iface.Addrs() + if err != nil { + return nil, fmt.Errorf("querying listener interface addresses: %v", err) + } + for _, ifaceAddr := range ifaceAddrs { + switch ifaceAddrValue := ifaceAddr.(type) { + case *net.IPAddr: + addresses = append(addresses, caddy.JoinNetworkAddress(lnNetw, ifaceAddrValue.IP.String(), "")) + case *net.IPNet: + addresses = append(addresses, caddy.JoinNetworkAddress(lnNetw, ifaceAddrValue.IP.String(), "")) + default: + return nil, fmt.Errorf("reading listener interface address: %v", err) + } + } + } for _, lnAddr := range lnCfgVal.addresses { lnNetw, lnHost, _, err := caddy.SplitNetworkAddress(lnAddr) if err != nil { @@ -350,6 +377,12 @@ func (st *ServerType) listenersForServerBlockAddress(sblock serverBlock, addr Ad return listeners, nil } +type bindOptions struct { + addresses []string + interfaces []string + protocols []string +} + // addressesWithProtocols associates a list of listen addresses // with a list of protocols to serve them with type addressesWithProtocols struct { diff --git a/caddyconfig/httpcaddyfile/builtins.go b/caddyconfig/httpcaddyfile/builtins.go index 061aaa48b8d..717a51b1514 100644 --- a/caddyconfig/httpcaddyfile/builtins.go +++ b/caddyconfig/httpcaddyfile/builtins.go @@ -57,16 +57,22 @@ func init() { // parseBind parses the bind directive. Syntax: // -// bind [{ -// protocols [h1|h2|h2c|h3] [...] -// }] +// bind [{ +// interfaces +// protocols [h1|h2|h2c|h3] [...] +// }] func parseBind(h Helper) ([]ConfigValue, error) { h.Next() // consume directive name - var addresses, protocols []string + var addresses, interfaces, protocols []string addresses = h.RemainingArgs() for h.NextBlock(0) { switch h.Val() { + case "interfaces": + interfaces = h.RemainingArgs() + if len(interfaces) == 0 { + return nil, h.Errf("interfaces requires one or more arguments") + } case "protocols": protocols = h.RemainingArgs() if len(protocols) == 0 { @@ -77,9 +83,10 @@ func parseBind(h Helper) ([]ConfigValue, error) { } } - return []ConfigValue{{Class: "bind", Value: addressesWithProtocols{ - addresses: addresses, - protocols: protocols, + return []ConfigValue{{Class: "bind", Value: bindOptions{ + addresses: addresses, + interfaces: interfaces, + protocols: protocols, }}}, nil } diff --git a/replacer_systemd.go b/replacer_systemd.go index d810861f9b0..8ac2809e891 100644 --- a/replacer_systemd.go +++ b/replacer_systemd.go @@ -65,14 +65,15 @@ func sdListenFdsWithNames() (map[string][]uint, error) { } func getSdListenFd(nameToFiles map[string][]uint, host string) (uint, error) { - name, index, li := host, uint(0), strings.Index(host, ":") - if li >= 0 { - name = host[:li] - i, err := strconv.ParseUint(host[li+1:], 0, strconv.IntSize) + index := uint(0) + + name, offset, found := strings.Cut(host, ":") + if found { + off, err := strconv.ParseUint(offset, 0, strconv.IntSize) if err != nil { return 0, err } - index += uint(i) + index += uint(off) } files, ok := nameToFiles[name] From b091080ebe5b7f331dbf473bf8d2fa8093744a44 Mon Sep 17 00:00:00 2001 From: Aaron Paterson Date: Wed, 5 Nov 2025 12:09:33 -0700 Subject: [PATCH 20/51] addresses from copy --- caddyconfig/httpcaddyfile/addresses.go | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/caddyconfig/httpcaddyfile/addresses.go b/caddyconfig/httpcaddyfile/addresses.go index 7b661806fc5..c81f44ec46a 100644 --- a/caddyconfig/httpcaddyfile/addresses.go +++ b/caddyconfig/httpcaddyfile/addresses.go @@ -356,7 +356,7 @@ func (st *ServerType) listenersForServerBlockAddress(sblock serverBlock, addr Ad } } } - for _, lnAddr := range lnCfgVal.addresses { + for _, lnAddr := range addresses { lnNetw, lnHost, _, err := caddy.SplitNetworkAddress(lnAddr) if err != nil { return nil, fmt.Errorf("splitting listener address: %v", err) From 9eb54beaeb5d3eb5717396b7630a4beb89ff489b Mon Sep 17 00:00:00 2001 From: Aaron Paterson Date: Wed, 5 Nov 2025 12:10:53 -0700 Subject: [PATCH 21/51] string in err --- caddyconfig/httpcaddyfile/addresses.go | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/caddyconfig/httpcaddyfile/addresses.go b/caddyconfig/httpcaddyfile/addresses.go index c81f44ec46a..dc547b5c118 100644 --- a/caddyconfig/httpcaddyfile/addresses.go +++ b/caddyconfig/httpcaddyfile/addresses.go @@ -352,7 +352,7 @@ func (st *ServerType) listenersForServerBlockAddress(sblock serverBlock, addr Ad case *net.IPNet: addresses = append(addresses, caddy.JoinNetworkAddress(lnNetw, ifaceAddrValue.IP.String(), "")) default: - return nil, fmt.Errorf("reading listener interface address: %v", err) + return nil, fmt.Errorf("reading listener interface address: %v", ifaceAddr.String()) } } } From a6dbe6b54329e561822f1df03ac2721c8828ab98 Mon Sep 17 00:00:00 2001 From: Aaron Paterson Date: Wed, 5 Nov 2025 12:22:19 -0700 Subject: [PATCH 22/51] interface address memo --- caddyconfig/httpcaddyfile/addresses.go | 38 +++++++++++++++----------- 1 file changed, 22 insertions(+), 16 deletions(-) diff --git a/caddyconfig/httpcaddyfile/addresses.go b/caddyconfig/httpcaddyfile/addresses.go index dc547b5c118..067ee6716cb 100644 --- a/caddyconfig/httpcaddyfile/addresses.go +++ b/caddyconfig/httpcaddyfile/addresses.go @@ -328,6 +328,7 @@ func (st *ServerType) listenersForServerBlockAddress(sblock serverBlock, addr Ad } // use a map to prevent duplication + interfaceAddress := map[string]string{} listeners := map[string]map[string]struct{}{} for _, lnCfgVal := range lnCfgVals { addresses := []string{} @@ -337,24 +338,29 @@ func (st *ServerType) listenersForServerBlockAddress(sblock serverBlock, addr Ad if err != nil { return nil, fmt.Errorf("splitting listener interface: %v", err) } - iface, err := net.InterfaceByName(lnDevice) - if err != nil || iface == nil { - return nil, fmt.Errorf("querying listener interface: %v", err) - } - ifaceAddrs, err := iface.Addrs() - if err != nil { - return nil, fmt.Errorf("querying listener interface addresses: %v", err) - } - for _, ifaceAddr := range ifaceAddrs { - switch ifaceAddrValue := ifaceAddr.(type) { - case *net.IPAddr: - addresses = append(addresses, caddy.JoinNetworkAddress(lnNetw, ifaceAddrValue.IP.String(), "")) - case *net.IPNet: - addresses = append(addresses, caddy.JoinNetworkAddress(lnNetw, ifaceAddrValue.IP.String(), "")) - default: - return nil, fmt.Errorf("reading listener interface address: %v", ifaceAddr.String()) + + address, ok := interfaceAddress[lnDevice] + if !ok { + iface, err := net.InterfaceByName(lnDevice) + if err != nil || iface == nil { + return nil, fmt.Errorf("querying listener interface: %v", err) + } + ifaceAddrs, err := iface.Addrs() + if err != nil { + return nil, fmt.Errorf("querying listener interface addresses: %v", err) + } + for _, ifaceAddr := range ifaceAddrs { + switch ifaceAddrValue := ifaceAddr.(type) { + case *net.IPAddr: + address = caddy.JoinNetworkAddress(lnNetw, ifaceAddrValue.IP.String(), "") + case *net.IPNet: + address = caddy.JoinNetworkAddress(lnNetw, ifaceAddrValue.IP.String(), "") + default: + return nil, fmt.Errorf("reading listener interface address: %v", ifaceAddr.String()) + } } } + addresses = append(addresses, address) } for _, lnAddr := range addresses { lnNetw, lnHost, _, err := caddy.SplitNetworkAddress(lnAddr) From 5710bb6d11dec8ef921d5d9d0111ee23a57575f3 Mon Sep 17 00:00:00 2001 From: Aaron Paterson Date: Wed, 5 Nov 2025 16:34:14 -0700 Subject: [PATCH 23/51] check iface network --- caddyconfig/httpcaddyfile/addresses.go | 19 ++++++++++++++----- networks.go | 20 ++++++++++++++++++-- 2 files changed, 32 insertions(+), 7 deletions(-) diff --git a/caddyconfig/httpcaddyfile/addresses.go b/caddyconfig/httpcaddyfile/addresses.go index 067ee6716cb..f6c80946e5e 100644 --- a/caddyconfig/httpcaddyfile/addresses.go +++ b/caddyconfig/httpcaddyfile/addresses.go @@ -328,7 +328,7 @@ func (st *ServerType) listenersForServerBlockAddress(sblock serverBlock, addr Ad } // use a map to prevent duplication - interfaceAddress := map[string]string{} + interfaceAddresses := map[string][]string{} listeners := map[string]map[string]struct{}{} for _, lnCfgVal := range lnCfgVals { addresses := []string{} @@ -339,7 +339,7 @@ func (st *ServerType) listenersForServerBlockAddress(sblock serverBlock, addr Ad return nil, fmt.Errorf("splitting listener interface: %v", err) } - address, ok := interfaceAddress[lnDevice] + ifaceAddresses, ok := interfaceAddresses[lnDevice] if !ok { iface, err := net.InterfaceByName(lnDevice) if err != nil || iface == nil { @@ -350,17 +350,26 @@ func (st *ServerType) listenersForServerBlockAddress(sblock serverBlock, addr Ad return nil, fmt.Errorf("querying listener interface addresses: %v", err) } for _, ifaceAddr := range ifaceAddrs { + var ip net.IP switch ifaceAddrValue := ifaceAddr.(type) { case *net.IPAddr: - address = caddy.JoinNetworkAddress(lnNetw, ifaceAddrValue.IP.String(), "") + ip = ifaceAddrValue.IP case *net.IPNet: - address = caddy.JoinNetworkAddress(lnNetw, ifaceAddrValue.IP.String(), "") + ip = ifaceAddrValue.IP default: return nil, fmt.Errorf("reading listener interface address: %v", ifaceAddr.String()) } + + if len(ip) == 4 && caddy.IsIPv4Network(lnNetw) || len(ip) == 16 && caddy.IsIPv6Network(lnNetw) { + ifaceAddresses = append(ifaceAddresses,caddy.JoinNetworkAddress(lnNetw, ip.String(), "")) + } + } + if len(ifaceAddresses) == 0 { + return nil, fmt.Errorf("querying listener interface addresses for network: %v for %v", lnDevice, lnNetw) } + interfaceAddresses[lnDevice] = ifaceAddresses } - addresses = append(addresses, address) + addresses = append(addresses, ifaceAddresses...) } for _, lnAddr := range addresses { lnNetw, lnHost, _, err := caddy.SplitNetworkAddress(lnAddr) diff --git a/networks.go b/networks.go index edcdfa48811..e8a7111f2a8 100644 --- a/networks.go +++ b/networks.go @@ -28,6 +28,14 @@ func IsUnixNetwork(netw string) bool { return netw == "unix" || netw == "unixgram" || netw == "unixpacket" || netw == "unix+h2c" } +func IsTCPNetwork(netw string) bool { + return netw == "tcp" || netw == "tcp4" || netw == "tcp6" +} + +func IsUDPNetwork(netw string) bool { + return netw == "udp" || netw == "udp4" || netw == "udp6" +} + // IsIpNetwork returns true if the netw is an ip network. func IsIpNetwork(netw string) bool { return strings.HasPrefix(netw, "ip:") || strings.HasPrefix(netw, "ip4:") || strings.HasPrefix(netw, "ip6:") @@ -39,13 +47,21 @@ func IsFdNetwork(netw string) bool { } func IsReservedNetwork(network string) bool { - return network == "tcp" || network == "tcp4" || network == "tcp6" || - network == "udp" || network == "udp4" || network == "udp6" || + return IsTCPNetwork(network) || + IsUDPNetwork(network) || IsUnixNetwork(network) || IsIpNetwork(network) || IsFdNetwork(network) } +func IsIPv4Network(netw string) bool { + return netw == "tcp" || netw == "udp" || netw == "tcp4" || netw == "udp4" || strings.HasPrefix(netw, "ip:") || strings.HasPrefix(netw, "ip4:") +} + +func IsIPv6Network(netw string) bool { + return netw == "tcp" || netw == "udp" || netw == "tcp6" || netw == "udp6" || strings.HasPrefix(netw, "ip:") || strings.HasPrefix(netw, "ip6:") +} + // ListenerFunc is a function that can return a listener given a network and address. // The listeners must be capable of overlapping: with Caddy, new configs are loaded // before old ones are unloaded, so listeners may overlap briefly if the configs From 7500d162bf0af74c685e2b03235b657200aa6a27 Mon Sep 17 00:00:00 2001 From: Aaron Paterson Date: Wed, 5 Nov 2025 16:40:23 -0700 Subject: [PATCH 24/51] more errs --- caddyconfig/httpcaddyfile/addresses.go | 13 ++++++++----- 1 file changed, 8 insertions(+), 5 deletions(-) diff --git a/caddyconfig/httpcaddyfile/addresses.go b/caddyconfig/httpcaddyfile/addresses.go index f6c80946e5e..3cfc9bacae2 100644 --- a/caddyconfig/httpcaddyfile/addresses.go +++ b/caddyconfig/httpcaddyfile/addresses.go @@ -342,12 +342,15 @@ func (st *ServerType) listenersForServerBlockAddress(sblock serverBlock, addr Ad ifaceAddresses, ok := interfaceAddresses[lnDevice] if !ok { iface, err := net.InterfaceByName(lnDevice) - if err != nil || iface == nil { - return nil, fmt.Errorf("querying listener interface: %v", err) + if err != nil { + return nil, fmt.Errorf("querying listener interface: %v: %v", lnDevice, err) + } + if iface == nil { + return nil, fmt.Errorf("querying listener interface: %v", lnDevice) } ifaceAddrs, err := iface.Addrs() if err != nil { - return nil, fmt.Errorf("querying listener interface addresses: %v", err) + return nil, fmt.Errorf("querying listener interface addresses: %v: %v", lnDevice, err) } for _, ifaceAddr := range ifaceAddrs { var ip net.IP @@ -357,7 +360,7 @@ func (st *ServerType) listenersForServerBlockAddress(sblock serverBlock, addr Ad case *net.IPNet: ip = ifaceAddrValue.IP default: - return nil, fmt.Errorf("reading listener interface address: %v", ifaceAddr.String()) + return nil, fmt.Errorf("reading listener interface address: %v: %v", lnDevice, ifaceAddr.String()) } if len(ip) == 4 && caddy.IsIPv4Network(lnNetw) || len(ip) == 16 && caddy.IsIPv6Network(lnNetw) { @@ -365,7 +368,7 @@ func (st *ServerType) listenersForServerBlockAddress(sblock serverBlock, addr Ad } } if len(ifaceAddresses) == 0 { - return nil, fmt.Errorf("querying listener interface addresses for network: %v for %v", lnDevice, lnNetw) + return nil, fmt.Errorf("querying listener interface addresses for network: %v: %v", lnDevice, lnNetw) } interfaceAddresses[lnDevice] = ifaceAddresses } From a8b2bb6f542aee32623e61297dafdef7483d379e Mon Sep 17 00:00:00 2001 From: Aaron Paterson Date: Wed, 5 Nov 2025 16:42:48 -0700 Subject: [PATCH 25/51] gofumpt --- caddyconfig/httpcaddyfile/addresses.go | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/caddyconfig/httpcaddyfile/addresses.go b/caddyconfig/httpcaddyfile/addresses.go index 3cfc9bacae2..24c54c6381d 100644 --- a/caddyconfig/httpcaddyfile/addresses.go +++ b/caddyconfig/httpcaddyfile/addresses.go @@ -364,10 +364,10 @@ func (st *ServerType) listenersForServerBlockAddress(sblock serverBlock, addr Ad } if len(ip) == 4 && caddy.IsIPv4Network(lnNetw) || len(ip) == 16 && caddy.IsIPv6Network(lnNetw) { - ifaceAddresses = append(ifaceAddresses,caddy.JoinNetworkAddress(lnNetw, ip.String(), "")) + ifaceAddresses = append(ifaceAddresses, caddy.JoinNetworkAddress(lnNetw, ip.String(), "")) } } - if len(ifaceAddresses) == 0 { + if len(ifaceAddresses) == 0 { return nil, fmt.Errorf("querying listener interface addresses for network: %v: %v", lnDevice, lnNetw) } interfaceAddresses[lnDevice] = ifaceAddresses From 319a7a0e75540af70f36f0a993163af0a9e2622a Mon Sep 17 00:00:00 2001 From: Aaron Paterson Date: Wed, 5 Nov 2025 17:19:14 -0700 Subject: [PATCH 26/51] ungofumpt --- caddyconfig/httpcaddyfile/builtins.go | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/caddyconfig/httpcaddyfile/builtins.go b/caddyconfig/httpcaddyfile/builtins.go index 717a51b1514..544943b0fad 100644 --- a/caddyconfig/httpcaddyfile/builtins.go +++ b/caddyconfig/httpcaddyfile/builtins.go @@ -57,10 +57,10 @@ func init() { // parseBind parses the bind directive. Syntax: // -// bind [{ -// interfaces -// protocols [h1|h2|h2c|h3] [...] -// }] +// bind [{ +// interfaces +// protocols [h1|h2|h2c|h3] [...] +// }] func parseBind(h Helper) ([]ConfigValue, error) { h.Next() // consume directive name var addresses, interfaces, protocols []string From 7da87c27811b36cce2d235580999957e292fc1e5 Mon Sep 17 00:00:00 2001 From: Aaron Paterson Date: Wed, 5 Nov 2025 17:19:31 -0700 Subject: [PATCH 27/51] ungofumpt --- caddyconfig/httpcaddyfile/builtins.go | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/caddyconfig/httpcaddyfile/builtins.go b/caddyconfig/httpcaddyfile/builtins.go index 544943b0fad..a0eb770470b 100644 --- a/caddyconfig/httpcaddyfile/builtins.go +++ b/caddyconfig/httpcaddyfile/builtins.go @@ -57,10 +57,10 @@ func init() { // parseBind parses the bind directive. Syntax: // -// bind [{ -// interfaces -// protocols [h1|h2|h2c|h3] [...] -// }] +// bind [{ +// interfaces +// protocols [h1|h2|h2c|h3] [...] +// }] func parseBind(h Helper) ([]ConfigValue, error) { h.Next() // consume directive name var addresses, interfaces, protocols []string From 2ce548d58a32338085c032ba6baa57e914090bb6 Mon Sep 17 00:00:00 2001 From: Aaron Paterson Date: Wed, 5 Nov 2025 17:55:05 -0700 Subject: [PATCH 28/51] tcp and udp na funcs --- listeners.go | 12 ++++++++++++ networks.go | 4 ++-- 2 files changed, 14 insertions(+), 2 deletions(-) diff --git a/listeners.go b/listeners.go index d8d567b5e5e..16e56b4e0f0 100644 --- a/listeners.go +++ b/listeners.go @@ -213,6 +213,18 @@ func (na NetworkAddress) IsUnixNetwork() bool { return IsUnixNetwork(na.Network) } +// IsTCPNetwork returns true if na.Network is +// tcp, tcp4, or tcp6. +func (na NetworkAddress) IsTCPNetwork() bool { + return IsTCPNetwork(na.Network) +} + +// IsUDPNetwork returns true if na.Network is +// udp, udp4, or udp6. +func (na NetworkAddress) IsUDPNetwork() bool { + return IsUDPNetwork(na.Network) +} + // IsIpNetwork returns true if na.Network starts with // ip: ip4: or ip6: func (na NetworkAddress) IsIpNetwork() bool { diff --git a/networks.go b/networks.go index e8a7111f2a8..b6222b75dc1 100644 --- a/networks.go +++ b/networks.go @@ -55,11 +55,11 @@ func IsReservedNetwork(network string) bool { } func IsIPv4Network(netw string) bool { - return netw == "tcp" || netw == "udp" || netw == "tcp4" || netw == "udp4" || strings.HasPrefix(netw, "ip:") || strings.HasPrefix(netw, "ip4:") + return netw == "tcp" || netw == "tcp4" || netw == "udp" || netw == "udp4" || strings.HasPrefix(netw, "ip:") || strings.HasPrefix(netw, "ip4:") } func IsIPv6Network(netw string) bool { - return netw == "tcp" || netw == "udp" || netw == "tcp6" || netw == "udp6" || strings.HasPrefix(netw, "ip:") || strings.HasPrefix(netw, "ip6:") + return netw == "tcp" || netw == "tcp6" || netw == "udp" || netw == "udp6" || strings.HasPrefix(netw, "ip:") || strings.HasPrefix(netw, "ip6:") } // ListenerFunc is a function that can return a listener given a network and address. From c11c2809a5c988d0d5b1bda682dce05a9fd5c8af Mon Sep 17 00:00:00 2001 From: Aaron Paterson Date: Wed, 5 Nov 2025 17:56:04 -0700 Subject: [PATCH 29/51] comments --- networks.go | 2 ++ 1 file changed, 2 insertions(+) diff --git a/networks.go b/networks.go index b6222b75dc1..642dfaf0f89 100644 --- a/networks.go +++ b/networks.go @@ -28,10 +28,12 @@ func IsUnixNetwork(netw string) bool { return netw == "unix" || netw == "unixgram" || netw == "unixpacket" || netw == "unix+h2c" } +// IsUnixNetwork returns true if the netw is a TCP network. func IsTCPNetwork(netw string) bool { return netw == "tcp" || netw == "tcp4" || netw == "tcp6" } +// IsUnixNetwork returns true if the netw is a UDP network. func IsUDPNetwork(netw string) bool { return netw == "udp" || netw == "udp4" || netw == "udp6" } From c72a6d3ae92ebfaf22bd38f6c9be99b0df46ef6f Mon Sep 17 00:00:00 2001 From: Aaron Paterson Date: Wed, 5 Nov 2025 17:57:15 -0700 Subject: [PATCH 30/51] order --- networks.go | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/networks.go b/networks.go index 642dfaf0f89..8580931ccc5 100644 --- a/networks.go +++ b/networks.go @@ -49,9 +49,9 @@ func IsFdNetwork(netw string) bool { } func IsReservedNetwork(network string) bool { - return IsTCPNetwork(network) || + return IsUnixNetwork(network) || + IsTCPNetwork(network) || IsUDPNetwork(network) || - IsUnixNetwork(network) || IsIpNetwork(network) || IsFdNetwork(network) } From c4ed4ba40d21cad9bd1412feb88df80990ca0cc1 Mon Sep 17 00:00:00 2001 From: Aaron Paterson Date: Wed, 5 Nov 2025 19:22:35 -0700 Subject: [PATCH 31/51] constants --- caddyconfig/httpcaddyfile/addresses.go | 2 +- listen.go | 6 +-- listen_unix.go | 9 ++-- listeners.go | 2 +- networks.go | 72 ++++++++++++++++++-------- 5 files changed, 58 insertions(+), 33 deletions(-) diff --git a/caddyconfig/httpcaddyfile/addresses.go b/caddyconfig/httpcaddyfile/addresses.go index 24c54c6381d..d70efbea82d 100644 --- a/caddyconfig/httpcaddyfile/addresses.go +++ b/caddyconfig/httpcaddyfile/addresses.go @@ -363,7 +363,7 @@ func (st *ServerType) listenersForServerBlockAddress(sblock serverBlock, addr Ad return nil, fmt.Errorf("reading listener interface address: %v: %v", lnDevice, ifaceAddr.String()) } - if len(ip) == 4 && caddy.IsIPv4Network(lnNetw) || len(ip) == 16 && caddy.IsIPv6Network(lnNetw) { + if len(ip) == net.IPv4len && caddy.IsIPv4Network(lnNetw) || len(ip) == net.IPv6len && caddy.IsIPv6Network(lnNetw) { ifaceAddresses = append(ifaceAddresses, caddy.JoinNetworkAddress(lnNetw, ip.String(), "")) } } diff --git a/listen.go b/listen.go index fba9c3a6ba6..c4600aa12b9 100644 --- a/listen.go +++ b/listen.go @@ -37,7 +37,7 @@ func reuseUnixSocket(_, _ string) (any, error) { func listenReusable(ctx context.Context, lnKey string, network, address string, config net.ListenConfig) (any, error) { var socketFile *os.File - fd := slices.Contains([]string{"fd", "fdgram"}, network) + fd := IsFdNetwork(network) if fd { socketFd, err := strconv.ParseUint(address, 0, strconv.IntSize) if err != nil { @@ -66,8 +66,8 @@ func listenReusable(ctx context.Context, lnKey string, network, address string, } } - datagram := slices.Contains([]string{"udp", "udp4", "udp6", "unixgram", "fdgram"}, network) - if datagram { + packet := IsPacketNetwork(network) + if packet { sharedPc, _, err := listenerPool.LoadOrNew(lnKey, func() (Destructor, error) { var ( pc net.PacketConn diff --git a/listen_unix.go b/listen_unix.go index d6ae0cb8ebb..856d0980ecf 100644 --- a/listen_unix.go +++ b/listen_unix.go @@ -27,7 +27,6 @@ import ( "io/fs" "net" "os" - "slices" "strconv" "sync" "sync/atomic" @@ -102,7 +101,7 @@ func listenReusable(ctx context.Context, lnKey string, network, address string, socketFile *os.File ) - fd := slices.Contains([]string{"fd", "fdgram"}, network) + fd := IsFdNetwork(network) if fd { socketFd, err := strconv.ParseUint(address, 0, strconv.IntSize) if err != nil { @@ -142,8 +141,8 @@ func listenReusable(ctx context.Context, lnKey string, network, address string, } } - datagram := slices.Contains([]string{"udp", "udp4", "udp6", "unixgram", "fdgram"}, network) - if datagram { + packet := IsPacketNetwork(network) + if packet { if fd { ln, err = net.FilePacketConn(socketFile) } else { @@ -161,7 +160,7 @@ func listenReusable(ctx context.Context, lnKey string, network, address string, listenerPool.LoadOrStore(lnKey, nil) } - if datagram { + if packet { if !fd { // TODO: Not 100% sure this is necessary, but we do this for net.UnixListener, so... if unix, ok := ln.(*net.UnixConn); ok { diff --git a/listeners.go b/listeners.go index 16e56b4e0f0..286a76599af 100644 --- a/listeners.go +++ b/listeners.go @@ -310,7 +310,7 @@ func (na NetworkAddress) port() string { // The output can be parsed by ParseNetworkAddress(). If the // address is a unix socket, any non-zero port will be dropped. func (na NetworkAddress) String() string { - if na.Network == "tcp" && (na.Host != "" || na.port() != "") { + if na.Network == TCP && (na.Host != "" || na.port() != "") { na.Network = "" // omit default network value for brevity } return JoinNetworkAddress(na.Network, na.Host, na.port()) diff --git a/networks.go b/networks.go index 8580931ccc5..cab873804de 100644 --- a/networks.go +++ b/networks.go @@ -23,29 +23,47 @@ import ( "go.uber.org/zap" ) +const ( + UNIX = "unix" + UNIX_H2C = "unix+h2c" + UNIXGRAM = "unixgram" + UNIXPACKET = "unixpacket" + TCP = "tcp" + TCP4 = "tcp4" + TCP6 = "tcp6" + UDP = "udp" + UDP4 = "udp4" + UDP6 = "udp6" + IP_ = "ip:" + IP4_ = "ip4:" + IP6_ = "ip6:" + FD = "fd" + FDGRAM = "fdgram" +) + // IsUnixNetwork returns true if the netw is a unix network. func IsUnixNetwork(netw string) bool { - return netw == "unix" || netw == "unixgram" || netw == "unixpacket" || netw == "unix+h2c" + return netw == UNIX || netw == UNIX_H2C || netw == UNIXGRAM || netw == UNIXPACKET } // IsUnixNetwork returns true if the netw is a TCP network. func IsTCPNetwork(netw string) bool { - return netw == "tcp" || netw == "tcp4" || netw == "tcp6" + return netw == TCP || netw == TCP4 || netw == TCP6 } // IsUnixNetwork returns true if the netw is a UDP network. func IsUDPNetwork(netw string) bool { - return netw == "udp" || netw == "udp4" || netw == "udp6" + return netw == UDP || netw == UDP4 || netw == UDP6 } // IsIpNetwork returns true if the netw is an ip network. func IsIpNetwork(netw string) bool { - return strings.HasPrefix(netw, "ip:") || strings.HasPrefix(netw, "ip4:") || strings.HasPrefix(netw, "ip6:") + return strings.HasPrefix(netw, IP_) || strings.HasPrefix(netw, IP4_) || strings.HasPrefix(netw, IP6_) } // IsFdNetwork returns true if the netw is a fd network. func IsFdNetwork(netw string) bool { - return netw == "fd" || netw == "fdgram" + return netw == FD || netw == FDGRAM } func IsReservedNetwork(network string) bool { @@ -57,11 +75,19 @@ func IsReservedNetwork(network string) bool { } func IsIPv4Network(netw string) bool { - return netw == "tcp" || netw == "tcp4" || netw == "udp" || netw == "udp4" || strings.HasPrefix(netw, "ip:") || strings.HasPrefix(netw, "ip4:") + return netw == TCP || netw == TCP4 || netw == UDP || netw == UDP4 || strings.HasPrefix(netw, IP_) || strings.HasPrefix(netw, IP4_) } func IsIPv6Network(netw string) bool { - return netw == "tcp" || netw == "tcp6" || netw == "udp" || netw == "udp6" || strings.HasPrefix(netw, "ip:") || strings.HasPrefix(netw, "ip6:") + return netw == TCP || netw == TCP6 || netw == UDP || netw == UDP6 || strings.HasPrefix(netw, IP_) || strings.HasPrefix(netw, IP6_) +} + +func IsStreamNetwork(netw string) bool { + return netw == UNIX || netw == UNIX_H2C || netw == UNIXPACKET || IsTCPNetwork(netw) || netw == FD +} + +func IsPacketNetwork(netw string) bool { + return netw == UNIXGRAM || IsUDPNetwork(netw) || IsIpNetwork(netw) || netw == FDGRAM } // ListenerFunc is a function that can return a listener given a network and address. @@ -132,22 +158,22 @@ func getHTTP3Plugin(originalNetwork string) (string, error) { func GetHTTP3Network(originalNetwork string) (string, error) { switch originalNetwork { - case "unixgram": - return "unixgram", nil - case "udp": - return "udp", nil - case "udp4": - return "udp4", nil - case "udp6": - return "udp6", nil - case "tcp": - return "udp", nil - case "tcp4": - return "udp4", nil - case "tcp6": - return "udp6", nil - case "fdgram": - return "fdgram", nil + case UNIXGRAM: + return UNIXGRAM, nil + case UDP: + return UDP, nil + case UDP4: + return UDP4, nil + case UDP6: + return UDP6, nil + case TCP: + return UDP, nil + case TCP4: + return UDP4, nil + case TCP6: + return UDP6, nil + case FDGRAM: + return FDGRAM, nil } return getHTTP3Plugin(originalNetwork) } From a6949c42f03a30695520c271631b7c02c014c89e Mon Sep 17 00:00:00 2001 From: Aaron Paterson Date: Wed, 5 Nov 2025 23:13:32 -0700 Subject: [PATCH 32/51] rename arg --- replacer_systemd.go | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/replacer_systemd.go b/replacer_systemd.go index 8ac2809e891..281d356232a 100644 --- a/replacer_systemd.go +++ b/replacer_systemd.go @@ -64,10 +64,10 @@ func sdListenFdsWithNames() (map[string][]uint, error) { return nameToFiles, nil } -func getSdListenFd(nameToFiles map[string][]uint, host string) (uint, error) { +func getSdListenFd(nameToFiles map[string][]uint, nameOffset string) (uint, error) { index := uint(0) - name, offset, found := strings.Cut(host, ":") + name, offset, found := strings.Cut(nameOffset, ":") if found { off, err := strconv.ParseUint(offset, 0, strconv.IntSize) if err != nil { From f53787068cafac2e2e2f288d112725a369c7a8ee Mon Sep 17 00:00:00 2001 From: Aaron Paterson Date: Thu, 6 Nov 2025 01:06:57 -0700 Subject: [PATCH 33/51] cherrypick networks --- listen.go | 6 +- listen_unix.go | 9 ++- listeners.go | 14 ++++- modules/caddyhttp/server.go | 48 +++++++++++++++- networks.go | 106 +++++++++++++++++------------------- 5 files changed, 115 insertions(+), 68 deletions(-) diff --git a/listen.go b/listen.go index fba9c3a6ba6..c4600aa12b9 100644 --- a/listen.go +++ b/listen.go @@ -37,7 +37,7 @@ func reuseUnixSocket(_, _ string) (any, error) { func listenReusable(ctx context.Context, lnKey string, network, address string, config net.ListenConfig) (any, error) { var socketFile *os.File - fd := slices.Contains([]string{"fd", "fdgram"}, network) + fd := IsFdNetwork(network) if fd { socketFd, err := strconv.ParseUint(address, 0, strconv.IntSize) if err != nil { @@ -66,8 +66,8 @@ func listenReusable(ctx context.Context, lnKey string, network, address string, } } - datagram := slices.Contains([]string{"udp", "udp4", "udp6", "unixgram", "fdgram"}, network) - if datagram { + packet := IsPacketNetwork(network) + if packet { sharedPc, _, err := listenerPool.LoadOrNew(lnKey, func() (Destructor, error) { var ( pc net.PacketConn diff --git a/listen_unix.go b/listen_unix.go index d6ae0cb8ebb..856d0980ecf 100644 --- a/listen_unix.go +++ b/listen_unix.go @@ -27,7 +27,6 @@ import ( "io/fs" "net" "os" - "slices" "strconv" "sync" "sync/atomic" @@ -102,7 +101,7 @@ func listenReusable(ctx context.Context, lnKey string, network, address string, socketFile *os.File ) - fd := slices.Contains([]string{"fd", "fdgram"}, network) + fd := IsFdNetwork(network) if fd { socketFd, err := strconv.ParseUint(address, 0, strconv.IntSize) if err != nil { @@ -142,8 +141,8 @@ func listenReusable(ctx context.Context, lnKey string, network, address string, } } - datagram := slices.Contains([]string{"udp", "udp4", "udp6", "unixgram", "fdgram"}, network) - if datagram { + packet := IsPacketNetwork(network) + if packet { if fd { ln, err = net.FilePacketConn(socketFile) } else { @@ -161,7 +160,7 @@ func listenReusable(ctx context.Context, lnKey string, network, address string, listenerPool.LoadOrStore(lnKey, nil) } - if datagram { + if packet { if !fd { // TODO: Not 100% sure this is necessary, but we do this for net.UnixListener, so... if unix, ok := ln.(*net.UnixConn); ok { diff --git a/listeners.go b/listeners.go index d8d567b5e5e..286a76599af 100644 --- a/listeners.go +++ b/listeners.go @@ -213,6 +213,18 @@ func (na NetworkAddress) IsUnixNetwork() bool { return IsUnixNetwork(na.Network) } +// IsTCPNetwork returns true if na.Network is +// tcp, tcp4, or tcp6. +func (na NetworkAddress) IsTCPNetwork() bool { + return IsTCPNetwork(na.Network) +} + +// IsUDPNetwork returns true if na.Network is +// udp, udp4, or udp6. +func (na NetworkAddress) IsUDPNetwork() bool { + return IsUDPNetwork(na.Network) +} + // IsIpNetwork returns true if na.Network starts with // ip: ip4: or ip6: func (na NetworkAddress) IsIpNetwork() bool { @@ -298,7 +310,7 @@ func (na NetworkAddress) port() string { // The output can be parsed by ParseNetworkAddress(). If the // address is a unix socket, any non-zero port will be dropped. func (na NetworkAddress) String() string { - if na.Network == "tcp" && (na.Host != "" || na.port() != "") { + if na.Network == TCP && (na.Host != "" || na.port() != "") { na.Network = "" // omit default network value for brevity } return JoinNetworkAddress(na.Network, na.Host, na.port()) diff --git a/modules/caddyhttp/server.go b/modules/caddyhttp/server.go index b4e8932726b..d3760bf3cc9 100644 --- a/modules/caddyhttp/server.go +++ b/modules/caddyhttp/server.go @@ -620,7 +620,7 @@ func (s *Server) findLastRouteWithHostMatcher() int { // not already done, and then uses that server to serve HTTP/3 over // the listener, with Server s as the handler. func (s *Server) serveHTTP3(addr caddy.NetworkAddress, tlsCfg *tls.Config) error { - h3net, err := caddy.GetHTTP3Network(addr.Network) + h3net, err := getNetworkHTTP3(addr.Network) if err != nil { return fmt.Errorf("starting HTTP/3 QUIC listener: %v", err) } @@ -1125,7 +1125,49 @@ const ( ClientIPVarKey string = "client_ip" ) -// DEPRECATED: moved to caddy.RegisterNetworkHTTP3 +var networkHTTP3Plugins = map[string]string{} + +// RegisterNetworkHTTP3 registers a mapping from non-HTTP/3 network to HTTP/3 +// network. This should be called during init() and will panic if the network +// type is standard, reserved, or already registered. +// +// EXPERIMENTAL: Subject to change. func RegisterNetworkHTTP3(originalNetwork, h3Network string) { - caddy.RegisterNetworkHTTP3(originalNetwork, h3Network) + if caddy.IsReservedNetwork(originalNetwork) { + panic("network type " + originalNetwork + " is reserved") + } + + if _, ok := networkHTTP3Plugins[strings.ToLower(originalNetwork)]; ok { + panic("network type " + originalNetwork + " is already registered") + } + + networkHTTP3Plugins[originalNetwork] = h3Network +} + +func getNetworkHTTP3(originalNetwork string) (string, error) { + switch originalNetwork { + case caddy.UNIXGRAM: + return caddy.UNIXGRAM, nil + case caddy.UDP: + return caddy.UDP, nil + case caddy.UDP4: + return caddy.UDP4, nil + case caddy.UDP6: + return caddy.UDP6, nil + case caddy.TCP: + return caddy.UDP, nil + case caddy.TCP4: + return caddy.UDP4, nil + case caddy.TCP6: + return caddy.UDP6, nil + case caddy.FDGRAM: + return caddy.FDGRAM, nil + } + + h3Network, ok := networkHTTP3Plugins[strings.ToLower(originalNetwork)] + if !ok { + return "", fmt.Errorf("network '%s' cannot handle HTTP/3 connections", originalNetwork) + } + + return h3Network, nil } diff --git a/networks.go b/networks.go index edcdfa48811..0b7e3859a96 100644 --- a/networks.go +++ b/networks.go @@ -16,36 +16,79 @@ package caddy import ( "context" - "fmt" "net" "strings" "go.uber.org/zap" ) +const ( + UNIX = "unix" + UNIX_H2C = "unix+h2c" + UNIXGRAM = "unixgram" + UNIXPACKET = "unixpacket" + TCP = "tcp" + TCP4 = "tcp4" + TCP6 = "tcp6" + UDP = "udp" + UDP4 = "udp4" + UDP6 = "udp6" + IP_ = "ip:" + IP4_ = "ip4:" + IP6_ = "ip6:" + FD = "fd" + FDGRAM = "fdgram" +) + // IsUnixNetwork returns true if the netw is a unix network. func IsUnixNetwork(netw string) bool { - return netw == "unix" || netw == "unixgram" || netw == "unixpacket" || netw == "unix+h2c" + return netw == UNIX || netw == UNIX_H2C || netw == UNIXGRAM || netw == UNIXPACKET +} + +// IsUnixNetwork returns true if the netw is a TCP network. +func IsTCPNetwork(netw string) bool { + return netw == TCP || netw == TCP4 || netw == TCP6 +} + +// IsUnixNetwork returns true if the netw is a UDP network. +func IsUDPNetwork(netw string) bool { + return netw == UDP || netw == UDP4 || netw == UDP6 } // IsIpNetwork returns true if the netw is an ip network. func IsIpNetwork(netw string) bool { - return strings.HasPrefix(netw, "ip:") || strings.HasPrefix(netw, "ip4:") || strings.HasPrefix(netw, "ip6:") + return strings.HasPrefix(netw, IP_) || strings.HasPrefix(netw, IP4_) || strings.HasPrefix(netw, IP6_) } // IsFdNetwork returns true if the netw is a fd network. func IsFdNetwork(netw string) bool { - return netw == "fd" || netw == "fdgram" + return netw == FD || netw == FDGRAM } func IsReservedNetwork(network string) bool { - return network == "tcp" || network == "tcp4" || network == "tcp6" || - network == "udp" || network == "udp4" || network == "udp6" || - IsUnixNetwork(network) || + return IsUnixNetwork(network) || + IsTCPNetwork(network) || + IsUDPNetwork(network) || IsIpNetwork(network) || IsFdNetwork(network) } +func IsIPv4Network(netw string) bool { + return netw == TCP || netw == TCP4 || netw == UDP || netw == UDP4 || strings.HasPrefix(netw, IP_) || strings.HasPrefix(netw, IP4_) +} + +func IsIPv6Network(netw string) bool { + return netw == TCP || netw == TCP6 || netw == UDP || netw == UDP6 || strings.HasPrefix(netw, IP_) || strings.HasPrefix(netw, IP6_) +} + +func IsStreamNetwork(netw string) bool { + return netw == UNIX || netw == UNIX_H2C || netw == UNIXPACKET || IsTCPNetwork(netw) || netw == FD +} + +func IsPacketNetwork(netw string) bool { + return netw == UNIXGRAM || IsUDPNetwork(netw) || IsIpNetwork(netw) || netw == FDGRAM +} + // ListenerFunc is a function that can return a listener given a network and address. // The listeners must be capable of overlapping: with Caddy, new configs are loaded // before old ones are unloaded, so listeners may overlap briefly if the configs @@ -84,52 +127,3 @@ func getListenerFromPlugin(ctx context.Context, network, host, port string, port return nil, nil } - -var networkHTTP3Plugins = map[string]string{} - -// RegisterNetworkHTTP3 registers a mapping from non-HTTP/3 network to HTTP/3 -// network. This should be called during init() and will panic if the network -// type is standard, reserved, or already registered. -// -// EXPERIMENTAL: Subject to change. -func RegisterNetworkHTTP3(originalNetwork, h3Network string) { - if IsReservedNetwork(originalNetwork) { - panic("network type " + originalNetwork + " is reserved") - } - if _, ok := networkHTTP3Plugins[strings.ToLower(originalNetwork)]; ok { - panic("network type " + originalNetwork + " is already registered") - } - - networkHTTP3Plugins[originalNetwork] = h3Network -} - -func getHTTP3Plugin(originalNetwork string) (string, error) { - h3Network, ok := networkHTTP3Plugins[strings.ToLower(originalNetwork)] - if !ok { - return "", fmt.Errorf("network '%s' cannot handle HTTP/3 connections", originalNetwork) - } - - return h3Network, nil -} - -func GetHTTP3Network(originalNetwork string) (string, error) { - switch originalNetwork { - case "unixgram": - return "unixgram", nil - case "udp": - return "udp", nil - case "udp4": - return "udp4", nil - case "udp6": - return "udp6", nil - case "tcp": - return "udp", nil - case "tcp4": - return "udp4", nil - case "tcp6": - return "udp6", nil - case "fdgram": - return "fdgram", nil - } - return getHTTP3Plugin(originalNetwork) -} From 1472a126386c4539f3945369f96af7f663dd93ae Mon Sep 17 00:00:00 2001 From: Aaron Paterson Date: Thu, 6 Nov 2025 01:11:32 -0700 Subject: [PATCH 34/51] unused import --- listen.go | 1 - 1 file changed, 1 deletion(-) diff --git a/listen.go b/listen.go index c4600aa12b9..466efd79588 100644 --- a/listen.go +++ b/listen.go @@ -21,7 +21,6 @@ import ( "fmt" "net" "os" - "slices" "strconv" "sync" "sync/atomic" From 01ae5606303d64a3da0ebe010abe8c6acf416fed Mon Sep 17 00:00:00 2001 From: Aaron Paterson Date: Thu, 6 Nov 2025 01:18:20 -0700 Subject: [PATCH 35/51] cherrypick again --- replacer_systemd.go | 13 +++++++------ 1 file changed, 7 insertions(+), 6 deletions(-) diff --git a/replacer_systemd.go b/replacer_systemd.go index d810861f9b0..281d356232a 100644 --- a/replacer_systemd.go +++ b/replacer_systemd.go @@ -64,15 +64,16 @@ func sdListenFdsWithNames() (map[string][]uint, error) { return nameToFiles, nil } -func getSdListenFd(nameToFiles map[string][]uint, host string) (uint, error) { - name, index, li := host, uint(0), strings.Index(host, ":") - if li >= 0 { - name = host[:li] - i, err := strconv.ParseUint(host[li+1:], 0, strconv.IntSize) +func getSdListenFd(nameToFiles map[string][]uint, nameOffset string) (uint, error) { + index := uint(0) + + name, offset, found := strings.Cut(nameOffset, ":") + if found { + off, err := strconv.ParseUint(offset, 0, strconv.IntSize) if err != nil { return 0, err } - index += uint(i) + index += uint(off) } files, ok := nameToFiles[name] From 4a20224f3daa5b5c5602e949f2be8428400aa9b8 Mon Sep 17 00:00:00 2001 From: Aaron Paterson Date: Thu, 6 Nov 2025 01:31:19 -0700 Subject: [PATCH 36/51] errors --- replacer_systemd.go | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/replacer_systemd.go b/replacer_systemd.go index 281d356232a..80777f7e790 100644 --- a/replacer_systemd.go +++ b/replacer_systemd.go @@ -8,6 +8,8 @@ import ( "os" "strconv" "strings" + + "go.uber.org/zap" ) func sdListenFds() (int, error) { @@ -98,10 +100,12 @@ func (f systemdReplacementProvider) replace(key string) (any, bool) { const systemdListenPrefix = "systemd.listen." if strings.HasPrefix(key, systemdListenPrefix) { if initNameToFilesErr != nil { + Log().Error("unable to read LISTEN_FDNAMES", zap.Error(initNameToFilesErr)) return nil, false } fd, err := getSdListenFd(initNameToFiles, key[len(systemdListenPrefix):]) if err != nil { + Log().Error("unable to parse LISTEN_FDNAMES", zap.Error(err)) return nil, false } return fd, true From a6eaddc18fa22ea24b65d702a23e9326dd490007 Mon Sep 17 00:00:00 2001 From: Aaron Paterson Date: Thu, 6 Nov 2025 01:34:54 -0700 Subject: [PATCH 37/51] better message --- replacer_systemd.go | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/replacer_systemd.go b/replacer_systemd.go index 80777f7e790..6f9b769134d 100644 --- a/replacer_systemd.go +++ b/replacer_systemd.go @@ -105,7 +105,7 @@ func (f systemdReplacementProvider) replace(key string) (any, bool) { } fd, err := getSdListenFd(initNameToFiles, key[len(systemdListenPrefix):]) if err != nil { - Log().Error("unable to parse LISTEN_FDNAMES", zap.Error(err)) + Log().Error("unable to process {" + key + "}", zap.Error(err)) return nil, false } return fd, true From 2b102e3ba3109b140c48cb9377a554e90dcb83a3 Mon Sep 17 00:00:00 2001 From: Aaron Paterson Date: Thu, 6 Nov 2025 01:42:59 -0700 Subject: [PATCH 38/51] gofumpt --- replacer_systemd.go | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/replacer_systemd.go b/replacer_systemd.go index 6f9b769134d..518ce365943 100644 --- a/replacer_systemd.go +++ b/replacer_systemd.go @@ -105,7 +105,7 @@ func (f systemdReplacementProvider) replace(key string) (any, bool) { } fd, err := getSdListenFd(initNameToFiles, key[len(systemdListenPrefix):]) if err != nil { - Log().Error("unable to process {" + key + "}", zap.Error(err)) + Log().Error("unable to process {"+key+"}", zap.Error(err)) return nil, false } return fd, true From 834b7feabfc189a1ecaf4c8be491cc977fcd7d5c Mon Sep 17 00:00:00 2001 From: Aaron Paterson Date: Thu, 6 Nov 2025 01:43:21 -0700 Subject: [PATCH 39/51] gofumpt --- replacer_systemd.go | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/replacer_systemd.go b/replacer_systemd.go index 6f9b769134d..518ce365943 100644 --- a/replacer_systemd.go +++ b/replacer_systemd.go @@ -105,7 +105,7 @@ func (f systemdReplacementProvider) replace(key string) (any, bool) { } fd, err := getSdListenFd(initNameToFiles, key[len(systemdListenPrefix):]) if err != nil { - Log().Error("unable to process {" + key + "}", zap.Error(err)) + Log().Error("unable to process {"+key+"}", zap.Error(err)) return nil, false } return fd, true From f5f56ec17e77e3179cd7224175e8380a0184aaab Mon Sep 17 00:00:00 2001 From: Aaron Paterson Date: Thu, 6 Nov 2025 01:54:11 -0700 Subject: [PATCH 40/51] log when addr cannot be read --- caddyconfig/httpcaddyfile/addresses.go | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/caddyconfig/httpcaddyfile/addresses.go b/caddyconfig/httpcaddyfile/addresses.go index d70efbea82d..db122e6beee 100644 --- a/caddyconfig/httpcaddyfile/addresses.go +++ b/caddyconfig/httpcaddyfile/addresses.go @@ -29,6 +29,7 @@ import ( "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" "github.com/caddyserver/caddy/v2/modules/caddyhttp" + "go.uber.org/zap" ) // mapAddressToProtocolToServerBlocks returns a map of listener address to list of server @@ -360,7 +361,8 @@ func (st *ServerType) listenersForServerBlockAddress(sblock serverBlock, addr Ad case *net.IPNet: ip = ifaceAddrValue.IP default: - return nil, fmt.Errorf("reading listener interface address: %v: %v", lnDevice, ifaceAddr.String()) + caddy.Log().Error("reading listener interface address", zap.String("device", lnDevice), zap.String("address", ifaceAddr.String())) + continue } if len(ip) == net.IPv4len && caddy.IsIPv4Network(lnNetw) || len(ip) == net.IPv6len && caddy.IsIPv6Network(lnNetw) { From a96dfbbd972951ce98bb72b5a1143087b602ff18 Mon Sep 17 00:00:00 2001 From: Aaron Paterson Date: Thu, 6 Nov 2025 02:04:49 -0700 Subject: [PATCH 41/51] cast to config values to bindOptions --- caddyconfig/httpcaddyfile/tlsapp.go | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/caddyconfig/httpcaddyfile/tlsapp.go b/caddyconfig/httpcaddyfile/tlsapp.go index 30948f84fff..b04d42daf48 100644 --- a/caddyconfig/httpcaddyfile/tlsapp.go +++ b/caddyconfig/httpcaddyfile/tlsapp.go @@ -221,7 +221,7 @@ func (st ServerType) buildTLSApp( if acmeIssuer.Challenges.BindHost == "" { // only binding to one host is supported var bindHost string - if asserted, ok := cfgVal.Value.(addressesWithProtocols); ok && len(asserted.addresses) > 0 { + if asserted, ok := cfgVal.Value.(bindOptions); ok && len(asserted.addresses) > 0 { bindHost = asserted.addresses[0] } acmeIssuer.Challenges.BindHost = bindHost @@ -613,7 +613,7 @@ func fillInGlobalACMEDefaults(issuer certmagic.Issuer, options map[string]any) e // In Linux the same call will error with EADDRINUSE whenever the listener for the automation policy is opened if acmeIssuer.Challenges == nil || (acmeIssuer.Challenges.DNS == nil && acmeIssuer.Challenges.BindHost == "") { if defBinds, ok := globalDefaultBind.([]ConfigValue); ok && len(defBinds) > 0 { - if abp, ok := defBinds[0].Value.(addressesWithProtocols); ok && len(abp.addresses) > 0 { + if abp, ok := defBinds[0].Value.(bindOptions); ok && len(abp.addresses) > 0 { if acmeIssuer.Challenges == nil { acmeIssuer.Challenges = new(caddytls.ChallengesConfig) } From d1423a7a9720e2a474ab62d7388be4abd9dbfc2d Mon Sep 17 00:00:00 2001 From: Aaron Paterson Date: Thu, 6 Nov 2025 02:06:42 -0700 Subject: [PATCH 42/51] remove newline --- caddyconfig/httpcaddyfile/addresses.go | 1 - 1 file changed, 1 deletion(-) diff --git a/caddyconfig/httpcaddyfile/addresses.go b/caddyconfig/httpcaddyfile/addresses.go index db122e6beee..6a43074c6f8 100644 --- a/caddyconfig/httpcaddyfile/addresses.go +++ b/caddyconfig/httpcaddyfile/addresses.go @@ -25,7 +25,6 @@ import ( "unicode" "github.com/caddyserver/certmagic" - "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" "github.com/caddyserver/caddy/v2/modules/caddyhttp" From 2e5e31d39bea3bb93859e147cc051f6478db43a4 Mon Sep 17 00:00:00 2001 From: Aaron Paterson Date: Thu, 6 Nov 2025 02:09:43 -0700 Subject: [PATCH 43/51] more newlines? --- caddyconfig/httpcaddyfile/addresses.go | 2 ++ 1 file changed, 2 insertions(+) diff --git a/caddyconfig/httpcaddyfile/addresses.go b/caddyconfig/httpcaddyfile/addresses.go index 6a43074c6f8..a7fc20197fd 100644 --- a/caddyconfig/httpcaddyfile/addresses.go +++ b/caddyconfig/httpcaddyfile/addresses.go @@ -25,9 +25,11 @@ import ( "unicode" "github.com/caddyserver/certmagic" + "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" "github.com/caddyserver/caddy/v2/modules/caddyhttp" + "go.uber.org/zap" ) From 1fcaf50273d1a80bf2923f918f8dd6e716691f07 Mon Sep 17 00:00:00 2001 From: Aaron Paterson Date: Thu, 6 Nov 2025 02:14:08 -0700 Subject: [PATCH 44/51] remove one newline? --- caddyconfig/httpcaddyfile/addresses.go | 1 - 1 file changed, 1 deletion(-) diff --git a/caddyconfig/httpcaddyfile/addresses.go b/caddyconfig/httpcaddyfile/addresses.go index a7fc20197fd..9b375ead9d1 100644 --- a/caddyconfig/httpcaddyfile/addresses.go +++ b/caddyconfig/httpcaddyfile/addresses.go @@ -23,7 +23,6 @@ import ( "strconv" "strings" "unicode" - "github.com/caddyserver/certmagic" "github.com/caddyserver/caddy/v2" From 5717418b7bac60650963097a01a12dbc9dcf5750 Mon Sep 17 00:00:00 2001 From: Aaron Paterson Date: Thu, 6 Nov 2025 02:21:32 -0700 Subject: [PATCH 45/51] Revert "log when addr cannot be read" This reverts commit f5f56ec17e77e3179cd7224175e8380a0184aaab. --- caddyconfig/httpcaddyfile/addresses.go | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/caddyconfig/httpcaddyfile/addresses.go b/caddyconfig/httpcaddyfile/addresses.go index 9b375ead9d1..2d450ef5190 100644 --- a/caddyconfig/httpcaddyfile/addresses.go +++ b/caddyconfig/httpcaddyfile/addresses.go @@ -361,8 +361,7 @@ func (st *ServerType) listenersForServerBlockAddress(sblock serverBlock, addr Ad case *net.IPNet: ip = ifaceAddrValue.IP default: - caddy.Log().Error("reading listener interface address", zap.String("device", lnDevice), zap.String("address", ifaceAddr.String())) - continue + return nil, fmt.Errorf("reading listener interface address: %v: %v", lnDevice, ifaceAddr.String()) } if len(ip) == net.IPv4len && caddy.IsIPv4Network(lnNetw) || len(ip) == net.IPv6len && caddy.IsIPv6Network(lnNetw) { From 97f5b2a47655524edbe79d03784eaede3c00154a Mon Sep 17 00:00:00 2001 From: Aaron Paterson Date: Thu, 6 Nov 2025 02:23:02 -0700 Subject: [PATCH 46/51] unrevert --- caddyconfig/httpcaddyfile/addresses.go | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/caddyconfig/httpcaddyfile/addresses.go b/caddyconfig/httpcaddyfile/addresses.go index 2d450ef5190..a7fc20197fd 100644 --- a/caddyconfig/httpcaddyfile/addresses.go +++ b/caddyconfig/httpcaddyfile/addresses.go @@ -23,6 +23,7 @@ import ( "strconv" "strings" "unicode" + "github.com/caddyserver/certmagic" "github.com/caddyserver/caddy/v2" @@ -361,7 +362,8 @@ func (st *ServerType) listenersForServerBlockAddress(sblock serverBlock, addr Ad case *net.IPNet: ip = ifaceAddrValue.IP default: - return nil, fmt.Errorf("reading listener interface address: %v: %v", lnDevice, ifaceAddr.String()) + caddy.Log().Error("reading listener interface address", zap.String("device", lnDevice), zap.String("address", ifaceAddr.String())) + continue } if len(ip) == net.IPv4len && caddy.IsIPv4Network(lnNetw) || len(ip) == net.IPv6len && caddy.IsIPv6Network(lnNetw) { From 33b30272a7304bed4d79bda509df7628103ce326 Mon Sep 17 00:00:00 2001 From: Aaron Paterson Date: Thu, 6 Nov 2025 02:24:20 -0700 Subject: [PATCH 47/51] import order? --- caddyconfig/httpcaddyfile/addresses.go | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/caddyconfig/httpcaddyfile/addresses.go b/caddyconfig/httpcaddyfile/addresses.go index a7fc20197fd..ef927a32213 100644 --- a/caddyconfig/httpcaddyfile/addresses.go +++ b/caddyconfig/httpcaddyfile/addresses.go @@ -24,12 +24,12 @@ import ( "strings" "unicode" - "github.com/caddyserver/certmagic" - "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" "github.com/caddyserver/caddy/v2/modules/caddyhttp" + "github.com/caddyserver/certmagic" + "go.uber.org/zap" ) From 8cc72d2028a4eeed6f04ed1023ffd51e3700a09f Mon Sep 17 00:00:00 2001 From: Aaron Paterson Date: Thu, 6 Nov 2025 02:28:29 -0700 Subject: [PATCH 48/51] gci write --- caddy.go | 5 ++--- caddyconfig/caddyfile/importargs.go | 3 +-- caddyconfig/caddyfile/parse.go | 3 +-- caddyconfig/httpcaddyfile/addresses.go | 2 -- caddyconfig/httpcaddyfile/builtins.go | 7 +++---- caddyconfig/httpcaddyfile/httptype.go | 3 +-- caddyconfig/httpcaddyfile/options.go | 7 +++---- caddyconfig/httpcaddyfile/serveroptions.go | 3 +-- caddyconfig/httpcaddyfile/tlsapp.go | 5 ++--- caddytest/caddytest.go | 4 +--- caddytest/integration/acme_test.go | 5 ++--- caddytest/integration/acmeserver_test.go | 3 +-- caddytest/integration/mockdns_test.go | 5 ++--- caddytest/integration/stream_test.go | 3 +-- cmd/caddy/main.go | 1 - cmd/cobra.go | 3 +-- cmd/commandfuncs.go | 3 +-- cmd/commands.go | 3 +-- cmd/main.go | 5 ++--- cmd/packagesfuncs.go | 3 +-- cmd/storagefuncs.go | 3 +-- context.go | 3 +-- listeners.go | 3 +-- logging.go | 3 +-- metrics.go | 3 +-- modules/caddyevents/app.go | 3 +-- modules/caddyfs/filesystem.go | 3 +-- modules/caddyhttp/app.go | 5 ++--- modules/caddyhttp/autohttps.go | 5 ++--- modules/caddyhttp/caddyauth/argon2id.go | 3 +-- modules/caddyhttp/caddyauth/basicauth.go | 3 +-- modules/caddyhttp/caddyauth/bcrypt.go | 3 +-- modules/caddyhttp/caddyauth/caddyauth.go | 5 ++--- modules/caddyhttp/caddyauth/command.go | 6 ++---- modules/caddyhttp/celmatcher.go | 5 ++--- modules/caddyhttp/encode/gzip/gzip.go | 3 +-- modules/caddyhttp/encode/zstd/zstd.go | 3 +-- modules/caddyhttp/fileserver/browse.go | 5 ++--- modules/caddyhttp/fileserver/browsetplcontext.go | 5 ++--- modules/caddyhttp/fileserver/command.go | 10 ++++------ modules/caddyhttp/fileserver/matcher.go | 7 +++---- modules/caddyhttp/fileserver/staticfiles.go | 5 ++--- modules/caddyhttp/intercept/intercept.go | 5 ++--- modules/caddyhttp/ip_matchers.go | 7 +++---- modules/caddyhttp/logging.go | 3 +-- modules/caddyhttp/logging/logadd.go | 3 +-- modules/caddyhttp/matchers.go | 5 ++--- modules/caddyhttp/metrics.go | 5 ++--- modules/caddyhttp/metrics_test.go | 3 +-- modules/caddyhttp/proxyprotocol/listenerwrapper.go | 3 +-- modules/caddyhttp/push/handler.go | 5 ++--- modules/caddyhttp/replacer.go | 5 ++--- modules/caddyhttp/requestbody/caddyfile.go | 3 +-- modules/caddyhttp/requestbody/requestbody.go | 5 ++--- modules/caddyhttp/reverseproxy/caddyfile.go | 3 +-- modules/caddyhttp/reverseproxy/command.go | 8 +++----- modules/caddyhttp/reverseproxy/fastcgi/client.go | 3 +-- modules/caddyhttp/reverseproxy/fastcgi/fastcgi.go | 5 ++--- modules/caddyhttp/reverseproxy/healthchecks.go | 5 ++--- modules/caddyhttp/reverseproxy/httptransport.go | 11 +++++------ modules/caddyhttp/reverseproxy/metrics.go | 3 +-- modules/caddyhttp/reverseproxy/reverseproxy.go | 7 +++---- modules/caddyhttp/reverseproxy/selectionpolicies.go | 3 +-- modules/caddyhttp/reverseproxy/streaming.go | 3 +-- modules/caddyhttp/reverseproxy/upstreams.go | 3 +-- modules/caddyhttp/rewrite/rewrite.go | 3 +-- modules/caddyhttp/server.go | 7 +++---- modules/caddyhttp/staticresp.go | 8 +++----- modules/caddyhttp/templates/templates.go | 3 +-- modules/caddyhttp/templates/tplcontext.go | 5 ++--- modules/caddyhttp/tracing/module.go | 3 +-- modules/caddyhttp/tracing/tracer.go | 5 ++--- modules/caddyhttp/vars.go | 5 ++--- modules/caddypki/acmeserver/acmeserver.go | 7 +++---- modules/caddypki/adminapi.go | 3 +-- modules/caddypki/ca.go | 3 +-- modules/caddypki/command.go | 6 ++---- modules/caddypki/pki.go | 3 +-- modules/caddytls/acmeissuer.go | 7 +++---- modules/caddytls/automation.go | 3 +-- modules/caddytls/capools.go | 3 +-- modules/caddytls/certmanagers.go | 5 ++--- modules/caddytls/certselection.go | 3 +-- modules/caddytls/connpolicy.go | 7 +++---- modules/caddytls/distributedstek/distributedstek.go | 3 +-- modules/caddytls/ech.go | 3 +-- modules/caddytls/internalissuer.go | 7 +++---- modules/caddytls/leafstorageloader.go | 3 +-- modules/caddytls/matchers.go | 7 +++---- modules/caddytls/ondemand.go | 5 ++--- modules/caddytls/storageloader.go | 3 +-- modules/caddytls/tls.go | 7 +++---- modules/caddytls/zerosslissuer.go | 5 ++--- modules/filestorage/filestorage.go | 3 +-- modules/internal/network/networkproxy.go | 3 +-- modules/logging/appendencoder.go | 7 +++---- modules/logging/cores.go | 3 +-- modules/logging/encoders.go | 5 ++--- modules/logging/filewriter.go | 3 +-- modules/logging/filterencoder.go | 7 +++---- modules/logging/filters.go | 3 +-- modules/logging/filters_test.go | 3 +-- modules/metrics/adminmetrics.go | 3 +-- modules/metrics/metrics.go | 7 +++---- service_windows.go | 3 +-- 105 files changed, 173 insertions(+), 285 deletions(-) diff --git a/caddy.go b/caddy.go index 5f71d8e8b53..990ebaac5c1 100644 --- a/caddy.go +++ b/caddy.go @@ -35,12 +35,11 @@ import ( "sync/atomic" "time" + "github.com/caddyserver/caddy/v2/internal/filesystems" + "github.com/caddyserver/caddy/v2/notify" "github.com/caddyserver/certmagic" "github.com/google/uuid" "go.uber.org/zap" - - "github.com/caddyserver/caddy/v2/internal/filesystems" - "github.com/caddyserver/caddy/v2/notify" ) // Config is the top (or beginning) of the Caddy configuration structure. diff --git a/caddyconfig/caddyfile/importargs.go b/caddyconfig/caddyfile/importargs.go index b2eb3e834dd..ee9a51ba001 100644 --- a/caddyconfig/caddyfile/importargs.go +++ b/caddyconfig/caddyfile/importargs.go @@ -19,9 +19,8 @@ import ( "strconv" "strings" - "go.uber.org/zap" - "github.com/caddyserver/caddy/v2" + "go.uber.org/zap" ) // parseVariadic determines if the token is a variadic placeholder, diff --git a/caddyconfig/caddyfile/parse.go b/caddyconfig/caddyfile/parse.go index 8439f3731df..26ec862a555 100644 --- a/caddyconfig/caddyfile/parse.go +++ b/caddyconfig/caddyfile/parse.go @@ -22,9 +22,8 @@ import ( "path/filepath" "strings" - "go.uber.org/zap" - "github.com/caddyserver/caddy/v2" + "go.uber.org/zap" ) // Parse parses the input just enough to group tokens, in diff --git a/caddyconfig/httpcaddyfile/addresses.go b/caddyconfig/httpcaddyfile/addresses.go index ef927a32213..f31845d4dd4 100644 --- a/caddyconfig/httpcaddyfile/addresses.go +++ b/caddyconfig/httpcaddyfile/addresses.go @@ -27,9 +27,7 @@ import ( "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" "github.com/caddyserver/caddy/v2/modules/caddyhttp" - "github.com/caddyserver/certmagic" - "go.uber.org/zap" ) diff --git a/caddyconfig/httpcaddyfile/builtins.go b/caddyconfig/httpcaddyfile/builtins.go index a0eb770470b..25c5fb9e09b 100644 --- a/caddyconfig/httpcaddyfile/builtins.go +++ b/caddyconfig/httpcaddyfile/builtins.go @@ -24,15 +24,14 @@ import ( "strings" "time" - "github.com/caddyserver/certmagic" - "github.com/mholt/acmez/v3/acme" - "go.uber.org/zap/zapcore" - "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/caddyconfig" "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" "github.com/caddyserver/caddy/v2/modules/caddyhttp" "github.com/caddyserver/caddy/v2/modules/caddytls" + "github.com/caddyserver/certmagic" + "github.com/mholt/acmez/v3/acme" + "go.uber.org/zap/zapcore" ) func init() { diff --git a/caddyconfig/httpcaddyfile/httptype.go b/caddyconfig/httpcaddyfile/httptype.go index 3dcd3ea5b62..b7ddfe7e2f5 100644 --- a/caddyconfig/httpcaddyfile/httptype.go +++ b/caddyconfig/httpcaddyfile/httptype.go @@ -25,14 +25,13 @@ import ( "strconv" "strings" - "go.uber.org/zap" - "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/caddyconfig" "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" "github.com/caddyserver/caddy/v2/modules/caddyhttp" "github.com/caddyserver/caddy/v2/modules/caddypki" "github.com/caddyserver/caddy/v2/modules/caddytls" + "go.uber.org/zap" ) func init() { diff --git a/caddyconfig/httpcaddyfile/options.go b/caddyconfig/httpcaddyfile/options.go index 336c6999f92..859e6d50b9a 100644 --- a/caddyconfig/httpcaddyfile/options.go +++ b/caddyconfig/httpcaddyfile/options.go @@ -18,15 +18,14 @@ import ( "slices" "strconv" - "github.com/caddyserver/certmagic" - "github.com/libdns/libdns" - "github.com/mholt/acmez/v3/acme" - "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/caddyconfig" "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" "github.com/caddyserver/caddy/v2/modules/caddyhttp" "github.com/caddyserver/caddy/v2/modules/caddytls" + "github.com/caddyserver/certmagic" + "github.com/libdns/libdns" + "github.com/mholt/acmez/v3/acme" ) func init() { diff --git a/caddyconfig/httpcaddyfile/serveroptions.go b/caddyconfig/httpcaddyfile/serveroptions.go index 9431f1aed58..5c8132b7904 100644 --- a/caddyconfig/httpcaddyfile/serveroptions.go +++ b/caddyconfig/httpcaddyfile/serveroptions.go @@ -20,12 +20,11 @@ import ( "slices" "strconv" - "github.com/dustin/go-humanize" - "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/caddyconfig" "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" "github.com/caddyserver/caddy/v2/modules/caddyhttp" + "github.com/dustin/go-humanize" ) // serverOptions collects server config overrides parsed from Caddyfile global options diff --git a/caddyconfig/httpcaddyfile/tlsapp.go b/caddyconfig/httpcaddyfile/tlsapp.go index b04d42daf48..c67407ddbc1 100644 --- a/caddyconfig/httpcaddyfile/tlsapp.go +++ b/caddyconfig/httpcaddyfile/tlsapp.go @@ -24,13 +24,12 @@ import ( "strconv" "strings" - "github.com/caddyserver/certmagic" - "github.com/mholt/acmez/v3/acme" - "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/caddyconfig" "github.com/caddyserver/caddy/v2/modules/caddyhttp" "github.com/caddyserver/caddy/v2/modules/caddytls" + "github.com/caddyserver/certmagic" + "github.com/mholt/acmez/v3/acme" ) func (st ServerType) buildTLSApp( diff --git a/caddytest/caddytest.go b/caddytest/caddytest.go index 7b56bb281cc..249ae464a73 100644 --- a/caddytest/caddytest.go +++ b/caddytest/caddytest.go @@ -23,10 +23,8 @@ import ( "time" "github.com/aryann/difflib" - - caddycmd "github.com/caddyserver/caddy/v2/cmd" - "github.com/caddyserver/caddy/v2/caddyconfig" + caddycmd "github.com/caddyserver/caddy/v2/cmd" // plug in Caddy modules here _ "github.com/caddyserver/caddy/v2/modules/standard" ) diff --git a/caddytest/integration/acme_test.go b/caddytest/integration/acme_test.go index f10aef6a86d..d7e4c296d50 100644 --- a/caddytest/integration/acme_test.go +++ b/caddytest/integration/acme_test.go @@ -12,14 +12,13 @@ import ( "strings" "testing" + "github.com/caddyserver/caddy/v2" + "github.com/caddyserver/caddy/v2/caddytest" "github.com/mholt/acmez/v3" "github.com/mholt/acmez/v3/acme" smallstepacme "github.com/smallstep/certificates/acme" "go.uber.org/zap" "go.uber.org/zap/exp/zapslog" - - "github.com/caddyserver/caddy/v2" - "github.com/caddyserver/caddy/v2/caddytest" ) const acmeChallengePort = 9081 diff --git a/caddytest/integration/acmeserver_test.go b/caddytest/integration/acmeserver_test.go index d6a9ba005ad..ca5845f8711 100644 --- a/caddytest/integration/acmeserver_test.go +++ b/caddytest/integration/acmeserver_test.go @@ -9,12 +9,11 @@ import ( "strings" "testing" + "github.com/caddyserver/caddy/v2/caddytest" "github.com/mholt/acmez/v3" "github.com/mholt/acmez/v3/acme" "go.uber.org/zap" "go.uber.org/zap/exp/zapslog" - - "github.com/caddyserver/caddy/v2/caddytest" ) func TestACMEServerDirectory(t *testing.T) { diff --git a/caddytest/integration/mockdns_test.go b/caddytest/integration/mockdns_test.go index e55a6df583c..9963bdf950d 100644 --- a/caddytest/integration/mockdns_test.go +++ b/caddytest/integration/mockdns_test.go @@ -3,11 +3,10 @@ package integration import ( "context" - "github.com/caddyserver/certmagic" - "github.com/libdns/libdns" - "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" + "github.com/caddyserver/certmagic" + "github.com/libdns/libdns" ) func init() { diff --git a/caddytest/integration/stream_test.go b/caddytest/integration/stream_test.go index 57231a5271b..d2f2fd79b95 100644 --- a/caddytest/integration/stream_test.go +++ b/caddytest/integration/stream_test.go @@ -13,10 +13,9 @@ import ( "testing" "time" + "github.com/caddyserver/caddy/v2/caddytest" "golang.org/x/net/http2" "golang.org/x/net/http2/h2c" - - "github.com/caddyserver/caddy/v2/caddytest" ) // (see https://github.com/caddyserver/caddy/issues/3556 for use case) diff --git a/cmd/caddy/main.go b/cmd/caddy/main.go index 48fa149aa08..425b8954f95 100644 --- a/cmd/caddy/main.go +++ b/cmd/caddy/main.go @@ -30,7 +30,6 @@ package main import ( caddycmd "github.com/caddyserver/caddy/v2/cmd" - // plug in Caddy modules here _ "github.com/caddyserver/caddy/v2/modules/standard" ) diff --git a/cmd/cobra.go b/cmd/cobra.go index 9ecb389e2aa..8d6d23b4841 100644 --- a/cmd/cobra.go +++ b/cmd/cobra.go @@ -3,9 +3,8 @@ package caddycmd import ( "fmt" - "github.com/spf13/cobra" - "github.com/caddyserver/caddy/v2" + "github.com/spf13/cobra" ) var defaultFactory = newRootCommandFactory(func() *cobra.Command { diff --git a/cmd/commandfuncs.go b/cmd/commandfuncs.go index 75d1149926c..690c4b2eb4f 100644 --- a/cmd/commandfuncs.go +++ b/cmd/commandfuncs.go @@ -34,12 +34,11 @@ import ( "strings" "github.com/aryann/difflib" - "go.uber.org/zap" - "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/caddyconfig" "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" "github.com/caddyserver/caddy/v2/internal" + "go.uber.org/zap" ) func cmdStart(fl Flags) (int, error) { diff --git a/cmd/commands.go b/cmd/commands.go index c9ea636b9d0..0a5ad66cfc1 100644 --- a/cmd/commands.go +++ b/cmd/commands.go @@ -22,10 +22,9 @@ import ( "strings" "sync" + "github.com/caddyserver/caddy/v2" "github.com/spf13/cobra" "github.com/spf13/cobra/doc" - - "github.com/caddyserver/caddy/v2" ) // Command represents a subcommand. Name, Func, diff --git a/cmd/main.go b/cmd/main.go index 411f4545d33..9b7b3cebb02 100644 --- a/cmd/main.go +++ b/cmd/main.go @@ -35,14 +35,13 @@ import ( "time" "github.com/KimMachineGun/automemlimit/memlimit" + "github.com/caddyserver/caddy/v2" + "github.com/caddyserver/caddy/v2/caddyconfig" "github.com/caddyserver/certmagic" "github.com/spf13/pflag" "go.uber.org/automaxprocs/maxprocs" "go.uber.org/zap" "go.uber.org/zap/exp/zapslog" - - "github.com/caddyserver/caddy/v2" - "github.com/caddyserver/caddy/v2/caddyconfig" ) func init() { diff --git a/cmd/packagesfuncs.go b/cmd/packagesfuncs.go index 4d0ff068038..5d7ab615656 100644 --- a/cmd/packagesfuncs.go +++ b/cmd/packagesfuncs.go @@ -28,9 +28,8 @@ import ( "runtime/debug" "strings" - "go.uber.org/zap" - "github.com/caddyserver/caddy/v2" + "go.uber.org/zap" ) func cmdUpgrade(fl Flags) (int, error) { diff --git a/cmd/storagefuncs.go b/cmd/storagefuncs.go index 5606fe4ae98..f2bce68517e 100644 --- a/cmd/storagefuncs.go +++ b/cmd/storagefuncs.go @@ -24,9 +24,8 @@ import ( "io/fs" "os" - "github.com/caddyserver/certmagic" - "github.com/caddyserver/caddy/v2" + "github.com/caddyserver/certmagic" ) type storVal struct { diff --git a/context.go b/context.go index 4c11399360d..d36d5640091 100644 --- a/context.go +++ b/context.go @@ -22,13 +22,12 @@ import ( "log/slog" "reflect" + "github.com/caddyserver/caddy/v2/internal/filesystems" "github.com/caddyserver/certmagic" "github.com/prometheus/client_golang/prometheus" "github.com/prometheus/client_golang/prometheus/collectors" "go.uber.org/zap" "go.uber.org/zap/exp/zapslog" - - "github.com/caddyserver/caddy/v2/internal/filesystems" ) // Context is a type which defines the lifetime of modules that diff --git a/listeners.go b/listeners.go index 286a76599af..a664b90f63e 100644 --- a/listeners.go +++ b/listeners.go @@ -29,13 +29,12 @@ import ( "sync" "sync/atomic" + "github.com/caddyserver/caddy/v2/internal" "github.com/quic-go/quic-go" "github.com/quic-go/quic-go/http3" "github.com/quic-go/quic-go/qlog" "go.uber.org/zap" "golang.org/x/time/rate" - - "github.com/caddyserver/caddy/v2/internal" ) // NetworkAddress represents one or more network addresses. diff --git a/logging.go b/logging.go index 2734b542517..8004c7ff776 100644 --- a/logging.go +++ b/logging.go @@ -25,11 +25,10 @@ import ( "sync" "time" + "github.com/caddyserver/caddy/v2/internal" "go.uber.org/zap" "go.uber.org/zap/zapcore" "golang.org/x/term" - - "github.com/caddyserver/caddy/v2/internal" ) func init() { diff --git a/metrics.go b/metrics.go index 0ee3853eb85..cc5181592cc 100644 --- a/metrics.go +++ b/metrics.go @@ -3,9 +3,8 @@ package caddy import ( "net/http" - "github.com/prometheus/client_golang/prometheus" - "github.com/caddyserver/caddy/v2/internal/metrics" + "github.com/prometheus/client_golang/prometheus" ) // define and register the metrics used in this package. diff --git a/modules/caddyevents/app.go b/modules/caddyevents/app.go index 6c2abbf7cbc..2bfdcddb2dd 100644 --- a/modules/caddyevents/app.go +++ b/modules/caddyevents/app.go @@ -21,9 +21,8 @@ import ( "fmt" "strings" - "go.uber.org/zap" - "github.com/caddyserver/caddy/v2" + "go.uber.org/zap" ) func init() { diff --git a/modules/caddyfs/filesystem.go b/modules/caddyfs/filesystem.go index 2ec43079a2f..2125ed9ec9e 100644 --- a/modules/caddyfs/filesystem.go +++ b/modules/caddyfs/filesystem.go @@ -5,12 +5,11 @@ import ( "fmt" "io/fs" - "go.uber.org/zap" - "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/caddyconfig" "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" "github.com/caddyserver/caddy/v2/caddyconfig/httpcaddyfile" + "go.uber.org/zap" ) func init() { diff --git a/modules/caddyhttp/app.go b/modules/caddyhttp/app.go index 6ad18d051f8..8d81677d2f3 100644 --- a/modules/caddyhttp/app.go +++ b/modules/caddyhttp/app.go @@ -26,12 +26,11 @@ import ( "sync" "time" - "go.uber.org/zap" - "golang.org/x/net/http2" - "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/modules/caddyevents" "github.com/caddyserver/caddy/v2/modules/caddytls" + "go.uber.org/zap" + "golang.org/x/net/http2" ) func init() { diff --git a/modules/caddyhttp/autohttps.go b/modules/caddyhttp/autohttps.go index 05f8a7517f0..aafa6488e55 100644 --- a/modules/caddyhttp/autohttps.go +++ b/modules/caddyhttp/autohttps.go @@ -21,12 +21,11 @@ import ( "strconv" "strings" - "github.com/caddyserver/certmagic" - "go.uber.org/zap" - "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/internal" "github.com/caddyserver/caddy/v2/modules/caddytls" + "github.com/caddyserver/certmagic" + "go.uber.org/zap" ) // AutoHTTPSConfig is used to disable automatic HTTPS diff --git a/modules/caddyhttp/caddyauth/argon2id.go b/modules/caddyhttp/caddyauth/argon2id.go index f1070ce4887..280dc42eb5c 100644 --- a/modules/caddyhttp/caddyauth/argon2id.go +++ b/modules/caddyhttp/caddyauth/argon2id.go @@ -22,9 +22,8 @@ import ( "strconv" "strings" - "golang.org/x/crypto/argon2" - "github.com/caddyserver/caddy/v2" + "golang.org/x/crypto/argon2" ) func init() { diff --git a/modules/caddyhttp/caddyauth/basicauth.go b/modules/caddyhttp/caddyauth/basicauth.go index 5a9e167e102..a23931660a7 100644 --- a/modules/caddyhttp/caddyauth/basicauth.go +++ b/modules/caddyhttp/caddyauth/basicauth.go @@ -24,9 +24,8 @@ import ( "strings" "sync" - "golang.org/x/sync/singleflight" - "github.com/caddyserver/caddy/v2" + "golang.org/x/sync/singleflight" ) func init() { diff --git a/modules/caddyhttp/caddyauth/bcrypt.go b/modules/caddyhttp/caddyauth/bcrypt.go index f6940996eaa..35d38d4a410 100644 --- a/modules/caddyhttp/caddyauth/bcrypt.go +++ b/modules/caddyhttp/caddyauth/bcrypt.go @@ -17,9 +17,8 @@ package caddyauth import ( "errors" - "golang.org/x/crypto/bcrypt" - "github.com/caddyserver/caddy/v2" + "golang.org/x/crypto/bcrypt" ) func init() { diff --git a/modules/caddyhttp/caddyauth/caddyauth.go b/modules/caddyhttp/caddyauth/caddyauth.go index 792c198ee5f..17ad462c396 100644 --- a/modules/caddyhttp/caddyauth/caddyauth.go +++ b/modules/caddyhttp/caddyauth/caddyauth.go @@ -18,11 +18,10 @@ import ( "fmt" "net/http" - "go.uber.org/zap" - "go.uber.org/zap/zapcore" - "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/modules/caddyhttp" + "go.uber.org/zap" + "go.uber.org/zap/zapcore" ) func init() { diff --git a/modules/caddyhttp/caddyauth/command.go b/modules/caddyhttp/caddyauth/command.go index e9c513005f2..c22200fb432 100644 --- a/modules/caddyhttp/caddyauth/command.go +++ b/modules/caddyhttp/caddyauth/command.go @@ -21,12 +21,10 @@ import ( "os" "os/signal" + "github.com/caddyserver/caddy/v2" + caddycmd "github.com/caddyserver/caddy/v2/cmd" "github.com/spf13/cobra" "golang.org/x/term" - - caddycmd "github.com/caddyserver/caddy/v2/cmd" - - "github.com/caddyserver/caddy/v2" ) func init() { diff --git a/modules/caddyhttp/celmatcher.go b/modules/caddyhttp/celmatcher.go index 66a60b817c7..7a41b360545 100644 --- a/modules/caddyhttp/celmatcher.go +++ b/modules/caddyhttp/celmatcher.go @@ -25,6 +25,8 @@ import ( "strings" "time" + "github.com/caddyserver/caddy/v2" + "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" "github.com/google/cel-go/cel" "github.com/google/cel-go/common" "github.com/google/cel-go/common/ast" @@ -37,9 +39,6 @@ import ( "github.com/google/cel-go/interpreter/functions" "github.com/google/cel-go/parser" "go.uber.org/zap" - - "github.com/caddyserver/caddy/v2" - "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" ) func init() { diff --git a/modules/caddyhttp/encode/gzip/gzip.go b/modules/caddyhttp/encode/gzip/gzip.go index 40f37ab8e35..c9d7e56757e 100644 --- a/modules/caddyhttp/encode/gzip/gzip.go +++ b/modules/caddyhttp/encode/gzip/gzip.go @@ -18,11 +18,10 @@ import ( "fmt" "strconv" - "github.com/klauspost/compress/gzip" - "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" "github.com/caddyserver/caddy/v2/modules/caddyhttp/encode" + "github.com/klauspost/compress/gzip" ) func init() { diff --git a/modules/caddyhttp/encode/zstd/zstd.go b/modules/caddyhttp/encode/zstd/zstd.go index 1706de89db7..5e3a080f4bc 100644 --- a/modules/caddyhttp/encode/zstd/zstd.go +++ b/modules/caddyhttp/encode/zstd/zstd.go @@ -17,11 +17,10 @@ package caddyzstd import ( "fmt" - "github.com/klauspost/compress/zstd" - "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" "github.com/caddyserver/caddy/v2/modules/caddyhttp/encode" + "github.com/klauspost/compress/zstd" ) func init() { diff --git a/modules/caddyhttp/fileserver/browse.go b/modules/caddyhttp/fileserver/browse.go index 52aa7a9f8e5..3925710fb79 100644 --- a/modules/caddyhttp/fileserver/browse.go +++ b/modules/caddyhttp/fileserver/browse.go @@ -32,12 +32,11 @@ import ( "text/template" "time" - "go.uber.org/zap" - "go.uber.org/zap/zapcore" - "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/modules/caddyhttp" "github.com/caddyserver/caddy/v2/modules/caddyhttp/templates" + "go.uber.org/zap" + "go.uber.org/zap/zapcore" ) // BrowseTemplate is the default template document to use for diff --git a/modules/caddyhttp/fileserver/browsetplcontext.go b/modules/caddyhttp/fileserver/browsetplcontext.go index b9489c6a6dc..7ac705bcd28 100644 --- a/modules/caddyhttp/fileserver/browsetplcontext.go +++ b/modules/caddyhttp/fileserver/browsetplcontext.go @@ -27,12 +27,11 @@ import ( "strings" "time" + "github.com/caddyserver/caddy/v2" + "github.com/caddyserver/caddy/v2/modules/caddyhttp" "github.com/dustin/go-humanize" "go.uber.org/zap" "go.uber.org/zap/zapcore" - - "github.com/caddyserver/caddy/v2" - "github.com/caddyserver/caddy/v2/modules/caddyhttp" ) func (fsrv *FileServer) directoryListing(ctx context.Context, fileSystem fs.FS, parentModTime time.Time, entries []fs.DirEntry, canGoUp bool, root, urlPath string, repl *caddy.Replacer) *browseTemplateContext { diff --git a/modules/caddyhttp/fileserver/command.go b/modules/caddyhttp/fileserver/command.go index a04d7cade07..c1582368ae2 100644 --- a/modules/caddyhttp/fileserver/command.go +++ b/modules/caddyhttp/fileserver/command.go @@ -23,17 +23,15 @@ import ( "strconv" "time" - "github.com/caddyserver/certmagic" - "github.com/spf13/cobra" - "go.uber.org/zap" - - caddycmd "github.com/caddyserver/caddy/v2/cmd" - "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/caddyconfig" + caddycmd "github.com/caddyserver/caddy/v2/cmd" "github.com/caddyserver/caddy/v2/modules/caddyhttp" "github.com/caddyserver/caddy/v2/modules/caddyhttp/encode" caddytpl "github.com/caddyserver/caddy/v2/modules/caddyhttp/templates" + "github.com/caddyserver/certmagic" + "github.com/spf13/cobra" + "go.uber.org/zap" ) func init() { diff --git a/modules/caddyhttp/fileserver/matcher.go b/modules/caddyhttp/fileserver/matcher.go index fbcd36e0aa8..2e31f567ea8 100644 --- a/modules/caddyhttp/fileserver/matcher.go +++ b/modules/caddyhttp/fileserver/matcher.go @@ -25,6 +25,9 @@ import ( "strconv" "strings" + "github.com/caddyserver/caddy/v2" + "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" + "github.com/caddyserver/caddy/v2/modules/caddyhttp" "github.com/google/cel-go/cel" "github.com/google/cel-go/common" "github.com/google/cel-go/common/ast" @@ -34,10 +37,6 @@ import ( "github.com/google/cel-go/parser" "go.uber.org/zap" "go.uber.org/zap/zapcore" - - "github.com/caddyserver/caddy/v2" - "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" - "github.com/caddyserver/caddy/v2/modules/caddyhttp" ) func init() { diff --git a/modules/caddyhttp/fileserver/staticfiles.go b/modules/caddyhttp/fileserver/staticfiles.go index 3daf8daefc1..5ee0030e9c4 100644 --- a/modules/caddyhttp/fileserver/staticfiles.go +++ b/modules/caddyhttp/fileserver/staticfiles.go @@ -30,12 +30,11 @@ import ( "strconv" "strings" - "go.uber.org/zap" - "go.uber.org/zap/zapcore" - "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/modules/caddyhttp" "github.com/caddyserver/caddy/v2/modules/caddyhttp/encode" + "go.uber.org/zap" + "go.uber.org/zap/zapcore" ) func init() { diff --git a/modules/caddyhttp/intercept/intercept.go b/modules/caddyhttp/intercept/intercept.go index bacdc74b533..31a2ff18957 100644 --- a/modules/caddyhttp/intercept/intercept.go +++ b/modules/caddyhttp/intercept/intercept.go @@ -23,13 +23,12 @@ import ( "strings" "sync" - "go.uber.org/zap" - "go.uber.org/zap/zapcore" - "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" "github.com/caddyserver/caddy/v2/caddyconfig/httpcaddyfile" "github.com/caddyserver/caddy/v2/modules/caddyhttp" + "go.uber.org/zap" + "go.uber.org/zap/zapcore" ) func init() { diff --git a/modules/caddyhttp/ip_matchers.go b/modules/caddyhttp/ip_matchers.go index 9335112e8be..be261e955a5 100644 --- a/modules/caddyhttp/ip_matchers.go +++ b/modules/caddyhttp/ip_matchers.go @@ -22,14 +22,13 @@ import ( "net/netip" "strings" + "github.com/caddyserver/caddy/v2" + "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" + "github.com/caddyserver/caddy/v2/internal" "github.com/google/cel-go/cel" "github.com/google/cel-go/common/types/ref" "go.uber.org/zap" "go.uber.org/zap/zapcore" - - "github.com/caddyserver/caddy/v2" - "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" - "github.com/caddyserver/caddy/v2/internal" ) // MatchRemoteIP matches requests by the remote IP address, diff --git a/modules/caddyhttp/logging.go b/modules/caddyhttp/logging.go index e8a1316bd73..d2a855e6595 100644 --- a/modules/caddyhttp/logging.go +++ b/modules/caddyhttp/logging.go @@ -21,10 +21,9 @@ import ( "net/http" "strings" + "github.com/caddyserver/caddy/v2" "go.uber.org/zap" "go.uber.org/zap/zapcore" - - "github.com/caddyserver/caddy/v2" ) // ServerLogConfig describes a server's logging configuration. If diff --git a/modules/caddyhttp/logging/logadd.go b/modules/caddyhttp/logging/logadd.go index 3b554367f93..c2320427019 100644 --- a/modules/caddyhttp/logging/logadd.go +++ b/modules/caddyhttp/logging/logadd.go @@ -18,10 +18,9 @@ import ( "net/http" "strings" - "go.uber.org/zap" - "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/modules/caddyhttp" + "go.uber.org/zap" ) func init() { diff --git a/modules/caddyhttp/matchers.go b/modules/caddyhttp/matchers.go index 22976cfbd20..c8fb2cce7ce 100644 --- a/modules/caddyhttp/matchers.go +++ b/modules/caddyhttp/matchers.go @@ -30,13 +30,12 @@ import ( "strconv" "strings" + "github.com/caddyserver/caddy/v2" + "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" "github.com/google/cel-go/cel" "github.com/google/cel-go/common/types" "github.com/google/cel-go/common/types/ref" "golang.org/x/net/idna" - - "github.com/caddyserver/caddy/v2" - "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" ) type ( diff --git a/modules/caddyhttp/metrics.go b/modules/caddyhttp/metrics.go index 424170732ab..afcfececbd5 100644 --- a/modules/caddyhttp/metrics.go +++ b/modules/caddyhttp/metrics.go @@ -8,11 +8,10 @@ import ( "sync" "time" - "github.com/prometheus/client_golang/prometheus" - "github.com/prometheus/client_golang/prometheus/promauto" - "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/internal/metrics" + "github.com/prometheus/client_golang/prometheus" + "github.com/prometheus/client_golang/prometheus/promauto" ) // Metrics configures metrics observations. diff --git a/modules/caddyhttp/metrics_test.go b/modules/caddyhttp/metrics_test.go index 9f6f598586c..b89ab7ce130 100644 --- a/modules/caddyhttp/metrics_test.go +++ b/modules/caddyhttp/metrics_test.go @@ -10,9 +10,8 @@ import ( "sync" "testing" - "github.com/prometheus/client_golang/prometheus/testutil" - "github.com/caddyserver/caddy/v2" + "github.com/prometheus/client_golang/prometheus/testutil" ) func TestServerNameFromContext(t *testing.T) { diff --git a/modules/caddyhttp/proxyprotocol/listenerwrapper.go b/modules/caddyhttp/proxyprotocol/listenerwrapper.go index f1d170c38ca..8508909cd53 100644 --- a/modules/caddyhttp/proxyprotocol/listenerwrapper.go +++ b/modules/caddyhttp/proxyprotocol/listenerwrapper.go @@ -19,9 +19,8 @@ import ( "net/netip" "time" - goproxy "github.com/pires/go-proxyproto" - "github.com/caddyserver/caddy/v2" + goproxy "github.com/pires/go-proxyproto" ) // ListenerWrapper provides PROXY protocol support to Caddy by implementing diff --git a/modules/caddyhttp/push/handler.go b/modules/caddyhttp/push/handler.go index 1fbe53d8366..8d5527dc034 100644 --- a/modules/caddyhttp/push/handler.go +++ b/modules/caddyhttp/push/handler.go @@ -19,12 +19,11 @@ import ( "net/http" "strings" - "go.uber.org/zap" - "go.uber.org/zap/zapcore" - "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/modules/caddyhttp" "github.com/caddyserver/caddy/v2/modules/caddyhttp/headers" + "go.uber.org/zap" + "go.uber.org/zap/zapcore" ) func init() { diff --git a/modules/caddyhttp/replacer.go b/modules/caddyhttp/replacer.go index 9c3ab85f201..a12e5327d6d 100644 --- a/modules/caddyhttp/replacer.go +++ b/modules/caddyhttp/replacer.go @@ -38,11 +38,10 @@ import ( "strings" "time" - "github.com/google/uuid" - "go.uber.org/zap" - "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/modules/caddytls" + "github.com/google/uuid" + "go.uber.org/zap" ) // NewTestReplacer creates a replacer for an http.Request diff --git a/modules/caddyhttp/requestbody/caddyfile.go b/modules/caddyhttp/requestbody/caddyfile.go index e2382d54683..15ca64cbcb4 100644 --- a/modules/caddyhttp/requestbody/caddyfile.go +++ b/modules/caddyhttp/requestbody/caddyfile.go @@ -17,10 +17,9 @@ package requestbody import ( "time" - "github.com/dustin/go-humanize" - "github.com/caddyserver/caddy/v2/caddyconfig/httpcaddyfile" "github.com/caddyserver/caddy/v2/modules/caddyhttp" + "github.com/dustin/go-humanize" ) func init() { diff --git a/modules/caddyhttp/requestbody/requestbody.go b/modules/caddyhttp/requestbody/requestbody.go index 65b09ded0c8..e88353ef452 100644 --- a/modules/caddyhttp/requestbody/requestbody.go +++ b/modules/caddyhttp/requestbody/requestbody.go @@ -21,11 +21,10 @@ import ( "strings" "time" - "go.uber.org/zap" - "go.uber.org/zap/zapcore" - "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/modules/caddyhttp" + "go.uber.org/zap" + "go.uber.org/zap/zapcore" ) func init() { diff --git a/modules/caddyhttp/reverseproxy/caddyfile.go b/modules/caddyhttp/reverseproxy/caddyfile.go index 8439d1d5157..d52265e6f5d 100644 --- a/modules/caddyhttp/reverseproxy/caddyfile.go +++ b/modules/caddyhttp/reverseproxy/caddyfile.go @@ -22,8 +22,6 @@ import ( "strconv" "strings" - "github.com/dustin/go-humanize" - "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/caddyconfig" "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" @@ -34,6 +32,7 @@ import ( "github.com/caddyserver/caddy/v2/modules/caddyhttp/rewrite" "github.com/caddyserver/caddy/v2/modules/caddytls" "github.com/caddyserver/caddy/v2/modules/internal/network" + "github.com/dustin/go-humanize" ) func init() { diff --git a/modules/caddyhttp/reverseproxy/command.go b/modules/caddyhttp/reverseproxy/command.go index 3f6ffa8cb02..edb53eddc75 100644 --- a/modules/caddyhttp/reverseproxy/command.go +++ b/modules/caddyhttp/reverseproxy/command.go @@ -21,17 +21,15 @@ import ( "strconv" "strings" - "github.com/spf13/cobra" - "go.uber.org/zap" - - caddycmd "github.com/caddyserver/caddy/v2/cmd" - "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/caddyconfig" "github.com/caddyserver/caddy/v2/caddyconfig/httpcaddyfile" + caddycmd "github.com/caddyserver/caddy/v2/cmd" "github.com/caddyserver/caddy/v2/modules/caddyhttp" "github.com/caddyserver/caddy/v2/modules/caddyhttp/headers" "github.com/caddyserver/caddy/v2/modules/caddytls" + "github.com/spf13/cobra" + "go.uber.org/zap" ) func init() { diff --git a/modules/caddyhttp/reverseproxy/fastcgi/client.go b/modules/caddyhttp/reverseproxy/fastcgi/client.go index 48599c27f7f..d1cece0d8f7 100644 --- a/modules/caddyhttp/reverseproxy/fastcgi/client.go +++ b/modules/caddyhttp/reverseproxy/fastcgi/client.go @@ -39,10 +39,9 @@ import ( "strings" "time" + "github.com/caddyserver/caddy/v2/modules/caddyhttp" "go.uber.org/zap" "go.uber.org/zap/zapcore" - - "github.com/caddyserver/caddy/v2/modules/caddyhttp" ) // FCGIListenSockFileno describes listen socket file number. diff --git a/modules/caddyhttp/reverseproxy/fastcgi/fastcgi.go b/modules/caddyhttp/reverseproxy/fastcgi/fastcgi.go index d451dd38019..0dec5a15aa1 100644 --- a/modules/caddyhttp/reverseproxy/fastcgi/fastcgi.go +++ b/modules/caddyhttp/reverseproxy/fastcgi/fastcgi.go @@ -24,13 +24,12 @@ import ( "strings" "time" - "go.uber.org/zap" - "go.uber.org/zap/zapcore" - "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/modules/caddyhttp" "github.com/caddyserver/caddy/v2/modules/caddyhttp/reverseproxy" "github.com/caddyserver/caddy/v2/modules/caddytls" + "go.uber.org/zap" + "go.uber.org/zap/zapcore" ) var noopLogger = zap.NewNop() diff --git a/modules/caddyhttp/reverseproxy/healthchecks.go b/modules/caddyhttp/reverseproxy/healthchecks.go index ac42570b2e1..079ee520107 100644 --- a/modules/caddyhttp/reverseproxy/healthchecks.go +++ b/modules/caddyhttp/reverseproxy/healthchecks.go @@ -28,11 +28,10 @@ import ( "strings" "time" - "go.uber.org/zap" - "go.uber.org/zap/zapcore" - "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/modules/caddyhttp" + "go.uber.org/zap" + "go.uber.org/zap/zapcore" ) // HealthChecks configures active and passive health checks. diff --git a/modules/caddyhttp/reverseproxy/httptransport.go b/modules/caddyhttp/reverseproxy/httptransport.go index 1e4cfa74386..6525e8bff54 100644 --- a/modules/caddyhttp/reverseproxy/httptransport.go +++ b/modules/caddyhttp/reverseproxy/httptransport.go @@ -31,17 +31,16 @@ import ( "strings" "time" - "github.com/pires/go-proxyproto" - "github.com/quic-go/quic-go/http3" - "go.uber.org/zap" - "go.uber.org/zap/zapcore" - "golang.org/x/net/http2" - "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/caddyconfig" "github.com/caddyserver/caddy/v2/modules/caddyhttp" "github.com/caddyserver/caddy/v2/modules/caddytls" "github.com/caddyserver/caddy/v2/modules/internal/network" + "github.com/pires/go-proxyproto" + "github.com/quic-go/quic-go/http3" + "go.uber.org/zap" + "go.uber.org/zap/zapcore" + "golang.org/x/net/http2" ) func init() { diff --git a/modules/caddyhttp/reverseproxy/metrics.go b/modules/caddyhttp/reverseproxy/metrics.go index 2488427304e..2ab73d8ff1a 100644 --- a/modules/caddyhttp/reverseproxy/metrics.go +++ b/modules/caddyhttp/reverseproxy/metrics.go @@ -6,11 +6,10 @@ import ( "sync" "time" + "github.com/caddyserver/caddy/v2" "github.com/prometheus/client_golang/prometheus" "go.uber.org/zap" "go.uber.org/zap/zapcore" - - "github.com/caddyserver/caddy/v2" ) var reverseProxyMetrics = struct { diff --git a/modules/caddyhttp/reverseproxy/reverseproxy.go b/modules/caddyhttp/reverseproxy/reverseproxy.go index 794860d8e02..d6b40cec319 100644 --- a/modules/caddyhttp/reverseproxy/reverseproxy.go +++ b/modules/caddyhttp/reverseproxy/reverseproxy.go @@ -34,16 +34,15 @@ import ( "sync" "time" - "go.uber.org/zap" - "go.uber.org/zap/zapcore" - "golang.org/x/net/http/httpguts" - "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" "github.com/caddyserver/caddy/v2/modules/caddyevents" "github.com/caddyserver/caddy/v2/modules/caddyhttp" "github.com/caddyserver/caddy/v2/modules/caddyhttp/headers" "github.com/caddyserver/caddy/v2/modules/caddyhttp/rewrite" + "go.uber.org/zap" + "go.uber.org/zap/zapcore" + "golang.org/x/net/http/httpguts" ) func init() { diff --git a/modules/caddyhttp/reverseproxy/selectionpolicies.go b/modules/caddyhttp/reverseproxy/selectionpolicies.go index 585fc340067..ae1b5de678f 100644 --- a/modules/caddyhttp/reverseproxy/selectionpolicies.go +++ b/modules/caddyhttp/reverseproxy/selectionpolicies.go @@ -28,12 +28,11 @@ import ( "sync/atomic" "time" - "github.com/cespare/xxhash/v2" - "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/caddyconfig" "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" "github.com/caddyserver/caddy/v2/modules/caddyhttp" + "github.com/cespare/xxhash/v2" ) func init() { diff --git a/modules/caddyhttp/reverseproxy/streaming.go b/modules/caddyhttp/reverseproxy/streaming.go index 66dd106d53c..b3ba3ae58c9 100644 --- a/modules/caddyhttp/reverseproxy/streaming.go +++ b/modules/caddyhttp/reverseproxy/streaming.go @@ -31,11 +31,10 @@ import ( "time" "unsafe" + "github.com/caddyserver/caddy/v2/modules/caddyhttp" "go.uber.org/zap" "go.uber.org/zap/zapcore" "golang.org/x/net/http/httpguts" - - "github.com/caddyserver/caddy/v2/modules/caddyhttp" ) type h2ReadWriteCloser struct { diff --git a/modules/caddyhttp/reverseproxy/upstreams.go b/modules/caddyhttp/reverseproxy/upstreams.go index e9eb7e60ac5..8d2ff8ace3a 100644 --- a/modules/caddyhttp/reverseproxy/upstreams.go +++ b/modules/caddyhttp/reverseproxy/upstreams.go @@ -11,10 +11,9 @@ import ( "sync" "time" + "github.com/caddyserver/caddy/v2" "go.uber.org/zap" "go.uber.org/zap/zapcore" - - "github.com/caddyserver/caddy/v2" ) func init() { diff --git a/modules/caddyhttp/rewrite/rewrite.go b/modules/caddyhttp/rewrite/rewrite.go index 2b18744db2d..325fbda4f79 100644 --- a/modules/caddyhttp/rewrite/rewrite.go +++ b/modules/caddyhttp/rewrite/rewrite.go @@ -22,10 +22,9 @@ import ( "strconv" "strings" - "go.uber.org/zap" - "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/modules/caddyhttp" + "go.uber.org/zap" ) func init() { diff --git a/modules/caddyhttp/server.go b/modules/caddyhttp/server.go index d3760bf3cc9..541bbcd67a3 100644 --- a/modules/caddyhttp/server.go +++ b/modules/caddyhttp/server.go @@ -30,16 +30,15 @@ import ( "sync" "time" + "github.com/caddyserver/caddy/v2" + "github.com/caddyserver/caddy/v2/modules/caddyevents" + "github.com/caddyserver/caddy/v2/modules/caddytls" "github.com/caddyserver/certmagic" "github.com/quic-go/quic-go" "github.com/quic-go/quic-go/http3" "github.com/quic-go/quic-go/qlog" "go.uber.org/zap" "go.uber.org/zap/zapcore" - - "github.com/caddyserver/caddy/v2" - "github.com/caddyserver/caddy/v2/modules/caddyevents" - "github.com/caddyserver/caddy/v2/modules/caddytls" ) // Server describes an HTTP server. diff --git a/modules/caddyhttp/staticresp.go b/modules/caddyhttp/staticresp.go index d783d1b0416..408eaa434cb 100644 --- a/modules/caddyhttp/staticresp.go +++ b/modules/caddyhttp/staticresp.go @@ -28,14 +28,12 @@ import ( "text/template" "time" - "github.com/spf13/cobra" - "go.uber.org/zap" - - caddycmd "github.com/caddyserver/caddy/v2/cmd" - "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/caddyconfig" "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" + caddycmd "github.com/caddyserver/caddy/v2/cmd" + "github.com/spf13/cobra" + "go.uber.org/zap" ) func init() { diff --git a/modules/caddyhttp/templates/templates.go b/modules/caddyhttp/templates/templates.go index eb648865983..9cdc5ea3db6 100644 --- a/modules/caddyhttp/templates/templates.go +++ b/modules/caddyhttp/templates/templates.go @@ -23,10 +23,9 @@ import ( "strings" "text/template" - "go.uber.org/zap" - "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/modules/caddyhttp" + "go.uber.org/zap" ) func init() { diff --git a/modules/caddyhttp/templates/tplcontext.go b/modules/caddyhttp/templates/tplcontext.go index ee553e7a560..4577611fd66 100644 --- a/modules/caddyhttp/templates/tplcontext.go +++ b/modules/caddyhttp/templates/tplcontext.go @@ -33,6 +33,8 @@ import ( "github.com/Masterminds/sprig/v3" chromahtml "github.com/alecthomas/chroma/v2/formatters/html" + "github.com/caddyserver/caddy/v2" + "github.com/caddyserver/caddy/v2/modules/caddyhttp" "github.com/dustin/go-humanize" "github.com/yuin/goldmark" highlighting "github.com/yuin/goldmark-highlighting/v2" @@ -40,9 +42,6 @@ import ( "github.com/yuin/goldmark/parser" gmhtml "github.com/yuin/goldmark/renderer/html" "go.uber.org/zap" - - "github.com/caddyserver/caddy/v2" - "github.com/caddyserver/caddy/v2/modules/caddyhttp" ) // TemplateContext is the TemplateContext with which HTTP templates are executed. diff --git a/modules/caddyhttp/tracing/module.go b/modules/caddyhttp/tracing/module.go index 85fd630020e..272ace5068b 100644 --- a/modules/caddyhttp/tracing/module.go +++ b/modules/caddyhttp/tracing/module.go @@ -4,12 +4,11 @@ import ( "fmt" "net/http" - "go.uber.org/zap" - "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" "github.com/caddyserver/caddy/v2/caddyconfig/httpcaddyfile" "github.com/caddyserver/caddy/v2/modules/caddyhttp" + "go.uber.org/zap" ) func init() { diff --git a/modules/caddyhttp/tracing/tracer.go b/modules/caddyhttp/tracing/tracer.go index ab2ddf8a2e3..ebc42592dc9 100644 --- a/modules/caddyhttp/tracing/tracer.go +++ b/modules/caddyhttp/tracing/tracer.go @@ -5,6 +5,8 @@ import ( "fmt" "net/http" + "github.com/caddyserver/caddy/v2" + "github.com/caddyserver/caddy/v2/modules/caddyhttp" "go.opentelemetry.io/contrib/exporters/autoexport" "go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp" "go.opentelemetry.io/contrib/propagators/autoprop" @@ -14,9 +16,6 @@ import ( semconv "go.opentelemetry.io/otel/semconv/v1.17.0" "go.opentelemetry.io/otel/trace" "go.uber.org/zap" - - "github.com/caddyserver/caddy/v2" - "github.com/caddyserver/caddy/v2/modules/caddyhttp" ) const ( diff --git a/modules/caddyhttp/vars.go b/modules/caddyhttp/vars.go index d01f4a4319e..a501a75e8b1 100644 --- a/modules/caddyhttp/vars.go +++ b/modules/caddyhttp/vars.go @@ -21,11 +21,10 @@ import ( "reflect" "strings" - "github.com/google/cel-go/cel" - "github.com/google/cel-go/common/types/ref" - "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" + "github.com/google/cel-go/cel" + "github.com/google/cel-go/common/types/ref" ) var stringSliceType = reflect.TypeFor[[]string]() diff --git a/modules/caddypki/acmeserver/acmeserver.go b/modules/caddypki/acmeserver/acmeserver.go index aeb4eab8ec3..04d65de4e53 100644 --- a/modules/caddypki/acmeserver/acmeserver.go +++ b/modules/caddypki/acmeserver/acmeserver.go @@ -26,6 +26,9 @@ import ( "strings" "time" + "github.com/caddyserver/caddy/v2" + "github.com/caddyserver/caddy/v2/modules/caddyhttp" + "github.com/caddyserver/caddy/v2/modules/caddypki" "github.com/go-chi/chi/v5" "github.com/smallstep/certificates/acme" "github.com/smallstep/certificates/acme/api" @@ -36,10 +39,6 @@ import ( "github.com/smallstep/nosql" "go.uber.org/zap" "go.uber.org/zap/zapcore" - - "github.com/caddyserver/caddy/v2" - "github.com/caddyserver/caddy/v2/modules/caddyhttp" - "github.com/caddyserver/caddy/v2/modules/caddypki" ) func init() { diff --git a/modules/caddypki/adminapi.go b/modules/caddypki/adminapi.go index 463e31f356e..3e009e06fe5 100644 --- a/modules/caddypki/adminapi.go +++ b/modules/caddypki/adminapi.go @@ -20,9 +20,8 @@ import ( "net/http" "strings" - "go.uber.org/zap" - "github.com/caddyserver/caddy/v2" + "go.uber.org/zap" ) func init() { diff --git a/modules/caddypki/ca.go b/modules/caddypki/ca.go index 5b17518caaa..254861f13e5 100644 --- a/modules/caddypki/ca.go +++ b/modules/caddypki/ca.go @@ -25,13 +25,12 @@ import ( "sync" "time" + "github.com/caddyserver/caddy/v2" "github.com/caddyserver/certmagic" "github.com/smallstep/certificates/authority" "github.com/smallstep/certificates/db" "github.com/smallstep/truststore" "go.uber.org/zap" - - "github.com/caddyserver/caddy/v2" ) // CA describes a certificate authority, which consists of diff --git a/modules/caddypki/command.go b/modules/caddypki/command.go index b7fa1bb7ce1..e78f35c88d0 100644 --- a/modules/caddypki/command.go +++ b/modules/caddypki/command.go @@ -23,12 +23,10 @@ import ( "os" "path" + "github.com/caddyserver/caddy/v2" + caddycmd "github.com/caddyserver/caddy/v2/cmd" "github.com/smallstep/truststore" "github.com/spf13/cobra" - - caddycmd "github.com/caddyserver/caddy/v2/cmd" - - "github.com/caddyserver/caddy/v2" ) func init() { diff --git a/modules/caddypki/pki.go b/modules/caddypki/pki.go index 9f974a956bb..2caeb2b5976 100644 --- a/modules/caddypki/pki.go +++ b/modules/caddypki/pki.go @@ -17,9 +17,8 @@ package caddypki import ( "fmt" - "go.uber.org/zap" - "github.com/caddyserver/caddy/v2" + "go.uber.org/zap" ) func init() { diff --git a/modules/caddytls/acmeissuer.go b/modules/caddytls/acmeissuer.go index 7f13fd71fb9..78c4a65ddbc 100644 --- a/modules/caddytls/acmeissuer.go +++ b/modules/caddytls/acmeissuer.go @@ -26,15 +26,14 @@ import ( "strings" "time" + "github.com/caddyserver/caddy/v2" + "github.com/caddyserver/caddy/v2/caddyconfig" + "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" "github.com/caddyserver/certmagic" "github.com/caddyserver/zerossl" "github.com/mholt/acmez/v3/acme" "go.uber.org/zap" "go.uber.org/zap/zapcore" - - "github.com/caddyserver/caddy/v2" - "github.com/caddyserver/caddy/v2/caddyconfig" - "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" ) func init() { diff --git a/modules/caddytls/automation.go b/modules/caddytls/automation.go index e69b5ad2f8f..14ffdc75023 100644 --- a/modules/caddytls/automation.go +++ b/modules/caddytls/automation.go @@ -24,13 +24,12 @@ import ( "slices" "strings" + "github.com/caddyserver/caddy/v2" "github.com/caddyserver/certmagic" "github.com/mholt/acmez/v3" "go.uber.org/zap" "go.uber.org/zap/zapcore" "golang.org/x/net/idna" - - "github.com/caddyserver/caddy/v2" ) // AutomationConfig governs the automated management of TLS certificates. diff --git a/modules/caddytls/capools.go b/modules/caddytls/capools.go index c73bc4832fd..363ef3ade5b 100644 --- a/modules/caddytls/capools.go +++ b/modules/caddytls/capools.go @@ -12,12 +12,11 @@ import ( "os" "reflect" - "github.com/caddyserver/certmagic" - "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/caddyconfig" "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" "github.com/caddyserver/caddy/v2/modules/caddypki" + "github.com/caddyserver/certmagic" ) func init() { diff --git a/modules/caddytls/certmanagers.go b/modules/caddytls/certmanagers.go index 0a9d459dfbe..ed5afcb4877 100644 --- a/modules/caddytls/certmanagers.go +++ b/modules/caddytls/certmanagers.go @@ -10,13 +10,12 @@ import ( "net/url" "strings" + "github.com/caddyserver/caddy/v2" + "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" "github.com/caddyserver/certmagic" "github.com/tailscale/tscert" "go.uber.org/zap" "go.uber.org/zap/zapcore" - - "github.com/caddyserver/caddy/v2" - "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" ) func init() { diff --git a/modules/caddytls/certselection.go b/modules/caddytls/certselection.go index ac210d3b697..daf4240c65f 100644 --- a/modules/caddytls/certselection.go +++ b/modules/caddytls/certselection.go @@ -22,9 +22,8 @@ import ( "math/big" "slices" - "github.com/caddyserver/certmagic" - "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" + "github.com/caddyserver/certmagic" ) // CustomCertSelectionPolicy represents a policy for selecting the certificate diff --git a/modules/caddytls/connpolicy.go b/modules/caddytls/connpolicy.go index 724271a8e38..ec5620e1f55 100644 --- a/modules/caddytls/connpolicy.go +++ b/modules/caddytls/connpolicy.go @@ -28,13 +28,12 @@ import ( "slices" "strings" - "github.com/mholt/acmez/v3" - "go.uber.org/zap" - "go.uber.org/zap/zapcore" - "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/caddyconfig" "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" + "github.com/mholt/acmez/v3" + "go.uber.org/zap" + "go.uber.org/zap/zapcore" ) func init() { diff --git a/modules/caddytls/distributedstek/distributedstek.go b/modules/caddytls/distributedstek/distributedstek.go index f6d0de064c0..18ed69496c5 100644 --- a/modules/caddytls/distributedstek/distributedstek.go +++ b/modules/caddytls/distributedstek/distributedstek.go @@ -33,10 +33,9 @@ import ( "runtime/debug" "time" - "github.com/caddyserver/certmagic" - "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/modules/caddytls" + "github.com/caddyserver/certmagic" ) func init() { diff --git a/modules/caddytls/ech.go b/modules/caddytls/ech.go index 1b3bacbd226..c47c21a38d4 100644 --- a/modules/caddytls/ech.go +++ b/modules/caddytls/ech.go @@ -13,14 +13,13 @@ import ( "strings" "time" + "github.com/caddyserver/caddy/v2" "github.com/caddyserver/certmagic" "github.com/cloudflare/circl/hpke" "github.com/cloudflare/circl/kem" "github.com/libdns/libdns" "go.uber.org/zap" "golang.org/x/crypto/cryptobyte" - - "github.com/caddyserver/caddy/v2" ) func init() { diff --git a/modules/caddytls/internalissuer.go b/modules/caddytls/internalissuer.go index be779757a87..127b26a84b8 100644 --- a/modules/caddytls/internalissuer.go +++ b/modules/caddytls/internalissuer.go @@ -21,13 +21,12 @@ import ( "encoding/pem" "time" - "github.com/caddyserver/certmagic" - "github.com/smallstep/certificates/authority/provisioner" - "go.uber.org/zap" - "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" "github.com/caddyserver/caddy/v2/modules/caddypki" + "github.com/caddyserver/certmagic" + "github.com/smallstep/certificates/authority/provisioner" + "go.uber.org/zap" ) func init() { diff --git a/modules/caddytls/leafstorageloader.go b/modules/caddytls/leafstorageloader.go index 0215c8af2a6..d966f932c74 100644 --- a/modules/caddytls/leafstorageloader.go +++ b/modules/caddytls/leafstorageloader.go @@ -20,9 +20,8 @@ import ( "encoding/pem" "fmt" - "github.com/caddyserver/certmagic" - "github.com/caddyserver/caddy/v2" + "github.com/caddyserver/certmagic" ) func init() { diff --git a/modules/caddytls/matchers.go b/modules/caddytls/matchers.go index dfbec94cc7a..04d522bbe06 100644 --- a/modules/caddytls/matchers.go +++ b/modules/caddytls/matchers.go @@ -25,13 +25,12 @@ import ( "strconv" "strings" - "github.com/caddyserver/certmagic" - "go.uber.org/zap" - "go.uber.org/zap/zapcore" - "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" "github.com/caddyserver/caddy/v2/internal" + "github.com/caddyserver/certmagic" + "go.uber.org/zap" + "go.uber.org/zap/zapcore" ) func init() { diff --git a/modules/caddytls/ondemand.go b/modules/caddytls/ondemand.go index 0970234cecd..abc27e720f6 100644 --- a/modules/caddytls/ondemand.go +++ b/modules/caddytls/ondemand.go @@ -24,12 +24,11 @@ import ( "net/url" "time" + "github.com/caddyserver/caddy/v2" + "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" "github.com/caddyserver/certmagic" "go.uber.org/zap" "go.uber.org/zap/zapcore" - - "github.com/caddyserver/caddy/v2" - "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" ) func init() { diff --git a/modules/caddytls/storageloader.go b/modules/caddytls/storageloader.go index c9487e89252..f8c1981a2e2 100644 --- a/modules/caddytls/storageloader.go +++ b/modules/caddytls/storageloader.go @@ -19,9 +19,8 @@ import ( "fmt" "strings" - "github.com/caddyserver/certmagic" - "github.com/caddyserver/caddy/v2" + "github.com/caddyserver/certmagic" ) func init() { diff --git a/modules/caddytls/tls.go b/modules/caddytls/tls.go index 7b49c020872..5293b8b1cc4 100644 --- a/modules/caddytls/tls.go +++ b/modules/caddytls/tls.go @@ -27,14 +27,13 @@ import ( "sync" "time" + "github.com/caddyserver/caddy/v2" + "github.com/caddyserver/caddy/v2/internal" + "github.com/caddyserver/caddy/v2/modules/caddyevents" "github.com/caddyserver/certmagic" "github.com/libdns/libdns" "go.uber.org/zap" "go.uber.org/zap/zapcore" - - "github.com/caddyserver/caddy/v2" - "github.com/caddyserver/caddy/v2/internal" - "github.com/caddyserver/caddy/v2/modules/caddyevents" ) func init() { diff --git a/modules/caddytls/zerosslissuer.go b/modules/caddytls/zerosslissuer.go index b8727ab669d..d65f633defe 100644 --- a/modules/caddytls/zerosslissuer.go +++ b/modules/caddytls/zerosslissuer.go @@ -21,12 +21,11 @@ import ( "strconv" "time" - "github.com/caddyserver/certmagic" - "go.uber.org/zap" - "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/caddyconfig" "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" + "github.com/caddyserver/certmagic" + "go.uber.org/zap" ) func init() { diff --git a/modules/filestorage/filestorage.go b/modules/filestorage/filestorage.go index 76aff4e8b7a..2615310dc5d 100644 --- a/modules/filestorage/filestorage.go +++ b/modules/filestorage/filestorage.go @@ -15,10 +15,9 @@ package filestorage import ( - "github.com/caddyserver/certmagic" - "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" + "github.com/caddyserver/certmagic" ) func init() { diff --git a/modules/internal/network/networkproxy.go b/modules/internal/network/networkproxy.go index f9deeb43a96..9307b60b022 100644 --- a/modules/internal/network/networkproxy.go +++ b/modules/internal/network/networkproxy.go @@ -6,10 +6,9 @@ import ( "net/url" "strings" - "go.uber.org/zap" - "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" + "go.uber.org/zap" ) func init() { diff --git a/modules/logging/appendencoder.go b/modules/logging/appendencoder.go index 63bd532d02b..6899aee49b9 100644 --- a/modules/logging/appendencoder.go +++ b/modules/logging/appendencoder.go @@ -21,14 +21,13 @@ import ( "strings" "time" + "github.com/caddyserver/caddy/v2" + "github.com/caddyserver/caddy/v2/caddyconfig" + "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" "go.uber.org/zap" "go.uber.org/zap/buffer" "go.uber.org/zap/zapcore" "golang.org/x/term" - - "github.com/caddyserver/caddy/v2" - "github.com/caddyserver/caddy/v2/caddyconfig" - "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" ) func init() { diff --git a/modules/logging/cores.go b/modules/logging/cores.go index 49aa7640ce3..c2ed9d60794 100644 --- a/modules/logging/cores.go +++ b/modules/logging/cores.go @@ -1,10 +1,9 @@ package logging import ( - "go.uber.org/zap/zapcore" - "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" + "go.uber.org/zap/zapcore" ) func init() { diff --git a/modules/logging/encoders.go b/modules/logging/encoders.go index 5c563114b35..5a3d5b60de1 100644 --- a/modules/logging/encoders.go +++ b/modules/logging/encoders.go @@ -17,12 +17,11 @@ package logging import ( "time" + "github.com/caddyserver/caddy/v2" + "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" "go.uber.org/zap" "go.uber.org/zap/buffer" "go.uber.org/zap/zapcore" - - "github.com/caddyserver/caddy/v2" - "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" ) func init() { diff --git a/modules/logging/filewriter.go b/modules/logging/filewriter.go index c3df562cbe5..32c7af98d8f 100644 --- a/modules/logging/filewriter.go +++ b/modules/logging/filewriter.go @@ -26,10 +26,9 @@ import ( "time" "github.com/DeRuina/timberjack" - "github.com/dustin/go-humanize" - "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" + "github.com/dustin/go-humanize" ) func init() { diff --git a/modules/logging/filterencoder.go b/modules/logging/filterencoder.go index 01333e1951f..6f9290a2803 100644 --- a/modules/logging/filterencoder.go +++ b/modules/logging/filterencoder.go @@ -20,14 +20,13 @@ import ( "os" "time" + "github.com/caddyserver/caddy/v2" + "github.com/caddyserver/caddy/v2/caddyconfig" + "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" "go.uber.org/zap" "go.uber.org/zap/buffer" "go.uber.org/zap/zapcore" "golang.org/x/term" - - "github.com/caddyserver/caddy/v2" - "github.com/caddyserver/caddy/v2/caddyconfig" - "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" ) func init() { diff --git a/modules/logging/filters.go b/modules/logging/filters.go index a2ce6502fd5..4961cb11534 100644 --- a/modules/logging/filters.go +++ b/modules/logging/filters.go @@ -25,11 +25,10 @@ import ( "strconv" "strings" - "go.uber.org/zap/zapcore" - "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" "github.com/caddyserver/caddy/v2/modules/caddyhttp" + "go.uber.org/zap/zapcore" ) func init() { diff --git a/modules/logging/filters_test.go b/modules/logging/filters_test.go index cf35e717827..8e6d44c8f72 100644 --- a/modules/logging/filters_test.go +++ b/modules/logging/filters_test.go @@ -5,10 +5,9 @@ import ( "strings" "testing" - "go.uber.org/zap/zapcore" - "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/modules/caddyhttp" + "go.uber.org/zap/zapcore" ) func TestIPMaskSingleValue(t *testing.T) { diff --git a/modules/metrics/adminmetrics.go b/modules/metrics/adminmetrics.go index 1e3a841ddb2..39394401188 100644 --- a/modules/metrics/adminmetrics.go +++ b/modules/metrics/adminmetrics.go @@ -18,9 +18,8 @@ import ( "errors" "net/http" - "github.com/prometheus/client_golang/prometheus" - "github.com/caddyserver/caddy/v2" + "github.com/prometheus/client_golang/prometheus" ) func init() { diff --git a/modules/metrics/metrics.go b/modules/metrics/metrics.go index 42b30d88dd7..15a3794a0ff 100644 --- a/modules/metrics/metrics.go +++ b/modules/metrics/metrics.go @@ -18,14 +18,13 @@ import ( "errors" "net/http" - "github.com/prometheus/client_golang/prometheus" - "github.com/prometheus/client_golang/prometheus/promhttp" - "go.uber.org/zap" - "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" "github.com/caddyserver/caddy/v2/caddyconfig/httpcaddyfile" "github.com/caddyserver/caddy/v2/modules/caddyhttp" + "github.com/prometheus/client_golang/prometheus" + "github.com/prometheus/client_golang/prometheus/promhttp" + "go.uber.org/zap" ) func init() { diff --git a/service_windows.go b/service_windows.go index 4720dbaa47b..357c9ac8ef1 100644 --- a/service_windows.go +++ b/service_windows.go @@ -18,9 +18,8 @@ import ( "os" "path/filepath" - "golang.org/x/sys/windows/svc" - "github.com/caddyserver/caddy/v2/notify" + "golang.org/x/sys/windows/svc" ) func init() { From 2f56d9c7ffb43b90394fd0c0a9e3f8a6581b459e Mon Sep 17 00:00:00 2001 From: Aaron Paterson Date: Thu, 6 Nov 2025 02:38:54 -0700 Subject: [PATCH 49/51] update default_bind --- caddyconfig/httpcaddyfile/options.go | 11 ++++++++--- 1 file changed, 8 insertions(+), 3 deletions(-) diff --git a/caddyconfig/httpcaddyfile/options.go b/caddyconfig/httpcaddyfile/options.go index 859e6d50b9a..0d4b7e6574b 100644 --- a/caddyconfig/httpcaddyfile/options.go +++ b/caddyconfig/httpcaddyfile/options.go @@ -306,8 +306,7 @@ func parseOptSingleString(d *caddyfile.Dispenser, _ any) (any, error) { func parseOptDefaultBind(d *caddyfile.Dispenser, _ any) (any, error) { d.Next() // consume option name - - var addresses, protocols []string + var addresses, interfaces, protocols []string addresses = d.RemainingArgs() if len(addresses) == 0 { @@ -316,6 +315,11 @@ func parseOptDefaultBind(d *caddyfile.Dispenser, _ any) (any, error) { for d.NextBlock(0) { switch d.Val() { + case "interfaces": + interfaces = d.RemainingArgs() + if len(interfaces) == 0 { + return nil, d.Errf("interfaces requires one or more arguments") + } case "protocols": protocols = d.RemainingArgs() if len(protocols) == 0 { @@ -326,8 +330,9 @@ func parseOptDefaultBind(d *caddyfile.Dispenser, _ any) (any, error) { } } - return []ConfigValue{{Class: "bind", Value: addressesWithProtocols{ + return []ConfigValue{{Class: "bind", Value: bindOptions{ addresses: addresses, + interfaces: interfaces, protocols: protocols, }}}, nil } From 9ad426b29d7d150741986df5c8c9335693939ca1 Mon Sep 17 00:00:00 2001 From: Aaron Paterson Date: Thu, 6 Nov 2025 02:48:17 -0700 Subject: [PATCH 50/51] golangci-lint fmt --- caddy.go | 5 +++-- caddyconfig/caddyfile/importargs.go | 3 ++- caddyconfig/caddyfile/parse.go | 3 ++- caddyconfig/httpcaddyfile/addresses.go | 5 +++-- caddyconfig/httpcaddyfile/builtins.go | 7 ++++--- caddyconfig/httpcaddyfile/httptype.go | 3 ++- caddyconfig/httpcaddyfile/options.go | 11 ++++++----- caddyconfig/httpcaddyfile/serveroptions.go | 3 ++- caddyconfig/httpcaddyfile/tlsapp.go | 5 +++-- caddytest/caddytest.go | 4 +++- caddytest/integration/acme_test.go | 5 +++-- caddytest/integration/acmeserver_test.go | 3 ++- caddytest/integration/mockdns_test.go | 5 +++-- caddytest/integration/stream_test.go | 3 ++- cmd/caddy/main.go | 1 + cmd/cobra.go | 3 ++- cmd/commandfuncs.go | 3 ++- cmd/commands.go | 3 ++- cmd/main.go | 5 +++-- cmd/packagesfuncs.go | 3 ++- cmd/storagefuncs.go | 3 ++- context.go | 3 ++- listeners.go | 3 ++- logging.go | 3 ++- metrics.go | 3 ++- modules/caddyevents/app.go | 3 ++- modules/caddyfs/filesystem.go | 3 ++- modules/caddyhttp/app.go | 5 +++-- modules/caddyhttp/autohttps.go | 5 +++-- modules/caddyhttp/caddyauth/argon2id.go | 3 ++- modules/caddyhttp/caddyauth/basicauth.go | 3 ++- modules/caddyhttp/caddyauth/bcrypt.go | 3 ++- modules/caddyhttp/caddyauth/caddyauth.go | 5 +++-- modules/caddyhttp/caddyauth/command.go | 6 ++++-- modules/caddyhttp/celmatcher.go | 5 +++-- modules/caddyhttp/encode/gzip/gzip.go | 3 ++- modules/caddyhttp/encode/zstd/zstd.go | 3 ++- modules/caddyhttp/fileserver/browse.go | 5 +++-- modules/caddyhttp/fileserver/browsetplcontext.go | 5 +++-- modules/caddyhttp/fileserver/command.go | 10 ++++++---- modules/caddyhttp/fileserver/matcher.go | 7 ++++--- modules/caddyhttp/fileserver/staticfiles.go | 5 +++-- modules/caddyhttp/intercept/intercept.go | 5 +++-- modules/caddyhttp/ip_matchers.go | 7 ++++--- modules/caddyhttp/logging.go | 3 ++- modules/caddyhttp/logging/logadd.go | 3 ++- modules/caddyhttp/matchers.go | 5 +++-- modules/caddyhttp/metrics.go | 5 +++-- modules/caddyhttp/metrics_test.go | 3 ++- modules/caddyhttp/proxyprotocol/listenerwrapper.go | 3 ++- modules/caddyhttp/push/handler.go | 5 +++-- modules/caddyhttp/replacer.go | 5 +++-- modules/caddyhttp/requestbody/caddyfile.go | 3 ++- modules/caddyhttp/requestbody/requestbody.go | 5 +++-- modules/caddyhttp/reverseproxy/caddyfile.go | 3 ++- modules/caddyhttp/reverseproxy/command.go | 8 +++++--- modules/caddyhttp/reverseproxy/fastcgi/client.go | 3 ++- modules/caddyhttp/reverseproxy/fastcgi/fastcgi.go | 5 +++-- modules/caddyhttp/reverseproxy/healthchecks.go | 5 +++-- modules/caddyhttp/reverseproxy/httptransport.go | 11 ++++++----- modules/caddyhttp/reverseproxy/metrics.go | 3 ++- modules/caddyhttp/reverseproxy/reverseproxy.go | 7 ++++--- modules/caddyhttp/reverseproxy/selectionpolicies.go | 3 ++- modules/caddyhttp/reverseproxy/streaming.go | 3 ++- modules/caddyhttp/reverseproxy/upstreams.go | 3 ++- modules/caddyhttp/rewrite/rewrite.go | 3 ++- modules/caddyhttp/server.go | 7 ++++--- modules/caddyhttp/staticresp.go | 8 +++++--- modules/caddyhttp/templates/templates.go | 3 ++- modules/caddyhttp/templates/tplcontext.go | 5 +++-- modules/caddyhttp/tracing/module.go | 3 ++- modules/caddyhttp/tracing/tracer.go | 5 +++-- modules/caddyhttp/vars.go | 5 +++-- modules/caddypki/acmeserver/acmeserver.go | 7 ++++--- modules/caddypki/adminapi.go | 3 ++- modules/caddypki/ca.go | 3 ++- modules/caddypki/command.go | 6 ++++-- modules/caddypki/pki.go | 3 ++- modules/caddytls/acmeissuer.go | 7 ++++--- modules/caddytls/automation.go | 3 ++- modules/caddytls/capools.go | 3 ++- modules/caddytls/certmanagers.go | 5 +++-- modules/caddytls/certselection.go | 3 ++- modules/caddytls/connpolicy.go | 7 ++++--- modules/caddytls/distributedstek/distributedstek.go | 3 ++- modules/caddytls/ech.go | 3 ++- modules/caddytls/internalissuer.go | 7 ++++--- modules/caddytls/leafstorageloader.go | 3 ++- modules/caddytls/matchers.go | 7 ++++--- modules/caddytls/ondemand.go | 5 +++-- modules/caddytls/storageloader.go | 3 ++- modules/caddytls/tls.go | 7 ++++--- modules/caddytls/zerosslissuer.go | 5 +++-- modules/filestorage/filestorage.go | 3 ++- modules/internal/network/networkproxy.go | 3 ++- modules/logging/appendencoder.go | 7 ++++--- modules/logging/cores.go | 3 ++- modules/logging/encoders.go | 5 +++-- modules/logging/filewriter.go | 3 ++- modules/logging/filterencoder.go | 7 ++++--- modules/logging/filters.go | 3 ++- modules/logging/filters_test.go | 3 ++- modules/metrics/adminmetrics.go | 3 ++- modules/metrics/metrics.go | 7 ++++--- service_windows.go | 3 ++- 105 files changed, 288 insertions(+), 177 deletions(-) diff --git a/caddy.go b/caddy.go index 990ebaac5c1..5f71d8e8b53 100644 --- a/caddy.go +++ b/caddy.go @@ -35,11 +35,12 @@ import ( "sync/atomic" "time" - "github.com/caddyserver/caddy/v2/internal/filesystems" - "github.com/caddyserver/caddy/v2/notify" "github.com/caddyserver/certmagic" "github.com/google/uuid" "go.uber.org/zap" + + "github.com/caddyserver/caddy/v2/internal/filesystems" + "github.com/caddyserver/caddy/v2/notify" ) // Config is the top (or beginning) of the Caddy configuration structure. diff --git a/caddyconfig/caddyfile/importargs.go b/caddyconfig/caddyfile/importargs.go index ee9a51ba001..b2eb3e834dd 100644 --- a/caddyconfig/caddyfile/importargs.go +++ b/caddyconfig/caddyfile/importargs.go @@ -19,8 +19,9 @@ import ( "strconv" "strings" - "github.com/caddyserver/caddy/v2" "go.uber.org/zap" + + "github.com/caddyserver/caddy/v2" ) // parseVariadic determines if the token is a variadic placeholder, diff --git a/caddyconfig/caddyfile/parse.go b/caddyconfig/caddyfile/parse.go index 26ec862a555..8439f3731df 100644 --- a/caddyconfig/caddyfile/parse.go +++ b/caddyconfig/caddyfile/parse.go @@ -22,8 +22,9 @@ import ( "path/filepath" "strings" - "github.com/caddyserver/caddy/v2" "go.uber.org/zap" + + "github.com/caddyserver/caddy/v2" ) // Parse parses the input just enough to group tokens, in diff --git a/caddyconfig/httpcaddyfile/addresses.go b/caddyconfig/httpcaddyfile/addresses.go index f31845d4dd4..c9dc9fc9688 100644 --- a/caddyconfig/httpcaddyfile/addresses.go +++ b/caddyconfig/httpcaddyfile/addresses.go @@ -24,11 +24,12 @@ import ( "strings" "unicode" + "github.com/caddyserver/certmagic" + "go.uber.org/zap" + "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" "github.com/caddyserver/caddy/v2/modules/caddyhttp" - "github.com/caddyserver/certmagic" - "go.uber.org/zap" ) // mapAddressToProtocolToServerBlocks returns a map of listener address to list of server diff --git a/caddyconfig/httpcaddyfile/builtins.go b/caddyconfig/httpcaddyfile/builtins.go index 25c5fb9e09b..a0eb770470b 100644 --- a/caddyconfig/httpcaddyfile/builtins.go +++ b/caddyconfig/httpcaddyfile/builtins.go @@ -24,14 +24,15 @@ import ( "strings" "time" + "github.com/caddyserver/certmagic" + "github.com/mholt/acmez/v3/acme" + "go.uber.org/zap/zapcore" + "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/caddyconfig" "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" "github.com/caddyserver/caddy/v2/modules/caddyhttp" "github.com/caddyserver/caddy/v2/modules/caddytls" - "github.com/caddyserver/certmagic" - "github.com/mholt/acmez/v3/acme" - "go.uber.org/zap/zapcore" ) func init() { diff --git a/caddyconfig/httpcaddyfile/httptype.go b/caddyconfig/httpcaddyfile/httptype.go index b7ddfe7e2f5..3dcd3ea5b62 100644 --- a/caddyconfig/httpcaddyfile/httptype.go +++ b/caddyconfig/httpcaddyfile/httptype.go @@ -25,13 +25,14 @@ import ( "strconv" "strings" + "go.uber.org/zap" + "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/caddyconfig" "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" "github.com/caddyserver/caddy/v2/modules/caddyhttp" "github.com/caddyserver/caddy/v2/modules/caddypki" "github.com/caddyserver/caddy/v2/modules/caddytls" - "go.uber.org/zap" ) func init() { diff --git a/caddyconfig/httpcaddyfile/options.go b/caddyconfig/httpcaddyfile/options.go index 0d4b7e6574b..c605ff21138 100644 --- a/caddyconfig/httpcaddyfile/options.go +++ b/caddyconfig/httpcaddyfile/options.go @@ -18,14 +18,15 @@ import ( "slices" "strconv" + "github.com/caddyserver/certmagic" + "github.com/libdns/libdns" + "github.com/mholt/acmez/v3/acme" + "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/caddyconfig" "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" "github.com/caddyserver/caddy/v2/modules/caddyhttp" "github.com/caddyserver/caddy/v2/modules/caddytls" - "github.com/caddyserver/certmagic" - "github.com/libdns/libdns" - "github.com/mholt/acmez/v3/acme" ) func init() { @@ -331,9 +332,9 @@ func parseOptDefaultBind(d *caddyfile.Dispenser, _ any) (any, error) { } return []ConfigValue{{Class: "bind", Value: bindOptions{ - addresses: addresses, + addresses: addresses, interfaces: interfaces, - protocols: protocols, + protocols: protocols, }}}, nil } diff --git a/caddyconfig/httpcaddyfile/serveroptions.go b/caddyconfig/httpcaddyfile/serveroptions.go index 5c8132b7904..9431f1aed58 100644 --- a/caddyconfig/httpcaddyfile/serveroptions.go +++ b/caddyconfig/httpcaddyfile/serveroptions.go @@ -20,11 +20,12 @@ import ( "slices" "strconv" + "github.com/dustin/go-humanize" + "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/caddyconfig" "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" "github.com/caddyserver/caddy/v2/modules/caddyhttp" - "github.com/dustin/go-humanize" ) // serverOptions collects server config overrides parsed from Caddyfile global options diff --git a/caddyconfig/httpcaddyfile/tlsapp.go b/caddyconfig/httpcaddyfile/tlsapp.go index c67407ddbc1..b04d42daf48 100644 --- a/caddyconfig/httpcaddyfile/tlsapp.go +++ b/caddyconfig/httpcaddyfile/tlsapp.go @@ -24,12 +24,13 @@ import ( "strconv" "strings" + "github.com/caddyserver/certmagic" + "github.com/mholt/acmez/v3/acme" + "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/caddyconfig" "github.com/caddyserver/caddy/v2/modules/caddyhttp" "github.com/caddyserver/caddy/v2/modules/caddytls" - "github.com/caddyserver/certmagic" - "github.com/mholt/acmez/v3/acme" ) func (st ServerType) buildTLSApp( diff --git a/caddytest/caddytest.go b/caddytest/caddytest.go index 249ae464a73..7b56bb281cc 100644 --- a/caddytest/caddytest.go +++ b/caddytest/caddytest.go @@ -23,8 +23,10 @@ import ( "time" "github.com/aryann/difflib" - "github.com/caddyserver/caddy/v2/caddyconfig" + caddycmd "github.com/caddyserver/caddy/v2/cmd" + + "github.com/caddyserver/caddy/v2/caddyconfig" // plug in Caddy modules here _ "github.com/caddyserver/caddy/v2/modules/standard" ) diff --git a/caddytest/integration/acme_test.go b/caddytest/integration/acme_test.go index d7e4c296d50..f10aef6a86d 100644 --- a/caddytest/integration/acme_test.go +++ b/caddytest/integration/acme_test.go @@ -12,13 +12,14 @@ import ( "strings" "testing" - "github.com/caddyserver/caddy/v2" - "github.com/caddyserver/caddy/v2/caddytest" "github.com/mholt/acmez/v3" "github.com/mholt/acmez/v3/acme" smallstepacme "github.com/smallstep/certificates/acme" "go.uber.org/zap" "go.uber.org/zap/exp/zapslog" + + "github.com/caddyserver/caddy/v2" + "github.com/caddyserver/caddy/v2/caddytest" ) const acmeChallengePort = 9081 diff --git a/caddytest/integration/acmeserver_test.go b/caddytest/integration/acmeserver_test.go index ca5845f8711..d6a9ba005ad 100644 --- a/caddytest/integration/acmeserver_test.go +++ b/caddytest/integration/acmeserver_test.go @@ -9,11 +9,12 @@ import ( "strings" "testing" - "github.com/caddyserver/caddy/v2/caddytest" "github.com/mholt/acmez/v3" "github.com/mholt/acmez/v3/acme" "go.uber.org/zap" "go.uber.org/zap/exp/zapslog" + + "github.com/caddyserver/caddy/v2/caddytest" ) func TestACMEServerDirectory(t *testing.T) { diff --git a/caddytest/integration/mockdns_test.go b/caddytest/integration/mockdns_test.go index 9963bdf950d..e55a6df583c 100644 --- a/caddytest/integration/mockdns_test.go +++ b/caddytest/integration/mockdns_test.go @@ -3,10 +3,11 @@ package integration import ( "context" - "github.com/caddyserver/caddy/v2" - "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" "github.com/caddyserver/certmagic" "github.com/libdns/libdns" + + "github.com/caddyserver/caddy/v2" + "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" ) func init() { diff --git a/caddytest/integration/stream_test.go b/caddytest/integration/stream_test.go index d2f2fd79b95..57231a5271b 100644 --- a/caddytest/integration/stream_test.go +++ b/caddytest/integration/stream_test.go @@ -13,9 +13,10 @@ import ( "testing" "time" - "github.com/caddyserver/caddy/v2/caddytest" "golang.org/x/net/http2" "golang.org/x/net/http2/h2c" + + "github.com/caddyserver/caddy/v2/caddytest" ) // (see https://github.com/caddyserver/caddy/issues/3556 for use case) diff --git a/cmd/caddy/main.go b/cmd/caddy/main.go index 425b8954f95..48fa149aa08 100644 --- a/cmd/caddy/main.go +++ b/cmd/caddy/main.go @@ -30,6 +30,7 @@ package main import ( caddycmd "github.com/caddyserver/caddy/v2/cmd" + // plug in Caddy modules here _ "github.com/caddyserver/caddy/v2/modules/standard" ) diff --git a/cmd/cobra.go b/cmd/cobra.go index 8d6d23b4841..9ecb389e2aa 100644 --- a/cmd/cobra.go +++ b/cmd/cobra.go @@ -3,8 +3,9 @@ package caddycmd import ( "fmt" - "github.com/caddyserver/caddy/v2" "github.com/spf13/cobra" + + "github.com/caddyserver/caddy/v2" ) var defaultFactory = newRootCommandFactory(func() *cobra.Command { diff --git a/cmd/commandfuncs.go b/cmd/commandfuncs.go index 690c4b2eb4f..75d1149926c 100644 --- a/cmd/commandfuncs.go +++ b/cmd/commandfuncs.go @@ -34,11 +34,12 @@ import ( "strings" "github.com/aryann/difflib" + "go.uber.org/zap" + "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/caddyconfig" "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" "github.com/caddyserver/caddy/v2/internal" - "go.uber.org/zap" ) func cmdStart(fl Flags) (int, error) { diff --git a/cmd/commands.go b/cmd/commands.go index 0a5ad66cfc1..c9ea636b9d0 100644 --- a/cmd/commands.go +++ b/cmd/commands.go @@ -22,9 +22,10 @@ import ( "strings" "sync" - "github.com/caddyserver/caddy/v2" "github.com/spf13/cobra" "github.com/spf13/cobra/doc" + + "github.com/caddyserver/caddy/v2" ) // Command represents a subcommand. Name, Func, diff --git a/cmd/main.go b/cmd/main.go index 9b7b3cebb02..411f4545d33 100644 --- a/cmd/main.go +++ b/cmd/main.go @@ -35,13 +35,14 @@ import ( "time" "github.com/KimMachineGun/automemlimit/memlimit" - "github.com/caddyserver/caddy/v2" - "github.com/caddyserver/caddy/v2/caddyconfig" "github.com/caddyserver/certmagic" "github.com/spf13/pflag" "go.uber.org/automaxprocs/maxprocs" "go.uber.org/zap" "go.uber.org/zap/exp/zapslog" + + "github.com/caddyserver/caddy/v2" + "github.com/caddyserver/caddy/v2/caddyconfig" ) func init() { diff --git a/cmd/packagesfuncs.go b/cmd/packagesfuncs.go index 5d7ab615656..4d0ff068038 100644 --- a/cmd/packagesfuncs.go +++ b/cmd/packagesfuncs.go @@ -28,8 +28,9 @@ import ( "runtime/debug" "strings" - "github.com/caddyserver/caddy/v2" "go.uber.org/zap" + + "github.com/caddyserver/caddy/v2" ) func cmdUpgrade(fl Flags) (int, error) { diff --git a/cmd/storagefuncs.go b/cmd/storagefuncs.go index f2bce68517e..5606fe4ae98 100644 --- a/cmd/storagefuncs.go +++ b/cmd/storagefuncs.go @@ -24,8 +24,9 @@ import ( "io/fs" "os" - "github.com/caddyserver/caddy/v2" "github.com/caddyserver/certmagic" + + "github.com/caddyserver/caddy/v2" ) type storVal struct { diff --git a/context.go b/context.go index d36d5640091..4c11399360d 100644 --- a/context.go +++ b/context.go @@ -22,12 +22,13 @@ import ( "log/slog" "reflect" - "github.com/caddyserver/caddy/v2/internal/filesystems" "github.com/caddyserver/certmagic" "github.com/prometheus/client_golang/prometheus" "github.com/prometheus/client_golang/prometheus/collectors" "go.uber.org/zap" "go.uber.org/zap/exp/zapslog" + + "github.com/caddyserver/caddy/v2/internal/filesystems" ) // Context is a type which defines the lifetime of modules that diff --git a/listeners.go b/listeners.go index a664b90f63e..286a76599af 100644 --- a/listeners.go +++ b/listeners.go @@ -29,12 +29,13 @@ import ( "sync" "sync/atomic" - "github.com/caddyserver/caddy/v2/internal" "github.com/quic-go/quic-go" "github.com/quic-go/quic-go/http3" "github.com/quic-go/quic-go/qlog" "go.uber.org/zap" "golang.org/x/time/rate" + + "github.com/caddyserver/caddy/v2/internal" ) // NetworkAddress represents one or more network addresses. diff --git a/logging.go b/logging.go index 8004c7ff776..2734b542517 100644 --- a/logging.go +++ b/logging.go @@ -25,10 +25,11 @@ import ( "sync" "time" - "github.com/caddyserver/caddy/v2/internal" "go.uber.org/zap" "go.uber.org/zap/zapcore" "golang.org/x/term" + + "github.com/caddyserver/caddy/v2/internal" ) func init() { diff --git a/metrics.go b/metrics.go index cc5181592cc..0ee3853eb85 100644 --- a/metrics.go +++ b/metrics.go @@ -3,8 +3,9 @@ package caddy import ( "net/http" - "github.com/caddyserver/caddy/v2/internal/metrics" "github.com/prometheus/client_golang/prometheus" + + "github.com/caddyserver/caddy/v2/internal/metrics" ) // define and register the metrics used in this package. diff --git a/modules/caddyevents/app.go b/modules/caddyevents/app.go index 2bfdcddb2dd..6c2abbf7cbc 100644 --- a/modules/caddyevents/app.go +++ b/modules/caddyevents/app.go @@ -21,8 +21,9 @@ import ( "fmt" "strings" - "github.com/caddyserver/caddy/v2" "go.uber.org/zap" + + "github.com/caddyserver/caddy/v2" ) func init() { diff --git a/modules/caddyfs/filesystem.go b/modules/caddyfs/filesystem.go index 2125ed9ec9e..2ec43079a2f 100644 --- a/modules/caddyfs/filesystem.go +++ b/modules/caddyfs/filesystem.go @@ -5,11 +5,12 @@ import ( "fmt" "io/fs" + "go.uber.org/zap" + "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/caddyconfig" "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" "github.com/caddyserver/caddy/v2/caddyconfig/httpcaddyfile" - "go.uber.org/zap" ) func init() { diff --git a/modules/caddyhttp/app.go b/modules/caddyhttp/app.go index 8d81677d2f3..6ad18d051f8 100644 --- a/modules/caddyhttp/app.go +++ b/modules/caddyhttp/app.go @@ -26,11 +26,12 @@ import ( "sync" "time" + "go.uber.org/zap" + "golang.org/x/net/http2" + "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/modules/caddyevents" "github.com/caddyserver/caddy/v2/modules/caddytls" - "go.uber.org/zap" - "golang.org/x/net/http2" ) func init() { diff --git a/modules/caddyhttp/autohttps.go b/modules/caddyhttp/autohttps.go index aafa6488e55..05f8a7517f0 100644 --- a/modules/caddyhttp/autohttps.go +++ b/modules/caddyhttp/autohttps.go @@ -21,11 +21,12 @@ import ( "strconv" "strings" + "github.com/caddyserver/certmagic" + "go.uber.org/zap" + "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/internal" "github.com/caddyserver/caddy/v2/modules/caddytls" - "github.com/caddyserver/certmagic" - "go.uber.org/zap" ) // AutoHTTPSConfig is used to disable automatic HTTPS diff --git a/modules/caddyhttp/caddyauth/argon2id.go b/modules/caddyhttp/caddyauth/argon2id.go index 280dc42eb5c..f1070ce4887 100644 --- a/modules/caddyhttp/caddyauth/argon2id.go +++ b/modules/caddyhttp/caddyauth/argon2id.go @@ -22,8 +22,9 @@ import ( "strconv" "strings" - "github.com/caddyserver/caddy/v2" "golang.org/x/crypto/argon2" + + "github.com/caddyserver/caddy/v2" ) func init() { diff --git a/modules/caddyhttp/caddyauth/basicauth.go b/modules/caddyhttp/caddyauth/basicauth.go index a23931660a7..5a9e167e102 100644 --- a/modules/caddyhttp/caddyauth/basicauth.go +++ b/modules/caddyhttp/caddyauth/basicauth.go @@ -24,8 +24,9 @@ import ( "strings" "sync" - "github.com/caddyserver/caddy/v2" "golang.org/x/sync/singleflight" + + "github.com/caddyserver/caddy/v2" ) func init() { diff --git a/modules/caddyhttp/caddyauth/bcrypt.go b/modules/caddyhttp/caddyauth/bcrypt.go index 35d38d4a410..f6940996eaa 100644 --- a/modules/caddyhttp/caddyauth/bcrypt.go +++ b/modules/caddyhttp/caddyauth/bcrypt.go @@ -17,8 +17,9 @@ package caddyauth import ( "errors" - "github.com/caddyserver/caddy/v2" "golang.org/x/crypto/bcrypt" + + "github.com/caddyserver/caddy/v2" ) func init() { diff --git a/modules/caddyhttp/caddyauth/caddyauth.go b/modules/caddyhttp/caddyauth/caddyauth.go index 17ad462c396..792c198ee5f 100644 --- a/modules/caddyhttp/caddyauth/caddyauth.go +++ b/modules/caddyhttp/caddyauth/caddyauth.go @@ -18,10 +18,11 @@ import ( "fmt" "net/http" - "github.com/caddyserver/caddy/v2" - "github.com/caddyserver/caddy/v2/modules/caddyhttp" "go.uber.org/zap" "go.uber.org/zap/zapcore" + + "github.com/caddyserver/caddy/v2" + "github.com/caddyserver/caddy/v2/modules/caddyhttp" ) func init() { diff --git a/modules/caddyhttp/caddyauth/command.go b/modules/caddyhttp/caddyauth/command.go index c22200fb432..e9c513005f2 100644 --- a/modules/caddyhttp/caddyauth/command.go +++ b/modules/caddyhttp/caddyauth/command.go @@ -21,10 +21,12 @@ import ( "os" "os/signal" - "github.com/caddyserver/caddy/v2" - caddycmd "github.com/caddyserver/caddy/v2/cmd" "github.com/spf13/cobra" "golang.org/x/term" + + caddycmd "github.com/caddyserver/caddy/v2/cmd" + + "github.com/caddyserver/caddy/v2" ) func init() { diff --git a/modules/caddyhttp/celmatcher.go b/modules/caddyhttp/celmatcher.go index 7a41b360545..66a60b817c7 100644 --- a/modules/caddyhttp/celmatcher.go +++ b/modules/caddyhttp/celmatcher.go @@ -25,8 +25,6 @@ import ( "strings" "time" - "github.com/caddyserver/caddy/v2" - "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" "github.com/google/cel-go/cel" "github.com/google/cel-go/common" "github.com/google/cel-go/common/ast" @@ -39,6 +37,9 @@ import ( "github.com/google/cel-go/interpreter/functions" "github.com/google/cel-go/parser" "go.uber.org/zap" + + "github.com/caddyserver/caddy/v2" + "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" ) func init() { diff --git a/modules/caddyhttp/encode/gzip/gzip.go b/modules/caddyhttp/encode/gzip/gzip.go index c9d7e56757e..40f37ab8e35 100644 --- a/modules/caddyhttp/encode/gzip/gzip.go +++ b/modules/caddyhttp/encode/gzip/gzip.go @@ -18,10 +18,11 @@ import ( "fmt" "strconv" + "github.com/klauspost/compress/gzip" + "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" "github.com/caddyserver/caddy/v2/modules/caddyhttp/encode" - "github.com/klauspost/compress/gzip" ) func init() { diff --git a/modules/caddyhttp/encode/zstd/zstd.go b/modules/caddyhttp/encode/zstd/zstd.go index 5e3a080f4bc..1706de89db7 100644 --- a/modules/caddyhttp/encode/zstd/zstd.go +++ b/modules/caddyhttp/encode/zstd/zstd.go @@ -17,10 +17,11 @@ package caddyzstd import ( "fmt" + "github.com/klauspost/compress/zstd" + "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" "github.com/caddyserver/caddy/v2/modules/caddyhttp/encode" - "github.com/klauspost/compress/zstd" ) func init() { diff --git a/modules/caddyhttp/fileserver/browse.go b/modules/caddyhttp/fileserver/browse.go index 3925710fb79..52aa7a9f8e5 100644 --- a/modules/caddyhttp/fileserver/browse.go +++ b/modules/caddyhttp/fileserver/browse.go @@ -32,11 +32,12 @@ import ( "text/template" "time" + "go.uber.org/zap" + "go.uber.org/zap/zapcore" + "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/modules/caddyhttp" "github.com/caddyserver/caddy/v2/modules/caddyhttp/templates" - "go.uber.org/zap" - "go.uber.org/zap/zapcore" ) // BrowseTemplate is the default template document to use for diff --git a/modules/caddyhttp/fileserver/browsetplcontext.go b/modules/caddyhttp/fileserver/browsetplcontext.go index 7ac705bcd28..b9489c6a6dc 100644 --- a/modules/caddyhttp/fileserver/browsetplcontext.go +++ b/modules/caddyhttp/fileserver/browsetplcontext.go @@ -27,11 +27,12 @@ import ( "strings" "time" - "github.com/caddyserver/caddy/v2" - "github.com/caddyserver/caddy/v2/modules/caddyhttp" "github.com/dustin/go-humanize" "go.uber.org/zap" "go.uber.org/zap/zapcore" + + "github.com/caddyserver/caddy/v2" + "github.com/caddyserver/caddy/v2/modules/caddyhttp" ) func (fsrv *FileServer) directoryListing(ctx context.Context, fileSystem fs.FS, parentModTime time.Time, entries []fs.DirEntry, canGoUp bool, root, urlPath string, repl *caddy.Replacer) *browseTemplateContext { diff --git a/modules/caddyhttp/fileserver/command.go b/modules/caddyhttp/fileserver/command.go index c1582368ae2..a04d7cade07 100644 --- a/modules/caddyhttp/fileserver/command.go +++ b/modules/caddyhttp/fileserver/command.go @@ -23,15 +23,17 @@ import ( "strconv" "time" + "github.com/caddyserver/certmagic" + "github.com/spf13/cobra" + "go.uber.org/zap" + + caddycmd "github.com/caddyserver/caddy/v2/cmd" + "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/caddyconfig" - caddycmd "github.com/caddyserver/caddy/v2/cmd" "github.com/caddyserver/caddy/v2/modules/caddyhttp" "github.com/caddyserver/caddy/v2/modules/caddyhttp/encode" caddytpl "github.com/caddyserver/caddy/v2/modules/caddyhttp/templates" - "github.com/caddyserver/certmagic" - "github.com/spf13/cobra" - "go.uber.org/zap" ) func init() { diff --git a/modules/caddyhttp/fileserver/matcher.go b/modules/caddyhttp/fileserver/matcher.go index 2e31f567ea8..fbcd36e0aa8 100644 --- a/modules/caddyhttp/fileserver/matcher.go +++ b/modules/caddyhttp/fileserver/matcher.go @@ -25,9 +25,6 @@ import ( "strconv" "strings" - "github.com/caddyserver/caddy/v2" - "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" - "github.com/caddyserver/caddy/v2/modules/caddyhttp" "github.com/google/cel-go/cel" "github.com/google/cel-go/common" "github.com/google/cel-go/common/ast" @@ -37,6 +34,10 @@ import ( "github.com/google/cel-go/parser" "go.uber.org/zap" "go.uber.org/zap/zapcore" + + "github.com/caddyserver/caddy/v2" + "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" + "github.com/caddyserver/caddy/v2/modules/caddyhttp" ) func init() { diff --git a/modules/caddyhttp/fileserver/staticfiles.go b/modules/caddyhttp/fileserver/staticfiles.go index 5ee0030e9c4..3daf8daefc1 100644 --- a/modules/caddyhttp/fileserver/staticfiles.go +++ b/modules/caddyhttp/fileserver/staticfiles.go @@ -30,11 +30,12 @@ import ( "strconv" "strings" + "go.uber.org/zap" + "go.uber.org/zap/zapcore" + "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/modules/caddyhttp" "github.com/caddyserver/caddy/v2/modules/caddyhttp/encode" - "go.uber.org/zap" - "go.uber.org/zap/zapcore" ) func init() { diff --git a/modules/caddyhttp/intercept/intercept.go b/modules/caddyhttp/intercept/intercept.go index 31a2ff18957..bacdc74b533 100644 --- a/modules/caddyhttp/intercept/intercept.go +++ b/modules/caddyhttp/intercept/intercept.go @@ -23,12 +23,13 @@ import ( "strings" "sync" + "go.uber.org/zap" + "go.uber.org/zap/zapcore" + "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" "github.com/caddyserver/caddy/v2/caddyconfig/httpcaddyfile" "github.com/caddyserver/caddy/v2/modules/caddyhttp" - "go.uber.org/zap" - "go.uber.org/zap/zapcore" ) func init() { diff --git a/modules/caddyhttp/ip_matchers.go b/modules/caddyhttp/ip_matchers.go index be261e955a5..9335112e8be 100644 --- a/modules/caddyhttp/ip_matchers.go +++ b/modules/caddyhttp/ip_matchers.go @@ -22,13 +22,14 @@ import ( "net/netip" "strings" - "github.com/caddyserver/caddy/v2" - "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" - "github.com/caddyserver/caddy/v2/internal" "github.com/google/cel-go/cel" "github.com/google/cel-go/common/types/ref" "go.uber.org/zap" "go.uber.org/zap/zapcore" + + "github.com/caddyserver/caddy/v2" + "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" + "github.com/caddyserver/caddy/v2/internal" ) // MatchRemoteIP matches requests by the remote IP address, diff --git a/modules/caddyhttp/logging.go b/modules/caddyhttp/logging.go index d2a855e6595..e8a1316bd73 100644 --- a/modules/caddyhttp/logging.go +++ b/modules/caddyhttp/logging.go @@ -21,9 +21,10 @@ import ( "net/http" "strings" - "github.com/caddyserver/caddy/v2" "go.uber.org/zap" "go.uber.org/zap/zapcore" + + "github.com/caddyserver/caddy/v2" ) // ServerLogConfig describes a server's logging configuration. If diff --git a/modules/caddyhttp/logging/logadd.go b/modules/caddyhttp/logging/logadd.go index c2320427019..3b554367f93 100644 --- a/modules/caddyhttp/logging/logadd.go +++ b/modules/caddyhttp/logging/logadd.go @@ -18,9 +18,10 @@ import ( "net/http" "strings" + "go.uber.org/zap" + "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/modules/caddyhttp" - "go.uber.org/zap" ) func init() { diff --git a/modules/caddyhttp/matchers.go b/modules/caddyhttp/matchers.go index c8fb2cce7ce..22976cfbd20 100644 --- a/modules/caddyhttp/matchers.go +++ b/modules/caddyhttp/matchers.go @@ -30,12 +30,13 @@ import ( "strconv" "strings" - "github.com/caddyserver/caddy/v2" - "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" "github.com/google/cel-go/cel" "github.com/google/cel-go/common/types" "github.com/google/cel-go/common/types/ref" "golang.org/x/net/idna" + + "github.com/caddyserver/caddy/v2" + "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" ) type ( diff --git a/modules/caddyhttp/metrics.go b/modules/caddyhttp/metrics.go index afcfececbd5..424170732ab 100644 --- a/modules/caddyhttp/metrics.go +++ b/modules/caddyhttp/metrics.go @@ -8,10 +8,11 @@ import ( "sync" "time" - "github.com/caddyserver/caddy/v2" - "github.com/caddyserver/caddy/v2/internal/metrics" "github.com/prometheus/client_golang/prometheus" "github.com/prometheus/client_golang/prometheus/promauto" + + "github.com/caddyserver/caddy/v2" + "github.com/caddyserver/caddy/v2/internal/metrics" ) // Metrics configures metrics observations. diff --git a/modules/caddyhttp/metrics_test.go b/modules/caddyhttp/metrics_test.go index b89ab7ce130..9f6f598586c 100644 --- a/modules/caddyhttp/metrics_test.go +++ b/modules/caddyhttp/metrics_test.go @@ -10,8 +10,9 @@ import ( "sync" "testing" - "github.com/caddyserver/caddy/v2" "github.com/prometheus/client_golang/prometheus/testutil" + + "github.com/caddyserver/caddy/v2" ) func TestServerNameFromContext(t *testing.T) { diff --git a/modules/caddyhttp/proxyprotocol/listenerwrapper.go b/modules/caddyhttp/proxyprotocol/listenerwrapper.go index 8508909cd53..f1d170c38ca 100644 --- a/modules/caddyhttp/proxyprotocol/listenerwrapper.go +++ b/modules/caddyhttp/proxyprotocol/listenerwrapper.go @@ -19,8 +19,9 @@ import ( "net/netip" "time" - "github.com/caddyserver/caddy/v2" goproxy "github.com/pires/go-proxyproto" + + "github.com/caddyserver/caddy/v2" ) // ListenerWrapper provides PROXY protocol support to Caddy by implementing diff --git a/modules/caddyhttp/push/handler.go b/modules/caddyhttp/push/handler.go index 8d5527dc034..1fbe53d8366 100644 --- a/modules/caddyhttp/push/handler.go +++ b/modules/caddyhttp/push/handler.go @@ -19,11 +19,12 @@ import ( "net/http" "strings" + "go.uber.org/zap" + "go.uber.org/zap/zapcore" + "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/modules/caddyhttp" "github.com/caddyserver/caddy/v2/modules/caddyhttp/headers" - "go.uber.org/zap" - "go.uber.org/zap/zapcore" ) func init() { diff --git a/modules/caddyhttp/replacer.go b/modules/caddyhttp/replacer.go index a12e5327d6d..9c3ab85f201 100644 --- a/modules/caddyhttp/replacer.go +++ b/modules/caddyhttp/replacer.go @@ -38,10 +38,11 @@ import ( "strings" "time" - "github.com/caddyserver/caddy/v2" - "github.com/caddyserver/caddy/v2/modules/caddytls" "github.com/google/uuid" "go.uber.org/zap" + + "github.com/caddyserver/caddy/v2" + "github.com/caddyserver/caddy/v2/modules/caddytls" ) // NewTestReplacer creates a replacer for an http.Request diff --git a/modules/caddyhttp/requestbody/caddyfile.go b/modules/caddyhttp/requestbody/caddyfile.go index 15ca64cbcb4..e2382d54683 100644 --- a/modules/caddyhttp/requestbody/caddyfile.go +++ b/modules/caddyhttp/requestbody/caddyfile.go @@ -17,9 +17,10 @@ package requestbody import ( "time" + "github.com/dustin/go-humanize" + "github.com/caddyserver/caddy/v2/caddyconfig/httpcaddyfile" "github.com/caddyserver/caddy/v2/modules/caddyhttp" - "github.com/dustin/go-humanize" ) func init() { diff --git a/modules/caddyhttp/requestbody/requestbody.go b/modules/caddyhttp/requestbody/requestbody.go index e88353ef452..65b09ded0c8 100644 --- a/modules/caddyhttp/requestbody/requestbody.go +++ b/modules/caddyhttp/requestbody/requestbody.go @@ -21,10 +21,11 @@ import ( "strings" "time" - "github.com/caddyserver/caddy/v2" - "github.com/caddyserver/caddy/v2/modules/caddyhttp" "go.uber.org/zap" "go.uber.org/zap/zapcore" + + "github.com/caddyserver/caddy/v2" + "github.com/caddyserver/caddy/v2/modules/caddyhttp" ) func init() { diff --git a/modules/caddyhttp/reverseproxy/caddyfile.go b/modules/caddyhttp/reverseproxy/caddyfile.go index d52265e6f5d..8439d1d5157 100644 --- a/modules/caddyhttp/reverseproxy/caddyfile.go +++ b/modules/caddyhttp/reverseproxy/caddyfile.go @@ -22,6 +22,8 @@ import ( "strconv" "strings" + "github.com/dustin/go-humanize" + "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/caddyconfig" "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" @@ -32,7 +34,6 @@ import ( "github.com/caddyserver/caddy/v2/modules/caddyhttp/rewrite" "github.com/caddyserver/caddy/v2/modules/caddytls" "github.com/caddyserver/caddy/v2/modules/internal/network" - "github.com/dustin/go-humanize" ) func init() { diff --git a/modules/caddyhttp/reverseproxy/command.go b/modules/caddyhttp/reverseproxy/command.go index edb53eddc75..3f6ffa8cb02 100644 --- a/modules/caddyhttp/reverseproxy/command.go +++ b/modules/caddyhttp/reverseproxy/command.go @@ -21,15 +21,17 @@ import ( "strconv" "strings" + "github.com/spf13/cobra" + "go.uber.org/zap" + + caddycmd "github.com/caddyserver/caddy/v2/cmd" + "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/caddyconfig" "github.com/caddyserver/caddy/v2/caddyconfig/httpcaddyfile" - caddycmd "github.com/caddyserver/caddy/v2/cmd" "github.com/caddyserver/caddy/v2/modules/caddyhttp" "github.com/caddyserver/caddy/v2/modules/caddyhttp/headers" "github.com/caddyserver/caddy/v2/modules/caddytls" - "github.com/spf13/cobra" - "go.uber.org/zap" ) func init() { diff --git a/modules/caddyhttp/reverseproxy/fastcgi/client.go b/modules/caddyhttp/reverseproxy/fastcgi/client.go index d1cece0d8f7..48599c27f7f 100644 --- a/modules/caddyhttp/reverseproxy/fastcgi/client.go +++ b/modules/caddyhttp/reverseproxy/fastcgi/client.go @@ -39,9 +39,10 @@ import ( "strings" "time" - "github.com/caddyserver/caddy/v2/modules/caddyhttp" "go.uber.org/zap" "go.uber.org/zap/zapcore" + + "github.com/caddyserver/caddy/v2/modules/caddyhttp" ) // FCGIListenSockFileno describes listen socket file number. diff --git a/modules/caddyhttp/reverseproxy/fastcgi/fastcgi.go b/modules/caddyhttp/reverseproxy/fastcgi/fastcgi.go index 0dec5a15aa1..d451dd38019 100644 --- a/modules/caddyhttp/reverseproxy/fastcgi/fastcgi.go +++ b/modules/caddyhttp/reverseproxy/fastcgi/fastcgi.go @@ -24,12 +24,13 @@ import ( "strings" "time" + "go.uber.org/zap" + "go.uber.org/zap/zapcore" + "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/modules/caddyhttp" "github.com/caddyserver/caddy/v2/modules/caddyhttp/reverseproxy" "github.com/caddyserver/caddy/v2/modules/caddytls" - "go.uber.org/zap" - "go.uber.org/zap/zapcore" ) var noopLogger = zap.NewNop() diff --git a/modules/caddyhttp/reverseproxy/healthchecks.go b/modules/caddyhttp/reverseproxy/healthchecks.go index 079ee520107..ac42570b2e1 100644 --- a/modules/caddyhttp/reverseproxy/healthchecks.go +++ b/modules/caddyhttp/reverseproxy/healthchecks.go @@ -28,10 +28,11 @@ import ( "strings" "time" - "github.com/caddyserver/caddy/v2" - "github.com/caddyserver/caddy/v2/modules/caddyhttp" "go.uber.org/zap" "go.uber.org/zap/zapcore" + + "github.com/caddyserver/caddy/v2" + "github.com/caddyserver/caddy/v2/modules/caddyhttp" ) // HealthChecks configures active and passive health checks. diff --git a/modules/caddyhttp/reverseproxy/httptransport.go b/modules/caddyhttp/reverseproxy/httptransport.go index 6525e8bff54..1e4cfa74386 100644 --- a/modules/caddyhttp/reverseproxy/httptransport.go +++ b/modules/caddyhttp/reverseproxy/httptransport.go @@ -31,16 +31,17 @@ import ( "strings" "time" - "github.com/caddyserver/caddy/v2" - "github.com/caddyserver/caddy/v2/caddyconfig" - "github.com/caddyserver/caddy/v2/modules/caddyhttp" - "github.com/caddyserver/caddy/v2/modules/caddytls" - "github.com/caddyserver/caddy/v2/modules/internal/network" "github.com/pires/go-proxyproto" "github.com/quic-go/quic-go/http3" "go.uber.org/zap" "go.uber.org/zap/zapcore" "golang.org/x/net/http2" + + "github.com/caddyserver/caddy/v2" + "github.com/caddyserver/caddy/v2/caddyconfig" + "github.com/caddyserver/caddy/v2/modules/caddyhttp" + "github.com/caddyserver/caddy/v2/modules/caddytls" + "github.com/caddyserver/caddy/v2/modules/internal/network" ) func init() { diff --git a/modules/caddyhttp/reverseproxy/metrics.go b/modules/caddyhttp/reverseproxy/metrics.go index 2ab73d8ff1a..2488427304e 100644 --- a/modules/caddyhttp/reverseproxy/metrics.go +++ b/modules/caddyhttp/reverseproxy/metrics.go @@ -6,10 +6,11 @@ import ( "sync" "time" - "github.com/caddyserver/caddy/v2" "github.com/prometheus/client_golang/prometheus" "go.uber.org/zap" "go.uber.org/zap/zapcore" + + "github.com/caddyserver/caddy/v2" ) var reverseProxyMetrics = struct { diff --git a/modules/caddyhttp/reverseproxy/reverseproxy.go b/modules/caddyhttp/reverseproxy/reverseproxy.go index d6b40cec319..794860d8e02 100644 --- a/modules/caddyhttp/reverseproxy/reverseproxy.go +++ b/modules/caddyhttp/reverseproxy/reverseproxy.go @@ -34,15 +34,16 @@ import ( "sync" "time" + "go.uber.org/zap" + "go.uber.org/zap/zapcore" + "golang.org/x/net/http/httpguts" + "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" "github.com/caddyserver/caddy/v2/modules/caddyevents" "github.com/caddyserver/caddy/v2/modules/caddyhttp" "github.com/caddyserver/caddy/v2/modules/caddyhttp/headers" "github.com/caddyserver/caddy/v2/modules/caddyhttp/rewrite" - "go.uber.org/zap" - "go.uber.org/zap/zapcore" - "golang.org/x/net/http/httpguts" ) func init() { diff --git a/modules/caddyhttp/reverseproxy/selectionpolicies.go b/modules/caddyhttp/reverseproxy/selectionpolicies.go index ae1b5de678f..585fc340067 100644 --- a/modules/caddyhttp/reverseproxy/selectionpolicies.go +++ b/modules/caddyhttp/reverseproxy/selectionpolicies.go @@ -28,11 +28,12 @@ import ( "sync/atomic" "time" + "github.com/cespare/xxhash/v2" + "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/caddyconfig" "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" "github.com/caddyserver/caddy/v2/modules/caddyhttp" - "github.com/cespare/xxhash/v2" ) func init() { diff --git a/modules/caddyhttp/reverseproxy/streaming.go b/modules/caddyhttp/reverseproxy/streaming.go index b3ba3ae58c9..66dd106d53c 100644 --- a/modules/caddyhttp/reverseproxy/streaming.go +++ b/modules/caddyhttp/reverseproxy/streaming.go @@ -31,10 +31,11 @@ import ( "time" "unsafe" - "github.com/caddyserver/caddy/v2/modules/caddyhttp" "go.uber.org/zap" "go.uber.org/zap/zapcore" "golang.org/x/net/http/httpguts" + + "github.com/caddyserver/caddy/v2/modules/caddyhttp" ) type h2ReadWriteCloser struct { diff --git a/modules/caddyhttp/reverseproxy/upstreams.go b/modules/caddyhttp/reverseproxy/upstreams.go index 8d2ff8ace3a..e9eb7e60ac5 100644 --- a/modules/caddyhttp/reverseproxy/upstreams.go +++ b/modules/caddyhttp/reverseproxy/upstreams.go @@ -11,9 +11,10 @@ import ( "sync" "time" - "github.com/caddyserver/caddy/v2" "go.uber.org/zap" "go.uber.org/zap/zapcore" + + "github.com/caddyserver/caddy/v2" ) func init() { diff --git a/modules/caddyhttp/rewrite/rewrite.go b/modules/caddyhttp/rewrite/rewrite.go index 325fbda4f79..2b18744db2d 100644 --- a/modules/caddyhttp/rewrite/rewrite.go +++ b/modules/caddyhttp/rewrite/rewrite.go @@ -22,9 +22,10 @@ import ( "strconv" "strings" + "go.uber.org/zap" + "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/modules/caddyhttp" - "go.uber.org/zap" ) func init() { diff --git a/modules/caddyhttp/server.go b/modules/caddyhttp/server.go index 541bbcd67a3..d3760bf3cc9 100644 --- a/modules/caddyhttp/server.go +++ b/modules/caddyhttp/server.go @@ -30,15 +30,16 @@ import ( "sync" "time" - "github.com/caddyserver/caddy/v2" - "github.com/caddyserver/caddy/v2/modules/caddyevents" - "github.com/caddyserver/caddy/v2/modules/caddytls" "github.com/caddyserver/certmagic" "github.com/quic-go/quic-go" "github.com/quic-go/quic-go/http3" "github.com/quic-go/quic-go/qlog" "go.uber.org/zap" "go.uber.org/zap/zapcore" + + "github.com/caddyserver/caddy/v2" + "github.com/caddyserver/caddy/v2/modules/caddyevents" + "github.com/caddyserver/caddy/v2/modules/caddytls" ) // Server describes an HTTP server. diff --git a/modules/caddyhttp/staticresp.go b/modules/caddyhttp/staticresp.go index 408eaa434cb..d783d1b0416 100644 --- a/modules/caddyhttp/staticresp.go +++ b/modules/caddyhttp/staticresp.go @@ -28,12 +28,14 @@ import ( "text/template" "time" + "github.com/spf13/cobra" + "go.uber.org/zap" + + caddycmd "github.com/caddyserver/caddy/v2/cmd" + "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/caddyconfig" "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" - caddycmd "github.com/caddyserver/caddy/v2/cmd" - "github.com/spf13/cobra" - "go.uber.org/zap" ) func init() { diff --git a/modules/caddyhttp/templates/templates.go b/modules/caddyhttp/templates/templates.go index 9cdc5ea3db6..eb648865983 100644 --- a/modules/caddyhttp/templates/templates.go +++ b/modules/caddyhttp/templates/templates.go @@ -23,9 +23,10 @@ import ( "strings" "text/template" + "go.uber.org/zap" + "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/modules/caddyhttp" - "go.uber.org/zap" ) func init() { diff --git a/modules/caddyhttp/templates/tplcontext.go b/modules/caddyhttp/templates/tplcontext.go index 4577611fd66..ee553e7a560 100644 --- a/modules/caddyhttp/templates/tplcontext.go +++ b/modules/caddyhttp/templates/tplcontext.go @@ -33,8 +33,6 @@ import ( "github.com/Masterminds/sprig/v3" chromahtml "github.com/alecthomas/chroma/v2/formatters/html" - "github.com/caddyserver/caddy/v2" - "github.com/caddyserver/caddy/v2/modules/caddyhttp" "github.com/dustin/go-humanize" "github.com/yuin/goldmark" highlighting "github.com/yuin/goldmark-highlighting/v2" @@ -42,6 +40,9 @@ import ( "github.com/yuin/goldmark/parser" gmhtml "github.com/yuin/goldmark/renderer/html" "go.uber.org/zap" + + "github.com/caddyserver/caddy/v2" + "github.com/caddyserver/caddy/v2/modules/caddyhttp" ) // TemplateContext is the TemplateContext with which HTTP templates are executed. diff --git a/modules/caddyhttp/tracing/module.go b/modules/caddyhttp/tracing/module.go index 272ace5068b..85fd630020e 100644 --- a/modules/caddyhttp/tracing/module.go +++ b/modules/caddyhttp/tracing/module.go @@ -4,11 +4,12 @@ import ( "fmt" "net/http" + "go.uber.org/zap" + "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" "github.com/caddyserver/caddy/v2/caddyconfig/httpcaddyfile" "github.com/caddyserver/caddy/v2/modules/caddyhttp" - "go.uber.org/zap" ) func init() { diff --git a/modules/caddyhttp/tracing/tracer.go b/modules/caddyhttp/tracing/tracer.go index ebc42592dc9..ab2ddf8a2e3 100644 --- a/modules/caddyhttp/tracing/tracer.go +++ b/modules/caddyhttp/tracing/tracer.go @@ -5,8 +5,6 @@ import ( "fmt" "net/http" - "github.com/caddyserver/caddy/v2" - "github.com/caddyserver/caddy/v2/modules/caddyhttp" "go.opentelemetry.io/contrib/exporters/autoexport" "go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp" "go.opentelemetry.io/contrib/propagators/autoprop" @@ -16,6 +14,9 @@ import ( semconv "go.opentelemetry.io/otel/semconv/v1.17.0" "go.opentelemetry.io/otel/trace" "go.uber.org/zap" + + "github.com/caddyserver/caddy/v2" + "github.com/caddyserver/caddy/v2/modules/caddyhttp" ) const ( diff --git a/modules/caddyhttp/vars.go b/modules/caddyhttp/vars.go index a501a75e8b1..d01f4a4319e 100644 --- a/modules/caddyhttp/vars.go +++ b/modules/caddyhttp/vars.go @@ -21,10 +21,11 @@ import ( "reflect" "strings" - "github.com/caddyserver/caddy/v2" - "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" "github.com/google/cel-go/cel" "github.com/google/cel-go/common/types/ref" + + "github.com/caddyserver/caddy/v2" + "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" ) var stringSliceType = reflect.TypeFor[[]string]() diff --git a/modules/caddypki/acmeserver/acmeserver.go b/modules/caddypki/acmeserver/acmeserver.go index 04d65de4e53..aeb4eab8ec3 100644 --- a/modules/caddypki/acmeserver/acmeserver.go +++ b/modules/caddypki/acmeserver/acmeserver.go @@ -26,9 +26,6 @@ import ( "strings" "time" - "github.com/caddyserver/caddy/v2" - "github.com/caddyserver/caddy/v2/modules/caddyhttp" - "github.com/caddyserver/caddy/v2/modules/caddypki" "github.com/go-chi/chi/v5" "github.com/smallstep/certificates/acme" "github.com/smallstep/certificates/acme/api" @@ -39,6 +36,10 @@ import ( "github.com/smallstep/nosql" "go.uber.org/zap" "go.uber.org/zap/zapcore" + + "github.com/caddyserver/caddy/v2" + "github.com/caddyserver/caddy/v2/modules/caddyhttp" + "github.com/caddyserver/caddy/v2/modules/caddypki" ) func init() { diff --git a/modules/caddypki/adminapi.go b/modules/caddypki/adminapi.go index 3e009e06fe5..463e31f356e 100644 --- a/modules/caddypki/adminapi.go +++ b/modules/caddypki/adminapi.go @@ -20,8 +20,9 @@ import ( "net/http" "strings" - "github.com/caddyserver/caddy/v2" "go.uber.org/zap" + + "github.com/caddyserver/caddy/v2" ) func init() { diff --git a/modules/caddypki/ca.go b/modules/caddypki/ca.go index 254861f13e5..5b17518caaa 100644 --- a/modules/caddypki/ca.go +++ b/modules/caddypki/ca.go @@ -25,12 +25,13 @@ import ( "sync" "time" - "github.com/caddyserver/caddy/v2" "github.com/caddyserver/certmagic" "github.com/smallstep/certificates/authority" "github.com/smallstep/certificates/db" "github.com/smallstep/truststore" "go.uber.org/zap" + + "github.com/caddyserver/caddy/v2" ) // CA describes a certificate authority, which consists of diff --git a/modules/caddypki/command.go b/modules/caddypki/command.go index e78f35c88d0..b7fa1bb7ce1 100644 --- a/modules/caddypki/command.go +++ b/modules/caddypki/command.go @@ -23,10 +23,12 @@ import ( "os" "path" - "github.com/caddyserver/caddy/v2" - caddycmd "github.com/caddyserver/caddy/v2/cmd" "github.com/smallstep/truststore" "github.com/spf13/cobra" + + caddycmd "github.com/caddyserver/caddy/v2/cmd" + + "github.com/caddyserver/caddy/v2" ) func init() { diff --git a/modules/caddypki/pki.go b/modules/caddypki/pki.go index 2caeb2b5976..9f974a956bb 100644 --- a/modules/caddypki/pki.go +++ b/modules/caddypki/pki.go @@ -17,8 +17,9 @@ package caddypki import ( "fmt" - "github.com/caddyserver/caddy/v2" "go.uber.org/zap" + + "github.com/caddyserver/caddy/v2" ) func init() { diff --git a/modules/caddytls/acmeissuer.go b/modules/caddytls/acmeissuer.go index 78c4a65ddbc..7f13fd71fb9 100644 --- a/modules/caddytls/acmeissuer.go +++ b/modules/caddytls/acmeissuer.go @@ -26,14 +26,15 @@ import ( "strings" "time" - "github.com/caddyserver/caddy/v2" - "github.com/caddyserver/caddy/v2/caddyconfig" - "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" "github.com/caddyserver/certmagic" "github.com/caddyserver/zerossl" "github.com/mholt/acmez/v3/acme" "go.uber.org/zap" "go.uber.org/zap/zapcore" + + "github.com/caddyserver/caddy/v2" + "github.com/caddyserver/caddy/v2/caddyconfig" + "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" ) func init() { diff --git a/modules/caddytls/automation.go b/modules/caddytls/automation.go index 14ffdc75023..e69b5ad2f8f 100644 --- a/modules/caddytls/automation.go +++ b/modules/caddytls/automation.go @@ -24,12 +24,13 @@ import ( "slices" "strings" - "github.com/caddyserver/caddy/v2" "github.com/caddyserver/certmagic" "github.com/mholt/acmez/v3" "go.uber.org/zap" "go.uber.org/zap/zapcore" "golang.org/x/net/idna" + + "github.com/caddyserver/caddy/v2" ) // AutomationConfig governs the automated management of TLS certificates. diff --git a/modules/caddytls/capools.go b/modules/caddytls/capools.go index 363ef3ade5b..c73bc4832fd 100644 --- a/modules/caddytls/capools.go +++ b/modules/caddytls/capools.go @@ -12,11 +12,12 @@ import ( "os" "reflect" + "github.com/caddyserver/certmagic" + "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/caddyconfig" "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" "github.com/caddyserver/caddy/v2/modules/caddypki" - "github.com/caddyserver/certmagic" ) func init() { diff --git a/modules/caddytls/certmanagers.go b/modules/caddytls/certmanagers.go index ed5afcb4877..0a9d459dfbe 100644 --- a/modules/caddytls/certmanagers.go +++ b/modules/caddytls/certmanagers.go @@ -10,12 +10,13 @@ import ( "net/url" "strings" - "github.com/caddyserver/caddy/v2" - "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" "github.com/caddyserver/certmagic" "github.com/tailscale/tscert" "go.uber.org/zap" "go.uber.org/zap/zapcore" + + "github.com/caddyserver/caddy/v2" + "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" ) func init() { diff --git a/modules/caddytls/certselection.go b/modules/caddytls/certselection.go index daf4240c65f..ac210d3b697 100644 --- a/modules/caddytls/certselection.go +++ b/modules/caddytls/certselection.go @@ -22,8 +22,9 @@ import ( "math/big" "slices" - "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" "github.com/caddyserver/certmagic" + + "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" ) // CustomCertSelectionPolicy represents a policy for selecting the certificate diff --git a/modules/caddytls/connpolicy.go b/modules/caddytls/connpolicy.go index ec5620e1f55..724271a8e38 100644 --- a/modules/caddytls/connpolicy.go +++ b/modules/caddytls/connpolicy.go @@ -28,12 +28,13 @@ import ( "slices" "strings" - "github.com/caddyserver/caddy/v2" - "github.com/caddyserver/caddy/v2/caddyconfig" - "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" "github.com/mholt/acmez/v3" "go.uber.org/zap" "go.uber.org/zap/zapcore" + + "github.com/caddyserver/caddy/v2" + "github.com/caddyserver/caddy/v2/caddyconfig" + "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" ) func init() { diff --git a/modules/caddytls/distributedstek/distributedstek.go b/modules/caddytls/distributedstek/distributedstek.go index 18ed69496c5..f6d0de064c0 100644 --- a/modules/caddytls/distributedstek/distributedstek.go +++ b/modules/caddytls/distributedstek/distributedstek.go @@ -33,9 +33,10 @@ import ( "runtime/debug" "time" + "github.com/caddyserver/certmagic" + "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/modules/caddytls" - "github.com/caddyserver/certmagic" ) func init() { diff --git a/modules/caddytls/ech.go b/modules/caddytls/ech.go index c47c21a38d4..1b3bacbd226 100644 --- a/modules/caddytls/ech.go +++ b/modules/caddytls/ech.go @@ -13,13 +13,14 @@ import ( "strings" "time" - "github.com/caddyserver/caddy/v2" "github.com/caddyserver/certmagic" "github.com/cloudflare/circl/hpke" "github.com/cloudflare/circl/kem" "github.com/libdns/libdns" "go.uber.org/zap" "golang.org/x/crypto/cryptobyte" + + "github.com/caddyserver/caddy/v2" ) func init() { diff --git a/modules/caddytls/internalissuer.go b/modules/caddytls/internalissuer.go index 127b26a84b8..be779757a87 100644 --- a/modules/caddytls/internalissuer.go +++ b/modules/caddytls/internalissuer.go @@ -21,12 +21,13 @@ import ( "encoding/pem" "time" - "github.com/caddyserver/caddy/v2" - "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" - "github.com/caddyserver/caddy/v2/modules/caddypki" "github.com/caddyserver/certmagic" "github.com/smallstep/certificates/authority/provisioner" "go.uber.org/zap" + + "github.com/caddyserver/caddy/v2" + "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" + "github.com/caddyserver/caddy/v2/modules/caddypki" ) func init() { diff --git a/modules/caddytls/leafstorageloader.go b/modules/caddytls/leafstorageloader.go index d966f932c74..0215c8af2a6 100644 --- a/modules/caddytls/leafstorageloader.go +++ b/modules/caddytls/leafstorageloader.go @@ -20,8 +20,9 @@ import ( "encoding/pem" "fmt" - "github.com/caddyserver/caddy/v2" "github.com/caddyserver/certmagic" + + "github.com/caddyserver/caddy/v2" ) func init() { diff --git a/modules/caddytls/matchers.go b/modules/caddytls/matchers.go index 04d522bbe06..dfbec94cc7a 100644 --- a/modules/caddytls/matchers.go +++ b/modules/caddytls/matchers.go @@ -25,12 +25,13 @@ import ( "strconv" "strings" - "github.com/caddyserver/caddy/v2" - "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" - "github.com/caddyserver/caddy/v2/internal" "github.com/caddyserver/certmagic" "go.uber.org/zap" "go.uber.org/zap/zapcore" + + "github.com/caddyserver/caddy/v2" + "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" + "github.com/caddyserver/caddy/v2/internal" ) func init() { diff --git a/modules/caddytls/ondemand.go b/modules/caddytls/ondemand.go index abc27e720f6..0970234cecd 100644 --- a/modules/caddytls/ondemand.go +++ b/modules/caddytls/ondemand.go @@ -24,11 +24,12 @@ import ( "net/url" "time" - "github.com/caddyserver/caddy/v2" - "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" "github.com/caddyserver/certmagic" "go.uber.org/zap" "go.uber.org/zap/zapcore" + + "github.com/caddyserver/caddy/v2" + "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" ) func init() { diff --git a/modules/caddytls/storageloader.go b/modules/caddytls/storageloader.go index f8c1981a2e2..c9487e89252 100644 --- a/modules/caddytls/storageloader.go +++ b/modules/caddytls/storageloader.go @@ -19,8 +19,9 @@ import ( "fmt" "strings" - "github.com/caddyserver/caddy/v2" "github.com/caddyserver/certmagic" + + "github.com/caddyserver/caddy/v2" ) func init() { diff --git a/modules/caddytls/tls.go b/modules/caddytls/tls.go index 5293b8b1cc4..7b49c020872 100644 --- a/modules/caddytls/tls.go +++ b/modules/caddytls/tls.go @@ -27,13 +27,14 @@ import ( "sync" "time" - "github.com/caddyserver/caddy/v2" - "github.com/caddyserver/caddy/v2/internal" - "github.com/caddyserver/caddy/v2/modules/caddyevents" "github.com/caddyserver/certmagic" "github.com/libdns/libdns" "go.uber.org/zap" "go.uber.org/zap/zapcore" + + "github.com/caddyserver/caddy/v2" + "github.com/caddyserver/caddy/v2/internal" + "github.com/caddyserver/caddy/v2/modules/caddyevents" ) func init() { diff --git a/modules/caddytls/zerosslissuer.go b/modules/caddytls/zerosslissuer.go index d65f633defe..b8727ab669d 100644 --- a/modules/caddytls/zerosslissuer.go +++ b/modules/caddytls/zerosslissuer.go @@ -21,11 +21,12 @@ import ( "strconv" "time" + "github.com/caddyserver/certmagic" + "go.uber.org/zap" + "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/caddyconfig" "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" - "github.com/caddyserver/certmagic" - "go.uber.org/zap" ) func init() { diff --git a/modules/filestorage/filestorage.go b/modules/filestorage/filestorage.go index 2615310dc5d..76aff4e8b7a 100644 --- a/modules/filestorage/filestorage.go +++ b/modules/filestorage/filestorage.go @@ -15,9 +15,10 @@ package filestorage import ( + "github.com/caddyserver/certmagic" + "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" - "github.com/caddyserver/certmagic" ) func init() { diff --git a/modules/internal/network/networkproxy.go b/modules/internal/network/networkproxy.go index 9307b60b022..f9deeb43a96 100644 --- a/modules/internal/network/networkproxy.go +++ b/modules/internal/network/networkproxy.go @@ -6,9 +6,10 @@ import ( "net/url" "strings" + "go.uber.org/zap" + "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" - "go.uber.org/zap" ) func init() { diff --git a/modules/logging/appendencoder.go b/modules/logging/appendencoder.go index 6899aee49b9..63bd532d02b 100644 --- a/modules/logging/appendencoder.go +++ b/modules/logging/appendencoder.go @@ -21,13 +21,14 @@ import ( "strings" "time" - "github.com/caddyserver/caddy/v2" - "github.com/caddyserver/caddy/v2/caddyconfig" - "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" "go.uber.org/zap" "go.uber.org/zap/buffer" "go.uber.org/zap/zapcore" "golang.org/x/term" + + "github.com/caddyserver/caddy/v2" + "github.com/caddyserver/caddy/v2/caddyconfig" + "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" ) func init() { diff --git a/modules/logging/cores.go b/modules/logging/cores.go index c2ed9d60794..49aa7640ce3 100644 --- a/modules/logging/cores.go +++ b/modules/logging/cores.go @@ -1,9 +1,10 @@ package logging import ( + "go.uber.org/zap/zapcore" + "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" - "go.uber.org/zap/zapcore" ) func init() { diff --git a/modules/logging/encoders.go b/modules/logging/encoders.go index 5a3d5b60de1..5c563114b35 100644 --- a/modules/logging/encoders.go +++ b/modules/logging/encoders.go @@ -17,11 +17,12 @@ package logging import ( "time" - "github.com/caddyserver/caddy/v2" - "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" "go.uber.org/zap" "go.uber.org/zap/buffer" "go.uber.org/zap/zapcore" + + "github.com/caddyserver/caddy/v2" + "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" ) func init() { diff --git a/modules/logging/filewriter.go b/modules/logging/filewriter.go index 32c7af98d8f..c3df562cbe5 100644 --- a/modules/logging/filewriter.go +++ b/modules/logging/filewriter.go @@ -26,9 +26,10 @@ import ( "time" "github.com/DeRuina/timberjack" + "github.com/dustin/go-humanize" + "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" - "github.com/dustin/go-humanize" ) func init() { diff --git a/modules/logging/filterencoder.go b/modules/logging/filterencoder.go index 6f9290a2803..01333e1951f 100644 --- a/modules/logging/filterencoder.go +++ b/modules/logging/filterencoder.go @@ -20,13 +20,14 @@ import ( "os" "time" - "github.com/caddyserver/caddy/v2" - "github.com/caddyserver/caddy/v2/caddyconfig" - "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" "go.uber.org/zap" "go.uber.org/zap/buffer" "go.uber.org/zap/zapcore" "golang.org/x/term" + + "github.com/caddyserver/caddy/v2" + "github.com/caddyserver/caddy/v2/caddyconfig" + "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" ) func init() { diff --git a/modules/logging/filters.go b/modules/logging/filters.go index 4961cb11534..a2ce6502fd5 100644 --- a/modules/logging/filters.go +++ b/modules/logging/filters.go @@ -25,10 +25,11 @@ import ( "strconv" "strings" + "go.uber.org/zap/zapcore" + "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" "github.com/caddyserver/caddy/v2/modules/caddyhttp" - "go.uber.org/zap/zapcore" ) func init() { diff --git a/modules/logging/filters_test.go b/modules/logging/filters_test.go index 8e6d44c8f72..cf35e717827 100644 --- a/modules/logging/filters_test.go +++ b/modules/logging/filters_test.go @@ -5,9 +5,10 @@ import ( "strings" "testing" + "go.uber.org/zap/zapcore" + "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/modules/caddyhttp" - "go.uber.org/zap/zapcore" ) func TestIPMaskSingleValue(t *testing.T) { diff --git a/modules/metrics/adminmetrics.go b/modules/metrics/adminmetrics.go index 39394401188..1e3a841ddb2 100644 --- a/modules/metrics/adminmetrics.go +++ b/modules/metrics/adminmetrics.go @@ -18,8 +18,9 @@ import ( "errors" "net/http" - "github.com/caddyserver/caddy/v2" "github.com/prometheus/client_golang/prometheus" + + "github.com/caddyserver/caddy/v2" ) func init() { diff --git a/modules/metrics/metrics.go b/modules/metrics/metrics.go index 15a3794a0ff..42b30d88dd7 100644 --- a/modules/metrics/metrics.go +++ b/modules/metrics/metrics.go @@ -18,13 +18,14 @@ import ( "errors" "net/http" + "github.com/prometheus/client_golang/prometheus" + "github.com/prometheus/client_golang/prometheus/promhttp" + "go.uber.org/zap" + "github.com/caddyserver/caddy/v2" "github.com/caddyserver/caddy/v2/caddyconfig/caddyfile" "github.com/caddyserver/caddy/v2/caddyconfig/httpcaddyfile" "github.com/caddyserver/caddy/v2/modules/caddyhttp" - "github.com/prometheus/client_golang/prometheus" - "github.com/prometheus/client_golang/prometheus/promhttp" - "go.uber.org/zap" ) func init() { diff --git a/service_windows.go b/service_windows.go index 357c9ac8ef1..4720dbaa47b 100644 --- a/service_windows.go +++ b/service_windows.go @@ -18,8 +18,9 @@ import ( "os" "path/filepath" - "github.com/caddyserver/caddy/v2/notify" "golang.org/x/sys/windows/svc" + + "github.com/caddyserver/caddy/v2/notify" ) func init() { From 1bf58bc85811f3a78613bd2fd1271737aeafb762 Mon Sep 17 00:00:00 2001 From: Aaron Paterson Date: Thu, 6 Nov 2025 02:51:24 -0700 Subject: [PATCH 51/51] remove old opts --- caddyconfig/httpcaddyfile/addresses.go | 7 ------- 1 file changed, 7 deletions(-) diff --git a/caddyconfig/httpcaddyfile/addresses.go b/caddyconfig/httpcaddyfile/addresses.go index c9dc9fc9688..ae70a92aaae 100644 --- a/caddyconfig/httpcaddyfile/addresses.go +++ b/caddyconfig/httpcaddyfile/addresses.go @@ -403,13 +403,6 @@ type bindOptions struct { protocols []string } -// addressesWithProtocols associates a list of listen addresses -// with a list of protocols to serve them with -type addressesWithProtocols struct { - addresses []string - protocols []string -} - // Address represents a site address. It contains // the original input value, and the component // parts of an address. The component parts may be