benbjohnson/litestream · error
host required for webdav replica URL
Error message
host required for webdav replica URL
What it means
When parsing a webdav:// replica URL, NewReplicaClientFromURL requires a host component to build the client's base URL. This error is thrown when the URL parses but contains no host (e.g. 'webdav:///path' or 'webdav://').
Source
Thrown at webdav/replica_client.go:78
// This is used by the replica client factory registration.
// URL format: webdav://[user[:password]@]host[:port]/path or webdavs://... (for HTTPS)
func NewReplicaClientFromURL(scheme, host, urlPath string, query url.Values, userinfo *url.Userinfo) (litestream.ReplicaClient, error) {
client := NewReplicaClient()
// Determine HTTP or HTTPS based on scheme
httpScheme := "http"
if scheme == "webdavs" {
httpScheme = "https"
}
// Extract credentials from userinfo
if userinfo != nil {
client.Username = userinfo.Username()
client.Password, _ = userinfo.Password()
}
if host == "" {
return nil, fmt.Errorf("host required for webdav replica URL")
}
client.URL = fmt.Sprintf("%s://%s", httpScheme, host)
client.Path = urlPath
return client, nil
}
func (c *ReplicaClient) Type() string {
return ReplicaClientType
}
func (c *ReplicaClient) Init(ctx context.Context) error {
_, err := c.init(ctx)
return err
}
// init initializes the connection and returns the WebDAV client.View on GitHub (pinned to 4ed7a308f6)
Solutions
- Add the host to the replica URL: webdav://user:pass@myserver.example.com:port/path
- Check the config with 'litestream replicas' or re-read the YAML — ensure nothing stripped the host (e.g. $HOST env var empty)
- Validate the URL with a parser before applying config: u, err := url.Parse(s); u.Host != ""
- If credentials live in the URL, confirm the '@' separates userinfo from the host and no '/' got misplaced
Example fix
// before url: "webdav:///dav/litestream" // after url: "webdav://user:pass@dav.example.com:5005/dav/litestream"
Defensive patterns
Strategy: validation
Validate before calling
u, err := url.Parse(cfg.WebdavURL)
if err != nil { return err }
if u.Host == "" {
return fmt.Errorf("webdav replica URL %q has no host", cfg.WebdavURL)
} Type guard
func hasURLHost(raw string) bool {
u, err := url.Parse(raw)
return err == nil && u.Host != ""
} Try / catch
client, err := webdav.NewReplicaClientFromURL(raw)
if err != nil && strings.Contains(err.Error(), "host required") {
return fmt.Errorf("check webdav url in config, host part missing: %w", err)
} Prevention
- Validate replica URLs with url.Parse at config-load time
- Keep scheme, host and path on one line in YAML to avoid splitting
- Watch for empty env-var interpolation in templated URLs
- Include port explicitly when non-default
When it happens
Trigger: Configuring a replica URL like 'webdav:///dav' or 'webdav://:8080/path' (empty host), or programmatically passing a URL built without the host part.
Common situations: YAML config typo where the hostname was omitted or the URL was split across lines; templating/config expansion left the host variable empty (unset env var interpolated to nothing).
Understand the failure class
Background: "Invalid URL" / "URL cannot be empty": fix the malformed or missing URL behind request-construction failures — this error's family across 50 libraries.
Related errors
- heartbeat URL must be a valid HTTP or HTTPS URL
- cannot specify url & path for webdav replica
- cannot specify url & webdav-url for webdav replica
- webdav-url required for webdav replica
- file replica path required
AI-assisted analysis of benbjohnson/litestream@4ed7a308f6 (2026-09-06).
Data as JSON: /api/errors/697948c69d6d94f4.
Report an issue: GitHub.