diff --git a/core/corehttp/gateway_handler.go b/core/corehttp/gateway_handler.go index 336169404..0a7e657de 100644 --- a/core/corehttp/gateway_handler.go +++ b/core/corehttp/gateway_handler.go @@ -372,7 +372,31 @@ func (i *gatewayHandler) getOrHeadHandler(ctx context.Context, w http.ResponseWr } } +type sizeReadSeeker interface { + Size() uint64 + + io.ReadSeeker +} + +type sizeSeeker struct { + sizeReadSeeker +} + +func (s *sizeSeeker) Seek(offset int64, whence int) (int64, error) { + if whence == io.SeekEnd && offset == 0 { + return int64(s.Size()), nil + } + + return s.sizeReadSeeker.Seek(offset, whence) +} + func (i *gatewayHandler) serverFile(w http.ResponseWriter, req *http.Request, name string, modtime time.Time, content io.ReadSeeker) { + if sp, ok := content.(sizeReadSeeker); ok { + content = &sizeSeeker{ + sizeReadSeeker: sp, + } + } + http.ServeContent(w, req, name, modtime, content) //TODO: check for errors in ServeContent.. somehow diff --git a/unixfs/io/pbdagreader.go b/unixfs/io/pbdagreader.go index 7ba63649f..dcd383460 100644 --- a/unixfs/io/pbdagreader.go +++ b/unixfs/io/pbdagreader.go @@ -188,6 +188,9 @@ func (dr *pbDagReader) Seek(offset int64, whence int) (int64, error) { if offset < 0 { return -1, errors.New("Invalid offset") } + if offset == dr.offset { + return offset, nil + } // Grab cached protobuf object (solely to make code look cleaner) pb := dr.pbdata @@ -239,6 +242,10 @@ func (dr *pbDagReader) Seek(offset int64, whence int) (int64, error) { return offset, nil case io.SeekCurrent: // TODO: be smarter here + if offset == 0 { + return dr.offset, nil + } + noffset := dr.offset + offset return dr.Seek(noffset, io.SeekStart) case io.SeekEnd: