Это широко известный Python-метод, в котором замыкание захватывает переменные по имени, а не по значению.В результате все экземпляры сопрограммы fake_json
ссылаются на одну и ту же query
переменную , поэтому все в конечном итоге ссылаются на ее последнее известное значение.
Чтобы решить эту проблему, необходимо изменить определение:
@asyncio.coroutine
def fake_json(self):
return query
на формулировку, которая фиксирует значение query
, например:
@asyncio.coroutine
def fake_json(self, query=query):
return query
await asyncio.sleep(5)
помогает, потому чтоон позволяет process_query
завершиться до того, как значение query
изменится из-под ног.Вы получите тот же эффект с await process_query(R)
.
Две точки, не связанные с вопросом:
Декоратор @asyncio.coroutine
устарел и нет причин использовать его в новом коде (если только вы не нацелены на совместимость с Python до 3.5).Вместо этого просто определите fake_json
, используя async def
.
Вам не нужно звонить __get__
, чтобы связать self
с fake_json
, что даже неиспользуй это.Вы можете определить fake_json
, который не self
, и просто назначить R.json = fake_json
.