From 8e99e8a818e62e4b3dbdfaf06b6aadbeccfb745f Mon Sep 17 00:00:00 2001 From: Leonard Lyubich Date: Thu, 24 Feb 2022 14:09:26 +0300 Subject: [PATCH] [#149] client: Do not finish on empty ID list in `ObjectListReader` In previous implementation `ObjectListReader.Read` returned `false` on server responded with empty ID list. This could cause premature end of reading since the protocol does not forbid intermediate empty lists. Do not stop if ID list from response body is empty. Signed-off-by: Leonard Lyubich --- client/object_search.go | 60 +++++++++++++++++++++++------------------ 1 file changed, 34 insertions(+), 26 deletions(-) diff --git a/client/object_search.go b/client/object_search.go index 9b932178..fc7fcdc0 100644 --- a/client/object_search.go +++ b/client/object_search.go @@ -136,34 +136,42 @@ func (x *ObjectListReader) Read(buf []oid.ID) (int, bool) { return read, true } - // receive next message - ok := x.ctxCall.readResponse() - if !ok { - return read, false + var ok bool + var ids []*v2refs.ObjectID + var i, ln, rem int + + for { + // receive next message + ok = x.ctxCall.readResponse() + if !ok { + return read, false + } + + // read new chunk of objects + ids = x.bodyResp.GetIDList() + + ln = len(ids) + if ln == 0 { + // just skip empty lists since they are not prohibited by protocol + continue + } + + if rem = len(buf) - read; ln > rem { + ln = rem + } + + for i = 0; i < ln; i++ { + buf[read+i] = *oid.NewIDFromV2(ids[i]) // need smth better + } + + read += ln + + // save the tail and break + x.tail = append(x.tail, ids[ln:]...) + + break } - // read new chunk of objects - ids := x.bodyResp.GetIDList() - ln := len(ids) - if ln == 0 { - x.ctxCall.err = io.EOF - return read, false - } - - buf = buf[read:] - if ln > len(buf) { - ln = len(buf) - } - - for i := 0; i < ln; i++ { - buf[i] = *oid.NewIDFromV2(ids[i]) // need smth better - } - - read += ln - - // save the tail - x.tail = append(x.tail, ids[ln:]...) - return read, true }