Source code for scripts.maintenance.addwikis
#!/usr/bin/env python3
"""Script that adds new wikis to the codes set in Wikimedia family files.
Usage:
python pwb.py addwikis [-family:<fam>] {<wiki>} {-family:<fam> {<wiki>}}
Example:
:code:`python pwb.py addwikis foo -family:wikisource bar baz`
adds code ``foo`` to the default (wikipedia) family, and codes ``bar``
and ``baz`` to wikisource.
.. versionadded:: 9.2
.. versionchanged:: 10.4
The options ``-h``, ``-help`` and ``--help`` display the help message.
.. deprecated:: 10.4
The ``help`` option
.. versionchanged:: 11.0
Multiple families can be given with one run.
"""
#
# (C) Pywikibot team, 2024-2025
#
# Distributed under the terms of the MIT license.
#
from __future__ import annotations
import re
import sys
from collections import defaultdict
from pathlib import Path
import pywikibot
from pywikibot.exceptions import ArgumentDeprecationWarning
from pywikibot.family import Family
from pywikibot.tools import issue_deprecation_warning
# supported families by this script
families_list = [
'wikibooks',
'wikinews',
'wikipedia',
'wikiquote',
'wikisource',
'wikiversity',
'wikivoyage',
'wiktionary',
]
[docs]
def update_family(family: str, wikis: set) -> None:
"""Update codes set in family file."""
joined_wikis = "', '".join(wikis)
pywikibot.info(f"Adding '{joined_wikis}' to {family} family...\n")
original = Family.load(family).codes
new_codes = set()
for wiki in list(wikis):
if wiki in original:
pywikibot.warning(
f'{wiki!r} is already in Family.codes; ignoring.')
else:
new_codes.add(wiki)
if not new_codes:
pywikibot.info('No wikis to add.')
return
# combine new codes set
new = sorted(original | new_codes)
pywikibot.info("The lists don't match, the new list is:\n")
text = ' codes = {\n'
line = ' ' * 7
for code in new:
if len(line) + len(code) >= 76:
text += line + '\n'
line = ' ' * 7
line += f" '{code}',"
text += line + '\n'
text += ' }'
pywikibot.info(text)
# update codes
filepath = Path(f'pywikibot/families/{family}_family.py')
family_text = filepath.read_text(encoding='utf8')
family_text = re.sub(r'(?ms)^ {4}codes = \{.+?\}',
text, family_text, count=1)
filepath.write_text(family_text, encoding='utf8')
[docs]
def main(*args: str) -> None:
"""Script entry point to handle args."""
if not args:
args = sys.argv[1:]
sys.argv = [sys.argv[0]]
current_family = 'wikipedia'
wikis = defaultdict(set)
for arg in args:
if arg.startswith('-family'):
current_family = arg.split(':')[1]
elif arg in ('help', '-h', '-help', '--help'):
if arg == 'help':
issue_deprecation_warning(
"'help' option",
"'-h', '-help' or '--help'",
since='10.4.0',
warning_class=ArgumentDeprecationWarning
)
pywikibot.show_help()
return
else:
wikis[current_family].add(arg)
if not wikis:
pywikibot.bot.suggest_help(
additional_text='No wiki is specified to be added.')
for family, codes in wikis.items():
if family not in families_list:
pywikibot.bot.suggest_help(
additional_text=f'Script cannot be used for {family} family.')
else:
update_family(family, codes)
if __name__ == '__main__':
main()