I've cherry picked these two commits from David and fixed a small conflict while applying the second one. The tests also discover some issues. Will open a bug for them.
Please comment on the PR state? Do you want me to squash the two commits together ?
From: David Shea dshea@redhat.com
--- tests/glade/icons/check_icons.py | 72 ++++++++++++++++++++++++++++++++++++++++ tests/lib/iconcheck.py | 41 +++++++++++++++++++++++ 2 files changed, 113 insertions(+) create mode 100755 tests/glade/icons/check_icons.py create mode 100644 tests/lib/iconcheck.py
diff --git a/tests/glade/icons/check_icons.py b/tests/glade/icons/check_icons.py new file mode 100755 index 0000000..e338ea2 --- /dev/null +++ b/tests/glade/icons/check_icons.py @@ -0,0 +1,72 @@ +#!/usr/bin/python +# +# Copyright (C) 2014 Red Hat, Inc. +# +# This program is free software; you can redistribute it and/or modify +# it under the terms of the GNU Lesser General Public License as published +# by the Free Software Foundation; either version 2.1 of the License, or +# (at your option) any later version. +# +# This program 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 Lesser General Public License for more details. +# +# You should have received a copy of the GNU Lesser General Public License +# along with this program. If not, see http://www.gnu.org/licenses/. +# +# Author: David Shea dshea@redhat.com +# +""" +Check that all icons referenced from glade files are valid in the gnome icon theme. +""" + +import argparse +import sys + +try: + from lxml import etree +except ImportError: + print("You need to install the python-lxml package to use check_pw_visibility.py") + sys.exit(1) + +from iconcheck import icon_exists + +def check_glade_file(glade_file_path): + glade_success = True + with open(glade_file_path) as glade_file: + # Parse the XML + glade_tree = etree.parse(glade_file) + + # Stock image names are deprecated + for element in glade_tree.xpath("//property[@name='stock' or @name='stock_id']"): + glade_success = False + print("Deprecated stock icon found at %s:%d" % (glade_file_path, element.sourceline)) + + # Check whether named icons exist + for element in glade_tree.xpath("//property[@name='icon_name']"): + if not icon_exists(element.text): + glade_success = False + print("Invalid icon name %s found at %s:%d" % (element.text, glade_file_path, element.sourceline)) + + return glade_success + +if __name__ == "__main__": + parser = argparse.ArgumentParser("Check that password entries have visibility set to False") + + # Ignore translation arguments + parser.add_argument("-t", "--translate", action='store_true', + help=argparse.SUPPRESS) + parser.add_argument("-p", "--podir", action='store', type=str, + metavar='PODIR', help=argparse.SUPPRESS, default='./po') + + parser.add_argument("glade_files", nargs="+", metavar="GLADE-FILE", + help='The glade file to check') + args = parser.parse_args(args=sys.argv[1:]) + + success = True + for file_path in args.glade_files: + if not check_glade_file(file_path): + success = False + + sys.exit(0 if success else 1) diff --git a/tests/lib/iconcheck.py b/tests/lib/iconcheck.py new file mode 100644 index 0000000..1e1118e --- /dev/null +++ b/tests/lib/iconcheck.py @@ -0,0 +1,41 @@ +# +# iconcheck.py: Gtk icon testing +# +# Copyright (C) 2014 Red Hat, Inc. +# +# This program is free software; you can redistribute it and/or modify +# it under the terms of the GNU Lesser General Public License as published +# by the Free Software Foundation; either version 2.1 of the License, or +# (at your option) any later version. +# +# This program 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 Lesser General Public License for more details. +# +# You should have received a copy of the GNU Lesser General Public License +# along with this program. If not, see http://www.gnu.org/licenses/. +# +# Author: David Shea dshea@redhat.com + +import os + +ICON_PATH = "/usr/share/icons/gnome" +ICON_EXTS = ("png", "jpg", "svg") + +# This method depends on gnome-icon-theme being installed. gnome-icon-theme-legacy +# may be installed, but the icons in it will not be considered. +def icon_exists(icon_name): + for dirpath, _dirs, files in os.walk(ICON_PATH): + for icon in (icon_name + "." + ext for ext in ICON_EXTS): + if icon in files: + icon_path = os.path.join(dirpath, icon) + + # If the file is a symbolic link, it's a legacy icon; reject it + if os.path.islink(icon_path): + return False + else: + return True + + # Nothing found + return False
From: David Shea dshea@redhat.com
This one might be a little confusing. Having translatable strings in glade works fine for the most part, but having translatable strings that contain format substitution information in glade is problematic. The format substitution is by necessity outside of glade, which causes two related problems. First, separating the string constant from the format operation looks confusing and needs information from another file to know the order or names of the arguments:
# I have no idea what is going on label.set_text(label.get_text() % ("huh", "ok"))
and second, the translations of the format strings can't be checked. Normally if a translator messes up one of our format strings, msgfmt will raise an error during the build. The strings in glade files, however, are supposed to be language-independent, so they don't get the c-format or python-format attributes that the strings in C and Python source files do, and the error happens at runtime.
Format strings without the translatable attribute are fine, since they're handy to use as placeholders. --- tests/glade/format_string/check_format_string.py | 78 ++++++++++++++++++++++++ 1 file changed, 78 insertions(+) create mode 100755 tests/glade/format_string/check_format_string.py
diff --git a/tests/glade/format_string/check_format_string.py b/tests/glade/format_string/check_format_string.py new file mode 100755 index 0000000..81191e1 --- /dev/null +++ b/tests/glade/format_string/check_format_string.py @@ -0,0 +1,78 @@ +#!/usr/bin/python +# +# Copyright (C) 2014 Red Hat, Inc. +# +# This program is free software; you can redistribute it and/or modify +# it under the terms of the GNU Lesser General Public License as published +# by the Free Software Foundation; either version 2.1 of the License, or +# (at your option) any later version. +# +# This program 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 Lesser General Public License for more details. +# +# You should have received a copy of the GNU Lesser General Public License +# along with this program. If not, see http://www.gnu.org/licenses/. +# +# Author: David Shea dshea@redhat.com +# + +""" +Python script to ensure that translatable format strings are not present +in Glade files. + +Since format substitution is language-dependent, gettext is unable to check +the validity of format string translations for strings within glade. Instead, +the format string constant, the translation substitution, and the format +substitution should all happen outside of glade. Untranslated placeholder +strings are allowable within glade. +""" + +import sys +import argparse +import re + +try: + from lxml import etree +except ImportError: + print("You need to install the python-lxml package to use check_format_string.py") + sys.exit(1) + +def check_glade_file(glade_file_path): + global success + + with open(glade_file_path) as glade_file: + # Parse the XML + glade_tree = etree.parse(glade_file) + + # Check any property with translatable="yes" + for translatable in glade_tree.xpath(".//*[@translatable='yes']"): + # Look for % followed by an open parenthesis (indicating %(name) + # style substitution), one of the python format conversion flags + # (#0- +hlL), or one of the python conversion types + # (diouxXeEfFgGcrs) + if re.search(r'%[-(#0 +hlLdiouxXeEfFgGcrs]', translatable.text): + print("Translatable format string found in glade at %s:%d" % \ + (glade_file_path, translatable.sourceline)) + success = False + +if __name__ == "__main__": + success = True + parser = argparse.ArgumentParser("Check that password entries have visibility set to False") + + # Ignore translation arguments + parser.add_argument("-t", "--translate", action='store_true', + help=argparse.SUPPRESS) + parser.add_argument("-p", "--podir", action='store', type=str, + metavar='PODIR', help=argparse.SUPPRESS, default='./po') + + parser.add_argument("glade_files", nargs="+", metavar="GLADE-FILE", + help='The glade file to check') + args = parser.parse_args(args=sys.argv[1:]) + + success = True + for file_path in args.glade_files: + check_glade_file(file_path) + + sys.exit(0 if success else 1)
I think we can safely pick this one as well: https://github.com/rhinstaller/anaconda/pull/32
Closed.
This was auto-closed by github when I rebased rhel7-branch. Reopening so I can do something with it.
Reopened.
Closed.
This got pulled in by the rebase, so it should be good.
anaconda-patches@lists.fedorahosted.org