@@ -44,21 +44,17 @@ class Paged(collections.Iterable):
4444 def __init__ (self , command , classes , raw_headers = None ):
4545 self .next_link = ""
4646 self .current_page = []
47+ self ._current_page_iter_index = 0
4748 self ._derserializer = Deserializer (classes )
4849 self ._get_next = command
4950 self ._response = None
5051 self ._raw_headers = raw_headers
5152
5253 def __iter__ (self ):
53- """Iterate over response items in current page, automatically
54- retrieves next page.
55- """
56- for i in self .current_page :
57- yield i
58-
59- while self .next_link is not None :
60- for i in self .next ():
61- yield i
54+ """Return 'self'."""
55+ # Since iteration mutates this object, consider it an iterator in-and-of
56+ # itself.
57+ return self
6258
6359 @classmethod
6460 def _get_subtype_map (cls ):
@@ -85,10 +81,21 @@ def reset(self):
8581 self .next_link = ""
8682 self .current_page = []
8783
88- def next (self ):
89- """Get next page."""
90- if self .next_link is None :
84+ def __next__ (self ):
85+ """Iterate through responses."""
86+ # Storing the list iterator might work out better, but there's no
87+ # guarantee that some code won't replace the list entirely with a copy,
88+ # invalidating an list iterator that might be saved between iterations.
89+ if self ._current_page_iter_index < len (self .current_page ):
90+ response = self .current_page [self ._current_page_iter_index ]
91+ self ._current_page_iter_index += 1
92+ return response
93+ elif self .next_link is None :
9194 raise GeneratorExit ("End of paging" )
92- self ._response = self ._get_next (self .next_link )
93- self ._derserializer (self , self ._response )
94- return self .current_page
95+ else :
96+ self ._current_page_iter_index = 0
97+ self ._response = self ._get_next (self .next_link )
98+ self ._derserializer (self , self ._response )
99+ return self .__next__ ()
100+
101+ next = __next__ # Python 2 compatibility.
0 commit comments