【问题标题】:python gettext different languages at same timepython gettext同时使用不同的语言
【发布时间】:2023-03-04 07:28:08
【问题描述】:

我正在使用烧瓶,pybabel for i18n。有时我需要向我的用户发送电子邮件。我想用他们自己的语言发送电子邮件。语言代码存储在数据库中,所以问题是用正确的语言翻译模板。这是我的发送功能的一部分:

            lang = user.get_lang()
            subject = _('Subject')
            for user in users:
                if user.email:
                        body = render_template('emails/template.eml', user=user)
                        recipients = [user.email]
                        msg = Message(subject, html=body, recipients=recipients)
                        conn.send(msg)

以及模板示例:

{{ _('Hi {name}. How are you?').format(user.name) }}

我需要的只是set_langauge(lang) 之类的东西,我可以在每个模板渲染之前调用它。我该怎么做?

谢谢。

【问题讨论】:

    标签: python flask internationalization gettext python-babel


    【解决方案1】:

    我有下一个render_template 电子邮件功能:

    def render_template(template_name_or_list, **context):
    
        # get  request context
        ctx = _request_ctx_stack.top
    
        # check request context
        # if function called without request context
        # then call with `test_tequest_context`
        # this because I send email from celery tasks
        if ctx is None:
            with current_app.test_request_context():
                return render_template(template_name_or_list, **context)
    
        # I have specific locale detection (from url)
        # and also use `lang` variable in template for `url_for` links
        # so you can just pass language parameter without context parameter
        # and always set `babel_locate` with passed language
        locale = getattr(ctx, 'babel_locale', None)
        if locale is None:
            ctx.babel_locale = Locale.parse(context['lang'])
    
        # render template without additinals context processor
        # because I don't need this context for emails
        # (compare with default flask `render_template` function)
        return _render(ctx.app.jinja_env.get_or_select_template(
            template_name_or_list), context, ctx.app)
    

    因此,如果您只需要在请求上下文中更改语言,请使用下一个代码(请参阅get_locale):

    def set_langauge(lang)
        ctx = _request_ctx_stack.top
        ctx.babel_locale = Locale.parse(lang)
    

    【讨论】:

      【解决方案2】:

      感谢@tbicr,我最终得到了这个解决方案。

      在我的 app.py 中,我有 set_locale 函数:

      from flask import _request_ctx_stack as ctx_stack
      # ...
      def set_locale(lang):
          ctx = ctx_stack.top
          ctx.babel_locale = lang
      # ...
      

      我在渲染电子邮件模板之前调用它。

      问题是我需要同时向许多不同语言的用户发送电子邮件:

      with app.test_request_context():
          with mail.connect() as conn:
              for user in users:
                  set_locale(user.get_lang())
                  subject = _(u'Best works').format(get_month_display(month))
                  body = render_template('emails/best_works.eml'
                      recipients = [user.email]
                      msg = Message(subject, html=body, recipients=recipients)
                      conn.send(msg)
      

      当我第一次调用 set_locale 时,locale 的值被缓存并且所有电子邮件都以第一个用户的语言呈现。

      解决方法是在set_locale之后每次调用flaskext.babel.refresh

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 2021-12-22
        • 2022-01-13
        • 1970-01-01
        • 2011-12-17
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多