Skip to content
Snippets Groups Projects
Unverified Commit 0caf2a33 authored by Jonathan de Jong's avatar Jonathan de Jong Committed by GitHub
Browse files

Fix federation stall on concurrent access errors (#9639)

parent 4ecba9bd
No related branches found
No related tags found
No related merge requests found
Fix bug where federation sending can stall due to `concurrent access` database exceptions when it falls behind.
...@@ -22,7 +22,6 @@ from canonicaljson import encode_canonical_json ...@@ -22,7 +22,6 @@ from canonicaljson import encode_canonical_json
from synapse.metrics.background_process_metrics import wrap_as_background_process from synapse.metrics.background_process_metrics import wrap_as_background_process
from synapse.storage._base import SQLBaseStore, db_to_json from synapse.storage._base import SQLBaseStore, db_to_json
from synapse.storage.database import DatabasePool, LoggingTransaction from synapse.storage.database import DatabasePool, LoggingTransaction
from synapse.storage.engines import PostgresEngine, Sqlite3Engine
from synapse.types import JsonDict from synapse.types import JsonDict
from synapse.util.caches.expiringcache import ExpiringCache from synapse.util.caches.expiringcache import ExpiringCache
...@@ -312,49 +311,23 @@ class TransactionStore(TransactionWorkerStore): ...@@ -312,49 +311,23 @@ class TransactionStore(TransactionWorkerStore):
stream_ordering: the stream_ordering of the event stream_ordering: the stream_ordering of the event
""" """
return await self.db_pool.runInteraction( await self.db_pool.simple_upsert_many(
"store_destination_rooms_entries", table="destinations",
self._store_destination_rooms_entries_txn, key_names=("destination",),
destinations, key_values=[(d,) for d in destinations],
room_id, value_names=[],
stream_ordering, value_values=[],
desc="store_destination_rooms_entries_dests",
) )
def _store_destination_rooms_entries_txn(
self,
txn: LoggingTransaction,
destinations: Iterable[str],
room_id: str,
stream_ordering: int,
) -> None:
# ensure we have a `destinations` row for this destination, as there is
# a foreign key constraint.
if isinstance(self.database_engine, PostgresEngine):
q = """
INSERT INTO destinations (destination)
VALUES (?)
ON CONFLICT DO NOTHING;
"""
elif isinstance(self.database_engine, Sqlite3Engine):
q = """
INSERT OR IGNORE INTO destinations (destination)
VALUES (?);
"""
else:
raise RuntimeError("Unknown database engine")
txn.execute_batch(q, ((destination,) for destination in destinations))
rows = [(destination, room_id) for destination in destinations] rows = [(destination, room_id) for destination in destinations]
await self.db_pool.simple_upsert_many(
self.db_pool.simple_upsert_many_txn(
txn,
table="destination_rooms", table="destination_rooms",
key_names=("destination", "room_id"), key_names=("destination", "room_id"),
key_values=rows, key_values=rows,
value_names=["stream_ordering"], value_names=["stream_ordering"],
value_values=[(stream_ordering,)] * len(rows), value_values=[(stream_ordering,)] * len(rows),
desc="store_destination_rooms_entries_rooms",
) )
async def get_destination_last_successful_stream_ordering( async def get_destination_last_successful_stream_ordering(
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment