Сам Django является синхронным, но я недавно запустил новый проект Django и решил с нуля настроить его с нуля, что означало, что я следовал большинству проектов django-каналов, с собственными асинхронными http-потребителями каналов и протокольный маршрутизатор, и вместо использования daphne я запускал gunicorn с работниками uvloop.
Одна вещь, которая стала очевидной, это то, что использование ORM для запросов к моей базе данных не было асинхронным. В Интернете не было никакой информации о том, как решить эту проблему, поэтому я подумал, почему бы не использовать внешний асинхронный клиентский пакет postgres (aiopg
) и передать сгенерированный ORM SQL-запрос в aiopg
, а затем просто преобразовать результаты обратно в экземпляры модели Django. Это работало, но при использовании apache bench до и после использования async aiopg я не видел абсолютно никакого увеличения запросов в секунду.
Следующий код показывает, как я это сделал.
import aiopg
dsn = 'dbname=db user=root password=password123 host=postgres-container port=5432'
pool = aiopg.create_pool(dsn)
async def async_query(q):
async with pool.acquire() as conn:
async with conn.cursor() as cur:
await cur.execute(q)
ret = []
async for row in cur:
ret.append(row)
return ret
async def list(self, body):
query = Model.objects.all().order_by("title")
ares = await async_query(str(query.query))
results = [Model(**{
"id": i[0],
"title": i[1],
"created": i[2].replace(tzinfo=None),
"updated": i[3].replace(tzinfo=None)
}) for i in ares]
return {
"data": ModelSerializer(results, many=True).data
}
А затем с помощью Apache bench просто менялось количество одновременных запросов и общее количество запросов, но без изменений