diff options
author | tjp <tjp@ctrl-c.club> | 2025-04-03 09:51:32 -0600 |
---|---|---|
committer | tjp <tjp@ctrl-c.club> | 2025-04-03 09:53:01 -0600 |
commit | 2e5ac8b9e1f2f705455d74750e465c2066ffdc7c (patch) | |
tree | c5763dddfa5184e642416bddbb97fa5cb8a782ba | |
parent | e111dae3f83831874d83ffe0349839a1cffcbaf7 (diff) |
empty path handling for spartan/gemini clients and servers
-rw-r--r-- | gemini/client.go | 4 | ||||
-rw-r--r-- | gemini/serve.go | 3 | ||||
-rw-r--r-- | spartan/client.go | 15 |
3 files changed, 20 insertions, 2 deletions
diff --git a/gemini/client.go b/gemini/client.go index 1e65a39..e0f70e4 100644 --- a/gemini/client.go +++ b/gemini/client.go @@ -97,6 +97,10 @@ func (client Client) RoundTrip(ctx context.Context, request *types.Request) (*ty } } + if destURL.Path == "" { + destURL.Path = "/" + } + if _, err := conn.Write([]byte(destURL.String() + "\r\n")); err != nil { return nil, err } diff --git a/gemini/serve.go b/gemini/serve.go index c76353c..b7b9256 100644 --- a/gemini/serve.go +++ b/gemini/serve.go @@ -55,6 +55,9 @@ func (s *server) handleConn(conn net.Conn) { if err != nil { response = BadRequest(err.Error()) } else { + if request.Path == "" { + request.Path = "/" + } request.Server = s request.RemoteAddr = conn.RemoteAddr() diff --git a/spartan/client.go b/spartan/client.go index d77e791..aff9276 100644 --- a/spartan/client.go +++ b/spartan/client.go @@ -8,6 +8,7 @@ import ( "net" neturl "net/url" "strconv" + "strings" "tildegit.org/tjp/sliderule/internal/types" ) @@ -30,7 +31,10 @@ func NewClient() Client { // single request by default. This can be changed by altering the MaxRedirects field. const DefaultMaxRedirects int = 2 -var ExceededMaxRedirects = errors.New("spartan.Client: exceeded MaxRedirects") +var ( + ErrExceededMaxRedirects = errors.New("spartan.Client: exceeded MaxRedirects") + ErrInvalidRequest = errors.New("spartan.Client: request is invalid") +) // RoundTrip sends a single spartan request and returns its response. func (c Client) RoundTrip(ctx context.Context, request *types.Request) (*types.Response, error) { @@ -64,6 +68,13 @@ func (c Client) RoundTrip(ctx context.Context, request *types.Request) (*types.R } } + if request.Path == "" { + request.Path = "/" + } + if !strings.HasPrefix(request.Path, "/") { + return nil, ErrInvalidRequest + } + requestLine := host + " " + request.EscapedPath() + " " + strconv.Itoa(int(rdr.N)) + "\r\n" if _, err := conn.Write([]byte(requestLine)); err != nil { @@ -114,7 +125,7 @@ func (c Client) Fetch(ctx context.Context, url string) (*types.Response, error) u = prev.ResolveReference(u) } - return nil, ExceededMaxRedirects + return nil, ErrExceededMaxRedirects } func (c Client) IsRedirect(response *types.Response) bool { |