MagicStack / MagicStack/asyncpg
asyncpg.exceptions.ReadOnlySQLTransactionError: cannot execute UNLISTEN during recovery
Chưa có ai nhận issue này.
- Ngôn ngữ chính
- Python
- Star
- 8.1k
- Fork
- 468
- Chỉ số merge pull request
- Không có pull request nào được merge trong 30 ngày
Mô tả
- asyncpg version: 0.22.0
- PostgreSQL version: 9.4
- Do you use a PostgreSQL SaaS? If so, which? Can you reproduce
the issue with a local PostgreSQL install?: Local PostgreSQL install - Python version: 3.8
- Platform: Linux
- Do you use pgbouncer?: Yes
- Did you install asyncpg with pip?: Yes
- If you built asyncpg locally, which version of Cython did you use?: 3.8?
- Can the issue be reproduced under both asyncio and
uvloop?:
When connected to a read-only replica (possibly reproducible even if not with connection server_settings={"options": "-c default_transaction_read_only=on"}), when asyncpg attempts to return the connection to the pool, its reset_query issues "UNLISTEN *" which results in the below:
...
File "/usr/local/lib/python3.8/site-packages/asyncpg/connection.py", line 1311, in reset
await self.execute(reset_query, timeout=timeout)
File "/usr/local/lib/python3.8/site-packages/asyncpg/connection.py", line 297, in execute
return await self._protocol.query(query, timeout)
File "asyncpg/protocol/protocol.pyx", line 336, in query
asyncpg.exceptions.ReadOnlySQLTransactionError: cannot execute UNLISTEN during recovery
UNLISTEN is a no-op in this context, and PostgreSQL 10.7+ ignore it with their patch "Allow UNLISTEN during recovery".
https://www.postgresql.org/docs/10/release-10-7.html
https://www.postgresql.org/message-id/15766.1548469030%40sss.pgh.pa.us
Ideally asyncpg could skip sending UNLISTEN when returning the connection to the pool when the connection is in recovery (read only), at least when connection server version is < 10.7.
A hacky workaround (so long as you are not using [UN]LISTEN) is to alter the connection's notifications capability as below after acquiring the connection from the pool:
conn._con._server_caps = conn._con._server_caps._replace(notifications=False)
Hướng dẫn đóng góp
Chưa lập chỉ mục được hướng dẫn đóng góp cho kho mã nguồn này
Bắt đầu từ đâu
- Đọc hết issue, rồi đọc hướng dẫn đóng góp của dự án.
- Bình luận trên issue rằng bạn sẽ nhận — tránh hai người làm cùng một việc.
- Fork repository và làm thay đổi trên một nhánh.
- Mở pull request có tham chiếu số hiệu của issue.
Hướng nghiên cứu
Bắt đầu trong asyncpg/connection.py tại Connection.reset, nơi reset_query được thực thi, và kiểm tra asyncpg/protocol/protocol.pyx để xem đường đi của truy vấn và cách xử lý khả năng của máy chủ. Tái hiện với một bản sao PostgreSQL chỉ đọc hoặc khi bật default_transaction_read_only; hoàn tất khi việc trả một kết nối như vậy về pool không còn gây lỗi trên UNLISTEN đối với các phiên bản máy chủ bị ảnh hưởng.
Do mô hình lập chỉ mục viết ra từ nội dung của issue.
Đánh giá
- Công nghệ
- postgresql, python
- Lĩnh vực
- databases
- Loại issue
- Lỗi
- Độ khó
- 3/5
- Thời gian dự kiến
- 1-2 ngày
- Mức độ hoạt động
- Đình trệ
- Độ rõ ràng
- Khá rõ ràng
- Mức phù hợp với người mới
- 38/100