[damned-lies] Moved test files as of new Django 1.6 test discovery
- From: Claude Paroz <claudep src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [damned-lies] Moved test files as of new Django 1.6 test discovery
- Date: Tue, 10 Dec 2013 08:09:18 +0000 (UTC)
commit 5550d9644a6689992ddad3186315612725f7241e
Author: Claude Paroz <claude 2xlibre net>
Date: Tue Dec 10 08:56:45 2013 +0100
Moved test files as of new Django 1.6 test discovery
Thanks Marcos Chavarría Teijeiro for noticing this issue.
languages/{tests/__init__.py => tests.py} | 0
people/{tests/__init__.py => tests.py} | 0
stats/tests/__init__.py | 327 +-------------------
stats/tests/tests.py | 325 +++++++++++++++++++
vertimus/tests/__init__.py | 502 +----------------------------
vertimus/tests/tests.py | 500 ++++++++++++++++++++++++++++
6 files changed, 829 insertions(+), 825 deletions(-)
---
diff --git a/languages/tests/__init__.py b/languages/tests.py
similarity index 100%
rename from languages/tests/__init__.py
rename to languages/tests.py
diff --git a/people/tests/__init__.py b/people/tests.py
similarity index 100%
rename from people/tests/__init__.py
rename to people/tests.py
diff --git a/stats/tests/__init__.py b/stats/tests/__init__.py
index df75a35..1ae7f52 100644
--- a/stats/tests/__init__.py
+++ b/stats/tests/__init__.py
@@ -1,325 +1,2 @@
-# -*- coding: utf-8 -*-
-#
-# Copyright (c) 2008-2012 Claude Paroz <claude 2xlibre net>
-#
-# This file is part of Damned Lies.
-#
-# Damned Lies is free software; you can redistribute it and/or modify
-# it under the terms of the GNU General Public License as published by
-# the Free Software Foundation; either version 2 of the License, or
-# (at your option) any later version.
-#
-# Damned Lies is distributed in the hope that it will be useful,
-# but WITHOUT ANY WARRANTY; without even the implied warranty of
-# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
-# GNU General Public License for more details.
-#
-# You should have received a copy of the GNU General Public License
-# along with Damned Lies; if not, write to the Free Software Foundation, Inc.,
-# 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
-
-import os
-import shutil
-import tarfile
-from datetime import date
-
-from django.test import TestCase
-from django.core import mail
-from django.core.exceptions import ValidationError
-from django.core.urlresolvers import reverse
-from django.conf import settings
-
-from stats.models import Module, Domain, Branch, Release, Statistics, FakeLangStatistics
-from stats.utils import check_program_presence, run_shell_command
-from languages.models import Language
-
-from fixture_factory import *
-
-def test_scratchdir(test_func):
- """ Decorator to temporarily use the scratchdir inside the test directory """
- def decorator(self):
- old_SCRATCHDIR = settings.SCRATCHDIR
- old_POTDIR = settings.POTDIR
- settings.SCRATCHDIR = os.path.join(os.path.dirname(os.path.abspath(__file__)), 'scratch')
- settings.POTDIR = os.path.join(settings.SCRATCHDIR, "POT")
- os.makedirs(settings.POTDIR)
- gnome_hello_tar = tarfile.open(os.path.join(os.path.dirname(os.path.abspath(__file__)),
'gnome-hello.tar.gz'))
- gnome_hello_tar.extractall(os.path.join(settings.SCRATCHDIR, 'git'))
- gnome_hello_tar.close()
- try:
- test_func(self)
- finally:
- shutil.rmtree(settings.SCRATCHDIR)
- settings.SCRATCHDIR = old_SCRATCHDIR
- settings.POTDIR = old_POTDIR
- return decorator
-
-def mocked_checkout(branch):
- """ Replace real vcs checkout by a mocked method """
- if branch.name == 'trunk2':
- raise
- return
-
-class ModuleTestCase(TestCase):
- fixtures = ['sample_data.json']
- SYS_DEPENDENCIES = (
- ('gettext', 'msgfmt'),
- ('intltool', 'intltool-update'),
- ('gnome-doc-utils', 'xml2po'),
- )
- def __init__(self, name):
- TestCase.__init__(self, name)
- for package, prog in self.SYS_DEPENDENCIES:
- if not check_program_presence(prog):
- raise Exception("You are missing a required system package needed by Damned Lies (%s)" %
package)
-
- def setUp(self):
- Branch.checkout_on_creation = False
- Branch.checkout = mocked_checkout
- self.mod = Module.objects.get(name="gnome-hello")
- self.branch = self.mod.branch_set.get(name="master")
-
- def test_module_methods(self):
- self.assertEqual(self.mod.get_description(), 'gnome-hello')
-
- def test_branch_methods(self):
- self.assertTrue(self.branch.is_head())
- self.assertEqual(self.branch.get_vcs_url(), "git://git.gnome.org/gnome-hello")
- self.assertEqual(self.branch.get_vcs_web_url(), "https://git.gnome.org/browse/gnome-hello/")
-
- @test_scratchdir
- def test_branch_stats(self):
- lang = Language.objects.create(name='xxx', locale='xxx')
- ghost_stat = Statistics.objects.create(branch=self.branch,
domain=self.mod.domain_set.get(name='po'), language=lang)
- # Check stats
- self.branch.update_stats(force=True)
- fr_po_stat = Statistics.objects.get(branch=self.branch, domain__name='po', language__locale='fr')
- self.assertEqual(fr_po_stat.translated(), 44)
- fr_doc_stat = Statistics.objects.get(branch=self.branch, domain__name='help', language__locale='fr')
- self.assertEqual(fr_doc_stat.translated(), 13)
- self.assertEqual(fr_po_stat.po_url(), u"/POT/gnome-hello.master/gnome-hello.master.fr.po")
- self.assertEqual(fr_po_stat.pot_url(), u"/POT/gnome-hello.master/gnome-hello.master.pot")
- self.assertEqual(fr_doc_stat.po_url(), u"/POT/gnome-hello.master/docs/gnome-hello-help.master.fr.po")
- self.assertRaises(Statistics.DoesNotExist, Statistics.objects.get, pk=ghost_stat.pk)
- from stats.utils import has_toolkit
- if has_toolkit:
- self.assertEqual(fr_po_stat.po_url(reduced=True),
u"/POT/gnome-hello.master/gnome-hello.master.fr.reduced.po")
- self.assertEqual(fr_po_stat.translated(scope='part'), 44)
-
- @test_scratchdir
- def test_delete_branch(self):
- """ Deleting the master branch of a git module deletes the checkout dir """
- checkout_path = self.branch.co_path()
- branch = Branch.objects.create(name="gnome-hello-1-4", module = self.mod)
- branch.delete()
- self.assertTrue(os.access(checkout_path, os.F_OK))
- self.branch.delete()
- self.assertFalse(os.access(checkout_path, os.F_OK))
-
- def test_create_unexisting_branch(self):
- """ Try to create a non-existing branch """
- Branch.checkout_on_creation = True
- branch = Branch(name="trunk2",
- module = self.mod)
- self.assertRaises(ValidationError, branch.clean)
-
- def test_branch_sorting(self):
- b1 = Branch(name='a-branch', module=self.mod)
- b1.save(update_statistics=False)
- b2 = Branch(name='p-branch', module=self.mod)
- b2.save(update_statistics=False)
- self.assertEqual([b.name for b in sorted(self.mod.branch_set.all())],
['master','p-branch','a-branch'])
- b1.weight = -1
- b1.save(update_statistics=False)
- self.assertEqual([b.name for b in sorted(self.mod.branch_set.all())],
['master','a-branch','p-branch'])
-
- @test_scratchdir
- def test_string_frozen_mail(self):
- """ String change for a module of a string_frozen release should generate a message """
- mail.outbox = []
- self.branch.update_stats(force=False)
-
- # Create a new file with translation
- new_file_path = os.path.join(self.branch.co_path(), "dummy_file.py")
- new_string = "Dummy string for D-L tests"
- f = open(new_file_path, 'w')
- f.write("a = _('%s')\n" % new_string)
- f.close()
- # Add the new file to POTFILES.in
- f = open(os.path.join(self.branch.co_path(), "po", "POTFILES.in"), 'a')
- f.write("dummy_file.py\n")
- f.close()
- # Regenerate stats (mail should be sent)
- self.branch.update_stats(force=False, checkout=False)
- # Assertions
- self.assertEqual(len(mail.outbox), 1);
- self.assertEqual(mail.outbox[0].subject, "String additions to 'gnome-hello.master'")
- self.assertIn('"%s"' % new_string, mail.outbox[0].body)
-
- def test_read_file_variable(self):
- from stats.utils import search_variable_in_file
- file_path = os.path.join(os.path.dirname(os.path.abspath(__file__)), "help_docbook", "Makefile.am")
- var_content = search_variable_in_file(file_path, "DOC_INCLUDES")
- self.assertEqual(var_content.split(), ['rnusers.xml', 'rnlookingforward.xml', '$(NULL)'])
-
- def test_generate_doc_potfile(self):
- from stats.utils import generate_doc_pot_file, get_fig_stats, DocFormat
- # Docbook-style help
- help_path = os.path.join(os.path.dirname(os.path.abspath(__file__)), "help_docbook")
- potfile, errs, doc_format = generate_doc_pot_file(help_path, 'release-notes', 'release-notes')
- pot_path = os.path.join(help_path, "C", "release-notes.pot")
- self.assertTrue(os.access(pot_path, os.R_OK))
- res = get_fig_stats(pot_path, doc_format=doc_format)
- self.assertEqual(len(res), 1)
- os.remove(pot_path)
- # Mallard-style help (with itstool)
- pot_path = os.path.join(os.path.dirname(os.path.abspath(__file__)), "help_mallard",
"gnome-help-itstool.pot")
- res = get_fig_stats(pot_path, doc_format=DocFormat(True, True))
- self.assertEqual(len(res), 2)
- self.assertEqual(res[0]['path'], "figures/gnome.png")
-
- @test_scratchdir
- def test_http_pot(self):
- dom = Domain.objects.create(
- module=self.mod, name='http-po',
- description='UI Translations', dtype='ui',
- pot_method='https://l10n.gnome.org/POT/damned-lies.master/damned-lies.master.pot')
- self.branch.checkout()
- potfile, errs = dom.generate_pot_file(self.branch)
- self.assertTrue(os.path.exists(potfile))
-
- @test_scratchdir
- def test_dynamic_po(self):
- """ Test the creation of a blank po file for a new language """
- lang = Language.objects.create(name="Tamil", locale="ta")
- self.branch.update_stats(force=False) # At least POT stats needed
- response = self.client.get('/module/po/gnome-hello/po/master/ta.po')
- self.assertContains(response, """# Tamil translation for gnome-hello.
-# Copyright (C) %s gnome-hello's COPYRIGHT HOLDER
-# This file is distributed under the same license as the gnome-hello package.
-# FIRST AUTHOR <EMAIL ADDRESS>, YEAR.""" % date.today().year)
- self.assertContains(response, "Language-Team: Tamil <ta li org>")
- try:
- response = self.client.get('/module/po/gnome-hello/po/master/ta-reduced.po')
- except OSError, e:
- if "msginit" in str(e):
- self.fail(
- "You are probably running an unpatched version of the translate-toolkit. "
- "See http://bugs.locamotion.org/show_bug.cgi?id=2129"
- )
- return
- else:
- raise e
- self.assertContains(response, """# Tamil translation for gnome-hello.""")
-
- @test_scratchdir
- def test_branch_file_changed(self):
- # file_hashes is empty in fixture, so first call should always return True
- self.assertTrue(self.mod.get_head_branch().file_changed("gnome-hello.doap"))
- self.assertFalse(self.mod.get_head_branch().file_changed("gnome-hello.doap"))
-
- @test_scratchdir
- def test_update_maintainers_from_doap_file(self):
- from stats.doap import update_doap_infos
- from people.models import Person
- # Add a maintainer which will be removed
- pers = Person(username="toto")
- pers.save()
- self.mod.maintainers.add(pers)
- update_doap_infos(self.mod)
- self.assertEqual(self.mod.maintainers.count(), 3)
- claude = self.mod.maintainers.get(email='claude 2xlibre net')
- self.assertEqual(claude.username, 'claudep')
-
- @test_scratchdir
- def test_update_doap_infos(self):
- from stats.doap import update_doap_infos
- update_doap_infos(self.mod)
- self.assertEqual(self.mod.homepage, "http://git.gnome.org/browse/gnome-hello")
-
-
-class StatisticsTests(TestCase):
- fixtures = ['sample_data.json']
- def test_total_stats_for_lang(self):
- rel = Release.objects.get(name="gnome-2-30")
- total_for_lang = rel.total_for_lang(Language.objects.get(locale='fr'))
- self.assertEqual(total_for_lang['ui']['total'], total_for_lang['ui_part']['total'])
- self.assertTrue(total_for_lang['ui']['untranslated'] == total_for_lang['ui_part']['untranslated'] ==
0)
- total_for_lang = rel.total_for_lang(Language.objects.get(locale='bem'))
- self.assertEqual(total_for_lang['ui']['total']-8, total_for_lang['ui_part']['total'])
- self.assertEqual(total_for_lang['ui']['untranslated'], 183)
- self.assertEqual(total_for_lang['ui_part']['untranslated'], 175)
-
- def test_stats_links(self):
- pot_stats = Statistics.objects.get(
- branch__module__name='zenity', branch__name='gnome-2-30',
- domain__name='po', language__isnull=True)
- self.assertEqual(pot_stats.po_url(), "/POT/zenity.gnome-2-30/zenity.gnome-2-30.pot")
- stats = Statistics.objects.get(
- branch__module__name='zenity', branch__name='gnome-2-30',
- domain__name='po', language__locale='it')
- self.assertEqual(stats.po_url(), "/POT/zenity.gnome-2-30/zenity.gnome-2-30.it.po")
- self.assertEqual(stats.po_url(reduced=True),
"/POT/zenity.gnome-2-30/zenity.gnome-2-30.it.reduced.po")
- # Same for a fake stats
- stats = FakeLangStatistics(pot_stats, Language.objects.get(locale='bem'))
- self.assertEqual(stats.po_url(), "/module/po/zenity/po/gnome-2-30/bem.po")
- self.assertEqual(stats.po_url(reduced=True), "/module/po/zenity/po/gnome-2-30/bem-reduced.po")
-
- def test_set_translation_stats(self):
- from vertimus.models import State, StateTranslating
- # Get a stat that has full_po and part_po
- stat = Statistics.objects.get(branch__module__name='zenity', branch__name='gnome-2-30',
language__locale='it', domain__dtype='ui')
- pers = Person.objects.create(username="toto")
- state = StateTranslating.objects.create(branch=stat.branch, domain=stat.domain,
language=stat.language, person=pers)
- # Mark file completely translated
- self.assertNotEqual(stat.part_po, stat.full_po)
- stat.set_translation_stats('dummy', 136, 0, 0)
- self.assertEqual(stat.part_po, stat.full_po)
- # Check state is still translating
- state = State.objects.filter(branch=stat.branch, domain=stat.domain, language=stat.language)
- self.assertEqual(len(state), 1)
- self.assertTrue(isinstance(state[0], StateTranslating))
-
-class FigureTests(TestCase):
- fixtures = ['sample_data.json']
- def test_figure_view(self):
- url = reverse('stats.views.docimages', args=['gnome-hello', 'help', 'master', 'fr'])
- response = self.client.get(url)
- self.assertContains(response, "gnome-hello-new.png")
- # Same for a non-existing language
- Language.objects.create(name='Afrikaans', locale='af')
- url = reverse('stats.views.docimages', args=['gnome-hello', 'help', 'master', 'af'])
- response = self.client.get(url)
- self.assertContains(response, "gnome-hello-new.png")
-
- def test_figure_URLs(self):
- """ Test if figure urls are properly constructed """
- stat = Statistics.objects.get(branch__module__name='gnome-hello', branch__name='master',
domain__dtype='doc', language__locale='fr')
- figs = stat.get_figures()
- self.assertEqual(figs[0]['orig_remote_url'],
'https://git.gnome.org/browse/gnome-hello/plain/help/C/figures/gnome-hello-new.png?h=master')
- self.assertFalse('trans_remote_url' in figs[0])
-
- @test_scratchdir
- def test_identical_figure_warning(self):
- """ Detect warning if translated figure is identical to original figure """
- from stats.utils import check_identical_figures
- branch = Branch.objects.get(module__name='gnome-hello', name='master')
- pot_stat = Statistics.objects.get(branch=branch, domain__name='help', language__isnull=True)
- fig_path = os.path.join(pot_stat.branch.co_path(), pot_stat.domain.directory, 'C',
pot_stat.get_figures()[0]['path'])
- shutil.copyfile(fig_path, fig_path.replace('/C/', '/fr/'))
- doc_stat = Statistics.objects.get(branch=branch, domain__name='help', language__locale='fr')
- errs = check_identical_figures(doc_stat.get_figures(), os.path.join(branch.co_path(), 'help'), 'fr')
- self.assertEqual(len(errs), 1)
- self.assertTrue(errs[0][1].startswith("Figures should not be copied"))
-
-class OtherTests(TestCase):
- def test_bugzilla_linkify(self):
- from stats.templatetags.stats_extras import bugzilla_linkify
- self.assertEqual(bugzilla_linkify(u"Sample normal text should not be altered."),
- u"Sample normal text should not be altered.")
- self.assertEqual(bugzilla_linkify(u"Bugzilla bug numbers like #669240 should be linkified"),
- u'Bugzilla bug numbers like <a rel="nofollow"
href="https://bugzilla.gnome.org/show_bug.cgi?id=669240">#669240</a> should be linkified')
- self.assertEqual(bugzilla_linkify(u"#669240 start or finish #669240"),
- u'<a rel="nofollow" href="https://bugzilla.gnome.org/show_bug.cgi?id=669240">#669240</a> start
or finish <a rel="nofollow" href="https://bugzilla.gnome.org/show_bug.cgi?id=669240">#669240</a>')
- self.assertEqual(bugzilla_linkify(u"Test with encoded entities (rock'n roll) should not."),
- u"Test with encoded entities (rock'n roll) should not.")
+# Temporary import to accomodate for Django < 1.6
+from .tests import *
diff --git a/stats/tests/tests.py b/stats/tests/tests.py
new file mode 100644
index 0000000..df75a35
--- /dev/null
+++ b/stats/tests/tests.py
@@ -0,0 +1,325 @@
+# -*- coding: utf-8 -*-
+#
+# Copyright (c) 2008-2012 Claude Paroz <claude 2xlibre net>
+#
+# This file is part of Damned Lies.
+#
+# Damned Lies is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2 of the License, or
+# (at your option) any later version.
+#
+# Damned Lies is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with Damned Lies; if not, write to the Free Software Foundation, Inc.,
+# 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+
+import os
+import shutil
+import tarfile
+from datetime import date
+
+from django.test import TestCase
+from django.core import mail
+from django.core.exceptions import ValidationError
+from django.core.urlresolvers import reverse
+from django.conf import settings
+
+from stats.models import Module, Domain, Branch, Release, Statistics, FakeLangStatistics
+from stats.utils import check_program_presence, run_shell_command
+from languages.models import Language
+
+from fixture_factory import *
+
+def test_scratchdir(test_func):
+ """ Decorator to temporarily use the scratchdir inside the test directory """
+ def decorator(self):
+ old_SCRATCHDIR = settings.SCRATCHDIR
+ old_POTDIR = settings.POTDIR
+ settings.SCRATCHDIR = os.path.join(os.path.dirname(os.path.abspath(__file__)), 'scratch')
+ settings.POTDIR = os.path.join(settings.SCRATCHDIR, "POT")
+ os.makedirs(settings.POTDIR)
+ gnome_hello_tar = tarfile.open(os.path.join(os.path.dirname(os.path.abspath(__file__)),
'gnome-hello.tar.gz'))
+ gnome_hello_tar.extractall(os.path.join(settings.SCRATCHDIR, 'git'))
+ gnome_hello_tar.close()
+ try:
+ test_func(self)
+ finally:
+ shutil.rmtree(settings.SCRATCHDIR)
+ settings.SCRATCHDIR = old_SCRATCHDIR
+ settings.POTDIR = old_POTDIR
+ return decorator
+
+def mocked_checkout(branch):
+ """ Replace real vcs checkout by a mocked method """
+ if branch.name == 'trunk2':
+ raise
+ return
+
+class ModuleTestCase(TestCase):
+ fixtures = ['sample_data.json']
+ SYS_DEPENDENCIES = (
+ ('gettext', 'msgfmt'),
+ ('intltool', 'intltool-update'),
+ ('gnome-doc-utils', 'xml2po'),
+ )
+ def __init__(self, name):
+ TestCase.__init__(self, name)
+ for package, prog in self.SYS_DEPENDENCIES:
+ if not check_program_presence(prog):
+ raise Exception("You are missing a required system package needed by Damned Lies (%s)" %
package)
+
+ def setUp(self):
+ Branch.checkout_on_creation = False
+ Branch.checkout = mocked_checkout
+ self.mod = Module.objects.get(name="gnome-hello")
+ self.branch = self.mod.branch_set.get(name="master")
+
+ def test_module_methods(self):
+ self.assertEqual(self.mod.get_description(), 'gnome-hello')
+
+ def test_branch_methods(self):
+ self.assertTrue(self.branch.is_head())
+ self.assertEqual(self.branch.get_vcs_url(), "git://git.gnome.org/gnome-hello")
+ self.assertEqual(self.branch.get_vcs_web_url(), "https://git.gnome.org/browse/gnome-hello/")
+
+ @test_scratchdir
+ def test_branch_stats(self):
+ lang = Language.objects.create(name='xxx', locale='xxx')
+ ghost_stat = Statistics.objects.create(branch=self.branch,
domain=self.mod.domain_set.get(name='po'), language=lang)
+ # Check stats
+ self.branch.update_stats(force=True)
+ fr_po_stat = Statistics.objects.get(branch=self.branch, domain__name='po', language__locale='fr')
+ self.assertEqual(fr_po_stat.translated(), 44)
+ fr_doc_stat = Statistics.objects.get(branch=self.branch, domain__name='help', language__locale='fr')
+ self.assertEqual(fr_doc_stat.translated(), 13)
+ self.assertEqual(fr_po_stat.po_url(), u"/POT/gnome-hello.master/gnome-hello.master.fr.po")
+ self.assertEqual(fr_po_stat.pot_url(), u"/POT/gnome-hello.master/gnome-hello.master.pot")
+ self.assertEqual(fr_doc_stat.po_url(), u"/POT/gnome-hello.master/docs/gnome-hello-help.master.fr.po")
+ self.assertRaises(Statistics.DoesNotExist, Statistics.objects.get, pk=ghost_stat.pk)
+ from stats.utils import has_toolkit
+ if has_toolkit:
+ self.assertEqual(fr_po_stat.po_url(reduced=True),
u"/POT/gnome-hello.master/gnome-hello.master.fr.reduced.po")
+ self.assertEqual(fr_po_stat.translated(scope='part'), 44)
+
+ @test_scratchdir
+ def test_delete_branch(self):
+ """ Deleting the master branch of a git module deletes the checkout dir """
+ checkout_path = self.branch.co_path()
+ branch = Branch.objects.create(name="gnome-hello-1-4", module = self.mod)
+ branch.delete()
+ self.assertTrue(os.access(checkout_path, os.F_OK))
+ self.branch.delete()
+ self.assertFalse(os.access(checkout_path, os.F_OK))
+
+ def test_create_unexisting_branch(self):
+ """ Try to create a non-existing branch """
+ Branch.checkout_on_creation = True
+ branch = Branch(name="trunk2",
+ module = self.mod)
+ self.assertRaises(ValidationError, branch.clean)
+
+ def test_branch_sorting(self):
+ b1 = Branch(name='a-branch', module=self.mod)
+ b1.save(update_statistics=False)
+ b2 = Branch(name='p-branch', module=self.mod)
+ b2.save(update_statistics=False)
+ self.assertEqual([b.name for b in sorted(self.mod.branch_set.all())],
['master','p-branch','a-branch'])
+ b1.weight = -1
+ b1.save(update_statistics=False)
+ self.assertEqual([b.name for b in sorted(self.mod.branch_set.all())],
['master','a-branch','p-branch'])
+
+ @test_scratchdir
+ def test_string_frozen_mail(self):
+ """ String change for a module of a string_frozen release should generate a message """
+ mail.outbox = []
+ self.branch.update_stats(force=False)
+
+ # Create a new file with translation
+ new_file_path = os.path.join(self.branch.co_path(), "dummy_file.py")
+ new_string = "Dummy string for D-L tests"
+ f = open(new_file_path, 'w')
+ f.write("a = _('%s')\n" % new_string)
+ f.close()
+ # Add the new file to POTFILES.in
+ f = open(os.path.join(self.branch.co_path(), "po", "POTFILES.in"), 'a')
+ f.write("dummy_file.py\n")
+ f.close()
+ # Regenerate stats (mail should be sent)
+ self.branch.update_stats(force=False, checkout=False)
+ # Assertions
+ self.assertEqual(len(mail.outbox), 1);
+ self.assertEqual(mail.outbox[0].subject, "String additions to 'gnome-hello.master'")
+ self.assertIn('"%s"' % new_string, mail.outbox[0].body)
+
+ def test_read_file_variable(self):
+ from stats.utils import search_variable_in_file
+ file_path = os.path.join(os.path.dirname(os.path.abspath(__file__)), "help_docbook", "Makefile.am")
+ var_content = search_variable_in_file(file_path, "DOC_INCLUDES")
+ self.assertEqual(var_content.split(), ['rnusers.xml', 'rnlookingforward.xml', '$(NULL)'])
+
+ def test_generate_doc_potfile(self):
+ from stats.utils import generate_doc_pot_file, get_fig_stats, DocFormat
+ # Docbook-style help
+ help_path = os.path.join(os.path.dirname(os.path.abspath(__file__)), "help_docbook")
+ potfile, errs, doc_format = generate_doc_pot_file(help_path, 'release-notes', 'release-notes')
+ pot_path = os.path.join(help_path, "C", "release-notes.pot")
+ self.assertTrue(os.access(pot_path, os.R_OK))
+ res = get_fig_stats(pot_path, doc_format=doc_format)
+ self.assertEqual(len(res), 1)
+ os.remove(pot_path)
+ # Mallard-style help (with itstool)
+ pot_path = os.path.join(os.path.dirname(os.path.abspath(__file__)), "help_mallard",
"gnome-help-itstool.pot")
+ res = get_fig_stats(pot_path, doc_format=DocFormat(True, True))
+ self.assertEqual(len(res), 2)
+ self.assertEqual(res[0]['path'], "figures/gnome.png")
+
+ @test_scratchdir
+ def test_http_pot(self):
+ dom = Domain.objects.create(
+ module=self.mod, name='http-po',
+ description='UI Translations', dtype='ui',
+ pot_method='https://l10n.gnome.org/POT/damned-lies.master/damned-lies.master.pot')
+ self.branch.checkout()
+ potfile, errs = dom.generate_pot_file(self.branch)
+ self.assertTrue(os.path.exists(potfile))
+
+ @test_scratchdir
+ def test_dynamic_po(self):
+ """ Test the creation of a blank po file for a new language """
+ lang = Language.objects.create(name="Tamil", locale="ta")
+ self.branch.update_stats(force=False) # At least POT stats needed
+ response = self.client.get('/module/po/gnome-hello/po/master/ta.po')
+ self.assertContains(response, """# Tamil translation for gnome-hello.
+# Copyright (C) %s gnome-hello's COPYRIGHT HOLDER
+# This file is distributed under the same license as the gnome-hello package.
+# FIRST AUTHOR <EMAIL ADDRESS>, YEAR.""" % date.today().year)
+ self.assertContains(response, "Language-Team: Tamil <ta li org>")
+ try:
+ response = self.client.get('/module/po/gnome-hello/po/master/ta-reduced.po')
+ except OSError, e:
+ if "msginit" in str(e):
+ self.fail(
+ "You are probably running an unpatched version of the translate-toolkit. "
+ "See http://bugs.locamotion.org/show_bug.cgi?id=2129"
+ )
+ return
+ else:
+ raise e
+ self.assertContains(response, """# Tamil translation for gnome-hello.""")
+
+ @test_scratchdir
+ def test_branch_file_changed(self):
+ # file_hashes is empty in fixture, so first call should always return True
+ self.assertTrue(self.mod.get_head_branch().file_changed("gnome-hello.doap"))
+ self.assertFalse(self.mod.get_head_branch().file_changed("gnome-hello.doap"))
+
+ @test_scratchdir
+ def test_update_maintainers_from_doap_file(self):
+ from stats.doap import update_doap_infos
+ from people.models import Person
+ # Add a maintainer which will be removed
+ pers = Person(username="toto")
+ pers.save()
+ self.mod.maintainers.add(pers)
+ update_doap_infos(self.mod)
+ self.assertEqual(self.mod.maintainers.count(), 3)
+ claude = self.mod.maintainers.get(email='claude 2xlibre net')
+ self.assertEqual(claude.username, 'claudep')
+
+ @test_scratchdir
+ def test_update_doap_infos(self):
+ from stats.doap import update_doap_infos
+ update_doap_infos(self.mod)
+ self.assertEqual(self.mod.homepage, "http://git.gnome.org/browse/gnome-hello")
+
+
+class StatisticsTests(TestCase):
+ fixtures = ['sample_data.json']
+ def test_total_stats_for_lang(self):
+ rel = Release.objects.get(name="gnome-2-30")
+ total_for_lang = rel.total_for_lang(Language.objects.get(locale='fr'))
+ self.assertEqual(total_for_lang['ui']['total'], total_for_lang['ui_part']['total'])
+ self.assertTrue(total_for_lang['ui']['untranslated'] == total_for_lang['ui_part']['untranslated'] ==
0)
+ total_for_lang = rel.total_for_lang(Language.objects.get(locale='bem'))
+ self.assertEqual(total_for_lang['ui']['total']-8, total_for_lang['ui_part']['total'])
+ self.assertEqual(total_for_lang['ui']['untranslated'], 183)
+ self.assertEqual(total_for_lang['ui_part']['untranslated'], 175)
+
+ def test_stats_links(self):
+ pot_stats = Statistics.objects.get(
+ branch__module__name='zenity', branch__name='gnome-2-30',
+ domain__name='po', language__isnull=True)
+ self.assertEqual(pot_stats.po_url(), "/POT/zenity.gnome-2-30/zenity.gnome-2-30.pot")
+ stats = Statistics.objects.get(
+ branch__module__name='zenity', branch__name='gnome-2-30',
+ domain__name='po', language__locale='it')
+ self.assertEqual(stats.po_url(), "/POT/zenity.gnome-2-30/zenity.gnome-2-30.it.po")
+ self.assertEqual(stats.po_url(reduced=True),
"/POT/zenity.gnome-2-30/zenity.gnome-2-30.it.reduced.po")
+ # Same for a fake stats
+ stats = FakeLangStatistics(pot_stats, Language.objects.get(locale='bem'))
+ self.assertEqual(stats.po_url(), "/module/po/zenity/po/gnome-2-30/bem.po")
+ self.assertEqual(stats.po_url(reduced=True), "/module/po/zenity/po/gnome-2-30/bem-reduced.po")
+
+ def test_set_translation_stats(self):
+ from vertimus.models import State, StateTranslating
+ # Get a stat that has full_po and part_po
+ stat = Statistics.objects.get(branch__module__name='zenity', branch__name='gnome-2-30',
language__locale='it', domain__dtype='ui')
+ pers = Person.objects.create(username="toto")
+ state = StateTranslating.objects.create(branch=stat.branch, domain=stat.domain,
language=stat.language, person=pers)
+ # Mark file completely translated
+ self.assertNotEqual(stat.part_po, stat.full_po)
+ stat.set_translation_stats('dummy', 136, 0, 0)
+ self.assertEqual(stat.part_po, stat.full_po)
+ # Check state is still translating
+ state = State.objects.filter(branch=stat.branch, domain=stat.domain, language=stat.language)
+ self.assertEqual(len(state), 1)
+ self.assertTrue(isinstance(state[0], StateTranslating))
+
+class FigureTests(TestCase):
+ fixtures = ['sample_data.json']
+ def test_figure_view(self):
+ url = reverse('stats.views.docimages', args=['gnome-hello', 'help', 'master', 'fr'])
+ response = self.client.get(url)
+ self.assertContains(response, "gnome-hello-new.png")
+ # Same for a non-existing language
+ Language.objects.create(name='Afrikaans', locale='af')
+ url = reverse('stats.views.docimages', args=['gnome-hello', 'help', 'master', 'af'])
+ response = self.client.get(url)
+ self.assertContains(response, "gnome-hello-new.png")
+
+ def test_figure_URLs(self):
+ """ Test if figure urls are properly constructed """
+ stat = Statistics.objects.get(branch__module__name='gnome-hello', branch__name='master',
domain__dtype='doc', language__locale='fr')
+ figs = stat.get_figures()
+ self.assertEqual(figs[0]['orig_remote_url'],
'https://git.gnome.org/browse/gnome-hello/plain/help/C/figures/gnome-hello-new.png?h=master')
+ self.assertFalse('trans_remote_url' in figs[0])
+
+ @test_scratchdir
+ def test_identical_figure_warning(self):
+ """ Detect warning if translated figure is identical to original figure """
+ from stats.utils import check_identical_figures
+ branch = Branch.objects.get(module__name='gnome-hello', name='master')
+ pot_stat = Statistics.objects.get(branch=branch, domain__name='help', language__isnull=True)
+ fig_path = os.path.join(pot_stat.branch.co_path(), pot_stat.domain.directory, 'C',
pot_stat.get_figures()[0]['path'])
+ shutil.copyfile(fig_path, fig_path.replace('/C/', '/fr/'))
+ doc_stat = Statistics.objects.get(branch=branch, domain__name='help', language__locale='fr')
+ errs = check_identical_figures(doc_stat.get_figures(), os.path.join(branch.co_path(), 'help'), 'fr')
+ self.assertEqual(len(errs), 1)
+ self.assertTrue(errs[0][1].startswith("Figures should not be copied"))
+
+class OtherTests(TestCase):
+ def test_bugzilla_linkify(self):
+ from stats.templatetags.stats_extras import bugzilla_linkify
+ self.assertEqual(bugzilla_linkify(u"Sample normal text should not be altered."),
+ u"Sample normal text should not be altered.")
+ self.assertEqual(bugzilla_linkify(u"Bugzilla bug numbers like #669240 should be linkified"),
+ u'Bugzilla bug numbers like <a rel="nofollow"
href="https://bugzilla.gnome.org/show_bug.cgi?id=669240">#669240</a> should be linkified')
+ self.assertEqual(bugzilla_linkify(u"#669240 start or finish #669240"),
+ u'<a rel="nofollow" href="https://bugzilla.gnome.org/show_bug.cgi?id=669240">#669240</a> start
or finish <a rel="nofollow" href="https://bugzilla.gnome.org/show_bug.cgi?id=669240">#669240</a>')
+ self.assertEqual(bugzilla_linkify(u"Test with encoded entities (rock'n roll) should not."),
+ u"Test with encoded entities (rock'n roll) should not.")
diff --git a/vertimus/tests/__init__.py b/vertimus/tests/__init__.py
index 1cd81d3..1ae7f52 100644
--- a/vertimus/tests/__init__.py
+++ b/vertimus/tests/__init__.py
@@ -1,500 +1,2 @@
-# -*- coding: utf-8 -*-
-#
-# Copyright (c) 2008 Stéphane Raimbault <stephane raimbault gmail com>
-#
-# This file is part of Damned Lies.
-#
-# Damned Lies is free software; you can redistribute it and/or modify
-# it under the terms of the GNU General Public License as published by
-# the Free Software Foundation; either version 2 of the License, or
-# (at your option) any later version.
-#
-# Damned Lies is distributed in the hope that it will be useful,
-# but WITHOUT ANY WARRANTY; without even the implied warranty of
-# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
-# GNU General Public License for more details.
-#
-# You should have received a copy of the GNU General Public License
-# along with Damned Lies; if not, write to the Free Software Foundation, Inc.,
-# 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
-
-import os
-
-from django.conf import settings
-from django.core.files.base import File, ContentFile
-from django.core.files.uploadedfile import SimpleUploadedFile
-from django.core import mail
-from django.core.urlresolvers import reverse
-from django.http import QueryDict
-from django.utils.datastructures import MultiValueDict
-
-from teams.tests import TeamsAndRolesTests
-from stats.models import Module, Branch, Release, Category, Domain, Statistics
-from stats.tests import test_scratchdir
-from vertimus.models import *
-from vertimus.forms import ActionForm
-
-class VertimusTest(TeamsAndRolesTests):
-
- def setUp(self):
- super(VertimusTest, self).setUp()
-
- self.m = Module.objects.create(name='gedit', description='GNOME Editor',
- bugs_base="https://bugzilla.gnome.org/",
- bugs_product='gedit', bugs_component='general',
- vcs_type='svn', vcs_root="http://svn.gnome.org/svn",
- vcs_web="http://svn.gnome.org/viewvc/gedit")
-
- Branch.checkout_on_creation = False
- self.b = Branch(name='gnome-2-24', module=self.m)
- # Block the update of Statistics by the thread
- self.b.save(update_statistics=False)
-
- self.r = Release.objects.create(name='gnome-2-24', status='official',
- description='GNOME 2.24 (stable)',
- string_frozen=True)
-
- self.c = Category.objects.create(release=self.r, branch=self.b, name='desktop')
-
- self.d = Domain.objects.create(module=self.m, name='po',
- description='UI translations',
- dtype='ui', directory='po')
- pot_stat = Statistics.objects.create(language=None, branch=self.b, domain=self.d)
- self.files_to_clean = []
-
- def tearDown(self):
- for path in self.files_to_clean:
- os.remove(path)
-
- def test_state_none(self):
- state = StateNone(branch=self.b, domain=self.d, language=self.l)
-
- action_names = [a.name for a in state.get_available_actions(self.pn)]
- self.assertEqual(action_names, ['WC'])
-
- for p in (self.pt, self.pr):
- action_names = [a.name for a in state.get_available_actions(p)]
- self.assertEqual(action_names, ['RT', 'WC'])
-
- for p in (self.pc, self.pcoo):
- action_names = [a.name for a in state.get_available_actions(p)]
- self.assertEqual(action_names, ['RT', 'WC', None, 'IC', 'AA'])
-
- def test_state_translating(self):
- state = StateTranslating(branch=self.b, domain=self.d, language=self.l, person=self.pt)
-
- for p in (self.pn, self.pr):
- action_names = [a.name for a in state.get_available_actions(p)]
- self.assertEqual(action_names, ['WC'])
-
- action_names = [a.name for a in state.get_available_actions(self.pc)]
- self.assertEqual(action_names, ['WC', None, 'IC', 'AA'])
-
- action_names = [a.name for a in state.get_available_actions(self.pcoo)]
- self.assertEqual(action_names, ['WC', 'UNDO', None, 'IC', 'AA'])
-
- # Same person
- action_names = [a.name for a in state.get_available_actions(self.pt)]
- self.assertEqual(action_names, ['UT', 'UNDO', 'WC'])
-
- def test_state_translated(self):
- state = StateTranslated(branch=self.b, domain=self.d, language=self.l, person=self.pt)
-
- action_names = [a.name for a in state.get_available_actions(self.pn)]
- self.assertEqual(action_names, ['WC'])
-
- action_names = [a.name for a in state.get_available_actions(self.pt)]
- self.assertEqual(action_names, ['RT', 'WC'])
-
- action_names = [a.name for a in state.get_available_actions(self.pr)]
- self.assertEqual(action_names, ['RP', 'TR', 'RT', 'WC'])
-
- for p in (self.pc, self.pcoo):
- action_names = [a.name for a in state.get_available_actions(p)]
- self.assertEqual(action_names, ['RP', 'TR', 'RT', 'TC', 'WC', None, 'IC', 'AA'])
-
- def test_state_proofreading(self):
- state = StateProofreading(branch=self.b, domain=self.d, language=self.l, person=self.pr)
-
- for p in (self.pn, self.pt):
- action_names = [a.name for a in state.get_available_actions(p)]
- self.assertEqual(action_names, ['WC'])
-
- action_names = [a.name for a in state.get_available_actions(self.pc)]
- self.assertEqual(action_names, ['WC', None, 'IC', 'AA'])
-
- action_names = [a.name for a in state.get_available_actions(self.pcoo)]
- self.assertEqual(action_names, ['WC', 'UNDO', None, 'IC', 'AA'])
-
- # Same person and reviewer
- action_names = [a.name for a in state.get_available_actions(self.pr)]
- self.assertEqual(action_names, ['UP', 'TR', 'TC', 'UNDO', 'WC'])
-
- def test_state_proofread(self):
- state = StateProofread(branch=self.b, domain=self.d, language=self.l, person=self.pr)
-
- for p in (self.pn, self.pt):
- action_names = [a.name for a in state.get_available_actions(p)]
- self.assertEqual(action_names, ['WC'])
-
- action_names = [a.name for a in state.get_available_actions(self.pr)]
- self.assertEqual(action_names, ['TC', 'RP', 'TR', 'WC'])
-
- for p in (self.pc, self.pcoo):
- action_names = [a.name for a in state.get_available_actions(p)]
- self.assertEqual(action_names, ['TC', 'RP', 'TR', 'WC', None, 'IC', 'AA'])
-
- def test_state_to_review(self):
- state = StateToReview(branch=self.b, domain=self.d, language=self.l, person=self.pt)
-
- action_names = [a.name for a in state.get_available_actions(self.pn)]
- self.assertEqual(action_names, ['WC'])
-
- for p in (self.pt, self.pr):
- action_names = [a.name for a in state.get_available_actions(p)]
- self.assertEqual(action_names, ['RT', 'WC'])
-
- for p in (self.pc, self.pcoo):
- action_names = [a.name for a in state.get_available_actions(p)]
- self.assertEqual(action_names, ['RT', 'WC', None, 'IC', 'AA'])
-
- def test_state_to_commit(self):
- state = StateToCommit(branch=self.b, domain=self.d, language=self.l, person=self.pr)
-
- for p in (self.pn, self.pt, self.pr):
- action_names = [a.name for a in state.get_available_actions(p)]
- self.assertEqual(action_names, ['WC'])
-
- for p in (self.pc, self.pcoo):
- action_names = [a.name for a in state.get_available_actions(p)]
- self.assertEqual(action_names, ['RC', 'TR', 'WC', None, 'IC', 'AA'])
-
- def test_state_committing(self):
- state = StateCommitting(branch=self.b, domain=self.d, language=self.l, person=self.pc)
-
- for p in (self.pn, self.pt, self.pr):
- action_names = [a.name for a in state.get_available_actions(p)]
- self.assertEqual(action_names, ['WC'])
-
- action_names = [a.name for a in state.get_available_actions(self.pcoo)]
- self.assertEqual(action_names, ['WC', 'UNDO', None, 'IC', 'AA'])
-
- action_names = [a.name for a in state.get_available_actions(self.pc)]
- self.assertEqual(action_names, ['IC', 'TR', 'UNDO', 'WC'])
-
- def test_state_committed(self):
- state = StateCommitted(branch=self.b, domain=self.d, language=self.l, person=self.pc)
-
- for p in (self.pn, self.pt, self.pr):
- action_names = [a.name for a in state.get_available_actions(p)]
- self.assertEqual(action_names, ['WC'])
-
- for p in (self.pc, self.pcoo):
- action_names = [a.name for a in state.get_available_actions(p)]
- self.assertEqual(action_names, ['AA', 'WC', None, 'IC', 'AA'])
-
- def test_action_wc(self):
- state = StateNone(branch=self.b, domain=self.d, language=self.l)
- state.save()
- prev_updated = state.updated
-
- action = Action.new_by_name('WC', person=self.pt, comment="Hi!")
- action.apply_on(state, action.send_mail_to_ml)
- self.assertEqual(len(mail.outbox), 1)
- self.assertEqual(mail.outbox[0].recipients(), [self.pt.email])
- # Test that submitting a comment without text generates a validation error
- form = ActionForm([ActionWC()], True, QueryDict('action=WC&comment='))
- self.assertTrue("A comment is needed" in str(form.errors))
- self.assertNotEqual(state.updated, prev_updated)
-
- # Test send comment to mailing list
- mail.outbox = []
- action = Action.new_by_name('WC', person=self.pt, comment="Hi again!")
- action.apply_on(state, True)
- self.assertEqual(len(mail.outbox), 1)
- self.assertEqual(mail.outbox[0].recipients(), [self.l.team.mailing_list])
- self.assertIn(u"Hi again!", mail.outbox[0].body)
-
- def test_action_rt(self):
- state = StateNone(branch=self.b, domain=self.d, language=self.l)
- state.save()
-
- action = Action.new_by_name('RT', person=self.pt, comment="Reserved!")
- action.apply_on(state, action.send_mail_to_ml)
- self.assertTrue(isinstance(state, StateTranslating))
-
- @test_scratchdir
- def test_action_ut(self):
- # Disabling the role
- role = Role.objects.get(person=self.pt, team=self.l.team)
- role.is_active = False
- role.save()
-
- state = StateTranslating(branch=self.b, domain=self.d, language=self.l, person=self.pt)
- state.save()
-
- test_file = open(os.path.join(os.path.dirname(os.path.abspath(__file__)), "valid_po.po"), 'r')
-
- action = Action.new_by_name('UT', person=self.pt, comment="Done by translator.",
file=File(test_file))
- action.apply_on(state, action.send_mail_to_ml)
-
- self.assertEqual(action.file.url, '/media/upload/gedit-gnome-2-24-po-fr-%d.po' % state.id)
- self.assertEqual(action.merged_file.url(), '/media/upload/gedit-gnome-2-24-po-fr-%d.merged.po' %
state.id)
- # Merged file will not be really produced as no pot file exists on the file system
- self.files_to_clean.append(action.file.path)
-
- self.assertTrue(isinstance(state, StateTranslated))
- # Mail sent to mailing list
- self.assertEqual(len(mail.outbox), 1)
- self.assertEqual(mail.outbox[0].recipients(), [self.l.team.mailing_list])
- self.assertEqual(mail.outbox[0].subject, "gedit - gnome-2-24")
-
- # Testing if the role was activated
- role = Role.objects.get(person=self.pt, team=self.l.team)
- self.assertTrue(role.is_active)
-
- def test_action_rp(self):
- state = StateTranslated(branch=self.b, domain=self.d, language=self.l)
- state.save()
-
- action = Action.new_by_name('RP', person=self.pr, comment="Reserved by a reviewer!")
- action.apply_on(state, action.send_mail_to_ml)
- self.assertTrue(isinstance(state, StateProofreading))
-
- def test_action_up(self):
- state = StateProofreading(branch=self.b, domain=self.d, language=self.l, person=self.pr)
- state.save()
-
- test_file = ContentFile('test content')
- test_file.name = 'mytestfile.po'
-
- action = Action.new_by_name('UP', person=self.pr, comment="Done.", file=test_file)
- action.apply_on(state, action.send_mail_to_ml)
- self.files_to_clean.append(action.file.path)
- self.assertTrue(isinstance(state, StateProofread))
-
- def test_action_tc(self):
- state = StateProofread(branch=self.b, domain=self.d, language=self.l)
- state.save()
-
- action = Action.new_by_name('TC', person=self.pr, comment="Ready!")
- action.apply_on(state, action.send_mail_to_ml)
- self.assertTrue(isinstance(state, StateToCommit))
-
- def test_action_rc(self):
- state = StateToCommit(branch=self.b, domain=self.d, language=self.l)
- state.save()
-
- action = Action.new_by_name('RC', person=self.pc, comment="This work is mine!")
- action.apply_on(state, action.send_mail_to_ml)
- self.assertTrue(isinstance(state, StateCommitting))
-
- def test_action_ic(self):
- state = StateProofreading(branch=self.b, domain=self.d, language=self.l, person=self.pr)
- state.save()
-
- # Create a new file
- test_file = ContentFile('test content')
- test_file.name = 'mytestfile.po'
-
- action = Action.new_by_name('UP', person=self.pr, comment="Done.", file=test_file)
- action.apply_on(state, action.send_mail_to_ml)
- self.assertEqual(len(mail.outbox), 1) # Mail sent to mailing list
- mail.outbox = []
-
- file_path = os.path.join(settings.MEDIA_ROOT, action.file.name)
- self.assertTrue(os.access(file_path, os.W_OK))
-
- action = Action.new_by_name('TC', person=self.pc, comment="To commit.")
- action.apply_on(state, action.send_mail_to_ml)
- self.assertEqual(len(mail.outbox), 1) # Mail sent to committers
- mail.outbox = []
-
- action = Action.new_by_name('RC', person=self.pc, comment="Reserved commit.")
- action.apply_on(state, action.send_mail_to_ml)
-
- action = Action.new_by_name('IC', person=self.pc, comment="Committed.")
- action.apply_on(state, action.send_mail_to_ml)
- # Mail sent to mailing list
- self.assertEqual(len(mail.outbox), 1)
- self.assertEqual(mail.outbox[0].recipients(), [self.l.team.mailing_list])
- # Team is French (but translations may not be compiled/up-to-date)
- self.assertTrue(u'Commité' in mail.outbox[0].body or "Committed" in mail.outbox[0].body)
-
- self.assertTrue(isinstance(state, StateNone))
- self.assertTrue(not os.access(file_path, os.F_OK), "%s not deleted" % file_path)
-
- # Remove test file
- action_archived = ActionArchived.objects.get(comment="Done.")
- filename_archived = os.path.join(settings.MEDIA_ROOT, action_archived.file.name)
- action_archived.delete()
- self.assertTrue(not os.access(filename_archived, os.F_OK), "%s not deleted" % filename_archived)
-
- def test_action_tr(self):
- state = StateTranslated(branch=self.b, domain=self.d, language=self.l)
- state.save()
-
- action = Action.new_by_name('TR', person=self.pc, comment="Bad work :-/")
- action.apply_on(state, action.send_mail_to_ml)
- self.assertTrue(isinstance(state, StateToReview))
-
- def test_action_aa(self):
- state = StateCommitted(branch=self.b, domain=self.d, language=self.l, person=self.pr)
- state.save()
-
- action = Action.new_by_name('AA', person=self.pc, comment="I don't want to disappear :)")
- action.apply_on(state, action.send_mail_to_ml)
-
- state = State.objects.get(branch=self.b, domain=self.d, language=self.l)
- self.assertTrue(isinstance(state, StateNone))
- self.assertEqual(state.action_set.count(), 0)
-
- def test_action_undo(self):
- state = StateNone(branch=self.b, domain=self.d, language=self.l)
- state.save()
-
- action = Action.new_by_name('RT', person=self.pt, comment="Reserved!")
- action.apply_on(state, action.send_mail_to_ml)
-
- action = Action.new_by_name('UNDO', person=self.pt, comment="Ooops! I don't want to do that. Sorry.")
- action.apply_on(state, action.send_mail_to_ml)
-
- self.assertEqual(state.name, 'None')
-
- action = Action.new_by_name('RT', person=self.pt, comment="Translating")
- action.apply_on(state, action.send_mail_to_ml)
-
- action = Action.new_by_name('UT', person=self.pt, comment="Translated")
- action.apply_on(state, action.send_mail_to_ml)
-
- action = Action.new_by_name('RT', person=self.pt, comment="Reserved!")
- action.apply_on(state, action.send_mail_to_ml)
-
- action = Action.new_by_name('UNDO', person=self.pt, comment="Ooops! I don't want to do that. Sorry.")
- action.apply_on(state, action.send_mail_to_ml)
-
- self.assertEqual(state.name, 'Translated')
-
- action = Action.new_by_name('RT', person=self.pt, comment="Translating 1")
- action.apply_on(state, action.send_mail_to_ml)
-
- action = Action.new_by_name('UNDO', person=self.pt, comment="Undo 1")
- action.apply_on(state, action.send_mail_to_ml)
-
- action = Action.new_by_name('RT', person=self.pt, comment="Translating 2")
- action.apply_on(state, action.send_mail_to_ml)
-
- action = Action.new_by_name('UNDO', person=self.pt, comment="Undo 2")
- action.apply_on(state, action.send_mail_to_ml)
-
- self.assertEqual(state.name, 'Translated')
-
- def test_delete(self):
- """ Test that a whole module tree can be properly deleted """
- state = StateNone(branch=self.b, domain=self.d, language=self.l)
- state.save()
-
- action = Action.new_by_name('WC', person=self.pt, comment="Hi!")
- action.apply_on(state, action.send_mail_to_ml)
-
- self.m.delete()
- self.assertEqual(Action.objects.all().count(), 0)
-
- def test_delete_domain(self):
- state = StateTranslating.objects.create(branch=self.b, domain=self.d, language=self.l,
person=self.pt)
- self.d.delete()
- self.assertEqual(State.objects.all().count(), 0)
-
- def test_delete_statistics(self):
- """ Test clean_dangling_states receiver """
- po_stat = Statistics.objects.create(branch=self.b, domain=self.d, language=self.l)
- state = StateTranslating.objects.create(branch=self.b, domain=self.d, language=self.l,
person=self.pt)
- po_stat.delete()
- self.assertEqual(State.objects.all().count(), 0)
-
- def test_vertimus_view(self):
- url = reverse('vertimus_by_ids', args=[self.b.id, self.d.id, self.l.id])
- response = self.client.get(url)
- self.assertNotContains(response, '<option value="WC">')
-
- self.client.login(username=self.pn.username, password='password')
- response = self.client.get(url)
- self.assertContains(response, '<option value="WC">')
-
- def test_uploaded_file_validation(self):
- # Test a non valid po file
- post_content = QueryDict('action=WC&comment=Test1')
- post_file = MultiValueDict({'file': [SimpleUploadedFile('filename.po', 'Not valid po file
content')]})
- form = ActionForm([ActionWC()], True, post_content, post_file)
-
- self.assertTrue('file' in form.errors)
-
- # Test a valid po file
- f = open(os.path.join(os.path.dirname(os.path.abspath(__file__)), "valid_po.po"), 'r')
- post_file = MultiValueDict({'file': [File(f)]})
- form = ActionForm([ActionWC()], True, post_content, post_file)
- self.assertTrue(form.is_valid())
-
- # Test form without file
- form = ActionForm([ActionWC()], True, post_content)
- self.assertTrue(form.is_valid())
-
- def test_feeds(self):
- state = StateNone(branch=self.b, domain=self.d, language=self.l)
- state.save()
-
- action = Action.new_by_name('RT', person=self.pt, comment="Translating")
- action.apply_on(state, action.send_mail_to_ml)
-
- response = self.client.get(reverse('lang_feed', args=[self.l.locale]))
- self.assertContains(response,
- """<rss xmlns:atom="http://www.w3.org/2005/Atom" version="2.0">""")
- self.assertContains(response,
- """<title>po (gedit/User Interface) - gedit (gnome-2-24) - Reserve for translation\n</title>""")
- self.assertContains(response,
- """<guid>http://example.com/vertimus/gedit/gnome-2-24/po/fr#%d</guid>""" % action.id)
-
- response = self.client.get(reverse('team_feed', args=[self.l.team.name]))
- self.assertContains(response,
- """<title>po (gedit/User Interface) - gedit (gnome-2-24) - Reserve for translation\n</title>""")
-
- def test_activity_summary(self):
- state = StateTranslating.objects.create(
- branch=self.b, domain=self.d,
- language=self.l,
- person=self.pt)
-
- response = self.client.get(reverse("activity_by_language", args=[self.l.locale]))
- self.assertContains(response, self.m.description)
-
- def test_mysql(self):
- # Copied from test_action_undo() with minor changes
- state = StateNone(branch=self.b, domain=self.d, language=self.l)
- state.save()
-
- action = Action.new_by_name('RT', person=self.pr, comment="Reserved!")
- action.apply_on(state, action.send_mail_to_ml)
-
- action = Action.new_by_name('UNDO', person=self.pr, comment="Ooops! I don't want to do that. Sorry.")
- action.apply_on(state, action.send_mail_to_ml)
-
- action = Action.new_by_name('RT', person=self.pr, comment="Translating")
- action.apply_on(state, action.send_mail_to_ml)
-
- action = Action.new_by_name('UT', person=self.pr, comment="Translated")
- action.apply_on(state, action.send_mail_to_ml)
-
- action = Action.new_by_name('RP', person=self.pr, comment="Proofreading")
- action.apply_on(state, action.send_mail_to_ml)
-
- action = Action.new_by_name('UNDO', person=self.pr, comment="Ooops! I don't want to do that. Sorry.")
- action.apply_on(state, action.send_mail_to_ml)
-
- actions_db = Action.objects.filter(state_db__id=state.id).exclude(name='WC').order_by('-id')
-
- # So the last action is UNDO
- self.assert_(isinstance(actions_db[0], ActionUNDO))
-
- # Here be dragons! A call to len() workaround the Django/MySQL bug!
- len(actions_db)
- self.assert_(isinstance(actions_db[0], ActionUNDO))
+# Temporary import to accomodate for Django < 1.6
+from .tests import *
diff --git a/vertimus/tests/tests.py b/vertimus/tests/tests.py
new file mode 100644
index 0000000..1cd81d3
--- /dev/null
+++ b/vertimus/tests/tests.py
@@ -0,0 +1,500 @@
+# -*- coding: utf-8 -*-
+#
+# Copyright (c) 2008 Stéphane Raimbault <stephane raimbault gmail com>
+#
+# This file is part of Damned Lies.
+#
+# Damned Lies is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2 of the License, or
+# (at your option) any later version.
+#
+# Damned Lies is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with Damned Lies; if not, write to the Free Software Foundation, Inc.,
+# 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+
+import os
+
+from django.conf import settings
+from django.core.files.base import File, ContentFile
+from django.core.files.uploadedfile import SimpleUploadedFile
+from django.core import mail
+from django.core.urlresolvers import reverse
+from django.http import QueryDict
+from django.utils.datastructures import MultiValueDict
+
+from teams.tests import TeamsAndRolesTests
+from stats.models import Module, Branch, Release, Category, Domain, Statistics
+from stats.tests import test_scratchdir
+from vertimus.models import *
+from vertimus.forms import ActionForm
+
+class VertimusTest(TeamsAndRolesTests):
+
+ def setUp(self):
+ super(VertimusTest, self).setUp()
+
+ self.m = Module.objects.create(name='gedit', description='GNOME Editor',
+ bugs_base="https://bugzilla.gnome.org/",
+ bugs_product='gedit', bugs_component='general',
+ vcs_type='svn', vcs_root="http://svn.gnome.org/svn",
+ vcs_web="http://svn.gnome.org/viewvc/gedit")
+
+ Branch.checkout_on_creation = False
+ self.b = Branch(name='gnome-2-24', module=self.m)
+ # Block the update of Statistics by the thread
+ self.b.save(update_statistics=False)
+
+ self.r = Release.objects.create(name='gnome-2-24', status='official',
+ description='GNOME 2.24 (stable)',
+ string_frozen=True)
+
+ self.c = Category.objects.create(release=self.r, branch=self.b, name='desktop')
+
+ self.d = Domain.objects.create(module=self.m, name='po',
+ description='UI translations',
+ dtype='ui', directory='po')
+ pot_stat = Statistics.objects.create(language=None, branch=self.b, domain=self.d)
+ self.files_to_clean = []
+
+ def tearDown(self):
+ for path in self.files_to_clean:
+ os.remove(path)
+
+ def test_state_none(self):
+ state = StateNone(branch=self.b, domain=self.d, language=self.l)
+
+ action_names = [a.name for a in state.get_available_actions(self.pn)]
+ self.assertEqual(action_names, ['WC'])
+
+ for p in (self.pt, self.pr):
+ action_names = [a.name for a in state.get_available_actions(p)]
+ self.assertEqual(action_names, ['RT', 'WC'])
+
+ for p in (self.pc, self.pcoo):
+ action_names = [a.name for a in state.get_available_actions(p)]
+ self.assertEqual(action_names, ['RT', 'WC', None, 'IC', 'AA'])
+
+ def test_state_translating(self):
+ state = StateTranslating(branch=self.b, domain=self.d, language=self.l, person=self.pt)
+
+ for p in (self.pn, self.pr):
+ action_names = [a.name for a in state.get_available_actions(p)]
+ self.assertEqual(action_names, ['WC'])
+
+ action_names = [a.name for a in state.get_available_actions(self.pc)]
+ self.assertEqual(action_names, ['WC', None, 'IC', 'AA'])
+
+ action_names = [a.name for a in state.get_available_actions(self.pcoo)]
+ self.assertEqual(action_names, ['WC', 'UNDO', None, 'IC', 'AA'])
+
+ # Same person
+ action_names = [a.name for a in state.get_available_actions(self.pt)]
+ self.assertEqual(action_names, ['UT', 'UNDO', 'WC'])
+
+ def test_state_translated(self):
+ state = StateTranslated(branch=self.b, domain=self.d, language=self.l, person=self.pt)
+
+ action_names = [a.name for a in state.get_available_actions(self.pn)]
+ self.assertEqual(action_names, ['WC'])
+
+ action_names = [a.name for a in state.get_available_actions(self.pt)]
+ self.assertEqual(action_names, ['RT', 'WC'])
+
+ action_names = [a.name for a in state.get_available_actions(self.pr)]
+ self.assertEqual(action_names, ['RP', 'TR', 'RT', 'WC'])
+
+ for p in (self.pc, self.pcoo):
+ action_names = [a.name for a in state.get_available_actions(p)]
+ self.assertEqual(action_names, ['RP', 'TR', 'RT', 'TC', 'WC', None, 'IC', 'AA'])
+
+ def test_state_proofreading(self):
+ state = StateProofreading(branch=self.b, domain=self.d, language=self.l, person=self.pr)
+
+ for p in (self.pn, self.pt):
+ action_names = [a.name for a in state.get_available_actions(p)]
+ self.assertEqual(action_names, ['WC'])
+
+ action_names = [a.name for a in state.get_available_actions(self.pc)]
+ self.assertEqual(action_names, ['WC', None, 'IC', 'AA'])
+
+ action_names = [a.name for a in state.get_available_actions(self.pcoo)]
+ self.assertEqual(action_names, ['WC', 'UNDO', None, 'IC', 'AA'])
+
+ # Same person and reviewer
+ action_names = [a.name for a in state.get_available_actions(self.pr)]
+ self.assertEqual(action_names, ['UP', 'TR', 'TC', 'UNDO', 'WC'])
+
+ def test_state_proofread(self):
+ state = StateProofread(branch=self.b, domain=self.d, language=self.l, person=self.pr)
+
+ for p in (self.pn, self.pt):
+ action_names = [a.name for a in state.get_available_actions(p)]
+ self.assertEqual(action_names, ['WC'])
+
+ action_names = [a.name for a in state.get_available_actions(self.pr)]
+ self.assertEqual(action_names, ['TC', 'RP', 'TR', 'WC'])
+
+ for p in (self.pc, self.pcoo):
+ action_names = [a.name for a in state.get_available_actions(p)]
+ self.assertEqual(action_names, ['TC', 'RP', 'TR', 'WC', None, 'IC', 'AA'])
+
+ def test_state_to_review(self):
+ state = StateToReview(branch=self.b, domain=self.d, language=self.l, person=self.pt)
+
+ action_names = [a.name for a in state.get_available_actions(self.pn)]
+ self.assertEqual(action_names, ['WC'])
+
+ for p in (self.pt, self.pr):
+ action_names = [a.name for a in state.get_available_actions(p)]
+ self.assertEqual(action_names, ['RT', 'WC'])
+
+ for p in (self.pc, self.pcoo):
+ action_names = [a.name for a in state.get_available_actions(p)]
+ self.assertEqual(action_names, ['RT', 'WC', None, 'IC', 'AA'])
+
+ def test_state_to_commit(self):
+ state = StateToCommit(branch=self.b, domain=self.d, language=self.l, person=self.pr)
+
+ for p in (self.pn, self.pt, self.pr):
+ action_names = [a.name for a in state.get_available_actions(p)]
+ self.assertEqual(action_names, ['WC'])
+
+ for p in (self.pc, self.pcoo):
+ action_names = [a.name for a in state.get_available_actions(p)]
+ self.assertEqual(action_names, ['RC', 'TR', 'WC', None, 'IC', 'AA'])
+
+ def test_state_committing(self):
+ state = StateCommitting(branch=self.b, domain=self.d, language=self.l, person=self.pc)
+
+ for p in (self.pn, self.pt, self.pr):
+ action_names = [a.name for a in state.get_available_actions(p)]
+ self.assertEqual(action_names, ['WC'])
+
+ action_names = [a.name for a in state.get_available_actions(self.pcoo)]
+ self.assertEqual(action_names, ['WC', 'UNDO', None, 'IC', 'AA'])
+
+ action_names = [a.name for a in state.get_available_actions(self.pc)]
+ self.assertEqual(action_names, ['IC', 'TR', 'UNDO', 'WC'])
+
+ def test_state_committed(self):
+ state = StateCommitted(branch=self.b, domain=self.d, language=self.l, person=self.pc)
+
+ for p in (self.pn, self.pt, self.pr):
+ action_names = [a.name for a in state.get_available_actions(p)]
+ self.assertEqual(action_names, ['WC'])
+
+ for p in (self.pc, self.pcoo):
+ action_names = [a.name for a in state.get_available_actions(p)]
+ self.assertEqual(action_names, ['AA', 'WC', None, 'IC', 'AA'])
+
+ def test_action_wc(self):
+ state = StateNone(branch=self.b, domain=self.d, language=self.l)
+ state.save()
+ prev_updated = state.updated
+
+ action = Action.new_by_name('WC', person=self.pt, comment="Hi!")
+ action.apply_on(state, action.send_mail_to_ml)
+ self.assertEqual(len(mail.outbox), 1)
+ self.assertEqual(mail.outbox[0].recipients(), [self.pt.email])
+ # Test that submitting a comment without text generates a validation error
+ form = ActionForm([ActionWC()], True, QueryDict('action=WC&comment='))
+ self.assertTrue("A comment is needed" in str(form.errors))
+ self.assertNotEqual(state.updated, prev_updated)
+
+ # Test send comment to mailing list
+ mail.outbox = []
+ action = Action.new_by_name('WC', person=self.pt, comment="Hi again!")
+ action.apply_on(state, True)
+ self.assertEqual(len(mail.outbox), 1)
+ self.assertEqual(mail.outbox[0].recipients(), [self.l.team.mailing_list])
+ self.assertIn(u"Hi again!", mail.outbox[0].body)
+
+ def test_action_rt(self):
+ state = StateNone(branch=self.b, domain=self.d, language=self.l)
+ state.save()
+
+ action = Action.new_by_name('RT', person=self.pt, comment="Reserved!")
+ action.apply_on(state, action.send_mail_to_ml)
+ self.assertTrue(isinstance(state, StateTranslating))
+
+ @test_scratchdir
+ def test_action_ut(self):
+ # Disabling the role
+ role = Role.objects.get(person=self.pt, team=self.l.team)
+ role.is_active = False
+ role.save()
+
+ state = StateTranslating(branch=self.b, domain=self.d, language=self.l, person=self.pt)
+ state.save()
+
+ test_file = open(os.path.join(os.path.dirname(os.path.abspath(__file__)), "valid_po.po"), 'r')
+
+ action = Action.new_by_name('UT', person=self.pt, comment="Done by translator.",
file=File(test_file))
+ action.apply_on(state, action.send_mail_to_ml)
+
+ self.assertEqual(action.file.url, '/media/upload/gedit-gnome-2-24-po-fr-%d.po' % state.id)
+ self.assertEqual(action.merged_file.url(), '/media/upload/gedit-gnome-2-24-po-fr-%d.merged.po' %
state.id)
+ # Merged file will not be really produced as no pot file exists on the file system
+ self.files_to_clean.append(action.file.path)
+
+ self.assertTrue(isinstance(state, StateTranslated))
+ # Mail sent to mailing list
+ self.assertEqual(len(mail.outbox), 1)
+ self.assertEqual(mail.outbox[0].recipients(), [self.l.team.mailing_list])
+ self.assertEqual(mail.outbox[0].subject, "gedit - gnome-2-24")
+
+ # Testing if the role was activated
+ role = Role.objects.get(person=self.pt, team=self.l.team)
+ self.assertTrue(role.is_active)
+
+ def test_action_rp(self):
+ state = StateTranslated(branch=self.b, domain=self.d, language=self.l)
+ state.save()
+
+ action = Action.new_by_name('RP', person=self.pr, comment="Reserved by a reviewer!")
+ action.apply_on(state, action.send_mail_to_ml)
+ self.assertTrue(isinstance(state, StateProofreading))
+
+ def test_action_up(self):
+ state = StateProofreading(branch=self.b, domain=self.d, language=self.l, person=self.pr)
+ state.save()
+
+ test_file = ContentFile('test content')
+ test_file.name = 'mytestfile.po'
+
+ action = Action.new_by_name('UP', person=self.pr, comment="Done.", file=test_file)
+ action.apply_on(state, action.send_mail_to_ml)
+ self.files_to_clean.append(action.file.path)
+ self.assertTrue(isinstance(state, StateProofread))
+
+ def test_action_tc(self):
+ state = StateProofread(branch=self.b, domain=self.d, language=self.l)
+ state.save()
+
+ action = Action.new_by_name('TC', person=self.pr, comment="Ready!")
+ action.apply_on(state, action.send_mail_to_ml)
+ self.assertTrue(isinstance(state, StateToCommit))
+
+ def test_action_rc(self):
+ state = StateToCommit(branch=self.b, domain=self.d, language=self.l)
+ state.save()
+
+ action = Action.new_by_name('RC', person=self.pc, comment="This work is mine!")
+ action.apply_on(state, action.send_mail_to_ml)
+ self.assertTrue(isinstance(state, StateCommitting))
+
+ def test_action_ic(self):
+ state = StateProofreading(branch=self.b, domain=self.d, language=self.l, person=self.pr)
+ state.save()
+
+ # Create a new file
+ test_file = ContentFile('test content')
+ test_file.name = 'mytestfile.po'
+
+ action = Action.new_by_name('UP', person=self.pr, comment="Done.", file=test_file)
+ action.apply_on(state, action.send_mail_to_ml)
+ self.assertEqual(len(mail.outbox), 1) # Mail sent to mailing list
+ mail.outbox = []
+
+ file_path = os.path.join(settings.MEDIA_ROOT, action.file.name)
+ self.assertTrue(os.access(file_path, os.W_OK))
+
+ action = Action.new_by_name('TC', person=self.pc, comment="To commit.")
+ action.apply_on(state, action.send_mail_to_ml)
+ self.assertEqual(len(mail.outbox), 1) # Mail sent to committers
+ mail.outbox = []
+
+ action = Action.new_by_name('RC', person=self.pc, comment="Reserved commit.")
+ action.apply_on(state, action.send_mail_to_ml)
+
+ action = Action.new_by_name('IC', person=self.pc, comment="Committed.")
+ action.apply_on(state, action.send_mail_to_ml)
+ # Mail sent to mailing list
+ self.assertEqual(len(mail.outbox), 1)
+ self.assertEqual(mail.outbox[0].recipients(), [self.l.team.mailing_list])
+ # Team is French (but translations may not be compiled/up-to-date)
+ self.assertTrue(u'Commité' in mail.outbox[0].body or "Committed" in mail.outbox[0].body)
+
+ self.assertTrue(isinstance(state, StateNone))
+ self.assertTrue(not os.access(file_path, os.F_OK), "%s not deleted" % file_path)
+
+ # Remove test file
+ action_archived = ActionArchived.objects.get(comment="Done.")
+ filename_archived = os.path.join(settings.MEDIA_ROOT, action_archived.file.name)
+ action_archived.delete()
+ self.assertTrue(not os.access(filename_archived, os.F_OK), "%s not deleted" % filename_archived)
+
+ def test_action_tr(self):
+ state = StateTranslated(branch=self.b, domain=self.d, language=self.l)
+ state.save()
+
+ action = Action.new_by_name('TR', person=self.pc, comment="Bad work :-/")
+ action.apply_on(state, action.send_mail_to_ml)
+ self.assertTrue(isinstance(state, StateToReview))
+
+ def test_action_aa(self):
+ state = StateCommitted(branch=self.b, domain=self.d, language=self.l, person=self.pr)
+ state.save()
+
+ action = Action.new_by_name('AA', person=self.pc, comment="I don't want to disappear :)")
+ action.apply_on(state, action.send_mail_to_ml)
+
+ state = State.objects.get(branch=self.b, domain=self.d, language=self.l)
+ self.assertTrue(isinstance(state, StateNone))
+ self.assertEqual(state.action_set.count(), 0)
+
+ def test_action_undo(self):
+ state = StateNone(branch=self.b, domain=self.d, language=self.l)
+ state.save()
+
+ action = Action.new_by_name('RT', person=self.pt, comment="Reserved!")
+ action.apply_on(state, action.send_mail_to_ml)
+
+ action = Action.new_by_name('UNDO', person=self.pt, comment="Ooops! I don't want to do that. Sorry.")
+ action.apply_on(state, action.send_mail_to_ml)
+
+ self.assertEqual(state.name, 'None')
+
+ action = Action.new_by_name('RT', person=self.pt, comment="Translating")
+ action.apply_on(state, action.send_mail_to_ml)
+
+ action = Action.new_by_name('UT', person=self.pt, comment="Translated")
+ action.apply_on(state, action.send_mail_to_ml)
+
+ action = Action.new_by_name('RT', person=self.pt, comment="Reserved!")
+ action.apply_on(state, action.send_mail_to_ml)
+
+ action = Action.new_by_name('UNDO', person=self.pt, comment="Ooops! I don't want to do that. Sorry.")
+ action.apply_on(state, action.send_mail_to_ml)
+
+ self.assertEqual(state.name, 'Translated')
+
+ action = Action.new_by_name('RT', person=self.pt, comment="Translating 1")
+ action.apply_on(state, action.send_mail_to_ml)
+
+ action = Action.new_by_name('UNDO', person=self.pt, comment="Undo 1")
+ action.apply_on(state, action.send_mail_to_ml)
+
+ action = Action.new_by_name('RT', person=self.pt, comment="Translating 2")
+ action.apply_on(state, action.send_mail_to_ml)
+
+ action = Action.new_by_name('UNDO', person=self.pt, comment="Undo 2")
+ action.apply_on(state, action.send_mail_to_ml)
+
+ self.assertEqual(state.name, 'Translated')
+
+ def test_delete(self):
+ """ Test that a whole module tree can be properly deleted """
+ state = StateNone(branch=self.b, domain=self.d, language=self.l)
+ state.save()
+
+ action = Action.new_by_name('WC', person=self.pt, comment="Hi!")
+ action.apply_on(state, action.send_mail_to_ml)
+
+ self.m.delete()
+ self.assertEqual(Action.objects.all().count(), 0)
+
+ def test_delete_domain(self):
+ state = StateTranslating.objects.create(branch=self.b, domain=self.d, language=self.l,
person=self.pt)
+ self.d.delete()
+ self.assertEqual(State.objects.all().count(), 0)
+
+ def test_delete_statistics(self):
+ """ Test clean_dangling_states receiver """
+ po_stat = Statistics.objects.create(branch=self.b, domain=self.d, language=self.l)
+ state = StateTranslating.objects.create(branch=self.b, domain=self.d, language=self.l,
person=self.pt)
+ po_stat.delete()
+ self.assertEqual(State.objects.all().count(), 0)
+
+ def test_vertimus_view(self):
+ url = reverse('vertimus_by_ids', args=[self.b.id, self.d.id, self.l.id])
+ response = self.client.get(url)
+ self.assertNotContains(response, '<option value="WC">')
+
+ self.client.login(username=self.pn.username, password='password')
+ response = self.client.get(url)
+ self.assertContains(response, '<option value="WC">')
+
+ def test_uploaded_file_validation(self):
+ # Test a non valid po file
+ post_content = QueryDict('action=WC&comment=Test1')
+ post_file = MultiValueDict({'file': [SimpleUploadedFile('filename.po', 'Not valid po file
content')]})
+ form = ActionForm([ActionWC()], True, post_content, post_file)
+
+ self.assertTrue('file' in form.errors)
+
+ # Test a valid po file
+ f = open(os.path.join(os.path.dirname(os.path.abspath(__file__)), "valid_po.po"), 'r')
+ post_file = MultiValueDict({'file': [File(f)]})
+ form = ActionForm([ActionWC()], True, post_content, post_file)
+ self.assertTrue(form.is_valid())
+
+ # Test form without file
+ form = ActionForm([ActionWC()], True, post_content)
+ self.assertTrue(form.is_valid())
+
+ def test_feeds(self):
+ state = StateNone(branch=self.b, domain=self.d, language=self.l)
+ state.save()
+
+ action = Action.new_by_name('RT', person=self.pt, comment="Translating")
+ action.apply_on(state, action.send_mail_to_ml)
+
+ response = self.client.get(reverse('lang_feed', args=[self.l.locale]))
+ self.assertContains(response,
+ """<rss xmlns:atom="http://www.w3.org/2005/Atom" version="2.0">""")
+ self.assertContains(response,
+ """<title>po (gedit/User Interface) - gedit (gnome-2-24) - Reserve for translation\n</title>""")
+ self.assertContains(response,
+ """<guid>http://example.com/vertimus/gedit/gnome-2-24/po/fr#%d</guid>""" % action.id)
+
+ response = self.client.get(reverse('team_feed', args=[self.l.team.name]))
+ self.assertContains(response,
+ """<title>po (gedit/User Interface) - gedit (gnome-2-24) - Reserve for translation\n</title>""")
+
+ def test_activity_summary(self):
+ state = StateTranslating.objects.create(
+ branch=self.b, domain=self.d,
+ language=self.l,
+ person=self.pt)
+
+ response = self.client.get(reverse("activity_by_language", args=[self.l.locale]))
+ self.assertContains(response, self.m.description)
+
+ def test_mysql(self):
+ # Copied from test_action_undo() with minor changes
+ state = StateNone(branch=self.b, domain=self.d, language=self.l)
+ state.save()
+
+ action = Action.new_by_name('RT', person=self.pr, comment="Reserved!")
+ action.apply_on(state, action.send_mail_to_ml)
+
+ action = Action.new_by_name('UNDO', person=self.pr, comment="Ooops! I don't want to do that. Sorry.")
+ action.apply_on(state, action.send_mail_to_ml)
+
+ action = Action.new_by_name('RT', person=self.pr, comment="Translating")
+ action.apply_on(state, action.send_mail_to_ml)
+
+ action = Action.new_by_name('UT', person=self.pr, comment="Translated")
+ action.apply_on(state, action.send_mail_to_ml)
+
+ action = Action.new_by_name('RP', person=self.pr, comment="Proofreading")
+ action.apply_on(state, action.send_mail_to_ml)
+
+ action = Action.new_by_name('UNDO', person=self.pr, comment="Ooops! I don't want to do that. Sorry.")
+ action.apply_on(state, action.send_mail_to_ml)
+
+ actions_db = Action.objects.filter(state_db__id=state.id).exclude(name='WC').order_by('-id')
+
+ # So the last action is UNDO
+ self.assert_(isinstance(actions_db[0], ActionUNDO))
+
+ # Here be dragons! A call to len() workaround the Django/MySQL bug!
+ len(actions_db)
+ self.assert_(isinstance(actions_db[0], ActionUNDO))
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]