Khi nào tôi nên sử dụng ugettext_lazy?


141

Tôi có một câu hỏi về việc sử dụng ugettext và ugettext_lazycho các bản dịch. Tôi đã học được rằng trong các mô hình tôi nên sử dụng ugettext_lazy, trong khi ở chế độ xem ugettext. Nhưng có nơi nào khác không, tôi cũng nên sử dụng ugettext_lazy? Những gì về định nghĩa hình thức? Có bất kỳ sự khác biệt hiệu suất giữa chúng?

Chỉnh sửa: Và một điều nữa. Đôi khi, thay vì ugettext_lazy, ugettext_noopđược sử dụng. Như tài liệu nói, các ugettext_noopchuỗi chỉ được đánh dấu để dịch và dịch vào thời điểm gần nhất có thể trước khi hiển thị chúng cho người dùng, nhưng tôi hơi bối rối ở đây, không giống như vậy phải ugettext_lazylàm gì? Tôi vẫn khó quyết định, tôi nên sử dụng mô hình và mẫu nào.

Câu trả lời:


196

ugettext() so với ugettext_lazy()

Trong các định nghĩa như biểu mẫu hoặc mô hình bạn nên sử dụng ugettext_lazyvì mã của định nghĩa này chỉ được thực thi một lần (chủ yếu là khi khởi động django); ugettext_lazydịch các chuỗi theo kiểu lười biếng, có nghĩa là, ví dụ. mỗi khi bạn truy cập tên của một thuộc tính trên một mô hình, chuỗi sẽ được dịch mới - điều này hoàn toàn có ý nghĩa bởi vì bạn có thể đang xem mô hình này bằng các ngôn ngữ khác nhau kể từ khi django được bắt đầu!

Trong chế độ xem và các lệnh gọi chức năng tương tự bạn có thể sử dụng ugettextmà không gặp sự cố, vì mỗi lần chế độ xem được gọi ugettextsẽ được thực hiện mới, vì vậy bạn sẽ luôn nhận được bản dịch phù hợp với yêu cầu!

Về ugettext_noop()

Như Bryce đã chỉ ra trong câu trả lời của mình, hàm này đánh dấu một chuỗi là có thể trích xuất để dịch nhưng không trả về chuỗi chưa được dịch. Điều này hữu ích cho việc sử dụng chuỗi ở hai nơi - được dịch và chưa được dịch. Xem ví dụ sau:

import logging
from django.http import HttpResponse
from django.utils.translation import ugettext as _, ugettext_noop as _noop

def view(request):
    msg = _noop("An error has occurred")
    logging.error(msg)
    return HttpResponse(_(msg))

15
Theo tôi thì điều đó dễ hiểu hơn lời giải thích trong tài liệu của Django. Cảm ơn @Bernhard.
Utku

14
Cảm ơn! Nó cũng sẽ hữu ích để giải thích khi không sử dụng ugettext_lazy, chẳng hạn như khi chuyển nó đến những thứ mong đợi một chuỗi như "" .replace, nối chuỗi và các thứ khác; một đối tượng proxy lười biếng sẽ không hoạt động trong những trường hợp đó. Mặt khác, câu trả lời này ngụ ý rằng bạn an toàn khi luôn sử dụng ugettext_lazy.
mrooney

4
@mrooney những trường hợp đó ít quan trọng hơn vì chúng sẽ gây ra lỗi cho bạn nếu bạn thực hiện chúng, thay vì âm thầm trả lại bản dịch ngôn ngữ sai. Ngoài ra, bạn có thể sử dụng "" .replace với ugettext_lazy, bạn chỉ cần gọi str () trên kết quả, ví dụ như lazytext = ugettext_lazy ('hello') và sau đó sử dụng str (lazytext) .replace.
fabspro

1
Thế còn msg = "An error has occurred"; logging.error(msg);return HttpResponse(_(msg))? why need _noop ?nếu không có _noop, django sẽ không tìm thấy chuỗi cần dịch?
WeizhongTu

1
Dịch hoạt động trên các biến. Một lần nữa, đây là một tài liệu ví dụ giống hệt nhau , vậy tại sao _noop?
WeizhongTu

17

Một cách sử dụng tuyệt vời của _noop, là khi bạn muốn đăng nhập một tin nhắn bằng tiếng Anh cho các nhà phát triển, nhưng trình bày chuỗi dịch cho người xem. Một ví dụ về điều này là tại http://blog.bessas.me/posts/USE-gettext-in-django/


4
Liên kết bị hỏng Từ
nalzok

5

Phiên bản lười biếng trả về một đối tượng proxy thay vì một chuỗi và trong một số trường hợp, nó sẽ không hoạt động như mong đợi. Ví dụ:

def get(self, request, format=None):
   search_str = request.GET.get('search', '')
   data = self.search(search_str)
   lst = []
   lst.append({'name': ugettext_lazy('Client'), 'result': data})
   return HttpResponse(json.dumps(lst), content_type='application/json')

sẽ thất bại vì dòng cuối cùng sẽ thử tuần tự hóa đối tượng lst thành JSON và thay vì một chuỗi cho "client", nó sẽ có một đối tượng proxy. Đối tượng proxy không được tuần tự hóa thành json.


2
Bạn nên sử dụng ugettext trong những trường hợp này.
sudip
Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.