# -*- coding: utf-8 -*- # # Copyright (C) 2007-2010 Edgewall Software # All rights reserved. # # This software is licensed as described in the file COPYING, which # you should have received as part of this distribution. The terms # are also available at http://genshi.edgewall.org/wiki/License. # # This software consists of voluntary contributions made by many # individuals. For the exact contribution history, see the revision # history and logs, available at http://genshi.edgewall.org/log/. from datetime import datetime from gettext import NullTranslations import unittest import six from genshi.core import Attrs from genshi.template import MarkupTemplate, Context from genshi.filters.i18n import Translator, extract from genshi.input import HTML from genshi.compat import IS_PYTHON2, StringIO from genshi.tests.test_utils import doctest_suite class DummyTranslations(NullTranslations): _domains = {} def __init__(self, catalog=()): NullTranslations.__init__(self) self._catalog = catalog or {} self.plural = lambda n: n != 1 def add_domain(self, domain, catalog): translation = DummyTranslations(catalog) translation.add_fallback(self) self._domains[domain] = translation def _domain_call(self, func, domain, *args, **kwargs): return getattr(self._domains.get(domain, self), func)(*args, **kwargs) if IS_PYTHON2: def ugettext(self, message): missing = object() tmsg = self._catalog.get(message, missing) if tmsg is missing: if self._fallback: return self._fallback.ugettext(message) return six.text_type(message) return tmsg else: def gettext(self, message): missing = object() tmsg = self._catalog.get(message, missing) if tmsg is missing: if self._fallback: return self._fallback.gettext(message) return six.text_type(message) return tmsg if IS_PYTHON2: def dugettext(self, domain, message): return self._domain_call('ugettext', domain, message) else: def dgettext(self, domain, message): return self._domain_call('gettext', domain, message) def ungettext(self, msgid1, msgid2, n): try: return self._catalog[(msgid1, self.plural(n))] except KeyError: if self._fallback: return self._fallback.ngettext(msgid1, msgid2, n) if n == 1: return msgid1 else: return msgid2 if not IS_PYTHON2: ngettext = ungettext del ungettext if IS_PYTHON2: def dungettext(self, domain, singular, plural, numeral): return self._domain_call( 'ungettext', domain, singular, plural, numeral) else: def dngettext(self, domain, singular, plural, numeral): return self._domain_call( 'ngettext', domain, singular, plural, numeral) if IS_PYTHON2: def upgettext(self, context, message): try: return self._catalog[(context, message)] except KeyError: if self._fallback: return self._fallback.upgettext(context, message) return unicode(message) else: def pgettext(self, context, message): try: return self._catalog[(context, message)] except KeyError: if self._fallback: return self._fallback.upgettext(context, message) return message if IS_PYTHON2: def dupgettext(self, domain, context, message): return self._domain_call('upgettext', domain, context, message) else: def dpgettext(self, domain, context, message): return self._domain_call('pgettext', domain, context, message) def unpgettext(self, context, msgid1, msgid2, n): try: return self._catalog[(context, msgid1, self.plural(n))] except KeyError: if self._fallback: return self._fallback.unpgettext(context, msgid1, msgid2, n) if n == 1: return msgid1 else: return msgid2 if not IS_PYTHON2: npgettext = unpgettext del unpgettext if IS_PYTHON2: def dunpgettext(self, domain, context, msgid1, msgid2, n): return self._domain_call('unpgettext', context, msgid1, msgid2, n) else: def dnpgettext(self, domain, context, msgid1, msgid2, n): return self._domain_call('npgettext', context, msgid1, msgid2, n) class TranslatorTestCase(unittest.TestCase): def test_translate_included_attribute_text(self): """ Verify that translated attributes end up in a proper `Attrs` instance. """ html = HTML(u""" """) translator = Translator(lambda s: u"Voh") stream = list(html.filter(translator)) kind, data, pos = stream[2] assert isinstance(data[1], Attrs) def test_extract_included_empty_attribute_text(self): tmpl = MarkupTemplate(u""" ... """) translator = Translator() messages = list(translator.extract(tmpl.stream)) self.assertEqual([], messages) def test_translate_included_empty_attribute_text(self): tmpl = MarkupTemplate(u""" ... """) translator = Translator(DummyTranslations({'': 'Project-Id-Version'})) translator.setup(tmpl) self.assertEqual(""" ... """, tmpl.generate().render()) def test_extract_without_text(self): tmpl = MarkupTemplate("""

Foo

${ngettext("Singular", "Plural", num)} """) translator = Translator(extract_text=False) messages = list(translator.extract(tmpl.stream)) self.assertEqual(1, len(messages)) self.assertEqual((3, 'ngettext', ('Singular', 'Plural', None), []), messages[0]) def test_extract_plural_form(self): tmpl = MarkupTemplate(""" ${ngettext("Singular", "Plural", num)} """) translator = Translator() messages = list(translator.extract(tmpl.stream)) self.assertEqual(1, len(messages)) self.assertEqual((2, 'ngettext', ('Singular', 'Plural', None), []), messages[0]) def test_extract_funky_plural_form(self): tmpl = MarkupTemplate(""" ${ngettext(len(items), *widget.display_names)} """) translator = Translator() messages = list(translator.extract(tmpl.stream)) self.assertEqual(1, len(messages)) self.assertEqual((2, 'ngettext', (None, None), []), messages[0]) def test_extract_gettext_with_unicode_string(self): tmpl = MarkupTemplate(""" ${gettext("Grüße")} """) translator = Translator() messages = list(translator.extract(tmpl.stream)) self.assertEqual(1, len(messages)) self.assertEqual((2, 'gettext', u'Gr\xfc\xdfe', []), messages[0]) def test_extract_included_attribute_text(self): tmpl = MarkupTemplate(""" """) translator = Translator() messages = list(translator.extract(tmpl.stream)) self.assertEqual(1, len(messages)) self.assertEqual((2, None, 'Foo', []), messages[0]) def test_extract_attribute_expr(self): tmpl = MarkupTemplate(""" """) translator = Translator() messages = list(translator.extract(tmpl.stream)) self.assertEqual(1, len(messages)) self.assertEqual((2, '_', 'Save', []), messages[0]) def test_extract_non_included_attribute_interpolated(self): tmpl = MarkupTemplate(""" Foo """) translator = Translator() messages = list(translator.extract(tmpl.stream)) self.assertEqual(1, len(messages)) self.assertEqual((2, None, 'Foo', []), messages[0]) def test_extract_text_from_sub(self): tmpl = MarkupTemplate(""" Foo """) translator = Translator() messages = list(translator.extract(tmpl.stream)) self.assertEqual(1, len(messages)) self.assertEqual((2, None, 'Foo', []), messages[0]) def test_ignore_tag_with_fixed_xml_lang(self): tmpl = MarkupTemplate("""

(c) 2007 Edgewall Software

""") translator = Translator() messages = list(translator.extract(tmpl.stream)) self.assertEqual(0, len(messages)) def test_extract_tag_with_variable_xml_lang(self): tmpl = MarkupTemplate("""

(c) 2007 Edgewall Software

""") translator = Translator() messages = list(translator.extract(tmpl.stream)) self.assertEqual(1, len(messages)) self.assertEqual((2, None, '(c) 2007 Edgewall Software', []), messages[0]) def test_ignore_attribute_with_expression(self): tmpl = MarkupTemplate(""" """) translator = Translator() messages = list(translator.extract(tmpl.stream)) self.assertEqual(0, len(messages)) def test_translate_with_translations_object(self): tmpl = MarkupTemplate("""

Foo

""") translator = Translator(DummyTranslations({'Foo': 'Voh'})) translator.setup(tmpl) self.assertEqual("""

Voh

""", tmpl.generate().render()) def test_extract_included_attribute_text_with_spaces(self): tmpl = MarkupTemplate(""" ... """) translator = Translator() messages = list(translator.extract(tmpl.stream)) self.assertEqual(1, len(messages)) self.assertEqual((2, None, 'Foo', []), messages[0]) def test_translate_included_attribute_text_with_spaces(self): tmpl = MarkupTemplate(""" ... """) translator = Translator(DummyTranslations({'Foo': 'Voh'})) translator.setup(tmpl) self.assertEqual(""" ... """, tmpl.generate().render()) class MsgDirectiveTestCase(unittest.TestCase): def test_extract_i18n_msg(self): tmpl = MarkupTemplate("""

Please see Help for details.

""") translator = Translator() tmpl.add_directives(Translator.NAMESPACE, translator) messages = list(translator.extract(tmpl.stream)) self.assertEqual(1, len(messages)) self.assertEqual('Please see [1:Help] for details.', messages[0][2]) def test_translate_i18n_msg(self): tmpl = MarkupTemplate("""

Please see Help for details.

""") gettext = lambda s: u"Für Details siehe bitte [1:Hilfe]." translator = Translator(gettext) translator.setup(tmpl) self.assertEqual(u"""

Für Details siehe bitte Hilfe.

""".encode('utf-8'), tmpl.generate().render(encoding='utf-8')) def test_extract_i18n_msg_nonewline(self): tmpl = MarkupTemplate("""

Please see Help

""") translator = Translator() tmpl.add_directives(Translator.NAMESPACE, translator) messages = list(translator.extract(tmpl.stream)) self.assertEqual(1, len(messages)) self.assertEqual('Please see [1:Help]', messages[0][2]) def test_translate_i18n_msg_nonewline(self): tmpl = MarkupTemplate("""

Please see Help

""") gettext = lambda s: u"Für Details siehe bitte [1:Hilfe]" translator = Translator(gettext) translator.setup(tmpl) self.assertEqual(u"""

Für Details siehe bitte Hilfe

""", tmpl.generate().render()) def test_extract_i18n_msg_elt_nonewline(self): tmpl = MarkupTemplate(""" Please see Help """) translator = Translator() tmpl.add_directives(Translator.NAMESPACE, translator) messages = list(translator.extract(tmpl.stream)) self.assertEqual(1, len(messages)) self.assertEqual('Please see [1:Help]', messages[0][2]) def test_translate_i18n_msg_elt_nonewline(self): tmpl = MarkupTemplate(""" Please see Help """) gettext = lambda s: u"Für Details siehe bitte [1:Hilfe]" translator = Translator(gettext) translator.setup(tmpl) self.assertEqual(u""" Für Details siehe bitte Hilfe """.encode('utf-8'), tmpl.generate().render(encoding='utf-8')) def test_extract_i18n_msg_with_attributes(self): tmpl = MarkupTemplate("""

Please see Help

""") translator = Translator() translator.setup(tmpl) messages = list(translator.extract(tmpl.stream)) self.assertEqual(3, len(messages)) self.assertEqual('A helpful paragraph', messages[0][2]) self.assertEqual(3, messages[0][0]) self.assertEqual('Click for help', messages[1][2]) self.assertEqual(4, messages[1][0]) self.assertEqual('Please see [1:Help]', messages[2][2]) self.assertEqual(3, messages[2][0]) def test_translate_i18n_msg_with_attributes(self): tmpl = MarkupTemplate("""

Please see Help

""") translator = Translator(lambda msgid: { 'A helpful paragraph': 'Ein hilfreicher Absatz', 'Click for help': u'Klicken für Hilfe', 'Please see [1:Help]': u'Siehe bitte [1:Hilfe]' }[msgid]) translator.setup(tmpl) self.assertEqual(u"""

Siehe bitte Hilfe

""", tmpl.generate().render(encoding=None)) def test_extract_i18n_msg_with_dynamic_attributes(self): tmpl = MarkupTemplate("""

Please see Help

""") translator = Translator() translator.setup(tmpl) messages = list(translator.extract(tmpl.stream)) self.assertEqual(3, len(messages)) self.assertEqual('A helpful paragraph', messages[0][2]) self.assertEqual(3, messages[0][0]) self.assertEqual('Click for help', messages[1][2]) self.assertEqual(4, messages[1][0]) self.assertEqual('Please see [1:Help]', messages[2][2]) self.assertEqual(3, messages[2][0]) def test_translate_i18n_msg_with_dynamic_attributes(self): tmpl = MarkupTemplate("""

Please see Help

""") translator = Translator(lambda msgid: { 'A helpful paragraph': 'Ein hilfreicher Absatz', 'Click for help': u'Klicken für Hilfe', 'Please see [1:Help]': u'Siehe bitte [1:Hilfe]' }[msgid]) translator.setup(tmpl) self.assertEqual(u"""

Siehe bitte Hilfe

""", tmpl.generate(_=translator.translate).render(encoding=None)) def test_extract_i18n_msg_as_element_with_attributes(self): tmpl = MarkupTemplate(""" Please see Help """) translator = Translator() translator.setup(tmpl) messages = list(translator.extract(tmpl.stream)) self.assertEqual(2, len(messages)) self.assertEqual('Click for help', messages[0][2]) self.assertEqual(4, messages[0][0]) self.assertEqual('Please see [1:Help]', messages[1][2]) self.assertEqual(3, messages[1][0]) def test_translate_i18n_msg_as_element_with_attributes(self): tmpl = MarkupTemplate(""" Please see Help """) translator = Translator(lambda msgid: { 'Click for help': u'Klicken für Hilfe', 'Please see [1:Help]': u'Siehe bitte [1:Hilfe]' }[msgid]) translator.setup(tmpl) self.assertEqual(u""" Siehe bitte Hilfe """, tmpl.generate().render(encoding=None)) def test_extract_i18n_msg_nested(self): tmpl = MarkupTemplate("""

Please see Help page for details.

""") translator = Translator() tmpl.add_directives(Translator.NAMESPACE, translator) messages = list(translator.extract(tmpl.stream)) self.assertEqual(1, len(messages)) self.assertEqual('Please see [1:[2:Help] page] for details.', messages[0][2]) def test_translate_i18n_msg_nested(self): tmpl = MarkupTemplate("""

Please see Help page for details.

""") gettext = lambda s: u"Für Details siehe bitte [1:[2:Hilfeseite]]." translator = Translator(gettext) translator.setup(tmpl) self.assertEqual(u"""

Für Details siehe bitte Hilfeseite.

""", tmpl.generate().render()) def test_extract_i18n_msg_label_with_nested_input(self): tmpl = MarkupTemplate("""
""") translator = Translator() tmpl.add_directives(Translator.NAMESPACE, translator) messages = list(translator.extract(tmpl.stream)) self.assertEqual(1, len(messages)) self.assertEqual('[1:[2:] days back]', messages[0][2]) def test_translate_i18n_msg_label_with_nested_input(self): tmpl = MarkupTemplate("""
""") gettext = lambda s: "[1:[2:] foo bar]" translator = Translator(gettext) translator.setup(tmpl) self.assertEqual("""
""", tmpl.generate().render()) def test_extract_i18n_msg_empty(self): tmpl = MarkupTemplate("""

Show me entries per page.

""") translator = Translator() tmpl.add_directives(Translator.NAMESPACE, translator) messages = list(translator.extract(tmpl.stream)) self.assertEqual(1, len(messages)) self.assertEqual('Show me [1:] entries per page.', messages[0][2]) def test_translate_i18n_msg_empty(self): tmpl = MarkupTemplate("""

Show me entries per page.

""") gettext = lambda s: u"[1:] Einträge pro Seite anzeigen." translator = Translator(gettext) translator.setup(tmpl) self.assertEqual(u"""

Einträge pro Seite anzeigen.

""", tmpl.generate().render()) def test_extract_i18n_msg_multiple(self): tmpl = MarkupTemplate("""

Please see Help for details.

""") translator = Translator() tmpl.add_directives(Translator.NAMESPACE, translator) messages = list(translator.extract(tmpl.stream)) self.assertEqual(1, len(messages)) self.assertEqual('Please see [1:Help] for [2:details].', messages[0][2]) def test_translate_i18n_msg_multiple(self): tmpl = MarkupTemplate("""

Please see Help for details.

""") gettext = lambda s: u"Für [2:Details] siehe bitte [1:Hilfe]." translator = Translator(gettext) translator.setup(tmpl) self.assertEqual(u"""

Für Details siehe bitte Hilfe.

""", tmpl.generate().render()) def test_extract_i18n_msg_multiple_empty(self): tmpl = MarkupTemplate("""

Show me entries per page, starting at page .

""") translator = Translator() tmpl.add_directives(Translator.NAMESPACE, translator) messages = list(translator.extract(tmpl.stream)) self.assertEqual(1, len(messages)) self.assertEqual('Show me [1:] entries per page, starting at page [2:].', messages[0][2]) def test_translate_i18n_msg_multiple_empty(self): tmpl = MarkupTemplate("""

Show me entries per page, starting at page .

""", encoding='utf-8') gettext = lambda s: u"[1:] Einträge pro Seite, beginnend auf Seite [2:]." translator = Translator(gettext) translator.setup(tmpl) self.assertEqual(u"""

Eintr\u00E4ge pro Seite, beginnend auf Seite .

""".encode('utf-8'), tmpl.generate().render(encoding='utf-8')) def test_extract_i18n_msg_with_param(self): tmpl = MarkupTemplate("""

Hello, ${user.name}!

""") translator = Translator() tmpl.add_directives(Translator.NAMESPACE, translator) messages = list(translator.extract(tmpl.stream)) self.assertEqual(1, len(messages)) self.assertEqual('Hello, %(name)s!', messages[0][2]) def test_translate_i18n_msg_with_param(self): tmpl = MarkupTemplate("""

Hello, ${user.name}!

""") gettext = lambda s: u"Hallo, %(name)s!" translator = Translator(gettext) translator.setup(tmpl) self.assertEqual("""

Hallo, Jim!

""", tmpl.generate(user=dict(name='Jim')).render()) def test_translate_i18n_msg_with_param_reordered(self): tmpl = MarkupTemplate("""

Hello, ${user.name}!

""") gettext = lambda s: u"%(name)s, sei gegrüßt!" translator = Translator(gettext) translator.setup(tmpl) self.assertEqual(u"""

Jim, sei gegrüßt!

""", tmpl.generate(user=dict(name='Jim')).render()) def test_translate_i18n_msg_with_attribute_param(self): tmpl = MarkupTemplate("""

Hello, dude!

""") gettext = lambda s: u"Sei gegrüßt, [1:Alter]!" translator = Translator(gettext) translator.setup(tmpl) self.assertEqual(u"""

Sei gegrüßt, Alter!

""", tmpl.generate(anchor='42').render()) def test_extract_i18n_msg_with_two_params(self): tmpl = MarkupTemplate("""

Posted by ${post.author} at ${entry.time.strftime('%H:%m')}

""") translator = Translator() tmpl.add_directives(Translator.NAMESPACE, translator) messages = list(translator.extract(tmpl.stream)) self.assertEqual(1, len(messages)) self.assertEqual('Posted by %(name)s at %(time)s', messages[0][2]) def test_translate_i18n_msg_with_two_params(self): tmpl = MarkupTemplate("""

Written by ${entry.author} at ${entry.time.strftime('%H:%M')}

""") gettext = lambda s: u"%(name)s schrieb dies um %(time)s" translator = Translator(gettext) translator.setup(tmpl) entry = { 'author': 'Jim', 'time': datetime(2008, 4, 1, 14, 30) } self.assertEqual("""

Jim schrieb dies um 14:30

""", tmpl.generate(entry=entry).render()) def test_extract_i18n_msg_with_directive(self): tmpl = MarkupTemplate("""

Show me entries per page.

""") translator = Translator() tmpl.add_directives(Translator.NAMESPACE, translator) messages = list(translator.extract(tmpl.stream)) self.assertEqual(1, len(messages)) self.assertEqual('Show me [1:] entries per page.', messages[0][2]) def test_translate_i18n_msg_with_directive(self): tmpl = MarkupTemplate("""

Show me entries per page.

""") gettext = lambda s: u"[1:] Einträge pro Seite anzeigen." translator = Translator(gettext) translator.setup(tmpl) self.assertEqual(u"""

Einträge pro Seite anzeigen.

""", tmpl.generate().render()) def test_extract_i18n_msg_with_comment(self): tmpl = MarkupTemplate("""

Foo

""") translator = Translator() tmpl.add_directives(Translator.NAMESPACE, translator) messages = list(translator.extract(tmpl.stream)) self.assertEqual(1, len(messages)) self.assertEqual((3, None, 'Foo', ['As in foo bar']), messages[0]) tmpl = MarkupTemplate("""

Foo

""") translator = Translator() tmpl.add_directives(Translator.NAMESPACE, translator) messages = list(translator.extract(tmpl.stream)) self.assertEqual(1, len(messages)) self.assertEqual((3, None, 'Foo', ['As in foo bar']), messages[0]) def test_translate_i18n_msg_with_comment(self): tmpl = MarkupTemplate("""

Foo

""") gettext = lambda s: u"Voh" translator = Translator(gettext) translator.setup(tmpl) self.assertEqual("""

Voh

""", tmpl.generate().render()) def test_extract_i18n_msg_with_attr(self): tmpl = MarkupTemplate("""

Foo

""") translator = Translator() messages = list(translator.extract(tmpl.stream)) self.assertEqual(2, len(messages)) self.assertEqual((3, None, 'Foo bar', []), messages[0]) self.assertEqual((3, None, 'Foo', []), messages[1]) def test_translate_i18n_msg_with_attr(self): tmpl = MarkupTemplate("""

Foo

""") gettext = lambda s: u"Voh" translator = Translator(DummyTranslations({ 'Foo': 'Voh', 'Foo bar': u'Voh bär' })) tmpl.filters.insert(0, translator) tmpl.add_directives(Translator.NAMESPACE, translator) self.assertEqual(u"""

Voh

""", tmpl.generate().render()) def test_translate_i18n_msg_and_py_strip_directives(self): tmpl = MarkupTemplate("""

Foo

Foo

""") translator = Translator(DummyTranslations({'Foo': 'Voh'})) translator.setup(tmpl) self.assertEqual(""" Voh Voh """, tmpl.generate().render()) def test_i18n_msg_ticket_300_extract(self): tmpl = MarkupTemplate(""" Changed ${ '10/12/2008' } ago by ${ 'me, the author' } """) translator = Translator() tmpl.add_directives(Translator.NAMESPACE, translator) messages = list(translator.extract(tmpl.stream)) self.assertEqual(1, len(messages)) self.assertEqual( (3, None, 'Changed %(date)s ago by %(author)s', []), messages[0] ) def test_i18n_msg_ticket_300_translate(self): tmpl = MarkupTemplate(""" Changed ${ date } ago by ${ author } """) translations = DummyTranslations({ 'Changed %(date)s ago by %(author)s': u'Modificado à %(date)s por %(author)s' }) translator = Translator(translations) translator.setup(tmpl) self.assertEqual(u""" Modificado à um dia por Pedro """.encode('utf-8'), tmpl.generate(date='um dia', author="Pedro").render(encoding='utf-8')) def test_i18n_msg_ticket_251_extract(self): tmpl = MarkupTemplate("""

Translation[ 0 ]: One coin

""") translator = Translator() tmpl.add_directives(Translator.NAMESPACE, translator) messages = list(translator.extract(tmpl.stream)) self.assertEqual(1, len(messages)) self.assertEqual( (3, None, u'[1:[2:Translation\\[\xa00\xa0\\]]: [3:One coin]]', []), messages[0] ) def test_i18n_msg_ticket_251_translate(self): tmpl = MarkupTemplate("""

Translation[ 0 ]: One coin

""") translations = DummyTranslations({ u'[1:[2:Translation\\[\xa00\xa0\\]]: [3:One coin]]': u'[1:[2:Trandução\\[\xa00\xa0\\]]: [3:Uma moeda]]' }) translator = Translator(translations) translator.setup(tmpl) self.assertEqual(u"""

Trandução[ 0 ]: Uma moeda

""".encode('utf-8'), tmpl.generate().render(encoding='utf-8')) def test_extract_i18n_msg_with_other_directives_nested(self): tmpl = MarkupTemplate("""

Before you do that, though, please first try searching for similar issues, as it is quite likely that this problem has been reported before. For questions about installation and configuration of Trac, please try the mailing list instead of filing a ticket.

""") translator = Translator() translator.setup(tmpl) messages = list(translator.extract(tmpl.stream)) self.assertEqual(1, len(messages)) self.assertEqual( 'Before you do that, though, please first try\n ' '[1:[2:searching]\n for similar issues], as it is ' 'quite likely that this problem\n has been reported ' 'before. For questions about installation\n and ' 'configuration of Trac, please try the\n ' '[3:mailing list]\n instead of filing a ticket.', messages[0][2] ) def test_translate_i18n_msg_with_other_directives_nested(self): tmpl = MarkupTemplate("""

Before you do that, though, please first try searching for similar issues, as it is quite likely that this problem has been reported before. For questions about installation and configuration of Trac, please try the mailing list instead of filing a ticket.

""") translations = DummyTranslations({ 'Before you do that, though, please first try\n ' '[1:[2:searching]\n for similar issues], as it is ' 'quite likely that this problem\n has been reported ' 'before. For questions about installation\n and ' 'configuration of Trac, please try the\n ' '[3:mailing list]\n instead of filing a ticket.': u'Antes de o fazer, porém,\n ' u'[1:por favor tente [2:procurar]\n por problemas semelhantes], uma vez que ' u'é muito provável que este problema\n já tenha sido reportado ' u'anteriormente. Para questões relativas à instalação\n e ' u'configuração do Trac, por favor tente a\n ' u'[3:mailing list]\n em vez de criar um assunto.' }) translator = Translator(translations) translator.setup(tmpl) messages = list(translator.extract(tmpl.stream)) self.assertEqual(1, len(messages)) ctx = Context() ctx.push({'trac': {'homepage': 'http://trac.edgewall.org/'}}) self.assertEqual(u"""

Antes de o fazer, porém, por favor tente procurar por problemas semelhantes, uma vez que é muito provável que este problema já tenha sido reportado anteriormente. Para questões relativas à instalação e configuração do Trac, por favor tente a mailing list em vez de criar um assunto.

""", tmpl.generate(ctx).render()) def test_i18n_msg_with_other_nested_directives_with_reordered_content(self): # See: http://genshi.edgewall.org/ticket/300#comment:10 tmpl = MarkupTemplate("""

Note: This repository is defined in trac.ini and cannot be edited on this page.

""") translations = DummyTranslations({ '[1:Note:] This repository is defined in\n ' '[2:[3:trac.ini]]\n and cannot be edited on this page.': u'[1:Nota:] Este repositório está definido em \n ' u'[2:[3:trac.ini]]\n e não pode ser editado nesta página.', }) translator = Translator(translations) translator.setup(tmpl) messages = list(translator.extract(tmpl.stream)) self.assertEqual(1, len(messages)) self.assertEqual( '[1:Note:] This repository is defined in\n ' '[2:[3:trac.ini]]\n and cannot be edited on this page.', messages[0][2] ) self.assertEqual(u"""

Nota: Este repositório está definido em trac.ini e não pode ser editado nesta página.

""".encode('utf-8'), tmpl.generate(editable=False).render(encoding='utf-8')) def test_extract_i18n_msg_with_py_strip(self): tmpl = MarkupTemplate("""

Please see Help for details.

""") translator = Translator() tmpl.add_directives(Translator.NAMESPACE, translator) messages = list(translator.extract(tmpl.stream)) self.assertEqual(1, len(messages)) self.assertEqual((3, None, 'Please see [1:Help] for details.', []), messages[0]) def test_extract_i18n_msg_with_py_strip_and_comment(self): tmpl = MarkupTemplate("""

Please see Help for details.

""") translator = Translator() tmpl.add_directives(Translator.NAMESPACE, translator) messages = list(translator.extract(tmpl.stream)) self.assertEqual(1, len(messages)) self.assertEqual((3, None, 'Please see [1:Help] for details.', ['Foo']), messages[0]) def test_translate_i18n_msg_and_comment_with_py_strip_directives(self): tmpl = MarkupTemplate("""

Foo

Foo

""") translator = Translator(DummyTranslations({'Foo': 'Voh'})) translator.setup(tmpl) self.assertEqual(""" Voh Voh """, tmpl.generate().render()) def test_translate_i18n_msg_ticket_404(self): tmpl = MarkupTemplate("""

$first $second KEPT Inside a tag tail

""") translator = Translator(DummyTranslations()) translator.setup(tmpl) self.assertEqual("""

FIRST SECOND KEPT Inside a tag tail""" """

""", tmpl.generate(first="FIRST", second="SECOND").render()) def test_translate_i18n_msg_ticket_404_regression(self): tmpl = MarkupTemplate("""

text $name

""") gettext = lambda s: u'head [1:%(name)s] tail' translator = Translator(gettext) translator.setup(tmpl) self.assertEqual("""

head NAME tail

""", tmpl.generate(name='NAME').render()) class ChooseDirectiveTestCase(unittest.TestCase): def test_translate_i18n_choose_as_attribute(self): tmpl = MarkupTemplate("""

FooBar

FooBars

FooBar

FooBars

""") translations = DummyTranslations() translator = Translator(translations) translator.setup(tmpl) self.assertEqual("""

FooBar

FooBars

""", tmpl.generate(one=1, two=2).render()) def test_translate_i18n_choose_as_directive(self): tmpl = MarkupTemplate("""

FooBar

FooBars

FooBar

FooBars

""") translations = DummyTranslations() translator = Translator(translations) translator.setup(tmpl) self.assertEqual("""

FooBars

FooBar

""", tmpl.generate(one=1, two=2).render()) def test_translate_i18n_choose_as_directive_singular_and_plural_with_strip(self): tmpl = MarkupTemplate("""

FooBar Singular with Strip

FooBars Plural without Strip

FooBar singular without strip

FooBars plural with strip

FooBar singular without strip

FooBars plural with strip

FooBar singular with strip

FooBars plural without strip

""") translations = DummyTranslations() translator = Translator(translations) translator.setup(tmpl) self.assertEqual("""

FooBars Plural without Strip

FooBars plural with strip

FooBar singular without strip

FooBar singular with strip """, tmpl.generate(one=1, two=2).render()) def test_translate_i18n_choose_plural_singular_as_directive(self): # Ticket 371 tmpl = MarkupTemplate(""" FooBar FooBars FooBar FooBars """) translations = DummyTranslations({ ('FooBar', 0): 'FuBar', ('FooBars', 1): 'FuBars', 'FooBar': 'FuBar', 'FooBars': 'FuBars', }) translator = Translator(translations) translator.setup(tmpl) self.assertEqual(""" FuBars FuBar """, tmpl.generate(one=1, two=2).render()) def test_translate_i18n_choose_as_attribute_with_params(self): tmpl = MarkupTemplate("""

Foo $fname $lname

Foos $fname $lname

""") translations = DummyTranslations({ ('Foo %(fname)s %(lname)s', 0): 'Voh %(fname)s %(lname)s', ('Foo %(fname)s %(lname)s', 1): 'Vohs %(fname)s %(lname)s', 'Foo %(fname)s %(lname)s': 'Voh %(fname)s %(lname)s', 'Foos %(fname)s %(lname)s': 'Vohs %(fname)s %(lname)s', }) translator = Translator(translations) translator.setup(tmpl) self.assertEqual("""

Vohs John Doe

""", tmpl.generate(two=2, fname='John', lname='Doe').render()) def test_translate_i18n_choose_as_attribute_with_params_and_domain_as_param(self): tmpl = MarkupTemplate("""

Foo $fname $lname

Foos $fname $lname

""") translations = DummyTranslations() translations.add_domain('foo', { ('Foo %(fname)s %(lname)s', 0): 'Voh %(fname)s %(lname)s', ('Foo %(fname)s %(lname)s', 1): 'Vohs %(fname)s %(lname)s', 'Foo %(fname)s %(lname)s': 'Voh %(fname)s %(lname)s', 'Foos %(fname)s %(lname)s': 'Vohs %(fname)s %(lname)s', }) translator = Translator(translations) translator.setup(tmpl) self.assertEqual("""

Vohs John Doe

""", tmpl.generate(two=2, fname='John', lname='Doe').render()) def test_translate_i18n_choose_as_directive_with_params(self): tmpl = MarkupTemplate("""

Foo ${fname} ${lname}

Foos ${fname} ${lname}

Foo ${fname} ${lname}

Foos ${fname} ${lname}

""") translations = DummyTranslations({ ('Foo %(fname)s %(lname)s', 0): 'Voh %(fname)s %(lname)s', ('Foo %(fname)s %(lname)s', 1): 'Vohs %(fname)s %(lname)s', 'Foo %(fname)s %(lname)s': 'Voh %(fname)s %(lname)s', 'Foos %(fname)s %(lname)s': 'Vohs %(fname)s %(lname)s', }) translator = Translator(translations) translator.setup(tmpl) self.assertEqual("""

Vohs John Doe

Voh John Doe

""", tmpl.generate(one=1, two=2, fname='John', lname='Doe').render()) def test_translate_i18n_choose_as_directive_with_params_and_domain_as_directive(self): tmpl = MarkupTemplate("""

Foo ${fname} ${lname}

Foos ${fname} ${lname}

Foo ${fname} ${lname}

Foos ${fname} ${lname}

""") translations = DummyTranslations() translations.add_domain('foo', { ('Foo %(fname)s %(lname)s', 0): 'Voh %(fname)s %(lname)s', ('Foo %(fname)s %(lname)s', 1): 'Vohs %(fname)s %(lname)s', 'Foo %(fname)s %(lname)s': 'Voh %(fname)s %(lname)s', 'Foos %(fname)s %(lname)s': 'Vohs %(fname)s %(lname)s', }) translator = Translator(translations) translator.setup(tmpl) self.assertEqual("""

Vohs John Doe

Foo John Doe

""", tmpl.generate(one=1, two=2, fname='John', lname='Doe').render()) def test_extract_i18n_choose_as_attribute(self): tmpl = MarkupTemplate("""

FooBar

FooBars

FooBar

FooBars

""") translator = Translator() tmpl.add_directives(Translator.NAMESPACE, translator) messages = list(translator.extract(tmpl.stream)) self.assertEqual(2, len(messages)) self.assertEqual((3, 'ngettext', ('FooBar', 'FooBars'), []), messages[0]) self.assertEqual((7, 'ngettext', ('FooBar', 'FooBars'), []), messages[1]) def test_extract_i18n_choose_as_directive(self): tmpl = MarkupTemplate("""

FooBar

FooBars

FooBar

FooBars

""") translator = Translator() tmpl.add_directives(Translator.NAMESPACE, translator) messages = list(translator.extract(tmpl.stream)) self.assertEqual(2, len(messages)) self.assertEqual((3, 'ngettext', ('FooBar', 'FooBars'), []), messages[0]) self.assertEqual((7, 'ngettext', ('FooBar', 'FooBars'), []), messages[1]) def test_extract_i18n_choose_as_attribute_with_params(self): tmpl = MarkupTemplate("""

Foo $fname $lname

Foos $fname $lname

""") translator = Translator() tmpl.add_directives(Translator.NAMESPACE, translator) messages = list(translator.extract(tmpl.stream)) self.assertEqual(1, len(messages)) self.assertEqual((3, 'ngettext', ('Foo %(fname)s %(lname)s', 'Foos %(fname)s %(lname)s'), []), messages[0]) def test_extract_i18n_choose_as_attribute_with_params_and_domain_as_param(self): tmpl = MarkupTemplate("""

Foo $fname $lname

Foos $fname $lname

""") translator = Translator() tmpl.add_directives(Translator.NAMESPACE, translator) messages = list(translator.extract(tmpl.stream)) self.assertEqual(1, len(messages)) self.assertEqual((4, 'ngettext', ('Foo %(fname)s %(lname)s', 'Foos %(fname)s %(lname)s'), []), messages[0]) def test_extract_i18n_choose_as_directive_with_params(self): tmpl = MarkupTemplate("""

Foo ${fname} ${lname}

Foos ${fname} ${lname}

Foo ${fname} ${lname}

Foos ${fname} ${lname}

""") translator = Translator() tmpl.add_directives(Translator.NAMESPACE, translator) messages = list(translator.extract(tmpl.stream)) self.assertEqual(2, len(messages)) self.assertEqual((3, 'ngettext', ('Foo %(fname)s %(lname)s', 'Foos %(fname)s %(lname)s'), []), messages[0]) self.assertEqual((7, 'ngettext', ('Foo %(fname)s %(lname)s', 'Foos %(fname)s %(lname)s'), []), messages[1]) def test_extract_i18n_choose_as_directive_with_params_and_domain_as_directive(self): tmpl = MarkupTemplate("""

Foo ${fname} ${lname}

Foos ${fname} ${lname}

Foo ${fname} ${lname}

Foos ${fname} ${lname}

""") translator = Translator() tmpl.add_directives(Translator.NAMESPACE, translator) messages = list(translator.extract(tmpl.stream)) self.assertEqual(2, len(messages)) self.assertEqual((4, 'ngettext', ('Foo %(fname)s %(lname)s', 'Foos %(fname)s %(lname)s'), []), messages[0]) self.assertEqual((9, 'ngettext', ('Foo %(fname)s %(lname)s', 'Foos %(fname)s %(lname)s'), []), messages[1]) def test_extract_i18n_choose_as_attribute_with_params_and_comment(self): tmpl = MarkupTemplate("""

Foo $fname $lname

Foos $fname $lname

""") translator = Translator() tmpl.add_directives(Translator.NAMESPACE, translator) messages = list(translator.extract(tmpl.stream)) self.assertEqual(1, len(messages)) self.assertEqual((3, 'ngettext', ('Foo %(fname)s %(lname)s', 'Foos %(fname)s %(lname)s'), ['As in Foo Bar']), messages[0]) def test_extract_i18n_choose_as_directive_with_params_and_comment(self): tmpl = MarkupTemplate("""

Foo ${fname} ${lname}

Foos ${fname} ${lname}

""") translator = Translator() tmpl.add_directives(Translator.NAMESPACE, translator) messages = list(translator.extract(tmpl.stream)) self.assertEqual(1, len(messages)) self.assertEqual((3, 'ngettext', ('Foo %(fname)s %(lname)s', 'Foos %(fname)s %(lname)s'), ['As in Foo Bar']), messages[0]) def test_extract_i18n_choose_with_attributes(self): tmpl = MarkupTemplate("""

There is ${num} thing. There are ${num} things.

""") translator = Translator() translator.setup(tmpl) messages = list(translator.extract(tmpl.stream)) self.assertEqual(4, len(messages)) self.assertEqual((3, None, 'Things', []), messages[0]) self.assertEqual((5, None, 'View thing', []), messages[1]) self.assertEqual((8, None, 'View things', []), messages[2]) self.assertEqual( (3, 'ngettext', ('There is [1:%(num)s thing].', 'There are [1:%(num)s things].'), []), messages[3]) def test_translate_i18n_choose_with_attributes(self): tmpl = MarkupTemplate("""

There is ${num} thing. There are ${num} things.

""") translations = DummyTranslations({ 'Things': 'Sachen', 'View thing': 'Sache betrachten', 'View things': 'Sachen betrachten', ('There is [1:%(num)s thing].', 0): 'Da ist [1:%(num)s Sache].', ('There is [1:%(num)s thing].', 1): 'Da sind [1:%(num)s Sachen].' }) translator = Translator(translations) translator.setup(tmpl) self.assertEqual(u"""

Da ist 1 Sache.

""", tmpl.generate(link="/things", num=1).render(encoding=None)) self.assertEqual(u"""

Da sind 3 Sachen.

""", tmpl.generate(link="/things", num=3).render(encoding=None)) def test_extract_i18n_choose_as_element_with_attributes(self): tmpl = MarkupTemplate("""

There is ${num} thing.

There are ${num} things.

""") translator = Translator() translator.setup(tmpl) messages = list(translator.extract(tmpl.stream)) self.assertEqual(5, len(messages)) self.assertEqual((4, None, 'Things', []), messages[0]) self.assertEqual((5, None, 'View thing', []), messages[1]) self.assertEqual((7, None, 'Things', []), messages[2]) self.assertEqual((8, None, 'View things', []), messages[3]) self.assertEqual( (3, 'ngettext', ('There is [1:%(num)s thing].', 'There are [1:%(num)s things].'), []), messages[4]) def test_translate_i18n_choose_as_element_with_attributes(self): tmpl = MarkupTemplate("""

There is ${num} thing.

There are ${num} things.

""") translations = DummyTranslations({ 'Things': 'Sachen', 'View thing': 'Sache betrachten', 'View things': 'Sachen betrachten', ('There is [1:%(num)s thing].', 0): 'Da ist [1:%(num)s Sache].', ('There is [1:%(num)s thing].', 1): 'Da sind [1:%(num)s Sachen].' }) translator = Translator(translations) translator.setup(tmpl) self.assertEqual(u"""

Da ist 1 Sache.

""", tmpl.generate(link="/things", num=1).render(encoding=None)) self.assertEqual(u"""

Da sind 3 Sachen.

""", tmpl.generate(link="/things", num=3).render(encoding=None)) def test_translate_i18n_choose_and_py_strip(self): tmpl = MarkupTemplate("""

Foo $fname $lname

Foos $fname $lname

""") translations = DummyTranslations({ ('Foo %(fname)s %(lname)s', 0): 'Voh %(fname)s %(lname)s', ('Foo %(fname)s %(lname)s', 1): 'Vohs %(fname)s %(lname)s', 'Foo %(fname)s %(lname)s': 'Voh %(fname)s %(lname)s', 'Foos %(fname)s %(lname)s': 'Vohs %(fname)s %(lname)s', }) translator = Translator(translations) translator.setup(tmpl) self.assertEqual("""

Vohs John Doe

""", tmpl.generate(two=2, fname='John', lname='Doe').render()) def test_translate_i18n_choose_and_domain_and_py_strip(self): tmpl = MarkupTemplate("""

Foo $fname $lname

Foos $fname $lname

""") translations = DummyTranslations() translations.add_domain('foo', { ('Foo %(fname)s %(lname)s', 0): 'Voh %(fname)s %(lname)s', ('Foo %(fname)s %(lname)s', 1): 'Vohs %(fname)s %(lname)s', 'Foo %(fname)s %(lname)s': 'Voh %(fname)s %(lname)s', 'Foos %(fname)s %(lname)s': 'Vohs %(fname)s %(lname)s', }) translator = Translator(translations) translator.setup(tmpl) self.assertEqual("""

Vohs John Doe

""", tmpl.generate(two=2, fname='John', lname='Doe').render()) def test_translate_i18n_choose_and_singular_with_py_strip(self): tmpl = MarkupTemplate("""

Foo $fname $lname

Foos $fname $lname

Foo $fname $lname

Foos $fname $lname

""") translations = DummyTranslations({ ('Foo %(fname)s %(lname)s', 0): 'Voh %(fname)s %(lname)s', ('Foo %(fname)s %(lname)s', 1): 'Vohs %(fname)s %(lname)s', 'Foo %(fname)s %(lname)s': 'Voh %(fname)s %(lname)s', 'Foos %(fname)s %(lname)s': 'Vohs %(fname)s %(lname)s', }) translator = Translator(translations) translator.setup(tmpl) self.assertEqual("""

Vohs John Doe

Voh John Doe
""", tmpl.generate( one=1, two=2, fname='John',lname='Doe').render()) def test_translate_i18n_choose_and_plural_with_py_strip(self): tmpl = MarkupTemplate("""

Foo $fname $lname

Foos $fname $lname

""") translations = DummyTranslations({ ('Foo %(fname)s %(lname)s', 0): 'Voh %(fname)s %(lname)s', ('Foo %(fname)s %(lname)s', 1): 'Vohs %(fname)s %(lname)s', 'Foo %(fname)s %(lname)s': 'Voh %(fname)s %(lname)s', 'Foos %(fname)s %(lname)s': 'Vohs %(fname)s %(lname)s', }) translator = Translator(translations) translator.setup(tmpl) self.assertEqual("""
Voh John Doe
""", tmpl.generate(two=1, fname='John', lname='Doe').render()) def test_extract_i18n_choose_as_attribute_and_py_strip(self): tmpl = MarkupTemplate("""

FooBar

FooBars

""") translator = Translator() tmpl.add_directives(Translator.NAMESPACE, translator) messages = list(translator.extract(tmpl.stream)) self.assertEqual(1, len(messages)) self.assertEqual((3, 'ngettext', ('FooBar', 'FooBars'), []), messages[0]) class DomainDirectiveTestCase(unittest.TestCase): def test_translate_i18n_domain_with_msg_directives(self): #"""translate with i18n:domain and nested i18n:msg directives """ tmpl = MarkupTemplate("""

FooBar

Bar

""") translations = DummyTranslations({'Bar': 'Voh'}) translations.add_domain('foo', {'FooBar': 'BarFoo', 'Bar': 'PT_Foo'}) translator = Translator(translations) translator.setup(tmpl) self.assertEqual("""

BarFoo

PT_Foo

""", tmpl.generate().render()) def test_translate_i18n_domain_with_inline_directives(self): #"""translate with inlined i18n:domain and i18n:msg directives""" tmpl = MarkupTemplate("""

FooBar

""") translations = DummyTranslations({'Bar': 'Voh'}) translations.add_domain('foo', {'FooBar': 'BarFoo'}) translator = Translator(translations) translator.setup(tmpl) self.assertEqual("""

BarFoo

""", tmpl.generate().render()) def test_translate_i18n_domain_without_msg_directives(self): #"""translate domain call without i18n:msg directives still uses current domain""" tmpl = MarkupTemplate("""

Bar

FooBar

Bar

Bar

Bar

""") translations = DummyTranslations({'Bar': 'Voh'}) translations.add_domain('foo', {'FooBar': 'BarFoo', 'Bar': 'PT_Foo'}) translator = Translator(translations) translator.setup(tmpl) self.assertEqual("""

Voh

BarFoo

PT_Foo

PT_Foo

Voh

""", tmpl.generate().render()) def test_translate_i18n_domain_as_directive_not_attribute(self): #"""translate with domain as directive""" tmpl = MarkupTemplate("""

FooBar

Bar

Bar

Bar

""") translations = DummyTranslations({'Bar': 'Voh'}) translations.add_domain('foo', {'FooBar': 'BarFoo', 'Bar': 'PT_Foo'}) translator = Translator(translations) translator.setup(tmpl) self.assertEqual("""

BarFoo

PT_Foo

PT_Foo

Voh

""", tmpl.generate().render()) def test_translate_i18n_domain_nested_directives(self): #"""translate with nested i18n:domain directives""" tmpl = MarkupTemplate("""

Bar

FooBar

Bar

Bar

Bar

""") translations = DummyTranslations({'Bar': 'Voh'}) translations.add_domain('foo', {'FooBar': 'BarFoo', 'Bar': 'foo_Bar'}) translations.add_domain('bar', {'Bar': 'bar_Bar'}) translator = Translator(translations) translator.setup(tmpl) self.assertEqual("""

Voh

BarFoo

bar_Bar

foo_Bar

Voh

""", tmpl.generate().render()) def test_translate_i18n_domain_with_empty_nested_domain_directive(self): #"""translate with empty nested i18n:domain directive does not use dngettext""" tmpl = MarkupTemplate("""

Bar

FooBar

Bar

Bar

Bar

""") translations = DummyTranslations({'Bar': 'Voh'}) translations.add_domain('foo', {'FooBar': 'BarFoo', 'Bar': 'foo_Bar'}) translations.add_domain('bar', {'Bar': 'bar_Bar'}) translator = Translator(translations) translator.setup(tmpl) self.assertEqual("""

Voh

BarFoo

Voh

foo_Bar

Voh

""", tmpl.generate().render()) def test_translate_i18n_domain_with_inline_directive_on_START_NS(self): tmpl = MarkupTemplate("""

FooBar

""") translations = DummyTranslations({'Bar': 'Voh'}) translations.add_domain('foo', {'FooBar': 'BarFoo'}) translator = Translator(translations) translator.setup(tmpl) self.assertEqual("""

BarFoo

""", tmpl.generate().render()) def test_translate_i18n_domain_with_inline_directive_on_START_NS_with_py_strip(self): tmpl = MarkupTemplate("""

FooBar

""") translations = DummyTranslations({'Bar': 'Voh'}) translations.add_domain('foo', {'FooBar': 'BarFoo'}) translator = Translator(translations) translator.setup(tmpl) self.assertEqual("""

BarFoo

""", tmpl.generate().render()) def test_translate_i18n_domain_with_nested_includes(self): import os, shutil, tempfile from genshi.template.loader import TemplateLoader dirname = tempfile.mkdtemp(suffix='genshi_test') try: for idx in range(7): file1 = open(os.path.join(dirname, 'tmpl%d.html' % idx), 'w') try: file1.write("""
Included tmpl$idx

Bar $idx

Bar

Bar $idx

Bar $idx

""") finally: file1.close() file2 = open(os.path.join(dirname, 'tmpl10.html'), 'w') try: file2.write(""" """) finally: file2.close() def callback(template): translations = DummyTranslations({'Bar %(idx)s': 'Voh %(idx)s'}) translations.add_domain('foo', {'Bar %(idx)s': 'foo_Bar %(idx)s'}) translations.add_domain('bar', {'Bar': 'bar_Bar'}) translator = Translator(translations) translator.setup(template) loader = TemplateLoader([dirname], callback=callback) tmpl = loader.load('tmpl10.html') self.assertEqual("""
Included tmpl0

foo_Bar 0

bar_Bar

Voh 0

Voh 0

Included tmpl1

foo_Bar 1

bar_Bar

Voh 1

Voh 1

Included tmpl2

foo_Bar 2

bar_Bar

Voh 2

Voh 2

Included tmpl3

foo_Bar 3

bar_Bar

Voh 3

Voh 3

Included tmpl4

foo_Bar 4

bar_Bar

Voh 4

Voh 4

Included tmpl5

foo_Bar 5

bar_Bar

Voh 5

Voh 5

Included tmpl6

foo_Bar 6

bar_Bar

Voh 6

Voh 6

""", tmpl.generate(idx=-1).render()) finally: shutil.rmtree(dirname) def test_translate_i18n_domain_with_nested_includes_with_translatable_attrs(self): import os, shutil, tempfile from genshi.template.loader import TemplateLoader dirname = tempfile.mkdtemp(suffix='genshi_test') try: for idx in range(4): file1 = open(os.path.join(dirname, 'tmpl%d.html' % idx), 'w') try: file1.write("""
Included tmpl$idx

Bar $idx

Bar

Bar $idx

Bar $idx

Bar $idx

""") finally: file1.close() file2 = open(os.path.join(dirname, 'tmpl10.html'), 'w') try: file2.write(""" """) finally: file2.close() translations = DummyTranslations({'Bar %(idx)s': 'Voh %(idx)s', 'Bar': 'Voh'}) translations.add_domain('foo', {'Bar %(idx)s': 'foo_Bar %(idx)s'}) translations.add_domain('bar', {'Bar': 'bar_Bar'}) translator = Translator(translations) def callback(template): translator.setup(template) loader = TemplateLoader([dirname], callback=callback) tmpl = loader.load('tmpl10.html') if IS_PYTHON2: dgettext = translations.dugettext else: dgettext = translations.dgettext self.assertEqual("""
Included tmpl0

foo_Bar 0

bar_Bar

Voh 0

Voh 0

Voh 0

Included tmpl1

foo_Bar 1

bar_Bar

Voh 1

Voh 1

Voh 1

Included tmpl2

foo_Bar 2

bar_Bar

Voh 2

Voh 2

Voh 2

Included tmpl3

foo_Bar 3

bar_Bar

Voh 3

Voh 3

Voh 3

""", tmpl.generate(idx=-1, dg=dgettext).render()) finally: shutil.rmtree(dirname) class ExtractTestCase(unittest.TestCase): def test_markup_template_extraction(self): buf = StringIO(""" Example

Example

${_("Hello, %(name)s") % dict(name=username)}

${ngettext("You have %d item", "You have %d items", num)}

""") results = list(extract(buf, ['_', 'ngettext'], [], {})) self.assertEqual([ (3, None, 'Example', []), (6, None, 'Example', []), (7, '_', 'Hello, %(name)s', []), (8, 'ngettext', ('You have %d item', 'You have %d items', None), []), ], results) def test_extraction_without_text(self): buf = StringIO("""

Foo

${ngettext("Singular", "Plural", num)} """) results = list(extract(buf, ['_', 'ngettext'], [], { 'extract_text': 'no' })) self.assertEqual([ (3, 'ngettext', ('Singular', 'Plural', None), []), ], results) def test_text_template_extraction(self): buf = StringIO("""${_("Dear %(name)s") % {'name': name}}, ${ngettext("Your item:", "Your items", len(items))} #for item in items * $item #end All the best, Foobar""") results = list(extract(buf, ['_', 'ngettext'], [], { 'template_class': 'genshi.template:TextTemplate' })) self.assertEqual([ (1, '_', 'Dear %(name)s', []), (3, 'ngettext', ('Your item:', 'Your items', None), []), (7, None, 'All the best,\n Foobar', []) ], results) def test_extraction_with_keyword_arg(self): buf = StringIO(""" ${gettext('Foobar', foo='bar')} """) results = list(extract(buf, ['gettext'], [], {})) self.assertEqual([ (2, 'gettext', ('Foobar'), []), ], results) def test_extraction_with_nonstring_arg(self): buf = StringIO(""" ${dgettext(curdomain, 'Foobar')} """) results = list(extract(buf, ['dgettext'], [], {})) self.assertEqual([ (2, 'dgettext', (None, 'Foobar'), []), ], results) def test_extraction_inside_ignored_tags(self): buf = StringIO(""" """) results = list(extract(buf, ['_'], [], {})) self.assertEqual([ (5, '_', 'Please wait...', []), ], results) def test_extraction_inside_ignored_tags_with_directives(self): buf = StringIO(""" """) self.assertEqual([], list(extract(buf, ['_'], [], {}))) def test_extract_py_def_directive_with_py_strip(self): # Failed extraction from Trac tmpl = MarkupTemplate("""
Show
Ignore:
""") translator = Translator() tmpl.add_directives(Translator.NAMESPACE, translator) messages = list(translator.extract(tmpl.stream)) self.assertEqual(10, len(messages)) self.assertEqual([ (3, None, 'View differences', []), (6, None, 'inline', []), (8, None, 'side by side', []), (10, None, 'Show', []), (13, None, 'lines around each change', []), (16, None, 'Ignore:', []), (20, None, 'Blank lines', []), (25, None, 'Case changes',[]), (30, None, 'White space changes', []), (34, '_', 'Update', [])], messages) class ContextDirectiveTestCase(unittest.TestCase): def test_extract_msgcontext(self): buf = StringIO("""

Foo, bar.

Foo, bar.

""") results = list(extract(buf, ['_'], [], {})) self.assertEqual((3, 'pgettext', ('foo', 'Foo, bar.'), []), results[0]) self.assertEqual((4, None, 'Foo, bar.', []), results[1]) def test_translate_msgcontext(self): tmpl = MarkupTemplate("""

Foo, bar.

Foo, bar.

""") translations = { ('foo', 'Foo, bar.'): 'Fooo! Barrr!', 'Foo, bar.': 'Foo --- bar.' } translator = Translator(DummyTranslations(translations)) translator.setup(tmpl) self.assertEqual("""

Fooo! Barrr!

Foo --- bar.

""", tmpl.generate().render()) def test_translate_msgcontext_with_domain(self): tmpl = MarkupTemplate("""

Foo, bar. foo

Foo, bar.

""") translations = DummyTranslations({ ('foo', 'Foo, bar.'): 'Fooo! Barrr!', 'Foo, bar.': 'Foo --- bar.' }) translations.add_domain('bar', { ('foo', 'foo'): 'BARRR', ('foo', 'Foo, bar.'): 'Bar, bar.' }) translator = Translator(translations) translator.setup(tmpl) self.assertEqual("""

Bar, bar. BARRR

Foo --- bar.

""", tmpl.generate().render()) def test_translate_msgcontext_with_plurals(self): tmpl = MarkupTemplate("""

There is ${num} bar There are ${num} bars

""") translations = DummyTranslations({ ('foo', 'There is %(num)s bar', 0): 'Hay %(num)s barre', ('foo', 'There is %(num)s bar', 1): 'Hay %(num)s barres' }) translator = Translator(translations) translator.setup(tmpl) self.assertEqual("""

Hay 1 barre

""", tmpl.generate(num=1).render()) self.assertEqual("""

Hay 2 barres

""", tmpl.generate(num=2).render()) def test_translate_context_with_msg(self): tmpl = MarkupTemplate("""

Foo There is ${num} bar Bar

""") translations = DummyTranslations({ ('foo', 'Foo [1:There is %(num)s bar] Bar'): 'Voh [1:Hay %(num)s barre] Barre' }) translator = Translator(translations) translator.setup(tmpl) self.assertEqual("""

Voh Hay 1 barre Barre

""", tmpl.generate(num=1).render()) def suite(): suite = unittest.TestSuite() suite.addTest(doctest_suite(Translator.__module__)) suite.addTest(unittest.makeSuite(TranslatorTestCase, 'test')) suite.addTest(unittest.makeSuite(MsgDirectiveTestCase, 'test')) suite.addTest(unittest.makeSuite(ChooseDirectiveTestCase, 'test')) suite.addTest(unittest.makeSuite(DomainDirectiveTestCase, 'test')) suite.addTest(unittest.makeSuite(ExtractTestCase, 'test')) suite.addTest(unittest.makeSuite(ContextDirectiveTestCase, 'test')) return suite if __name__ == '__main__': unittest.main(defaultTest='suite')