lionsoul2014/ip2region · error
seek to get xdb file length: %w
Error message
seek to get xdb file length: %w
What it means
LoadContent seeks to offset 0 (to measure and stream the whole file) before io.ReadAll. If Seek(0,0) fails, the error is wrapped as 'seek to get xdb file length: %w'. It indicates the content could not be loaded because the handle is not seekable or the seek failed.
Source
Thrown at binding/golang/xdb/util.go:274
if err != nil {
return nil, fmt.Errorf("open xdb file `%s`: %w", dbFile, err)
}
defer handle.Close()
vIndex, err := LoadVectorIndex(handle)
if err != nil {
return nil, err
}
return vIndex, nil
}
// LoadContent load the whole xdb content from the specified file handle
func LoadContent(handle io.ReadSeeker) ([]byte, error) {
// seek to the head of the file
_, err := handle.Seek(0, 0)
if err != nil {
return nil, fmt.Errorf("seek to get xdb file length: %w", err)
}
return io.ReadAll(handle)
}
// LoadContentFromFile load the whole xdb content from the specified db file path
func LoadContentFromFile(dbFile string) ([]byte, error) {
handle, err := os.OpenFile(dbFile, os.O_RDONLY, 0600)
if err != nil {
return nil, fmt.Errorf("open xdb file `%s`: %w", dbFile, err)
}
defer handle.Close()
cBuff, err := LoadContent(handle)
if err != nil {
return nil, err
}
View on GitHub (pinned to c1a1fc7d59)
Solutions
- Pass an io.ReadSeeker (*os.File, bytes.Reader); if the source is a stream, buffer it fully with io.ReadAll first and wrap in bytes.NewReader.
- Use LoadContentFromFS for embedded files instead of ad-hoc stream handling.
- Unwrap the error to find the underlying seek failure.
Example fix
// before content, err := xdb.LoadContent(cmd.StdoutPipe()) // not seekable // after raw, _ := io.ReadAll(cmd.StdoutPipe()) content, err := xdb.LoadContent(bytes.NewReader(raw))
Defensive patterns
Strategy: type-guard
Validate before calling
func isSeekable(r io.Reader) bool {
_, ok := r.(io.Seeker)
return ok
} Type guard
func asReadSeeker(r io.Reader) (io.ReadSeeker, bool) {
s, ok := r.(io.ReadSeeker)
return s, ok
} Try / catch
cBuff, err := xdb.LoadContent(handle)
if err != nil {
if strings.Contains(err.Error(), "seek to get xdb file length") {
return fmt.Errorf("source is not seekable: %w", err)
}
return err
} Prevention
- Wrap stream sources in bytes.NewReader after full buffering
- Do not pass bufio.Reader, pipes, or HTTP bodies directly
- Prefer the FromFile/FromFS loaders for disk and embedded sources
When it happens
Trigger: Calling LoadContent (or LoadContentFromFile-backed searchers) with a non-seekable io.ReadSeeker — pipes, network streams, stdin — or a broken/closed descriptor.
Common situations: Piping an xdb from curl into the program and passing the pipe reader directly; reading from a gzip stream without buffering; wrapping the file in a bufio.Reader (which is not a Seeker).
Related errors
- seek to the header: %w
- seek to vector index: %w
- incomplete read: readed bytes should be %d
- invalid input buffer
- read vector index block at %d: %w
AI-assisted analysis of lionsoul2014/ip2region@c1a1fc7d59 (2026-09-02).
Data as JSON: /api/errors/ad2efa66c63b8671.
Report an issue: GitHub.