John Vandenberg has uploaded a new change for review. https://gerrit.wikimedia.org/r/151617
Change subject: Add Namespace class ...................................................................... Add Namespace class Replaces the current implicit data structure of site._namespaces with a class with variables with names that explain their contents. Change-Id: I0cce21e6161031861c0056dc5498f47bc26e1cc8 --- M pywikibot/site.py M tests/dry_api_tests.py M tests/dry_site_tests.py M tests/site_tests.py 4 files changed, 95 insertions(+), 48 deletions(-) git pull ssh://gerrit.wikimedia.org:29418/pywikibot/core refs/changes/17/151617/1 diff --git a/pywikibot/site.py b/pywikibot/site.py index c26e8cd..3d9cf70 100644 --- a/pywikibot/site.py +++ b/pywikibot/site.py @@ -20,6 +20,7 @@ import re import sys from distutils.version import LooseVersion as LV +from collections import Iterable import threading import time import urllib @@ -121,6 +122,51 @@ return _families[fam] +class Namespace(Iterable): + + """ Namespace site data object. + + This is backwards compatible with the structure of entries + in site._namespaces which were a list of + [customised namespace?, + canonical namespace name, + namespace alias*] + """ + + def __init__(self, canonical_name, custom_name=None, aliases=None): + """Constructor.""" + self.canonical_name = canonical_name + self.custom_name = custom_name + if aliases is None: + self.aliases = list() + else: + self.aliases = aliases + + def __len__(self): + """Obtain length of the iterable.""" + if self.custom_name: + return len(self.aliases) + 2 + else: + return len(self.aliases) + 1 + + def __iter__(self): + """Obtain length of the iterable.""" + return iter([self.canonical_name, self.custom_name] + self.aliases) + + def __getitem__(self, index): + """Obtain an item from the iterable.""" + if self.custom_name: + if index == 0: + return self.custom_name + else: + index -= 1 + + if index == 0: + return self.canonical_name + else: + return self.aliases[index - 2] + + class BaseSite(object): """Site methods that are independent of the communication interface.""" @@ -144,6 +190,35 @@ self.__family = Family(fam, fatal=False) else: self.__family = fam + + self._namespaces = { + # These are the MediaWiki built-in names, which always work. + # Localized names are loaded later upon accessing the wiki. + # Namespace prefixes are always case-insensitive, but the + # canonical forms are capitalized + -2: [u"Media"], + -1: [u"Special"], + 0: [u""], + 1: [u"Talk"], + 2: [u"User"], + 3: [u"User talk"], + 4: [u"Project"], + 5: [u"Project talk"], + 6: [u"Image"], + 7: [u"Image talk"], + 8: [u"MediaWiki"], + 9: [u"MediaWiki talk"], + 10: [u"Template"], + 11: [u"Template talk"], + 12: [u"Help"], + 13: [u"Help talk"], + 14: [u"Category"], + 15: [u"Category talk"], + } + # .version() depends on __family + if LV(self.version()) >= LV("1.14"): + self._namespaces[6] = [u"File"] + self._namespaces[7] = [u"File talk"] self.obsolete = False # if we got an outdated language code, use the new one instead. @@ -633,33 +708,6 @@ def __init__(self, code, fam=None, user=None, sysop=None): """ Constructor. """ BaseSite.__init__(self, code, fam, user, sysop) - self._namespaces = { - # These are the MediaWiki built-in names, which always work. - # Localized names are loaded later upon accessing the wiki. - # Namespace prefixes are always case-insensitive, but the - # canonical forms are capitalized - -2: [u"Media"], - -1: [u"Special"], - 0: [u""], - 1: [u"Talk"], - 2: [u"User"], - 3: [u"User talk"], - 4: [u"Project"], - 5: [u"Project talk"], - 6: [u"Image"], - 7: [u"Image talk"], - 8: [u"MediaWiki"], - 9: [u"MediaWiki talk"], - 10: [u"Template"], - 11: [u"Template talk"], - 12: [u"Help"], - 13: [u"Help talk"], - 14: [u"Category"], - 15: [u"Category talk"], - } - if LV(self.version()) >= LV("1.14"): - self._namespaces[6] = [u"File"] - self._namespaces[7] = [u"File talk"] self._msgcache = {} self._loginstatus = LoginStatus.NOT_ATTEMPTED return @@ -1214,31 +1262,25 @@ self._siteinfo = sidata['general'] nsdata = sidata['namespaces'] + aliasdata = None + if 'namespacealiases' in sidata: + aliasdata = sidata['namespacealiases'] + for nskey in nsdata: ns = int(nskey) - # this is the preferred form so it goes at front of list - self._namespaces.setdefault(ns, []).insert(0, nsdata[nskey]["*"]) - - if LV(self.version()) >= LV("1.14"): - # nsdata["0"] has no canonical key. - # canonical ns -2 to 15 are hard coded in self._namespaces - # do not get them from API result to avoid canonical duplicates - if -2 <= ns <= 15: - continue - if 'canonical' not in nsdata[nskey]: - pywikibot.warning( - u'namespace %s without a canonical name. Misconfigured?' - % self._namespaces[ns][0]) - continue - self._namespaces.setdefault(ns, []).append(nsdata[nskey]["canonical"]) + if ns == 0: + canonical = '' + else: + assert('canonical' in nsdata[nskey]) + canonical = nsdata[nskey]['canonical'] + namespace = Namespace(canonical, nsdata[nskey]["*"]) + self._namespaces[ns] = namespace if 'namespacealiases' in sidata: aliasdata = sidata['namespacealiases'] for item in aliasdata: - if item["*"] in self._namespaces[int(item['id'])]: - continue - # this is a less preferred form so it goes at the end - self._namespaces[int(item['id'])].append(item["*"]) + id = int(item['id']) + self._namespaces[id].aliases.append(item["*"]) if 'extensions' in sidata: self._extensions = sidata['extensions'] diff --git a/tests/dry_api_tests.py b/tests/dry_api_tests.py index 1714b59..af05a86 100644 --- a/tests/dry_api_tests.py +++ b/tests/dry_api_tests.py @@ -68,6 +68,9 @@ self._user = 'anon' pywikibot.site.BaseSite.__init__(self, 'mock', MockFamily()) + def version(self): + return '1.13' # pre 1.14 + def languages(self): return ['mock'] diff --git a/tests/dry_site_tests.py b/tests/dry_site_tests.py index 573c89e..c67e87f 100644 --- a/tests/dry_site_tests.py +++ b/tests/dry_site_tests.py @@ -53,6 +53,7 @@ self._logged_in_as = None self.obsolete = False super(TestMustBe, self).setUp() + self.version = lambda: '1.13' # pre 1.14 def login(self, sysop): # mock call diff --git a/tests/site_tests.py b/tests/site_tests.py index 4550618..9a90848 100644 --- a/tests/site_tests.py +++ b/tests/site_tests.py @@ -11,6 +11,7 @@ from distutils.version import LooseVersion as LV +from collections import Iterable import pywikibot from tests.utils import PywikibotTestCase, unittest @@ -115,14 +116,14 @@ self.assertType(mysite.ns_normalize("project"), basestring) self.assertTrue(all(isinstance(key, int) for key in ns)) - self.assertTrue(all(isinstance(val, list) + self.assertTrue(all(isinstance(val, Iterable) for val in ns.values())) self.assertTrue(all(isinstance(name, basestring) for val in ns.values() for name in val)) self.assertTrue(all(isinstance(mysite.namespace(key), basestring) for key in ns)) - self.assertTrue(all(isinstance(mysite.namespace(key, True), list) + self.assertTrue(all(isinstance(mysite.namespace(key, True), Iterable) for key in ns)) self.assertTrue(all(isinstance(item, basestring) for key in ns -- To view, visit https://gerrit.wikimedia.org/r/151617 To unsubscribe, visit https://gerrit.wikimedia.org/r/settings Gerrit-MessageType: newchange Gerrit-Change-Id: I0cce21e6161031861c0056dc5498f47bc26e1cc8 Gerrit-PatchSet: 1 Gerrit-Project: pywikibot/core Gerrit-Branch: master Gerrit-Owner: John Vandenberg <jay...@gmail.com> _______________________________________________ MediaWiki-commits mailing list MediaWiki-commits@lists.wikimedia.org https://lists.wikimedia.org/mailman/listinfo/mediawiki-commits