changeset 465:fc9cdf513432

CheckTranslation.py: Added several features to action. * List of pages in translated language not in i18n.strings['all_pges'] * Warnings about missing or wrong special comments * Information about outdated translations based on special comments
author Eugene Syromyatnikov <evgsyr@gmail.com>
date Mon, 21 Dec 2009 12:58:23 +0300
parents 328f45d3937e
children b7757d0badd7
files data/plugin/action/CheckTranslation.py
diffstat 1 files changed, 113 insertions(+), 2 deletions(-) [+]
line wrap: on
line diff
--- a/data/plugin/action/CheckTranslation.py	Wed Dec 16 19:39:54 2009 +0100
+++ b/data/plugin/action/CheckTranslation.py	Mon Dec 21 12:58:23 2009 +0300
@@ -6,11 +6,13 @@
     if the users language is anything else than en
 
     @copyright: 2009 MoinMoin:ReimarBauer,
-                2009 MoinMoin:ThomasWaldmann
+                2009 MoinMoin:ThomasWaldmann,
+                2009 MoinMoin:EugeneSyromyatnikov
     @license: GNU GPL, see COPYING for details.
 """
 
-from MoinMoin import i18n
+import re, time
+from MoinMoin import i18n, search
 from MoinMoin.i18n import strings
 i18n.strings = strings
 
@@ -25,6 +27,23 @@
 </style>
 """
 
+translation_warnings = {
+    'missing_master_page_meta': True,
+    'wrong_master_page': True,
+    'missing_master_date_or_rev_meta': True,
+    'outdated_master_rev': True,
+    'outdated_master_date': True,
+    'not_in_i18n_strings_pages': True,
+}
+
+special_comment_re = r'(?im)^##master-%(meta)s[ :][ \t]*(?P<%(meta)s>[^\n]*)[ \t]*$'
+
+date_format_guesses = [
+    '%Y-%m-%dT%H:%M:%SZ',
+    '%Y-%m-%d %H:%M:%S',
+    '%Y-%m-%d',
+]
+
 def execute(pagename, request):
     _ = request.getText
 
@@ -89,8 +108,99 @@
                 info += " %(editor)s %(time)s" % last_edit
             trans_status.append(info)
 
+            if trans_page.exists():
+                if trans_page.pi['language'] != lang:
+                    trans_status.append(_('/!\\ Translated page language ("%(page_lang)s") is not "%(lang)s"', wiki=True) % {
+                        'lang': request.formatter.text(lang),
+                        'page_lang': request.formatter.text(trans_page.pi['language']),
+                    })
+
+                master_meta_names = ['page', 'date', 'rev']
+                master_metas = {}
+
+                for meta in master_meta_names:
+                    m = re.search(special_comment_re % {'meta': meta}, trans_page.body)
+                    if m:
+                        master_metas[meta] = m.group(meta)
+
+                if 'page' in master_metas:
+                    if master_metas['page'] != orig_page_name and translation_warnings['wrong_master_page']:
+                        trans_status.append(_(u'/!\\ Translated page has ##master-page special comment with value other than "%(orig_page)s" (current value is "%(master_page)s").', wiki=True) % {
+                            'orig_page': request.formatter.text(orig_page_name),
+                            'master_page': request.formatter.text(master_metas['page']),
+                        })
+                else:
+                    if translation_warnings['missing_master_page_meta']:
+                        trans_status.append(_('/!\\ Translated page has no ##master-page special comment. Please, add line "##master_page:%s" somewhere at beginning of the translated page.', wiki=True) % request.formatter.text(orig_page_name))
+
+                if 'date' not in master_metas and 'rev' not in master_metas and translation_warnings['missing_master_date_or_rev_meta']:
+                    trans_status.append(_('/!\\ Translated page has neither of ##master-date or ##master-rev special comments. Please, add at least one.', wiki=True))
+
+                if 'rev' in master_metas:
+                    orig_page_rev = orig_page.get_rev()[1]
+                    master_rev = master_metas['rev']
+
+                    try:
+                        rev_num = int(master_rev)
+                    except ValueError:
+                        trans_status.append(_('/!\\ ##master_date special comment can\'t be parsed. Value of special comment: "%s". Please use correct revision number.', wiki=True) % request.formatter.text(master_rev))
+                    else:
+                        if rev_num < orig_page_rev and translation_warnings['outdated_master_rev']:
+                            trans_status.append(_('(!) Translated page is outdated: it is based on revision %(trans_rev)s, but original page has revision %(orig_rev)s.', wiki=True) % {
+                                'orig_rev': request.formatter.text(orig_page_rev),
+                                'trans_rev': request.formatter.text(master_rev),
+                            })
+
+                if 'date' in master_metas and translation_warnings['outdated_master_date']:
+                    master_date = None
+                    for guess in date_format_guesses:
+                        try:
+                            master_date = time.strptime(master_metas['date'], guess)
+                            break
+                        except ValueError:
+                            pass
+
+                    if not master_date:
+                        trans_status.append(_('/!\\ ##master_date special comment can\'t be parsed. Value of special comment: "%s". Please use ISO format (yyyy-mm-dd HH:MM:SS) or @DATE@/@TIME@ variables.', wiki=True) % request.formatter.text(master_metas['date']))
+                    else:
+                        orig_date = time.gmtime(orig_page.mtime_usecs() / 1000000.0)
+                        orig_date_s = time.strftime('%Y-%m-%d %H:%M:%S', orig_date)
+
+                        if master_date < orig_date:
+                            trans_status.append(_('(!) Translated page is outdated: it has master date %(master_date)s, but original page last edited at %(orig_date)s.', wiki=True) % {
+                                'orig_date': request.formatter.text(orig_date_s),
+                                'master_date': request.formatter.text(time.strftime('%Y-%m-%d %H:%M:%S', master_date)),
+                            })
+
         data.addRow(("<br>".join(orig_status), "<br>".join(trans_status)))
 
+
+    search_results = set([p.page_name for p in search.searchPages(request, 'lang:%s' % lang,
+                                     titlesearch=1, sort='page_name').hits])
+    search_results = list(search_results - set([trans(p) for p in i18n.strings.all_pages]))
+    search_results.sort()
+
+    not_listed = []
+
+    if search_results and translation_warnings['not_in_i18n_strings_pages']:
+        not_listed += [
+                       request.formatter.heading(1, 3),
+                       request.formatter.text(_('Pages with language "%s" not listed above:') % lang),
+                       request.formatter.heading(0, 3),
+                      ]
+
+        not_listed.append(request.formatter.number_list(1))
+        for page in search_results:
+            not_listed += [
+                           request.formatter.listitem(1),
+                           request.formatter.pagelink(1, page),
+                           request.formatter.text(page),
+                           request.formatter.pagelink(0),
+                           request.formatter.listitem(0),
+                          ]
+        not_listed.append(request.formatter.number_list(0))
+
+
     table = DataBrowserWidget(request)
     table.setData(data)
     page_table = ''.join(table.format(method='GET'))
@@ -128,6 +238,7 @@
     request.write(lang_selector)
     request.write(pageset_selector)
     request.write(page_table)
+    request.write(''.join(not_listed))
     request.write(request.formatter.endContent())
     request.theme.send_footer(pagename)
     request.theme.send_closing_html()