Пример #1
0
    def test_do_change_realm_description_clears_cached_descriptions(self) -> None:
        realm = get_realm("zulip")
        rendered_description = get_realm_rendered_description(realm)
        text_description = get_realm_text_description(realm)

        realm.description = "New description"
        realm.save(update_fields=["description"])

        new_rendered_description = get_realm_rendered_description(realm)
        self.assertNotEqual(rendered_description, new_rendered_description)
        self.assertIn(realm.description, new_rendered_description)

        new_text_description = get_realm_text_description(realm)
        self.assertNotEqual(text_description, new_text_description)
        self.assertEqual(realm.description, new_text_description)
Пример #2
0
def login_context(request: HttpRequest) -> Dict[str, Any]:
    realm = get_realm_from_request(request)

    if realm is None:
        realm_description = None
        realm_invite_required = False
        realm_web_public_access_enabled = False
    else:
        realm_description = get_realm_rendered_description(realm)
        realm_invite_required = realm.invite_required
        # We offer web-public access only if the realm has actual web
        # public streams configured, in addition to having it enabled.
        realm_web_public_access_enabled = realm.allow_web_public_streams_access(
        )

    context: Dict[str, Any] = {
        "realm_invite_required": realm_invite_required,
        "realm_description": realm_description,
        "require_email_format_usernames":
        require_email_format_usernames(realm),
        "password_auth_enabled": password_auth_enabled(realm),
        "two_factor_authentication_enabled":
        settings.TWO_FACTOR_AUTHENTICATION_ENABLED,
        "realm_web_public_access_enabled": realm_web_public_access_enabled,
    }

    if realm is not None and realm.description:
        context["OPEN_GRAPH_TITLE"] = realm.name
        context["OPEN_GRAPH_DESCRIPTION"] = get_realm_text_description(realm)

    # Add the keys for our standard authentication backends.
    no_auth_enabled = True
    for auth_backend_name in AUTH_BACKEND_NAME_MAP:
        name_lower = auth_backend_name.lower()
        key = f"{name_lower}_auth_enabled"
        is_enabled = auth_enabled_helper([auth_backend_name], realm)
        context[key] = is_enabled
        if is_enabled:
            no_auth_enabled = False

    context["external_authentication_methods"] = get_external_method_dicts(
        realm)
    context["no_auth_enabled"] = no_auth_enabled

    # Include another copy of external_authentication_methods in page_params for use
    # by the desktop client. We expand it with IDs of the <button> elements corresponding
    # to the authentication methods.
    context["page_params"] = dict(
        external_authentication_methods=get_external_method_dicts(realm), )
    for auth_dict in context["page_params"]["external_authentication_methods"]:
        auth_dict["button_id_suffix"] = "auth_button_{}".format(
            auth_dict["name"])

    return context
Пример #3
0
def login_context(request: HttpRequest) -> Dict[str, Any]:
    realm = get_realm_from_request(request)

    if realm is None:
        realm_description = None
        realm_invite_required = False
    else:
        realm_description = get_realm_rendered_description(realm)
        realm_invite_required = realm.invite_required

    context: Dict[str, Any] = {
        'realm_invite_required':
        realm_invite_required,
        'realm_description':
        realm_description,
        'require_email_format_usernames':
        require_email_format_usernames(realm),
        'password_auth_enabled':
        password_auth_enabled(realm),
        'any_social_backend_enabled':
        any_social_backend_enabled(realm),
        'two_factor_authentication_enabled':
        settings.TWO_FACTOR_AUTHENTICATION_ENABLED,
    }

    if realm is not None and realm.description:
        context['OPEN_GRAPH_TITLE'] = realm.name
        context['OPEN_GRAPH_DESCRIPTION'] = get_realm_text_description(realm)

    # Add the keys for our standard authentication backends.
    no_auth_enabled = True
    for auth_backend_name in AUTH_BACKEND_NAME_MAP:
        name_lower = auth_backend_name.lower()
        key = f"{name_lower}_auth_enabled"
        is_enabled = auth_enabled_helper([auth_backend_name], realm)
        context[key] = is_enabled
        if is_enabled:
            no_auth_enabled = False

    context['external_authentication_methods'] = get_external_method_dicts(
        realm)
    context['no_auth_enabled'] = no_auth_enabled

    # Include another copy of external_authentication_methods in page_params for use
    # by the desktop client. We expand it with IDs of the <button> elements corresponding
    # to the authentication methods.
    context['page_params'] = dict(
        external_authentication_methods=get_external_method_dicts(realm), )
    for auth_dict in context['page_params']['external_authentication_methods']:
        auth_dict['button_id_suffix'] = "auth_button_{}".format(
            auth_dict['name'])

    return context
Пример #4
0
def login_context(request: HttpRequest) -> Dict[str, Any]:
    realm = get_realm_from_request(request)

    if realm is None:
        realm_description = None
        realm_invite_required = False
    else:
        realm_description = get_realm_rendered_description(realm)
        realm_invite_required = realm.invite_required

    context = {
        'realm_invite_required': realm_invite_required,
        'realm_description': realm_description,
        'require_email_format_usernames': require_email_format_usernames(realm),
        'password_auth_enabled': password_auth_enabled(realm),
        'any_oauth_backend_enabled': any_oauth_backend_enabled(realm),
        'two_factor_authentication_enabled': settings.TWO_FACTOR_AUTHENTICATION_ENABLED,
    }  # type: Dict[str, Any]

    # Add the keys for our standard authentication backends.
    no_auth_enabled = True
    social_backends = []
    for auth_backend_name in AUTH_BACKEND_NAME_MAP:
        name_lower = auth_backend_name.lower()
        key = "%s_auth_enabled" % (name_lower,)
        is_enabled = auth_enabled_helper([auth_backend_name], realm)
        context[key] = is_enabled
        if is_enabled:
            no_auth_enabled = False

        # Now add the enabled social backends to the social_backends
        # list used to generate buttons for login/register pages.
        backend = AUTH_BACKEND_NAME_MAP[auth_backend_name]
        if not is_enabled or backend not in SOCIAL_AUTH_BACKENDS:
            continue
        social_backends.append({
            'name': backend.name,
            'display_name': backend.auth_backend_name,
            'login_url': reverse('login-social', args=(backend.name,)),
            'signup_url': reverse('signup-social', args=(backend.name,)),
            'sort_order': backend.sort_order,
        })
    context['social_backends'] = sorted(social_backends, key=lambda x: x['sort_order'], reverse=True)
    context['no_auth_enabled'] = no_auth_enabled

    return context
Пример #5
0
def login_context(request: HttpRequest) -> Dict[str, Any]:
    realm = get_realm_from_request(request)

    if realm is None:
        realm_description = None
        realm_invite_required = False
    else:
        realm_description = get_realm_rendered_description(realm)
        realm_invite_required = realm.invite_required

    context = {
        'realm_invite_required':
        realm_invite_required,
        'realm_description':
        realm_description,
        'require_email_format_usernames':
        require_email_format_usernames(realm),
        'password_auth_enabled':
        password_auth_enabled(realm),
        'any_social_backend_enabled':
        any_social_backend_enabled(realm),
        'two_factor_authentication_enabled':
        settings.TWO_FACTOR_AUTHENTICATION_ENABLED,
    }  # type: Dict[str, Any]

    if realm is not None and realm.description:
        context['OPEN_GRAPH_TITLE'] = realm.name
        context['OPEN_GRAPH_DESCRIPTION'] = get_realm_text_description(realm)

    # Add the keys for our standard authentication backends.
    no_auth_enabled = True
    for auth_backend_name in AUTH_BACKEND_NAME_MAP:
        name_lower = auth_backend_name.lower()
        key = "%s_auth_enabled" % (name_lower, )
        is_enabled = auth_enabled_helper([auth_backend_name], realm)
        context[key] = is_enabled
        if is_enabled:
            no_auth_enabled = False

    context['external_authentication_methods'] = get_external_method_dicts(
        realm)
    context['no_auth_enabled'] = no_auth_enabled

    return context
Пример #6
0
def build_page_params_for_home_page_load(
    request: HttpRequest,
    user_profile: Optional[UserProfile],
    realm: Realm,
    insecure_desktop_app: bool,
    narrow: List[List[str]],
    narrow_stream: Optional[Stream],
    narrow_topic: Optional[str],
    first_in_realm: bool,
    prompt_for_invites: bool,
    needs_tutorial: bool,
) -> Tuple[int, Dict[str, Any]]:
    """
    This function computes page_params for when we load the home page.

    The page_params data structure gets sent to the client.
    """
    client_capabilities = {
        "notification_settings_null": True,
        "bulk_message_deletion": True,
        "user_avatar_url_field_optional": True,
        "stream_typing_notifications":
        False,  # Set this to True when frontend support is implemented.
        "user_settings_object": True,
    }

    if user_profile is not None:
        client = RequestNotes.get_notes(request).client
        assert client is not None
        register_ret = do_events_register(
            user_profile,
            realm,
            client,
            apply_markdown=True,
            client_gravatar=True,
            slim_presence=True,
            client_capabilities=client_capabilities,
            narrow=narrow,
            include_streams=False,
        )
        default_language = register_ret["user_settings"]["default_language"]
    else:
        # The spectator client will be fetching the /register response
        # for spectators via the API. But we still need to set the
        # values not presence in that object.
        register_ret = {
            "queue_id": None,
        }
        default_language = realm.default_language

    furthest_read_time = get_furthest_read_time(user_profile)

    request_language = get_and_set_request_language(
        request,
        default_language,
        translation.get_language_from_path(request.path_info),
    )

    two_fa_enabled = settings.TWO_FACTOR_AUTHENTICATION_ENABLED and user_profile is not None
    billing_info = get_billing_info(user_profile)
    user_permission_info = get_user_permission_info(user_profile)

    # Pass parameters to the client-side JavaScript code.
    # These end up in a JavaScript Object named 'page_params'.
    page_params = dict(
        ## Server settings.
        test_suite=settings.TEST_SUITE,
        insecure_desktop_app=insecure_desktop_app,
        login_page=settings.HOME_NOT_LOGGED_IN,
        warn_no_email=settings.WARN_NO_EMAIL,
        search_pills_enabled=settings.SEARCH_PILLS_ENABLED,
        # Only show marketing email settings if on Zulip Cloud
        corporate_enabled=settings.CORPORATE_ENABLED,
        ## Misc. extra data.
        language_list=get_language_list(),
        needs_tutorial=needs_tutorial,
        first_in_realm=first_in_realm,
        prompt_for_invites=prompt_for_invites,
        furthest_read_time=furthest_read_time,
        bot_types=get_bot_types(user_profile),
        two_fa_enabled=two_fa_enabled,
        apps_page_url=get_apps_page_url(),
        show_billing=billing_info.show_billing,
        promote_sponsoring_zulip=promote_sponsoring_zulip_in_realm(realm),
        show_plans=billing_info.show_plans,
        show_webathena=user_permission_info.show_webathena,
        # Adding two_fa_enabled as condition saves us 3 queries when
        # 2FA is not enabled.
        two_fa_enabled_user=two_fa_enabled
        and bool(default_device(user_profile)),
        is_spectator=user_profile is None,
        # There is no event queue for spectators since
        # events support for spectators is not implemented yet.
        no_event_queue=user_profile is None,
    )

    for field_name in register_ret.keys():
        page_params[field_name] = register_ret[field_name]

    if narrow_stream is not None:
        # In narrow_stream context, initial pointer is just latest message
        recipient = narrow_stream.recipient
        try:
            max_message_id = (Message.objects.filter(
                recipient=recipient).order_by("id").reverse()[0].id)
        except IndexError:
            max_message_id = -1
        page_params["narrow_stream"] = narrow_stream.name
        if narrow_topic is not None:
            page_params["narrow_topic"] = narrow_topic
        page_params["narrow"] = [
            dict(operator=term[0], operand=term[1]) for term in narrow
        ]
        page_params["max_message_id"] = max_message_id
        assert isinstance(page_params["user_settings"], dict)
        page_params["user_settings"]["enable_desktop_notifications"] = False

    page_params["translation_data"] = get_language_translation_data(
        request_language)

    if user_profile is None:
        # Get rendered version of realm description which is displayed in right
        # sidebar for spectator.
        page_params[
            "realm_rendered_description"] = get_realm_rendered_description(
                realm)

    return register_ret["queue_id"], page_params
Пример #7
0
def zulip_default_context(request: HttpRequest) -> Dict[str, Any]:
    """Context available to all Zulip Jinja2 templates that have a request
    passed in.  Designed to provide the long list of variables at the
    bottom of this function in a wide range of situations: logged-in
    or logged-out, subdomains or not, etc.

    The main variable in the below is whether we know what realm the
    user is trying to interact with.
    """
    realm = get_realm_from_request(request)

    if realm is None:
        realm_uri = settings.ROOT_DOMAIN_URI
        realm_name = None
        realm_icon = None
        realm_description = None
        realm_invite_required = False
        realm_plan_type = 0
    else:
        realm_uri = realm.uri
        realm_name = realm.name
        realm_icon = get_realm_icon_url(realm)
        realm_description = get_realm_rendered_description(realm)
        realm_invite_required = realm.invite_required
        realm_plan_type = realm.plan_type

    register_link_disabled = settings.REGISTER_LINK_DISABLED
    login_link_disabled = settings.LOGIN_LINK_DISABLED
    find_team_link_disabled = settings.FIND_TEAM_LINK_DISABLED
    allow_search_engine_indexing = False

    if (settings.ROOT_DOMAIN_LANDING_PAGE
            and get_subdomain(request) == Realm.SUBDOMAIN_FOR_ROOT_DOMAIN):
        register_link_disabled = True
        login_link_disabled = True
        find_team_link_disabled = False
        allow_search_engine_indexing = True

    apps_page_url = 'https://zulipchat.com/apps/'
    if settings.ZILENCER_ENABLED:
        apps_page_url = '/apps/'

    user_is_authenticated = False
    if hasattr(request, 'user') and hasattr(request.user, 'is_authenticated'):
        user_is_authenticated = request.user.is_authenticated.value

    if settings.DEVELOPMENT:
        secrets_path = "zproject/dev-secrets.conf"
        settings_path = "zproject/dev_settings.py"
        settings_comments_path = "zproject/prod_settings_template.py"
    else:
        secrets_path = "/etc/zulip/zulip-secrets.conf"
        settings_path = "/etc/zulip/settings.py"
        settings_comments_path = "/etc/zulip/settings.py"

    # We can't use request.client here because we might not be using
    # an auth decorator that sets it, but we can call its helper to
    # get the same result.
    platform = get_client_name(request, True)

    context = {
        'root_domain_landing_page': settings.ROOT_DOMAIN_LANDING_PAGE,
        'custom_logo_url': settings.CUSTOM_LOGO_URL,
        'register_link_disabled': register_link_disabled,
        'login_link_disabled': login_link_disabled,
        'terms_of_service': settings.TERMS_OF_SERVICE,
        'privacy_policy': settings.PRIVACY_POLICY,
        'login_url': settings.HOME_NOT_LOGGED_IN,
        'only_sso': settings.ONLY_SSO,
        'external_host': settings.EXTERNAL_HOST,
        'external_uri_scheme': settings.EXTERNAL_URI_SCHEME,
        'realm_invite_required': realm_invite_required,
        'realm_uri': realm_uri,
        'realm_name': realm_name,
        'realm_icon': realm_icon,
        'realm_description': realm_description,
        'realm_plan_type': realm_plan_type,
        'root_domain_uri': settings.ROOT_DOMAIN_URI,
        'apps_page_url': apps_page_url,
        'open_realm_creation': settings.OPEN_REALM_CREATION,
        'password_auth_enabled': password_auth_enabled(realm),
        'require_email_format_usernames':
        require_email_format_usernames(realm),
        'any_oauth_backend_enabled': any_oauth_backend_enabled(realm),
        'development_environment': settings.DEVELOPMENT,
        'support_email': FromAddress.SUPPORT,
        'find_team_link_disabled': find_team_link_disabled,
        'password_min_length': settings.PASSWORD_MIN_LENGTH,
        'password_min_guesses': settings.PASSWORD_MIN_GUESSES,
        'jitsi_server_url': settings.JITSI_SERVER_URL,
        'two_factor_authentication_enabled':
        settings.TWO_FACTOR_AUTHENTICATION_ENABLED,
        'zulip_version': ZULIP_VERSION,
        'latest_release_version': LATEST_RELEASE_VERSION,
        'latest_major_version': LATEST_MAJOR_VERSION,
        'latest_release_announcement': LATEST_RELEASE_ANNOUNCEMENT,
        'user_is_authenticated': user_is_authenticated,
        'settings_path': settings_path,
        'secrets_path': secrets_path,
        'settings_comments_path': settings_comments_path,
        'platform': platform,
        'allow_search_engine_indexing': allow_search_engine_indexing,
    }

    # Add the keys for our standard authentication backends.
    no_auth_enabled = True
    social_backends = []
    for auth_backend_name in AUTH_BACKEND_NAME_MAP:
        name_lower = auth_backend_name.lower()
        key = "%s_auth_enabled" % (name_lower, )
        is_enabled = auth_enabled_helper([auth_backend_name], realm)
        context[key] = is_enabled
        if is_enabled:
            no_auth_enabled = False

        # Now add the enabled social backends to the social_backends
        # list used to generate buttons for login/register pages.
        backend = AUTH_BACKEND_NAME_MAP[auth_backend_name]
        if not is_enabled or backend not in SOCIAL_AUTH_BACKENDS:
            continue
        social_backends.append({
            'name':
            backend.name,
            'display_name':
            backend.auth_backend_name,
            'login_url':
            reverse('login-social', args=(backend.name, )),
            'signup_url':
            reverse('signup-social', args=(backend.name, )),
            'sort_order':
            backend.sort_order,
        })
    context['social_backends'] = sorted(social_backends,
                                        key=lambda x: x['sort_order'],
                                        reverse=True)
    context["no_auth_enabled"] = no_auth_enabled

    return context