<s> import collections <EOL> class WriteBuffer ( object ) : <EOL> """<STR_LIT>""" <EOL> def __init__ ( self , use_memory_view_min_size = <NUM_LIT> ) : <EOL> """<STR_LIT>""" <EOL> self . use_memory_view_min_size = use_memory_view_min_size <EOL> self . _deque = collections . deque ( ) <EOL> self . clear ( ) <EOL> def clear ( self ) : <EOL> """<STR_LIT>""" <EOL> self . _deque . clear ( ) <EOL> self . _total_length = <NUM_LIT:0> <EOL> self . _has_view = False <EOL> def __str__ ( self ) : <EOL> return self . _tobytes ( ) <EOL> def __bytes__ ( self ) : <EOL> return self . _tobytes ( ) <EOL> def __len__ ( self ) : <EOL> return self . _total_length <EOL> def _tobytes ( self ) : <EOL> """<STR_LIT>""" <EOL> if not self . _has_view : <EOL> if len ( self . _deque ) == <NUM_LIT:0> : <EOL> return b"<STR_LIT>" <EOL> elif len ( self . _deque ) == <NUM_LIT:1> : <EOL> return self . _deque [ <NUM_LIT:0> ] <EOL> else : <EOL> return b"<STR_LIT>" . join ( self . _deque ) <EOL> else : <EOL> tmp = [ x . tobytes ( ) if isinstance ( x , memoryview ) else x <EOL> for x in self . _deque ] <EOL> return b"<STR_LIT>" . join ( tmp ) <EOL> def is_empty ( self ) : <EOL> """<STR_LIT>""" <EOL> return self . _total_length == <NUM_LIT:0> <EOL> def append ( self , data ) : <EOL> """<STR_LIT>""" <EOL> self . _append ( data , True ) <EOL> def appendleft ( self , data ) : <EOL> """<STR_LIT>""" <EOL> self . _append ( data , False ) <EOL> def _append ( self , data , right ) : <EOL> if isinstance ( data , WriteBuffer ) : <EOL> if right : <EOL> self . _deque . extend ( data . _deque ) <EOL> else : <EOL> self . _deque . extendleft ( data . _deque ) <EOL> self . _total_length += data . _total_length <EOL> self . _has_view = self . _has_view and data . _has_view <EOL> else : <EOL> length = len ( data ) <EOL> if length == <NUM_LIT:0> : <EOL> return <EOL> if isinstance ( data , memoryview ) : <EOL> self . _has_view = True <EOL> self . _total_length += length <EOL> if right : <EOL> self . _deque . append ( data ) <EOL> else : <EOL> self . _deque . appendleft ( data ) <EOL> def _get_pointer_or_memoryview ( self , data , data_length ) : <EOL> if data_length < self . use_memory_view_min_size or isinstance ( data , memoryview ) : <EOL> return data <EOL> else : <EOL> return memoryview ( data ) <EOL> def pop_chunk ( self , chunk_max_size ) : <EOL> """<STR_LIT>""" <EOL> if self . _total_length < chunk_max_size : <EOL> res = self . _tobytes ( ) <EOL> self . clear ( ) <EOL> return res <EOL> first_iteration = True <EOL> while True : <EOL> try : <EOL> data = self . _deque . popleft ( ) <EOL> data_length = len ( data ) <EOL> self . _total_length -= data_length <EOL> if first_iteration : <EOL> if data_length == chunk_max_size : <EOL> return data <EOL> elif data_length > chunk_max_size : <EOL> view = self . _get_pointer_or_memoryview ( data , <EOL> data_length ) <EOL> self . appendleft ( view [ chunk_max_size : ] ) <EOL> return view [ : chunk_max_size ] <EOL> else : <EOL> chunk_write_buffer = WriteBuffer ( ) <EOL> else : <EOL> if chunk_write_buffer . _total_length + data_length > chunk_max_size : <EOL> view = self . _get_pointer_or_memoryview ( data , <EOL> data_length ) <EOL> limit = chunk_max_size - chunk_write_buffer . _total_length - data_length <EOL> self . appendleft ( view [ limit : ] ) <EOL> data = view [ : limit ] <EOL> chunk_write_buffer . append ( data ) <EOL> if chunk_write_buffer . _total_length >= chunk_max_size : <EOL> break <EOL> except IndexError : <EOL> self . _has_view = False <EOL> break <EOL> first_iteration = False <EOL> return chunk_write_buffer . _tobytes ( ) </s>
