1
0
Fork 0
mirror of https://code.forgejo.org/forgejo/runner.git synced 2025-08-26 18:20:59 +00:00

fix: artifacts: format IP:port pair using net.JoinHostPort()

This ensures that brackets are added for IPv6 addresses.
Without this, This could result in addresses like "2001:db8::1:3456",
which - obviously - would break further down and prevent the server from
starting.

Signed-off-by: Christoph Heiss <christoph@c8h4.io>
This commit is contained in:
Christoph Heiss 2025-05-25 19:16:18 +02:00
parent cade5051a8
commit 92b7df3da7
3 changed files with 41 additions and 5 deletions

View file

@ -115,10 +115,10 @@ func StartHandler(dir, outboundIP string, port uint16, secret string, logger log
} }
func (h *Handler) ExternalURL() string { func (h *Handler) ExternalURL() string {
port := strconv.Itoa(h.listener.Addr().(*net.TCPAddr).Port)
// TODO: make the external url configurable if necessary // TODO: make the external url configurable if necessary
return fmt.Sprintf("http://%s:%d", return fmt.Sprintf("http://%s", net.JoinHostPort(h.outboundIP, port))
h.outboundIP,
h.listener.Addr().(*net.TCPAddr).Port)
} }
func (h *Handler) Close() error { func (h *Handler) Close() error {

View file

@ -746,3 +746,38 @@ func TestHandler_gcCache(t *testing.T) {
} }
require.NoError(t, db.Close()) require.NoError(t, db.Close())
} }
func TestHandler_ExternalURL(t *testing.T) {
t.Run("reports correct URL on IPv4", func(t *testing.T) {
dir := filepath.Join(t.TempDir(), "artifactcache")
handler, err := StartHandler(dir, "127.0.0.1", 34567, "secret", nil)
require.NoError(t, err)
assert.Equal(t, handler.ExternalURL(), "http://127.0.0.1:34567")
require.NoError(t, handler.Close())
assert.Nil(t, handler.server)
assert.Nil(t, handler.listener)
})
t.Run("reports correct URL on IPv6 zero host", func(t *testing.T) {
dir := filepath.Join(t.TempDir(), "artifactcache")
handler, err := StartHandler(dir, "2001:db8::", 34567, "secret", nil)
require.NoError(t, err)
assert.Equal(t, handler.ExternalURL(), "http://[2001:db8::]:34567")
require.NoError(t, handler.Close())
assert.Nil(t, handler.server)
assert.Nil(t, handler.listener)
})
t.Run("reports correct URL on IPv6", func(t *testing.T) {
dir := filepath.Join(t.TempDir(), "artifactcache")
handler, err := StartHandler(dir, "2001:db8::1:2:3:4", 34567, "secret", nil)
require.NoError(t, err)
assert.Equal(t, handler.ExternalURL(), "http://[2001:db8::1:2:3:4]:34567")
require.NoError(t, handler.Close())
assert.Nil(t, handler.server)
assert.Nil(t, handler.listener)
})
}

View file

@ -7,6 +7,7 @@ import (
"fmt" "fmt"
"io" "io"
"io/fs" "io/fs"
"net"
"net/http" "net/http"
"os" "os"
"path/filepath" "path/filepath"
@ -291,14 +292,14 @@ func Serve(ctx context.Context, artifactPath string, addr string, port string) c
downloads(router, artifactPath, fsys) downloads(router, artifactPath, fsys)
server := &http.Server{ server := &http.Server{
Addr: fmt.Sprintf("%s:%s", addr, port), Addr: net.JoinHostPort(addr, port),
ReadHeaderTimeout: 2 * time.Second, ReadHeaderTimeout: 2 * time.Second,
Handler: router, Handler: router,
} }
// run server // run server
go func() { go func() {
logger.Infof("Start server on http://%s:%s", addr, port) logger.Infof("Start server on http://%s", server.Addr)
if err := server.ListenAndServe(); err != nil && err != http.ErrServerClosed { if err := server.ListenAndServe(); err != nil && err != http.ErrServerClosed {
logger.Fatalf("http listener: %v", err) logger.Fatalf("http listener: %v", err)
} }