mirror of
https://github.com/element-hq/synapse
synced 2024-08-20 05:00:20 +00:00
Sanity-check database before running upgrades (#6982)
Some of the database deltas rely on `config.server_name` being set correctly, so we should check that it is before running the deltas. Fixes #6870.
This commit is contained in:
parent
bbf8886a05
commit
e66f099ca9
3 changed files with 33 additions and 17 deletions
1
changelog.d/6982.feature
Normal file
1
changelog.d/6982.feature
Normal file
|
@ -0,0 +1 @@
|
||||||
|
Check that server_name is correctly set before running database updates.
|
|
@ -20,6 +20,7 @@ import logging
|
||||||
import time
|
import time
|
||||||
|
|
||||||
from synapse.api.constants import PresenceState
|
from synapse.api.constants import PresenceState
|
||||||
|
from synapse.config.homeserver import HomeServerConfig
|
||||||
from synapse.storage.database import Database
|
from synapse.storage.database import Database
|
||||||
from synapse.storage.engines import PostgresEngine
|
from synapse.storage.engines import PostgresEngine
|
||||||
from synapse.storage.util.id_generators import (
|
from synapse.storage.util.id_generators import (
|
||||||
|
@ -117,16 +118,6 @@ class DataStore(
|
||||||
self._clock = hs.get_clock()
|
self._clock = hs.get_clock()
|
||||||
self.database_engine = database.engine
|
self.database_engine = database.engine
|
||||||
|
|
||||||
all_users_native = are_all_users_on_domain(
|
|
||||||
db_conn.cursor(), database.engine, hs.hostname
|
|
||||||
)
|
|
||||||
if not all_users_native:
|
|
||||||
raise Exception(
|
|
||||||
"Found users in database not native to %s!\n"
|
|
||||||
"You cannot changed a synapse server_name after it's been configured"
|
|
||||||
% (hs.hostname,)
|
|
||||||
)
|
|
||||||
|
|
||||||
self._stream_id_gen = StreamIdGenerator(
|
self._stream_id_gen = StreamIdGenerator(
|
||||||
db_conn,
|
db_conn,
|
||||||
"events",
|
"events",
|
||||||
|
@ -567,13 +558,26 @@ class DataStore(
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|
||||||
def are_all_users_on_domain(txn, database_engine, domain):
|
def check_database_before_upgrade(cur, database_engine, config: HomeServerConfig):
|
||||||
|
"""Called before upgrading an existing database to check that it is broadly sane
|
||||||
|
compared with the configuration.
|
||||||
|
"""
|
||||||
|
domain = config.server_name
|
||||||
|
|
||||||
sql = database_engine.convert_param_style(
|
sql = database_engine.convert_param_style(
|
||||||
"SELECT COUNT(*) FROM users WHERE name NOT LIKE ?"
|
"SELECT COUNT(*) FROM users WHERE name NOT LIKE ?"
|
||||||
)
|
)
|
||||||
pat = "%:" + domain
|
pat = "%:" + domain
|
||||||
txn.execute(sql, (pat,))
|
cur.execute(sql, (pat,))
|
||||||
num_not_matching = txn.fetchall()[0][0]
|
num_not_matching = cur.fetchall()[0][0]
|
||||||
if num_not_matching == 0:
|
if num_not_matching == 0:
|
||||||
return True
|
return
|
||||||
return False
|
|
||||||
|
raise Exception(
|
||||||
|
"Found users in database not native to %s!\n"
|
||||||
|
"You cannot changed a synapse server_name after it's been configured"
|
||||||
|
% (domain,)
|
||||||
|
)
|
||||||
|
|
||||||
|
|
||||||
|
__all__ = ["DataStore", "check_database_before_upgrade"]
|
||||||
|
|
|
@ -278,13 +278,17 @@ def _upgrade_existing_database(
|
||||||
the current_version wasn't generated by applying those delta files.
|
the current_version wasn't generated by applying those delta files.
|
||||||
database_engine (DatabaseEngine)
|
database_engine (DatabaseEngine)
|
||||||
config (synapse.config.homeserver.HomeServerConfig|None):
|
config (synapse.config.homeserver.HomeServerConfig|None):
|
||||||
application config, or None if we are connecting to an existing
|
None if we are initialising a blank database, otherwise the application
|
||||||
database which we expect to be configured already
|
config
|
||||||
data_stores (list[str]): The names of the data stores to instantiate
|
data_stores (list[str]): The names of the data stores to instantiate
|
||||||
on the given database.
|
on the given database.
|
||||||
is_empty (bool): Is this a blank database? I.e. do we need to run the
|
is_empty (bool): Is this a blank database? I.e. do we need to run the
|
||||||
upgrade portions of the delta scripts.
|
upgrade portions of the delta scripts.
|
||||||
"""
|
"""
|
||||||
|
if is_empty:
|
||||||
|
assert not applied_delta_files
|
||||||
|
else:
|
||||||
|
assert config
|
||||||
|
|
||||||
if current_version > SCHEMA_VERSION:
|
if current_version > SCHEMA_VERSION:
|
||||||
raise ValueError(
|
raise ValueError(
|
||||||
|
@ -292,6 +296,13 @@ def _upgrade_existing_database(
|
||||||
+ "new for the server to understand"
|
+ "new for the server to understand"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
# some of the deltas assume that config.server_name is set correctly, so now
|
||||||
|
# is a good time to run the sanity check.
|
||||||
|
if not is_empty and "main" in data_stores:
|
||||||
|
from synapse.storage.data_stores.main import check_database_before_upgrade
|
||||||
|
|
||||||
|
check_database_before_upgrade(cur, database_engine, config)
|
||||||
|
|
||||||
start_ver = current_version
|
start_ver = current_version
|
||||||
if not upgraded:
|
if not upgraded:
|
||||||
start_ver += 1
|
start_ver += 1
|
||||||
|
|
Loading…
Reference in a new issue