realm: Prefetch group settings only for "/register" response.

This commit updates code to prefetch realm group settings like
"can_create_public_channel_group" only when computing settings
for "/register" response by refetching the realm object with
select_related instead of fetching those settings in UserProfile
query.

This change is done because we do not need to prefetch these
settings for every UserProfile object and for most of the cases
where these settings are actually accessed, we can afford extra
query like when checking permission to create streams. But we
cannot afford one query extra for each setting when computing
these settings for "/register" response, so we re-fetch the
realm object with select_related leading to only one extra
query.

The query count changes in tests are -
- Query count increases by 1 when calling fetch_initial_state_data
for computing can_create_public_streams because Realm object from
UserProfile does not have prefetched setting fields.

- Query count increases by one in test_subs where streams are
created which is as expected due to the setting not being prefetched.

- Query count increases by 2 in tests in test_home.py where one
query is to refetch the realm object and one for computing
can_create_public_streams as mentioned above.
This commit is contained in:
Sahil Batra
2024-06-12 19:13:02 +05:30
committed by Tim Abbott
parent dea62a3fd9
commit e23af20079
6 changed files with 34 additions and 16 deletions

View File

@@ -94,6 +94,7 @@ from zerver.models.realms import (
EditTopicPolicyEnum,
get_corresponding_policy_value_for_group_setting,
get_realm_domains,
get_realm_with_settings,
)
from zerver.models.streams import get_default_stream_groups
from zerver.tornado.django_api import get_user_events, request_event_queue
@@ -1642,6 +1643,11 @@ def do_events_register(
else:
event_types_set = None
# Fetch the realm object again to prefetch all the
# group settings which support anonymous groups
# to avoid unnecessary DB queries.
realm = get_realm_with_settings(realm_id=realm.id)
if user_profile is None:
# TODO: Unify the two fetch_initial_state_data code paths.
assert client_gravatar is False