From 3ba5ab329165d8f39ceb335276e47e21dcab9748 Mon Sep 17 00:00:00 2001 From: Darien Raymond Date: Fri, 2 Dec 2016 15:06:04 +0100 Subject: [PATCH] bring back high volumn mode in adaptive reader --- common/io/reader.go | 32 +++++++++++++++++++++++++++----- common/io/reader_test.go | 9 ++++++++- 2 files changed, 35 insertions(+), 6 deletions(-) diff --git a/common/io/reader.go b/common/io/reader.go index 2e4288e0e..d0c01ca3b 100644 --- a/common/io/reader.go +++ b/common/io/reader.go @@ -16,28 +16,50 @@ type Reader interface { // AdaptiveReader is a Reader that adjusts its reading speed automatically. type AdaptiveReader struct { - reader io.Reader - allocate func() *alloc.Buffer + reader io.Reader + largeBuffer *alloc.Buffer + highVolumn bool } // NewAdaptiveReader creates a new AdaptiveReader. // The AdaptiveReader instance doesn't take the ownership of reader. func NewAdaptiveReader(reader io.Reader) *AdaptiveReader { return &AdaptiveReader{ - reader: reader, - allocate: alloc.NewBuffer, + reader: reader, } } // Read implements Reader.Read(). func (v *AdaptiveReader) Read() (*alloc.Buffer, error) { - buffer := v.allocate().Clear() + if v.highVolumn && v.largeBuffer.IsEmpty() { + if v.largeBuffer == nil { + v.largeBuffer = alloc.NewLocalBuffer(256 * 1024).Clear() + } + nBytes, err := v.largeBuffer.FillFrom(v.reader) + if err != nil { + return nil, err + } + if nBytes < alloc.BufferSize { + v.highVolumn = false + } + } + + buffer := alloc.NewBuffer().Clear() + if !v.largeBuffer.IsEmpty() { + buffer.FillFrom(v.largeBuffer) + return buffer, nil + } + _, err := buffer.FillFrom(v.reader) if err != nil { buffer.Release() return nil, err } + if buffer.IsFull() { + v.highVolumn = true + } + return buffer, nil } diff --git a/common/io/reader_test.go b/common/io/reader_test.go index 44b3cccbf..ff6eb0c8b 100644 --- a/common/io/reader_test.go +++ b/common/io/reader_test.go @@ -13,10 +13,17 @@ func TestAdaptiveReader(t *testing.T) { assert := assert.On(t) rawContent := make([]byte, 1024*1024) + buffer := bytes.NewBuffer(rawContent) - reader := NewAdaptiveReader(bytes.NewBuffer(rawContent)) + reader := NewAdaptiveReader(buffer) b1, err := reader.Read() assert.Error(err).IsNil() assert.Bool(b1.IsFull()).IsTrue() assert.Int(b1.Len()).Equals(alloc.BufferSize) + assert.Int(buffer.Len()).Equals(cap(rawContent) - alloc.BufferSize) + + b2, err := reader.Read() + assert.Error(err).IsNil() + assert.Bool(b2.IsFull()).IsTrue() + assert.Int(buffer.Len()).Equals(778272) }