def render()

in lib/l10n_utils/__init__.py [0:0]


def render(request, template, context=None, ftl_files=None, activation_files=None, **kwargs):
    """
    Same as django's render() shortcut, but with l10n template support.
    If used like this::

        return l10n_utils.render(request, 'myapp/mytemplate.html')

    ... this helper will render the following template::

        l10n/LANG/myapp/mytemplate.html

    if present, otherwise, it'll render the specified (en-US) template.
    """
    # use copy() here to avoid modifying the dict in a view that will then
    # be different on the next call to the view.
    context = context.copy() if context else {}
    l10n = None
    ftl_files = ftl_files or context.get("ftl_files")
    locale = get_locale(request)

    # is this a non-locale page?
    name_prefix = request.path_info.split("/", 2)[1]
    non_locale_url = name_prefix in settings.SUPPORTED_NONLOCALES or request.path_info in settings.SUPPORTED_LOCALE_IGNORE

    # is this a CMS page?
    is_cms_page = hasattr(request, "is_cms_page") and request.is_cms_page

    # Make sure we have a single template
    if isinstance(template, list):
        template = template[0]

    if ftl_files:
        if isinstance(ftl_files, str):
            ftl_files = [ftl_files]

        # do not use list.extend() or += here to avoid modifying
        # the original list passed to the function
        ftl_files = ftl_files + settings.FLUENT_DEFAULT_FILES

        context["fluent_l10n"] = l10n = fluent_l10n([locale, "en"], ftl_files)
    else:
        context["fluent_l10n"] = fluent_l10n([locale, "en"], settings.FLUENT_DEFAULT_FILES)

    context["fluent_files"] = ftl_files or settings.FLUENT_DEFAULT_FILES
    context["template"] = template
    context["template_source_url"] = template_source_url(template)

    # if it's a CMS page, draw the active locales from the Page data.
    # if `active_locales` is given use it as the full list of active translations
    translations = []

    if is_cms_page and request._locales_available_via_cms:
        translations = request._locales_available_via_cms
    elif "active_locales" in context:
        translations = context["active_locales"]
        del context["active_locales"]
    else:
        if activation_files:
            translations = set()
            for af in activation_files:
                translations.update(ftl_active_locales(af))
            translations = sorted(translations)  # `sorted` returns a list.
        elif l10n:
            translations = l10n.active_locales

        # if `add_active_locales` is given then add it to the translations for the template
        if "add_active_locales" in context:
            translations.extend(context["add_active_locales"])
            del context["add_active_locales"]

        if not translations:
            translations = [settings.LANGUAGE_CODE]

    context["translations"] = get_translations_native_names(translations)

    # Ensure the path requires a locale prefix.
    if not non_locale_url:
        # If the requested path's locale is different from the best matching
        # locale stored on the `request`, and that locale is one of the active
        # translations, redirect to it. Otherwise we need to find the best
        # matching locale.

        # Does that path's locale match the request's locale?
        # AND is it NOT for the root path with no discernable lang?
        if locale in translations and not is_root_path_with_no_language_clues(request):
            # Redirect to the locale if:
            # - The URL is the root path but is missing the trailing slash OR
            # - The locale isn't the current prefix in the URL
            if request.path == f"/{locale}" or locale != request.path.lstrip("/").partition("/")[0]:
                return redirect_to_locale(request, locale)
        else:
            return redirect_to_best_locale(request, translations)

        # Look for locale-specific template in app/templates/
        locale_tmpl = f".{locale}".join(splitext(template))
        try:
            return django_render(request, locale_tmpl, context, **kwargs)
        except TemplateDoesNotExist:
            pass

    # Render originally requested/default template.
    return django_render(request, template, context, **kwargs)