Skip to content
Snippets Groups Projects
Unverified Commit 5b452df2 authored by Richard van der Hoff's avatar Richard van der Hoff Committed by GitHub
Browse files

Run database updates in a transaction (#8265)

Fixes: #6467
parent 765437df
Branches
Tags
No related merge requests found
Fix logstanding bug which could lead to incomplete database upgrades on SQLite.
...@@ -19,12 +19,15 @@ import logging ...@@ -19,12 +19,15 @@ import logging
import os import os
import re import re
from collections import Counter from collections import Counter
from typing import TextIO from typing import Optional, TextIO
import attr import attr
from synapse.config.homeserver import HomeServerConfig
from synapse.storage.engines import BaseDatabaseEngine
from synapse.storage.engines.postgres import PostgresEngine from synapse.storage.engines.postgres import PostgresEngine
from synapse.storage.types import Cursor from synapse.storage.types import Connection, Cursor
from synapse.types import Collection
logger = logging.getLogger(__name__) logger = logging.getLogger(__name__)
...@@ -47,7 +50,12 @@ class UpgradeDatabaseException(PrepareDatabaseException): ...@@ -47,7 +50,12 @@ class UpgradeDatabaseException(PrepareDatabaseException):
pass pass
def prepare_database(db_conn, database_engine, config, databases=["main", "state"]): def prepare_database(
db_conn: Connection,
database_engine: BaseDatabaseEngine,
config: Optional[HomeServerConfig],
databases: Collection[str] = ["main", "state"],
):
"""Prepares a physical database for usage. Will either create all necessary tables """Prepares a physical database for usage. Will either create all necessary tables
or upgrade from an older schema version. or upgrade from an older schema version.
...@@ -57,15 +65,24 @@ def prepare_database(db_conn, database_engine, config, databases=["main", "state ...@@ -57,15 +65,24 @@ def prepare_database(db_conn, database_engine, config, databases=["main", "state
Args: Args:
db_conn: db_conn:
database_engine: database_engine:
config (synapse.config.homeserver.HomeServerConfig|None): config :
application config, or None if we are connecting to an existing application config, or None if we are connecting to an existing
database which we expect to be configured already database which we expect to be configured already
databases (list[str]): The name of the databases that will be used databases: The name of the databases that will be used
with this physical database. Defaults to all databases. with this physical database. Defaults to all databases.
""" """
try: try:
cur = db_conn.cursor() cur = db_conn.cursor()
# sqlite does not automatically start transactions for DDL / SELECT statements,
# so we start one before running anything. This ensures that any upgrades
# are either applied completely, or not at all.
#
# (psycopg2 automatically starts a transaction as soon as we run any statements
# at all, so this is redundant but harmless there.)
cur.execute("BEGIN TRANSACTION")
version_info = _get_or_create_schema_state(cur, database_engine) version_info = _get_or_create_schema_state(cur, database_engine)
if version_info: if version_info:
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Please register or to comment