Convert simple_delete to async/await. (#8191)

This commit is contained in:
Patrick Cloke 2020-08-27 14:16:41 -04:00 committed by GitHub
parent 9b7ac03af3
commit b71d4a094c
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
5 changed files with 90 additions and 37 deletions

1
changelog.d/8191.misc Normal file
View file

@ -0,0 +1 @@
Convert various parts of the codebase to async/await.

View file

@ -614,6 +614,7 @@ class DatabasePool(object):
"""Runs a single query for a result set. """Runs a single query for a result set.
Args: Args:
desc: description of the transaction, for logging and metrics
decoder - The function which can resolve the cursor results to decoder - The function which can resolve the cursor results to
something meaningful. something meaningful.
query - The query string to execute query - The query string to execute
@ -649,7 +650,7 @@ class DatabasePool(object):
or_ignore: bool stating whether an exception should be raised or_ignore: bool stating whether an exception should be raised
when a conflicting row already exists. If True, False will be when a conflicting row already exists. If True, False will be
returned by the function instead returned by the function instead
desc: string giving a description of the transaction desc: description of the transaction, for logging and metrics
Returns: Returns:
Whether the row was inserted or not. Only useful when `or_ignore` is True Whether the row was inserted or not. Only useful when `or_ignore` is True
@ -686,7 +687,7 @@ class DatabasePool(object):
Args: Args:
table: string giving the table name table: string giving the table name
values: dict of new column names and values for them values: dict of new column names and values for them
desc: string giving a description of the transaction desc: description of the transaction, for logging and metrics
""" """
await self.runInteraction(desc, self.simple_insert_many_txn, table, values) await self.runInteraction(desc, self.simple_insert_many_txn, table, values)
@ -700,7 +701,6 @@ class DatabasePool(object):
txn: The transaction to use. txn: The transaction to use.
table: string giving the table name table: string giving the table name
values: dict of new column names and values for them values: dict of new column names and values for them
desc: string giving a description of the transaction
""" """
if not values: if not values:
return return
@ -755,6 +755,7 @@ class DatabasePool(object):
keyvalues: The unique key columns and their new values keyvalues: The unique key columns and their new values
values: The nonunique columns and their new values values: The nonunique columns and their new values
insertion_values: additional key/values to use only when inserting insertion_values: additional key/values to use only when inserting
desc: description of the transaction, for logging and metrics
lock: True to lock the table when doing the upsert. lock: True to lock the table when doing the upsert.
Returns: Returns:
Native upserts always return None. Emulated upserts return True if a Native upserts always return None. Emulated upserts return True if a
@ -1081,6 +1082,7 @@ class DatabasePool(object):
retcols: list of strings giving the names of the columns to return retcols: list of strings giving the names of the columns to return
allow_none: If true, return None instead of failing if the SELECT allow_none: If true, return None instead of failing if the SELECT
statement returns no rows statement returns no rows
desc: description of the transaction, for logging and metrics
""" """
return await self.runInteraction( return await self.runInteraction(
desc, self.simple_select_one_txn, table, keyvalues, retcols, allow_none desc, self.simple_select_one_txn, table, keyvalues, retcols, allow_none
@ -1166,6 +1168,7 @@ class DatabasePool(object):
table: table name table: table name
keyvalues: column names and values to select the rows with keyvalues: column names and values to select the rows with
retcol: column whos value we wish to retrieve. retcol: column whos value we wish to retrieve.
desc: description of the transaction, for logging and metrics
Returns: Returns:
Results in a list Results in a list
@ -1190,6 +1193,7 @@ class DatabasePool(object):
column names and values to select the rows with, or None to not column names and values to select the rows with, or None to not
apply a WHERE clause. apply a WHERE clause.
retcols: the names of the columns to return retcols: the names of the columns to return
desc: description of the transaction, for logging and metrics
Returns: Returns:
A list of dictionaries. A list of dictionaries.
@ -1243,14 +1247,16 @@ class DatabasePool(object):
"""Executes a SELECT query on the named table, which may return zero or """Executes a SELECT query on the named table, which may return zero or
more rows, returning the result as a list of dicts. more rows, returning the result as a list of dicts.
Filters rows by if value of `column` is in `iterable`. Filters rows by whether the value of `column` is in `iterable`.
Args: Args:
table: string giving the table name table: string giving the table name
column: column name to test for inclusion against `iterable` column: column name to test for inclusion against `iterable`
iterable: list iterable: list
keyvalues: dict of column names and values to select the rows with
retcols: list of strings giving the names of the columns to return retcols: list of strings giving the names of the columns to return
keyvalues: dict of column names and values to select the rows with
desc: description of the transaction, for logging and metrics
batch_size: the number of rows for each select query
""" """
results = [] # type: List[Dict[str, Any]] results = [] # type: List[Dict[str, Any]]
@ -1291,7 +1297,7 @@ class DatabasePool(object):
"""Executes a SELECT query on the named table, which may return zero or """Executes a SELECT query on the named table, which may return zero or
more rows, returning the result as a list of dicts. more rows, returning the result as a list of dicts.
Filters rows by if value of `column` is in `iterable`. Filters rows by whether the value of `column` is in `iterable`.
Args: Args:
txn: Transaction object txn: Transaction object
@ -1367,6 +1373,7 @@ class DatabasePool(object):
table: string giving the table name table: string giving the table name
keyvalues: dict of column names and values to select the row with keyvalues: dict of column names and values to select the row with
updatevalues: dict giving column names and values to update updatevalues: dict giving column names and values to update
desc: description of the transaction, for logging and metrics
""" """
await self.runInteraction( await self.runInteraction(
desc, self.simple_update_one_txn, table, keyvalues, updatevalues desc, self.simple_update_one_txn, table, keyvalues, updatevalues
@ -1426,6 +1433,7 @@ class DatabasePool(object):
Args: Args:
table: string giving the table name table: string giving the table name
keyvalues: dict of column names and values to select the row with keyvalues: dict of column names and values to select the row with
desc: description of the transaction, for logging and metrics
""" """
await self.runInteraction(desc, self.simple_delete_one_txn, table, keyvalues) await self.runInteraction(desc, self.simple_delete_one_txn, table, keyvalues)
@ -1451,13 +1459,38 @@ class DatabasePool(object):
if txn.rowcount > 1: if txn.rowcount > 1:
raise StoreError(500, "More than one row matched (%s)" % (table,)) raise StoreError(500, "More than one row matched (%s)" % (table,))
def simple_delete(self, table: str, keyvalues: Dict[str, Any], desc: str): async def simple_delete(
return self.runInteraction(desc, self.simple_delete_txn, table, keyvalues) self, table: str, keyvalues: Dict[str, Any], desc: str
) -> int:
"""Executes a DELETE query on the named table.
Filters rows by the key-value pairs.
Args:
table: string giving the table name
keyvalues: dict of column names and values to select the row with
desc: description of the transaction, for logging and metrics
Returns:
The number of deleted rows.
"""
return await self.runInteraction(desc, self.simple_delete_txn, table, keyvalues)
@staticmethod @staticmethod
def simple_delete_txn( def simple_delete_txn(
txn: LoggingTransaction, table: str, keyvalues: Dict[str, Any] txn: LoggingTransaction, table: str, keyvalues: Dict[str, Any]
) -> int: ) -> int:
"""Executes a DELETE query on the named table.
Filters rows by the key-value pairs.
Args:
table: string giving the table name
keyvalues: dict of column names and values to select the row with
Returns:
The number of deleted rows.
"""
sql = "DELETE FROM %s WHERE %s" % ( sql = "DELETE FROM %s WHERE %s" % (
table, table,
" AND ".join("%s = ?" % (k,) for k in keyvalues), " AND ".join("%s = ?" % (k,) for k in keyvalues),
@ -1474,6 +1507,20 @@ class DatabasePool(object):
keyvalues: Dict[str, Any], keyvalues: Dict[str, Any],
desc: str, desc: str,
) -> int: ) -> int:
"""Executes a DELETE query on the named table.
Filters rows by if value of `column` is in `iterable`.
Args:
table: string giving the table name
column: column name to test for inclusion against `iterable`
iterable: list
keyvalues: dict of column names and values to select the rows with
desc: description of the transaction, for logging and metrics
Returns:
Number rows deleted
"""
return await self.runInteraction( return await self.runInteraction(
desc, self.simple_delete_many_txn, table, column, iterable, keyvalues desc, self.simple_delete_many_txn, table, column, iterable, keyvalues
) )

View file

@ -728,11 +728,13 @@ class GroupServerStore(GroupServerWorkerStore):
}, },
) )
def remove_room_from_summary(self, group_id, room_id, category_id): async def remove_room_from_summary(
self, group_id: str, room_id: str, category_id: str
) -> int:
if category_id is None: if category_id is None:
category_id = _DEFAULT_CATEGORY_ID category_id = _DEFAULT_CATEGORY_ID
return self.db_pool.simple_delete( return await self.db_pool.simple_delete(
table="group_summary_rooms", table="group_summary_rooms",
keyvalues={ keyvalues={
"group_id": group_id, "group_id": group_id,
@ -772,8 +774,8 @@ class GroupServerStore(GroupServerWorkerStore):
desc="upsert_group_category", desc="upsert_group_category",
) )
def remove_group_category(self, group_id, category_id): async def remove_group_category(self, group_id: str, category_id: str) -> int:
return self.db_pool.simple_delete( return await self.db_pool.simple_delete(
table="group_room_categories", table="group_room_categories",
keyvalues={"group_id": group_id, "category_id": category_id}, keyvalues={"group_id": group_id, "category_id": category_id},
desc="remove_group_category", desc="remove_group_category",
@ -809,8 +811,8 @@ class GroupServerStore(GroupServerWorkerStore):
desc="upsert_group_role", desc="upsert_group_role",
) )
def remove_group_role(self, group_id, role_id): async def remove_group_role(self, group_id: str, role_id: str) -> int:
return self.db_pool.simple_delete( return await self.db_pool.simple_delete(
table="group_roles", table="group_roles",
keyvalues={"group_id": group_id, "role_id": role_id}, keyvalues={"group_id": group_id, "role_id": role_id},
desc="remove_group_role", desc="remove_group_role",
@ -940,11 +942,13 @@ class GroupServerStore(GroupServerWorkerStore):
}, },
) )
def remove_user_from_summary(self, group_id, user_id, role_id): async def remove_user_from_summary(
self, group_id: str, user_id: str, role_id: str
) -> int:
if role_id is None: if role_id is None:
role_id = _DEFAULT_ROLE_ID role_id = _DEFAULT_ROLE_ID
return self.db_pool.simple_delete( return await self.db_pool.simple_delete(
table="group_summary_users", table="group_summary_users",
keyvalues={"group_id": group_id, "role_id": role_id, "user_id": user_id}, keyvalues={"group_id": group_id, "role_id": role_id, "user_id": user_id},
desc="remove_user_from_summary", desc="remove_user_from_summary",
@ -1264,16 +1268,16 @@ class GroupServerStore(GroupServerWorkerStore):
desc="update_remote_attestion", desc="update_remote_attestion",
) )
def remove_attestation_renewal(self, group_id, user_id): async def remove_attestation_renewal(self, group_id: str, user_id: str) -> int:
"""Remove an attestation that we thought we should renew, but actually """Remove an attestation that we thought we should renew, but actually
shouldn't. Ideally this would never get called as we would never shouldn't. Ideally this would never get called as we would never
incorrectly try and do attestations for local users on local groups. incorrectly try and do attestations for local users on local groups.
Args: Args:
group_id (str) group_id
user_id (str) user_id
""" """
return self.db_pool.simple_delete( return await self.db_pool.simple_delete(
table="group_attestations_renewals", table="group_attestations_renewals",
keyvalues={"group_id": group_id, "user_id": user_id}, keyvalues={"group_id": group_id, "user_id": user_id},
desc="remove_attestation_renewal", desc="remove_attestation_renewal",

View file

@ -529,21 +529,21 @@ class RegistrationWorkerStore(SQLBaseStore):
"user_get_threepids", "user_get_threepids",
) )
def user_delete_threepid(self, user_id, medium, address): async def user_delete_threepid(self, user_id, medium, address) -> None:
return self.db_pool.simple_delete( await self.db_pool.simple_delete(
"user_threepids", "user_threepids",
keyvalues={"user_id": user_id, "medium": medium, "address": address}, keyvalues={"user_id": user_id, "medium": medium, "address": address},
desc="user_delete_threepid", desc="user_delete_threepid",
) )
def user_delete_threepids(self, user_id: str): async def user_delete_threepids(self, user_id: str) -> None:
"""Delete all threepid this user has bound """Delete all threepid this user has bound
Args: Args:
user_id: The user id to delete all threepids of user_id: The user id to delete all threepids of
""" """
return self.db_pool.simple_delete( await self.db_pool.simple_delete(
"user_threepids", "user_threepids",
keyvalues={"user_id": user_id}, keyvalues={"user_id": user_id},
desc="user_delete_threepids", desc="user_delete_threepids",
@ -597,21 +597,20 @@ class RegistrationWorkerStore(SQLBaseStore):
desc="user_get_bound_threepids", desc="user_get_bound_threepids",
) )
def remove_user_bound_threepid(self, user_id, medium, address, id_server): async def remove_user_bound_threepid(
self, user_id: str, medium: str, address: str, id_server: str
) -> None:
"""The server proxied an unbind request to the given identity server on """The server proxied an unbind request to the given identity server on
behalf of the given user, so we remove the mapping of threepid to behalf of the given user, so we remove the mapping of threepid to
identity server. identity server.
Args: Args:
user_id (str) user_id
medium (str) medium
address (str) address
id_server (str) id_server
Returns:
Deferred
""" """
return self.db_pool.simple_delete( await self.db_pool.simple_delete(
table="user_threepid_id_server", table="user_threepid_id_server",
keyvalues={ keyvalues={
"user_id": user_id, "user_id": user_id,
@ -1247,14 +1246,14 @@ class RegistrationStore(RegistrationBackgroundUpdateStore):
desc="add_user_pending_deactivation", desc="add_user_pending_deactivation",
) )
def del_user_pending_deactivation(self, user_id): async def del_user_pending_deactivation(self, user_id: str) -> None:
""" """
Removes the given user to the table of users who need to be parted from all the Removes the given user to the table of users who need to be parted from all the
rooms they're in, effectively marking that user as fully deactivated. rooms they're in, effectively marking that user as fully deactivated.
""" """
# XXX: This should be simple_delete_one but we failed to put a unique index on # XXX: This should be simple_delete_one but we failed to put a unique index on
# the table, so somehow duplicate entries have ended up in it. # the table, so somehow duplicate entries have ended up in it.
return self.db_pool.simple_delete( await self.db_pool.simple_delete(
"users_pending_deactivation", "users_pending_deactivation",
keyvalues={"user_id": user_id}, keyvalues={"user_id": user_id},
desc="del_user_pending_deactivation", desc="del_user_pending_deactivation",

View file

@ -123,9 +123,11 @@ class EventPushActionsStoreTestCase(tests.unittest.TestCase):
yield _inject_actions(6, PlAIN_NOTIF) yield _inject_actions(6, PlAIN_NOTIF)
yield _rotate(7) yield _rotate(7)
yield self.store.db_pool.simple_delete( yield defer.ensureDeferred(
self.store.db_pool.simple_delete(
table="event_push_actions", keyvalues={"1": 1}, desc="" table="event_push_actions", keyvalues={"1": 1}, desc=""
) )
)
yield _assert_counts(1, 0) yield _assert_counts(1, 0)