wichert / lingua

Translation toolkit for Python
Other
46 stars 33 forks source link

Added support for extracting plural forms from zope.i18nmessageid messages #10

Closed thomasmassmann closed 10 years ago

thomasmassmann commented 12 years ago

With the plural form support for zope.i18n* (see https://bitbucket.org/thomas_massmann/zope.i18nmessageid and https://bitbucket.org/thomas_massmann/zope.i18n - I will merge it into the SVN soon) it is necessary to support the extraction of those messages and their plural forms as well.

A new method stateWaitForPlural looks for the plural parameter, but only if the funcname (or keyword) is within one of the plural keywords: ngettext, ungettext.

In Zope, a Message ID is then defined like:

from zope.i18nmessageid import MessageFactory
_ = MessageFactory('my.package')

message_one = _.ungettext(u'There is one file.', plural=u'There are %d files.')

message_two = _.ungettext(u'label_other_files', u'There are %d other files.',
    default=u'There is another file.',
)

The result looks something like this:

#: src/my/package/__init__.py:4
#, python-format
msgid "There is one file."
msgid_plural "There are %d files."
msgstr[0] ""
msgstr[1] ""

Default texts are only supported for singular versions:

#. Default: There is another file.
#: src/my/package/__init__.py:6
#, python-format
msgid "label_other_files"
msgid_plural "There are %d other files."
msgstr[0] ""
msgstr[1] ""

I know that lingua is widely used by Pyramid, and there plural messages are handled in another way. I haven't tested this within Pyramid, but it should not affect it.

Cheers, Thomas

wichert commented 12 years ago

Would you be willing to submit a pull request with similar support for translationstring as well? You can find the code on github under the Pylons account.

thomasmassmann commented 12 years ago

I can take a look at it. I haven't done any Pyramid (or Pylons) project until now (just a sample 'Hello World'). During my research for the plural support I noticed that the localizer in Pyramid has a pluralizemethod. But this one simply takes two singular message ids and returns just one of them depending on the n parameter. This works for languages with 2 plural forms, but not for e.g. Polish (3 forms) or Japanese (no plural).

If we extend Pylons translationsstring the way I did with zope.i18nmessageid, then it should be supported out of the box.

thomasmassmann commented 12 years ago

Every framework that uses ngettext(singular, plural, n) or ungettext(singular, plural, n) to define plural message id's is supported by the patch (for dngettext() and udngettext() some additional code is necessary due to the domain parameter).

If I get it right Pylons uses ngettext and ungettext, so this should work. But I have to test it.

MatthewWilkes commented 11 years ago

Actually, that's now how pluralize() works, its 'singular' argument is the plural msgid and the plural argument is the default plural form, just the same as it does in gettext. It falls back to returning singular for n==1 otherwise plural if singular isn't registered as a msgid_plural.

I submitted a pull request before I saw this, that does the same, but in a slightly different way,

wichert commented 10 years ago

I rewrote lingua's python extractor yesterday, so this patch no longer applies. I am interested in improving plural support, so I'll try to add something similar.

wichert commented 10 years ago

It seems zope.i18nmessageid never got any support for plurals, and I would rather not add something to lingua that is non-standard. lingua does have a new --keyword option now which allows you to trivially support this without requiring any code changes.

MatthewWilkes commented 10 years ago

Will you add a warning to the readme to this effect, showing how to support plurals?