Diforc'hioù etre adstummoù "Modulenn:Central-s-br"

j'essaie de supprimer ce module pour voir
(ModuleCentralizer Begin to search 7 Lua-coders OK 2)
(j'essaie de supprimer ce module pour voir)
Tikedenn : Erlerc'hiet
 
local Central = {} -- The main central module install central libraries and bind the main and its sub-modules
local p = Central
-- See the documentation in: MediaWiki:Scribunto/Central_modules_reference_manual
 
-- ModuleCentralizer-s-fr for task T198107 Begin T20180625.lua
p.version = { -- Modules dependencies. Dependencias del módulo. Dépendances du module.
versionName = "Central-s-fr", versionNumber = "1.0.0(180722T20:20)", versionDate = "2018-07-22T20:20:00",
-- UTC version structure : main.fonction.task(yymmddThh:mm)
mainDescription = "Begin to use", functionDescription = "first functional support", taskDescription = "T198107 Begin to use central modules",
sought = "Central;Centralizer/I18N;Mathroman;TestRequire", -- Sought module and submodules versions
known = "Central;Central-s-fr;Central-14 * Centralizer/I18N;Central/i18n * Mathroman22;Mathroman34", -- Known module and submodules versions
}
-- https://www.MediaWiki.org/wiki/Module:drop_box https://fr.wikisource.org/wiki/Module:drop_box
Central.Central_version = Central.version.versionName
p.ModuleNS = mw.site.namespaces.Module.name .. ":" -- translate Module: in other languages
-- cut_libraries
 
-- - - - ------------------ - - - - ------------------ - - - - -----------------------------
-- Development guide line for i18n translations
--
-- The Library:tests_groups initialises, runs and formats groups of tests for MediaWiki and users.
--
-- A central module could need a translation service and a versioning service to enhance its functions or its stability without disturbing the preview normal use.
-- A main module can define its sought sub-modules versions names and its known sub-modules versions names.
-- The Library:versions installs other libraries, supports versions, binds modules, libraries and i18n translations.
-- A central module and its translations can inpedendently change. Its p.version{} identifications change also.
-- For this goal a module contains at least one i18n tranlations table. Its /I18N sub-modules contains translations in several languages.
-- Central Libraries, like modules, contain their own p.version{} identifications and i18n translations in Module:Library/library_name/I18N.
-- The adaptation to any number of languages is automatic.
-- The highest level is the main module. The lowest level is the libraries level.
--
-- Any module or library can contain i18n tables.
-- i18n tables are mixed from the lowest to the highest level, to permit at upper module to adapt the meaning of string to a new use.
-- Each library is independent of other ones and they can be mixed in any order.
-- To avoid conflict of translations keys between libraries, all translations keys names start with the library name.
--
-- - - - ------------------ - - - - ------------------ - - - - -----------------------------
 
-- The central system permits to convert any module as central.
-- The Lua part of the central modules support contains some libraries used by central modules.
-- The Module:Centralizer installs central libraries (waiting stable Scribunto central repository).
-- An object has a function object.new() to form several objects
-- A library is unic and come from Scribunto.
-- Unique declarations of libraries and objects:
-- To split ModuleCentral-s-fr delete activity. on 2018-01-10T09:35:00
activity = {} -- Library:activity from 20170611 Search story in Central modules.txt
args = {} -- Object:args from 20180106 form known arguments to import, complete from datas and finalize
boxviews = {} -- Object:boxviews from 20170723 in draft state
datas = {} -- Library:datas from ?
drop_box = {} -- Object:drop_box from 20170615 rename viewers.drop_box() in viewers.drop_box on 20170615
events = {} -- Object:events from ? "events"
langs = {} -- Library:langs from i18n tables on 20130118, br-de-en-es-fr-vi from 20170217,
lua_table = {} -- Library:lua_table from lua_table.level_list() from 20170808
mathroman = {} -- Library:mathroman from ?
modes = {} -- Library:modes from arguments support on 20130125 in Module:Author, 20130312 in Module:ControlArgs
central_library = {} -- Object:central_library from versions.central_library on 20171211 in Module:Centralizer
tableview = {} -- Object:tableview from 20170208
tab_view = {} -- Object:tab_view from 20170208
tests_groups = {} -- Library:tests_groups from Initialises, runs and formats groups of tests for MediaWiki and users.
tracker = {} -- Object:tracker from 20170628
versions = {} -- Library:versions from versioning on 20170316. From versions support in Module:Author3 on 20150225.
viewers = {} -- Library:viewers from 20170209
versions.args = args -- Object:args from 20180106 todo
viewers.boxviews = boxviews -- Object:boxviews from 20170723 ok on
-- Records are in function versions.setup_central_libraries(bindable_libraries, opt) -- Install central bindable libraries in package.loaded
 
Central.infos = { -- from 20171218
["libname"] = "Central", typ = "Module",
libdesc = "The main central module install central libraries and bind the main and sub modules.",
versfirst = "130312.12:00", verslast = "180626:08:54",
versionName = "Central-s-fr", versionNumber = "180626:08:54", versionDate = "2018-03-13 10:31", -- UTC
versions = {
{ ["libname"] = "Central", verstime = "2018-01-06T08:30:10", versid = "180106.0830", phabtask = "T135845", subtask = "S180106arg", change = "new: args.infos todo later", },
{ ["libname"] = "Central", verstime = "2017-12-25T23:10:10", versid = "171225.2310", phabtask = "T135845", subtask = "S170901mMW", change = "MWversions_report()", },
{ ["libname"] = "Central", verstime = "2013-03-12T12:00:00", versid = "130312.1200", phabtask = "T135845", subtask = "S000000new", change = "new: manage translations, arguments for central modules", },
}, -- infos.version
} -- infos
-- see Central modules.txt : Short story of development
-- * On [https://test2.wikipedia.org/w/index.php?title=Module:ControlArgs&oldid=48210 2013-03-12],
-- the Module:ControlArgs groups complex translations and arguments support for other modules to become <b>centralisable</b>.
 
activity.infos = { -- from 20171218
["libname"] = "activity", typ = "Library",
libdesc = "The Library:activity supports Lua-coders sub-tasks and inter-wikis central modules.",
versfirst = "171218.12:00", verslast = "180626:08:54",
versionName = "Central-s-fr", versionNumber = "1.0.0(180624T09:12)", versionDate = "2018-06-24T09:12:00",
-- UTC version structure : main.fonction.task(yymmdd:hh:mm)
mainDescription = "Begin to use", functionDescription = "first functional support", taskDescription = "T198107 Begin to use central modules",
versions = {
{ ["libname"] = "activity", verstime = "2018-06-24T09:12:00", versid = "1.0.0(180624T09:12)",
phabtask = "T198107", subtask = "S180625btu", change = "S171201xyz", },
{ ["libname"] = "activity", verstime = "2017-12-14T20:13:27", versid = "171214.13:27",
phabtask = "T000000", subtask = "S171201xyz", change = "S171201xyz", },
{ ["libname"] = "activity", verstime = "2017-12-12T00:00:00", versid = "171212.00:00",
phabtask = "T000000", subtask = "S171201xyz", change = "S171201xyz", },
}, -- infos.version
} -- infos asterisk
 
activity.describ_version = "The Library:activity supports Lua-coders sub-tasks and inter-wikis central modules."
activity.libname = "activity"
activity.name = "activity"
activity.infos.libname = "activity"
activity.infos.name = "activity"
activity.previous_versions = {
{ ["libname"] = "activity", verstime = "2017-12-14T20:13:27", versid = "171213.10", phabtask = "fr.wikisource", subtask = "fr.wikisource", },
{ ["libname"] = "activity", verstime = "2017-12-14T20:13:27", versid = "171213.10", phabtask = "fr.wikisource", subtask = "fr.wikisource", },
{ ["libname"] = "activity", verstime = "2017-12-14T20:13:27", versid = "171213.10", phabtask = "fr.wikisource", subtask = "fr.wikisource", },
}
 
args.infos = { -- from 20180106
["libname"] = "args", typ = "Object",
libdesc = "The Object:args form known arguments to import, complete from datas and finalize.",
versfirst = "180106.08:15", verslast = "180106.08:15",
versions = {
{ ["libname"] = "args", verstime = "2018-01-06T08:30:10", versid = "180106.0830", phabtask = "T135845", subtask = "S180106arg", change = "new: args.infos todo later", },
}, -- infos.version
} -- infos
 
central_library.infos = { -- from 20171218
["libname"] = "central_library", typ = "Object",
libdesc = "The Object:central_library, in the Library:versions, begin to form libraries and their properties.",
versions = {
{ ["libname"] = "central_library", verstime = "2017-12-14T20:13:27", versid = "171213.10", phabtask = "T000000", subtask = "S000000abc", },
{ ["libname"] = "central_library", verstime = "2017-12-14T20:13:27", versid = "171213.10", phabtask = "T000000", subtask = "S000000abc", },
{ ["libname"] = "central_library", verstime = "2017-12-14T20:13:27", versid = "171213.10", phabtask = "T000000", subtask = "S000000abc", },
}, -- infos.version
} -- infos
 
events.infos = { -- from 20171218
["libname"] = "events", typ = "Library",
libdesc = "The Library:events form events like erros, warnings and categories.",
versfirst = "130312.12:00", verslast = "171221.07:43",
versions = {
{ ["libname"] = "events", verstime = "2017-12-14T20:13:27", versid = "171213.10", phabtask = "T000000", subtask = "S000000abc", },
{ ["libname"] = "events", verstime = "2017-12-14T20:13:27", versid = "171213.10", phabtask = "T000000", subtask = "S000000abc", },
{ ["libname"] = "events", verstime = "2017-12-14T20:13:27", versid = "171213.10", phabtask = "T000000", subtask = "S000000abc", },
}, -- infos.version
} -- infos
 
langs.infos = { -- from 20171218
["libname"] = "langs", typ = "Library",
libdesc = "The Library:lua_table i18n translates: arguments names, sentencies, error messages, catégories...",
versfirst = "130312.12:00", verslast = "171221.07:43",
versions = {
{ ["libname"] = "langs", verstime = "2017-12-14T20:13:27", versid = "171213.10", phabtask = "T000000", subtask = "S000000abc", },
{ ["libname"] = "langs", verstime = "2017-12-14T20:13:27", versid = "171213.10", phabtask = "T000000", subtask = "S000000abc", },
{ ["libname"] = "langs", verstime = "2017-12-14T20:13:27", versid = "171213.10", phabtask = "T000000", subtask = "S000000abc", },
}, -- infos.version
} -- infos
 
lua_table.infos = { -- from 20171218
["libname"] = "lua_table", typ = "Library",
libdesc = "The Library:lua_table enhances previous table library for counts and structure. It also converts to list or to rough_view.",
versfirst = "130312.12:00", verslast = "171221.07:43",
versions = {
{ ["libname"] = "lua_table", verstime = "2017-12-14T20:13:27", versid = "171213.10", phabtask = "T000000", subtask = "S000000abc", },
{ ["libname"] = "lua_table", verstime = "2017-12-14T20:13:27", versid = "171213.10", phabtask = "T000000", subtask = "S000000abc", },
{ ["libname"] = "lua_table", verstime = "2017-12-14T20:13:27", versid = "171213.10", phabtask = "T000000", subtask = "S000000abc", },
}, -- infos.version
} -- infos
 
mathroman.infos = { -- from 20130312
["libname"] = "mathroman", typ = "Library",
libdesc = "The Library:mathroman converts roman to digital numbers and reverse. It also detects errors.",
versfirst = "130312.12:00", verslast = "171221.07:43",
versions = {
{ ["libname"] = "mathroman", verstime = "2017-12-14T20:13:27", versid = "171213.1000", phabtask = "T000000", subtask = "S000000abc", },
{ ["libname"] = "mathroman", verstime = "2017-12-14T20:13:27", versid = "171213.1000", phabtask = "T000000", subtask = "S000000abc", },
{ ["libname"] = "mathroman", verstime = "2017-12-14T20:13:27", versid = "171213.1000", phabtask = "T000000", subtask = "S000000abc", },
}, -- infos.version
} -- infos
 
modes.infos = { -- from 20171218
["libname"] = "modes", typ = "Library",
libdesc = "The Library:modes support modes and their options, like p.read(frame).",
versfirst = "130312.12:00", verslast = "171221.07:43",
versions = {
{ ["libname"] = "modes", verstime = "2017-12-14T20:13:27", versid = "171213.1000", phabtask = "T000000", subtask = "S000000abc", },
{ ["libname"] = "modes", verstime = "2017-12-14T20:13:27", versid = "171213.1000", phabtask = "T000000", subtask = "S000000abc", },
{ ["libname"] = "modes", verstime = "2017-12-14T20:13:27", versid = "171213.1000", phabtask = "T000000", subtask = "S000000abc", },
}, -- infos.version
} -- infos
 
tableview.infos = { -- from 20171218
["libname"] = "tableview", typ = "Object",
libdesc = "The Object:tableview and tab_view, in the Library:viewers, formats tables in lines and columns.",
versfirst = "130312.12:00", verslast = "171221.07:43",
versions = {
{ ["libname"] = "tableview", verstime = "2017-12-14T20:13:27", versid = "171213.10", phabtask = "T000000", subtask = "S000000abc", },
{ ["libname"] = "tableview", verstime = "2017-12-14T20:13:27", versid = "171213.10", phabtask = "T000000", subtask = "S000000abc", },
{ ["libname"] = "tableview", verstime = "2017-12-14T20:13:27", versid = "171213.10", phabtask = "T000000", subtask = "S000000abc", },
}, -- infos.version
} -- infos
 
tests_groups.infos = { -- from 20171218
["libname"] = "tests_groups", typ = "Library",
libdesc = "The Library:tests_groups, initialises, runs and formats groups of tests for MediaWiki and users.",
versions = {
{ ["libname"] = "tests_groups", verstime = "2017-12-14T20:13:27", versid = "171213.10", phabtask = "T000000", subtask = "S000000abc", },
{ ["libname"] = "tests_groups", verstime = "2017-12-14T20:13:27", versid = "171213.10", phabtask = "T000000", subtask = "S000000abc", },
{ ["libname"] = "tests_groups", verstime = "2017-12-14T20:13:27", versid = "171213.10", phabtask = "T000000", subtask = "S000000abc", },
}, -- infos.version
} -- infos
 
versions.infos = { -- from 20130312
["libname"] = "versions", typ = "Library",
libdesc = "The Library:versions installs central libraries, modules and translations. Also support versions management.",
versfirst = "130312.12:00", verslast = "171221.07:43",
versions = {
{ ["libname"] = "versions", verstime = "2017-12-14T20:13:27", versid = "171221.0743", phabtask = "T000000", subtask = "S000000abc", },
{ ["libname"] = "versions", verstime = "2017-12-14T20:13:27", versid = "171213.1000", phabtask = "T000000", subtask = "S000000abc", },
{ ["libname"] = "versions", verstime = "2017-12-14T20:13:27", versid = "130312.1200", phabtask = "T000000", subtask = "S000000abc", },
}, -- infos.version
} -- infos
 
viewers.infos = { -- from 20130312
["libname"] = "viewers", typ = "Library",
libdesc = "The Library:viewers can formats texts to document in some languages.",
versfirst = "130312.12:00", verslast = "171221.07:43",
versions = {
{ ["libname"] = "viewers", verstime = "2017-12-14T20:13:27", versid = "171221.0743", phabtask = "T000000", subtask = "S000000abc", },
{ ["libname"] = "viewers", verstime = "2017-12-13T10:10:00", versid = "171213.1000", phabtask = "T000000", subtask = "S000000abc", },
{ ["libname"] = "viewers", verstime = "2013-03-12T20:12:00", versid = "130312.1200", phabtask = "T000000", subtask = "S000000abc", },
}, -- infos.version
} -- infos
 
modes.central_libraries = { -- New libraries to record in package.loaded[]
{ "activity", "The Library:activity supports Lua-coders sub-tasks and inter-wikis central modules.", },
{ "datas", "The Library:datas gets datas from the Wikibase.", },
{ "events", "The Library:events form events like erros, warnings and categories.", },
{ "langs", "The Library:langs supports i18n translations.", },
{ "lua_table", "The Library:lua_table enhances the native Lua table library, to avoid ambiguities. To enhance, we could write here : lua_table = table.", },
{ "mathroman", "The Library:mathroman converts roman numbers and detect errors. It is here as an example of very small central library.", },
{ "modes", "The Library:modes supports the modes and their options, like p.read(frame).", },
-- { "tests_groups", "The Library:tests_groups, initialises, runs and formats groups of tests for MediaWiki and users.", },
{ "versions", "The Library:versions installs all central libraries, modules, their i18n translations and versions.", },
{ "viewers", "The Library:viewer translates and formats strings to document texts and table views.", },
-- Objects have a function object.new() to form several objects.
-- { "boxviews", "The Object:boxviews, in the Library:viewers, formats boxes, their styles and structures.", },
{ "drop_box", "The Object:drop_box, in the Library:viewers, formats dropboxes and their styles.", },
{ "central_library","The Object:central_library, in the Library:versions, formats the basis of libraries and their properties.", },
{ "tableview", "The Object:tableview, in the Library:viewers, formats some viewers for tables, in lines and columns.", },
{ "tracker", "The Object:tracker, in the Library:activity, formats parametrables tracks to help to debug the code.", },
}
 
-- cut_libraries
 
-- - - - ------------------ - - - - ------------------ - - - - -----------------------------
-- - - - ------------------ - - - - ------------------ - - - - -----------------------------
-- The Library:activity begins to support other tests wikis. It translates tests pages names for these wikis.
-- - - - ------------------ - - - - ------------------ - - - - -----------------------------
-- - - - ------------------ - - - - ------------------ - - - - -----------------------------
 
-- == Central modules ==
 
-- Translations for begin library
activity.i18n = {}
activity.i18n.br = { -- br = Breton = Brezhoneg
-- Pour traduire, les langues de référence sont l'anglais et le français.
-- Pour traduire, ne traduisez pas des parties comme celles-ci : <b>%1</b> ; <b>%1</b> = <b>%2</b> (%3) ; <code>Q535</code> ; <br/> ; \n* ; _G.
["docfunc"] = "docfunc",
["docitem"] = "docitem",
["dockey"] = "dockey",
activity_description = "La Library:activity soutient la gestion des tâches de phabricator, des sous-tâches inter Lua-codeurs et des modules centraux interwikis.",
activity_central_library_description = "La Library:activity soutient la gestion des tâches de phabricator, des sous-tâches inter Lua-codeurs et des modules centraux interwikis.",
activity_display_central_libraries_title = "activity.describe_central_libraries() Description des bibliothèques centrales",
activity_translate_string_guide = "Pour traduire, ne traduisez pas les parties comme celles-ci : <b>%1</b> ; <b>%1</b> = <b>%2</b> (%3) ; <code>Q535</code> ; <br/> ; <br/> ; \n* ; _G.",
activity_Module_Central_central_version = "Module:Centralizer",
activity_Library_translate_I18N = "Module:Library/translate/I18N",
activity_Central_modules_reference_manual = "Scribunto/Central modules reference manual",
activity_report_subtasks_title = 'activity.central_subtasks_report(t) Surveiller les sous-tâches. Voir "NOW".',
activity_MW_Versions_report_title = "<b>activity.MW_Versions_report()</b> Surveiller les versions de MediaWiki, les 3 derniers mois.", -- fr
activity_central_count_admins_active_users = "Ce site, fr.wikisource.org, compte <b>%1</b> administrateurs pour <b>%2</b> utilisateurs actifs.",
activity_support_central_modules_title = "activity.begin_central_modules_support() Soutenir les premières utilisations des Central modules.",
activity_support_central_modules_headers = "Project; Language; Admins; Assets; Lien Modèle; Lien Module; Lien Tests; Début; Utilisé depuis; Codeur; OK", -- fr
activity_phabricator_tasks_title = "activity.phabricator_tasks_report() États des tâches connexes dans Phabricator",
activity_phabricator_tasks_headers = "Importance, modifiée le; Tâche; Etat; Titre",
activity_central_functions_report_title = "activity.central_functions_report(t) Lister les fonctions actuelles.",
activity_check_html_bold_tags_title = "activity.check_html_bold_tags() Signaler les déséquilibres des débuts et des fins de gras dans le code.",
} -- activity.i18n.br
activity.i18n.de = { -- de = German = Deutsche
-- Modul:Central-s-de/Doku {{#invoke:Central-s-de|read}} de = German = Deutsch
["docfunc"] = "docfunc",
["docitem"] = "docitem",
["dockey"] = "dockey",
activity_description = "Das Library:activity Das Ding unterstützt das Management von phaborator-Aufgaben, von inter-Lua-Coder-Unteraufgaben und von interwikis-Zentralmodulen.",
activity_central_library_description = "Das Library:activity Das Ding unterstützt das Management von phaborator-Aufgaben, von inter-Lua-Coder-Unteraufgaben und von interwikis-Zentralmodulen.",
activity_display_central_libraries_title = "activity.describe_central_libraries() Zentrale Bibliotheksbeschreibungen",
activity_Module_Central_central_version = "Modul:Central",
activity_Library_translate_I18N = "Modul:Library/translate/I18N",
activity_Central_modules_reference_manual = "Scribunto/Central modules reference manual",
activity_support_central_modules_title = "<b>activity.begin_central_modules_support()</b> Unterstützen Sie die ersten Anwendungen von Central-Modulen.",
activity_support_central_modules_headers = "Projekt; Speicher; Admins; Vermögenswerte; Modellverbindung; Modulverbindung; LinkTests; beginnen; Gebraucht seit; Encoder; Ok", -- fr
activity_report_subtasks_title = 'activity.central_subtasks_report(t) Überwachen Sie den aktuellen Stand der subtasks. See "NOW".',
activity_MW_Versions_report_title = "<b>activity.MW_Versions_report()</b> Überwachen von MediaWiki-Versionen, letzten 3 Monate.", -- de
activity_central_count_admins_active_users = "Für diese Seite, br.wikisource.org, Konto <b>%1</b> Direktoren für <b>%2</b> aktive Nutzer.",
activity_phabricator_tasks_title = "activity.phabricator_tasks_report() Zuständige Aufgaben in Phabricator",
activity_phabricator_tasks_headers = "Wichtigkeit; modifiziert die; Aufgabe; Status; Titel",
activity_central_functions_report_title = "activity.central_functions_report(t) Listen Sie die aktuellen Funktionen auf.",
activity_check_html_bold_tags_title = "activity.check_html_bold_tags() Melden Sie Ungleichgewichte von Anfang und Ende von Fett im Code.",
} -- activity.i18n.de
activity.i18n.en = { -- en = English = English
-- To translate, referral languages are English and French.
-- To translate, do not translate parts like these: <b>%1</b> ; <b>%1</b> = <b>%2</b> (%3) ; <code>Q535</code> ; <br/> ; \n* ; _G.
["docfunc"] = "docfunc",
["docitem"] = "docitem",
["dockey"] = "dockey",
activity_description = "The Library:activity supports the management of phabricator tasks, of inter Lua coders sub-tasks, and of interwikis central modules.",
activity_central_library_description = "The Library:activity supports the management of phabricator tasks, of inter Lua coders sub-tasks, and of interwikis central modules.",
activity_display_central_libraries_title = "activity.describe_central_libraries() Central libraries descriptions",
activity_translate_string_guide = "To translate, do not translate parts like these: <b>%1</b> ; <b>%1</b> = <b>%2</b> (%3) ; <code>Q535</code> ; <br/> ; <br/> ; \n* ; _G.",
activity_Module_Central_central_version = "Module:Centralizer",
activity_Library_translate_I18N = "Module:Library/translate/I18N",
activity_Central_modules_reference_manual = "Scribunto/Central modules reference manual",
activity_report_subtasks_title = 'activity.central_subtasks_report(t) Monitor the current subtasks. See "NOW".',
activity_MW_Versions_report_title = "<b>activity.MW_Versions_report()</b> Monitor MediaWiki versions, last 3 months.", -- en
activity_central_count_admins_active_users = "This site, br.wikisource.org, count <b>%1</b> administrators for <b>%2</b> active users.",
activity_support_central_modules_title = "<b>activity.begin_central_modules_support()</b> Support the first uses of Central modules.",
activity_support_central_modules_headers = "Project; Save; Admins; assets; Model link; Module link; Link Tests; start; Used since; encoder; OK", -- fr
activity_phabricator_tasks_title = "activity.phabricator_tasks_report() States of related tasks in Phabricator",
activity_phabricator_tasks_headers = "Importance; modified on; Task; Status; Title",
activity_central_functions_report_title = "activity.central_functions_report(t) List actual functions.",
activity_check_html_bold_tags_title = "activity.check_html_bold_tags() Report imbalances of beginnings and ends of bold in code.",
} -- activity.i18n.en
activity.i18n.es = { -- es = Spanish = español
-- To translate, referral languages are English and French.
-- To translate, do not translate parts like these: <b>%1</b> ; <b>%1</b> = <b>%2</b> (%3) ; <code>Q535</code> ; <br/> ; \n* ; _G.
["docfunc"] = "docfunc",
["docitem"] = "docitem",
["dockey"] = "dockey",
activity_description = "La Library:activity soporta la gestión de tareas de phabricator, de sub-tareas inter Lua coders, y de módulos interwikis centrales.",
activity_central_library_description = "La Library:activity soporta la gestión de tareas de phabricator, de sub-tareas inter Lua coders, y de módulos interwikis centrales.",
activity_display_central_libraries_title = "activity.describe_central_libraries() Descripciones de bibliotecas centrales",
activity_translate_string_guide = "Para traducir, no traducir partes como estas: <b>%1</b> ; <b>%1</b> = <b>%2</b> (%3) ; <code>Q535</code> ; <br/> ; <br/> ; \n* ; _G.",
activity_Module_Central_central_version = "Módulo:Central",
activity_Library_translate_I18N = "Módulo:Library/translate/I18N",
activity_Central_modules_reference_manual = "Scribunto/Central modules reference manual",
activity_support_central_modules_title = "activity.begin_central_modules_support() Apoye los primeros usos de los módulos centrales.",
activity_support_central_modules_headers = "proyecto; Guarde; Administradores; activos; Enlace modelo; Enlace del módulo; Enlace Tests; Inicio; Usado desde entonces; codificador; bueno", -- fr
activity_report_subtasks_title = 'activity.central_subtasks_report(t) Monitorear las subtareas. See "NOW".',
activity_MW_Versions_report_title = "<b>activity.MW_Versions_report()</b> Monitorear las versiones de MediaWiki, últimos 3 meses.", -- es
activity_central_count_admins_active_users = "Este sitio, br.wikisource.org, cuenta <b>%1</b> administradores para <b>%2</b> usuarios activos.",
activity_phabricator_tasks_title = "activity.phabricator_tasks_report() Tareas relacionadas con los estados en Phabricator",
activity_phabricator_tasks_headers = "Importancia; modificado; Tarea; Estado; Título",
activity_central_functions_report_title = "activity.central_functions_report(t) Listar funciones actuales.",
activity_check_html_bold_tags_title = "activity.check_html_bold_tags() Informe los desequilibrios de los comienzos y los extremos de negrita en el código.",
} -- activity.i18n.es
activity.i18n.fr = { -- fr = French = Français
-- Pour traduire, les langues de référence sont l'anglais et le français.
-- Pour traduire, ne traduisez pas des parties comme celles-ci : <b>%1</b> ; <b>%1</b> = <b>%2</b> (%3) ; <code>Q535</code> ; <br/> ; \n* ; _G.
["docfunc"] = "docfunc",
["docitem"] = "docitem",
["dockey"] = "dockey",
activity_description = "La Library:activity soutient la gestion des tâches de phabricator, des sous-tâches inter Lua-codeurs et des modules centraux interwikis.",
activity_central_library_description = "La Library:activity soutient la gestion des tâches de phabricator, des sous-tâches inter Lua-codeurs et des modules centraux interwikis.",
activity_display_central_libraries_title = "activity.describe_central_libraries() Description des bibliothèques centrales",
activity_translate_string_guide = "Pour traduire, ne traduisez pas les parties comme celles-ci : <b>%1</b> ; <b>%1</b> = <b>%2</b> (%3) ; <code>Q535</code> ; <br/> ; <br/> ; \n* ; _G.",
activity_Module_Central_central_version = "Module:Centralizer",
activity_Library_translate_I18N = "Module:Library/translate/I18N",
activity_Central_modules_reference_manual = "Scribunto/Central modules reference manual",
activity_report_subtasks_title = 'activity.central_subtasks_report(t) Surveiller les sous-tâches. Voir "NOW".',
activity_MW_Versions_report_title = "<b>activity.MW_Versions_report()</b> Surveiller les versions de MediaWiki, les 3 derniers mois.", -- fr
activity_central_count_admins_active_users = "Ce site, fr.wikisource.org, compte <b>%1</b> administrateurs pour <b>%2</b> utilisateurs actifs.",
activity_support_central_modules_title = "activity.begin_central_modules_support() Soutenir les premières utilisations des Central modules.",
activity_support_central_modules_headers = "Project; Language; Admins; Assets; Lien Modèle; Lien Module; Lien Tests; Début; Utilisé depuis; Codeur; OK", -- fr
activity_phabricator_tasks_title = "activity.phabricator_tasks_report() États des tâches connexes dans Phabricator",
activity_phabricator_tasks_headers = "Importance, modifiée le; Tâche; Etat; Titre",
activity_central_functions_report_title = "activity.central_functions_report(t) Lister les fonctions actuelles.",
activity_check_html_bold_tags_title = "activity.check_html_bold_tags() Signaler les déséquilibres des débuts et des fins de gras dans le code.",
} -- activity.i18n.fr
activity.i18n.hu = { -- hu = Hungarian = Magyar -- Il n'y a aucun module dans l'espace module Modul:Central-w-hu/doc {{#invoke:Central-w-hu|read}}
-- To translate, referral languages are English and French.
-- To translate, do not translate parts like these: <b>%1</b> ; <b>%1</b> = <b>%2</b> (%3) ; <code>Q535</code> ; <br/> ; \n* ; _G.
["docfunc"] = "docfunc",
["docitem"] = "docitem",
["dockey"] = "dockey",
activity_description = "A Library:activity a phabricator feladatok kezelését, az inter Lua-kódoló al-feladatok és az interwikis központi modulok kezelését.",
activity_central_library_description = "A Library:activity a phabricator feladatok kezelését, az inter Lua-kódoló al-feladatok és az interwikis központi modulok kezelését.",
activity_display_central_libraries_title = "activity.describe_central_libraries() Központi könyvtárak leírása",
activity_translate_string_guide = "Töltsd le a szöveget, és nyomd le a partit a cellák között: <b>%1</b> ; <b>%1</b> = <b>%2</b> (%3) ; <code>Q535</code> ; <br/> ; <br/> ; \n* ; _G.",
activity_Module_Central_central_version = "Modul:Central",
activity_Library_translate_I18N = "Modul:Library/translate/I18N",
activity_Central_modules_reference_manual = "Scribunto/Central modules reference manual",
activity_report_subtasks_title = 'activity.central_subtasks_report(t) Kíséri részfeladatok. See "NOW".',
activity_MW_Versions_report_title = "<b>activity.MW_Versions_report()</b> Monitor MediaWiki verziók, az elmúlt 3 hónapban.", -- hu
activity_central_count_admins_active_users = "Ez az oldal, br.wikisource.org, fiók <b>%1</b> rendszergazdák és <b>%2</b> felhasználók aktív.",
activity_support_central_modules_title = "activity.begin_central_modules_support() Támogassa a központi modulok első használatát.",
activity_support_central_modules_headers = "Project mentése; Adminok; eszközöket; Modell link; Modul kapcsolat; Link Tests; indul el; Óta használják; jeladó; rendben", -- fr
activity_phabricator_tasks_title = "activity.phabricator_tasks_report() Államokkal kapcsolatos feladatok a Phabricator",
activity_phabricator_tasks_headers = "Fontosság; módosította; a Feladat; Állapot; Cím",
activity_central_functions_report_title = "activity.central_functions_report(t) Listázza az aktuális funkciókat.",
activity_check_html_bold_tags_title = "activity.check_html_bold_tags() Jelentés a merész kódok kezdetének és végének egyenlőtlenségeiről.",
} -- activity.i18n.hu
activity.i18n.vi = { -- vi = Vietnamese = Tiếng việt
-- To translate, referral languages are English and French.
-- To translate, do not translate parts like these: <b>%1</b> ; <b>%1</b> = <b>%2</b> (%3) ; <code>Q535</code> ; <br/> ; \n* ; _G.
["docfunc"] = "docfunc",
["docitem"] = "docitem",
["dockey"] = "dockey",
activity_central_library_description = "Điều này Library:activity hỗ trợ việc quản lý các công việc để nhà phân tích, các nhiệm vụ phụ liên Lua coders, và các mô-đun trung tâm liên thông.",
activity_display_central_libraries_title = "activity.describe_central_libraries() Mô tả thư viện trung ương",
activity_translate_string_guide = "Để dịch, không dịch các phần như thế này : <b>%1</b> ; <b>%1</b> = <b>%2</b> (%3) ; <code>Q535</code> ; <br/> ; \n* ; _G.",
activity_Module_Central_central_version = "Mô đun:Central",
activity_Library_translate_I18N = "Mô đun:Library/translate/I18N",
activity_Central_modules_reference_manual = "Scribunto/Central modules reference manual",
activity_report_subtasks_title = 'activity.central_subtasks_report(t) Xem việc phụ. See "NOW".',
activity_MW_Versions_report_title = "<b>activity.MW_Versions_report()</b> Giám sát các phiên bản MediaWiki, 3 tháng gần đây.", -- vi
activity_central_count_admins_active_users = "Trang web này, Br.wikisource.org có <b>%1</b> quản trị viên cho <b>%2</b> người dùng hoạt động.",
activity_support_central_modules_title = "activity.begin_central_modules_support() Hỗ trợ sử dụng đầu tiên để mô-đun Trung tâm.",
activity_support_central_modules_headers = "dự án; lưu; Quản trị viên; tài sản; Liên kết mô hình; Liên kết mô-đun; Liên kết Tests; bắt đầu; Được sử dụng kể từ; encoder; tốt",
activity_phabricator_tasks_title = "activity.phabricator_tasks_report() Các nhiệm vụ liên quan đến Nhà nước trong Phabricator",
activity_phabricator_tasks_headers = "Tầm quan trọng; sửa đổi; nhiệm vụ; tình trạng; tiêu đề",
activity_central_functions_report_title = "activity.central_functions_report(t) Liệt kê các chức năng hiện tại.",
activity_check_html_bold_tags_title = "activity.check_html_bold_tags() Báo cáo sự mất cân đối của các khởi đầu và kết thúc bằng chữ in đậm.",
} -- activity.i18n.vi
 
function activity.describe_central_libraries(t) -- Central libraries descriptions, activity_display_central_libraries_title
local memo = viewers.save_configs("activity.describe_central_libraries") -- Save global configuration before eventual changes.
local t = t or "\n* <b>activity.describe_central_libraries()</b> Monitor central libraries descriptions." -- t or
local tab_view = { -- Group datas and options for a table view with lines and columns.
test_group = modes.central_libraries, -- List of subtasks to monitor.
title_memo = "activity_display_central_libraries_title", -- "activity.describe_central_libraries() Monitor central libraries descriptions",
-- headers = "activity_monitor_central_libraries_headers", -- " Name; Description of the library ",
headers = " Name; Description of the library ",
headers_class = "wikitable alternative center sortable",
rowGroup = {},
-- track_on == "details",
}
t = t .. tableview.new(tab_view) -- Formats a table view with lines and columns.
viewers.restore_configs(memo, "activity.describe_central_libraries") -- Restore global configurations after eventual changes.
return t
end
 
activity.wikis_names = { -- see mw:Extension:WikimediaIncubator
["b"] = "wikibooks", ["cm"] = "commons", ["meta"] = "meta", ["mw"] = "MediaWiki", ["d"] = "wikidata",
["n"] = "wikinews", ["p"] = "wiki", ["q"] = "wikiquote", ["s"] = "wikisource",
["species"] = "species", ["t"] = "wiktionary", ["test"] = "test", ["test2"] = "test2",
["v"] = "wikiversity", ["w"] = "wikipedia", ["wm"] = "wikimedia", ["y"] = "wikivoyage",
} -- activity.wikis_names
-- see https://fr.wikisource.org/wiki/Spécial:Interwiki
-- see https://www.MediaWiki.org/wiki/Special:Interwiki
-- see https://fr.wikisource.org/wiki/Sp%C3%A9cial:Matrice_des_sites
activity.kiwis_names = {
["commons"] = "cm", ["MediaWiki"] = "mw", ["meta"] = "meta", ["species"] = "species", ["wikidata"] = "d",
["test"] = "test", ["test2"] = "test2", ["wiki"] = "p", ["wikibooks"] = "b",
["wikimedia"] = "wm", ["wikinews"] = "n", ["wikipedia"] = "w", ["wikiquote"] = "q",
["wikisource"] = "s", ["wikiversity"] = "v", ["wikivoyage"] = "y", ["wiktionary"] = "t",
}
 
activity.proto_version = "Centralizer-s-fr"
activity.local_version = "Centralizer-s-fr" -- default Patrom:Central
 
activity.coder_lang_module = { -- List to report of Module:Centralizer for 'Begin to use' 7 central modules, 7 coders, 7 projets, 7 langs to get.
-- br.wikisource.org/wiki/Modulenn:Centralizer-s-br/doc {{#invoke:Centralizer-s-br|read}} fr = Breton = Breton = Breitz
{ ["lang"] = "br", ["project"] = "wikisource", ["module_vers"] = "Centralizer-s-br", ["coder"] = "[[:s:br:Implijer:VIGNERON|VIGNERON]]", ["ok"] = "ok",
["project_short"] = "s", ["tests_lang"] = "Centralizer/Tests", ["template"] = "Patrom", ["template_vers"] = "Centralizer",
["module"] = "Modulenn", ["admins"] = "16", ["assets"] = "236", ["beginon"] = "20180719 ?", ["usedfrom"] = "20180719 ?", },
--
-- de.wikisource.org/wiki/Modul:Centralizer-s-de/Doku {{#invoke:Centralizer-s-de|read}} de = German = Deutsch
{ ["lang"] = "de", ["project"] = "wikisource", ["module_vers"] = "Centralizer-s-de", ["coder"] = "[[:s:de:Benutzer:DerFussi|DerFussi]]", ["ok"] = "...",
["project_short"] = "s", ["tests_lang"] = "Centralizer/Tests", ["template"] = "Vorlage", ["template_vers"] = "Centralizer",
["module"] = "Modul", ["admins"] = "16", ["assets"] = "236", ["beginon"] = "20180719 ?", ["usedfrom"] = "20180719 ?", },
--
-- en.wikipedia.org/wiki/Module:Centralizer-w-en/Documentation {{#invoke:Centralizer-w-en|read}} en = English = English
{ ["lang"] = "en", ["project"] = "wikipedia", ["module_vers"] = "Centralizer-w-en", ["coder"] = "[[:w:en:User:Toohool|Toohool]]", ["ok"] = "...",
["project_short"] = "w", ["tests_lang"] = "Centralizer/Tests", ["template"] = "Template", ["template_vers"] = "Centralizer",
["module"] = "Module", ["admins"] = "0", ["assets"] = "0", ["beginon"] = "20180719 ?", ["usedfrom"] = "20180719 ?", },
--
-- es.wikipedia.org/wiki/Módulo:Centralizer-w-es/Documentación {{#invoke:Centralizer-w-es|read}} es = Spanish = español
{ ["lang"] = "es", ["project"] = "wikipedia", ["module_vers"] = "Centralizer-s-es", ["coder"] = "[[:w:es:Usuario:Juan_Mayordomo|Juan_Mayordomo]]", ["ok"] = "...",
["project_short"] = "w", ["tests_lang"] = "Centralizer/Tests", ["template"] = "Plantilla", ["template_vers"] = "Centralizer",
["module"] = "Módulo", ["admins"] = "16", ["assets"] = "236", ["beginon"] = "20180719 ?", ["usedfrom"] = "20180719 ?", },
--
-- es.wikisource.org/wiki/Módulo:Centralizer-s-es/Documentación {{#invoke:Centralizer-s-es|read}} es = Spanish = española
{ ["lang"] = "es", ["project"] = "wikisource", ["module_vers"] = "Centralizer-s-es", ["coder"] = "[[:s:es:Usuario:Alex brollo|Alex brollo]]", ["ok"] = "...", -- Usuario:Juan_Mayordomo
["project_short"] = "s", ["tests_lang"] = "Centralizer/Tests", ["template"] = "Plantilla", ["template_vers"] = "Centralizer",
["module"] = "Módulo", ["admins"] = "22", ["assets"] = "234", ["beginon"] = "20180719 ?", ["usedfrom"] = "20180719 ?", },
--
-- fr.wikisource.org/wiki/Module:Centralizer-s-fr/Documentation {{#invoke:Centralizer-s-fr|read}} fr = French = Français
{ ["lang"] = "fr", ["project"] = "wikisource", ["module_vers"] = "Centralizer-s-fr", ["coder"] = "[[:s:fr:Utilisateur:Rical|Rical]]", ["ok"] = "ok",
["project_short"] = "s", ["tests_lang"] = "Centralizer/Tests", ["template"] = "Modèle", ["template_vers"] = "Centralizer",
["module"] = "Module", ["admins"] = "16", ["assets"] = "204", ["beginon"] = "20180719", ["usedfrom"] = "20180719 ?", },
--
-- fr.wikisource.org/wiki/Module:Auteur2Tpt/Tests {{#invoke:Auteur2Tpt|read}} fr = French = Français
{ ["lang"] = "fr", ["project"] = "wikisource", ["module_vers"] = "Auteur2Tpt", ["coder"] = "[[:s:fr:Utilisateur:Rical|Rical]]", ["ok"] = "ok",
["project_short"] = "s", ["tests_lang"] = "Auteur2Tpt/Tests", ["template"] = "Modèle", ["template_vers"] = "Auteur2Tpt",
["module"] = "Module", ["admins"] = "16", ["assets"] = "204", ["beginon"] = "20180719", ["usedfrom"] = "20180719 ?", },
--
-- hu.wikipedia.org/wiki/Modul:Centralizer-w-hu/doc {{#invoke:Centralizer-w-hu|read}} hu = Hungarian = Magyar
{ ["lang"] = "hu", ["project"] = "wikipedia", ["module_vers"] = "Centralizer-w-hu", ["coder"] = "[[:w:hu:Szerkesztő:Tacsipacsi|Tacsipacsi]]", ["ok"] = "...",
["project_short"] = "w", ["tests_lang"] = "Centralizer/Tests", ["template"] = "Sablon", ["template_vers"] = "Centralizer",
["module"] = "Modul", ["admins"] = "3", ["assets"] = "77", ["beginon"] = "20180719 ?", ["usedfrom"] = "20180719 ?", },
--
-- vi.wikipedia.org/wiki/Mô đun:Centralizer-w-vi/tài liệu {{#invoke:Centralizer-w-vi|read}} vi = Vietnamese = Tiếng Việt
{ ["lang"] = "vi", ["project"] = "wikipedia", ["module_vers"] = "Centralizer-w-vi", ["coder"] = "[[:w:vi:Thành viên:mxn|mxn]]", ["ok"] = "...",
["project_short"] = "w", ["tests_lang"] = "Centralizer/Tests", ["template"] = "Bản mẫu", ["template_vers"] = "Centralizer",
["module"] = "Mô đun", ["admins"] = "3", ["assets"] = "77", ["beginon"] = "20180719 ?", ["usedfrom"] = "20180719 ?", },
-- Projects : MediaWikis wikidata wikipedia wikisource wikiquote meta test2
-- NOWNOW
-- { "20170805", "20170807", "todo", "Rical", "S170702ALC", "Ask Lua coders: Oliv0, Tpt, Od1n, Ayack, Kertraon, Julien1978, Thibaut120094", },
-- { "20170805", "20170807", "todo", "Rical", "S170702ALC", "Ask Lua coders: Zolo, Zebulon84, Hlm Z., Cantons-de-l'Est, Daehan", },
}
 
function activity.begin_central_modules_support(t) -- Supports the first uses of Central modules.
local memo = viewers.save_configs("activity.begin_central_modules_support") -- Save global configuration before eventual changes.
local t = t or "\n* <b>activity.begin_central_modules_support()</b> Support the first uses of Central modules."
local tab_view = { -- Group datas and options for a table view with lines and columns.
test_group = activity.coder_lang_module, -- CLM
rowGroup = {},
form_one_case = function(case) -- Convert a case from test_group to rowGroup.
local mwuri = mw.uri.new()
local hostPort = mwuri.hostPort
local selector = mwuri.hostPort
case = activity.central_module_descriptor(case) -- Begin to adapt the main central module version to a case.
case.lang = tostring(case.lang)
case.project = tostring(case.project)
case.admins = tostring(case.admins)
case.assets = tostring(case.assets)
case.template = tostring(case.template)
case.template_vers = tostring(case.template_vers)
case.module = tostring(case.module)
case.module_vers = tostring(case.module_vers)
case.version = tostring(case.version)
case.page_template = case.template .. ":" .. case.template_vers
case.link_template = "[[" .. case.project_short .. ":" .. case.lang .. ":" .. case.page_template .. "|" .. case.page_template .. "]]"
case.page_module = case.module .. ":" .. case.module_vers
case.link_module = "[[" .. case.project_short .. ":" .. case.lang .. ":" .. case.page_module .. "|" .. case.page_module .. "]]"
-- case.page_doc = case.tests_lang
-- case.page_doc = case.module .. ":" .. case.tests_lang
-- case.link_doc = "[[" .. case.project_short .. ":" .. case.lang .. ":" .. case.module .. ":" .. case.tests_lang .. "|" .. case.tests_lang .. "]]"
case.link_Tests = "[[" .. case.project_short .. ":" .. case.lang .. ":" .. case.module .. ":" .. case.tests_lang .. "|" .. case.tests_lang .. "]]"
return { case.project, case.lang, case.admins, case.assets, case.link_template, case.link_module, case.link_Tests, case.beginon, case.usedfrom, case.coder, case.ok }
end,
title_memo = "activity_support_central_modules_title",
headers = "Project; Language; Admins; Assets; Lien Modèle; Lien Module; Lien Tests; Début; Utilisé depuis; Codeur; OK",
activity_support_central_modules_headers = "Project; Language; Admins; Assets; Module version; Link to Tests; Start; Used since; Coder; OK", -- en
}
t = t .. tableview.new(tab_view) -- Formats a table view with lines and columns.
local langs, coders, projects, versions = {}, {}, {}, {}
for i, case in pairs(activity.coder_lang_module) do
if (type(case.lang) == "string") then table.insert(langs, case.lang) end
if (type(case.coder) == "string") then table.insert(coders, case.coder) end
if (type(case.project) == "string") then table.insert(projects, case.project) end
if (type(case.module_vers) == "string") then table.insert(versions, case.module_vers) end
end
local counter = lua_table.count_values(coders, "lang")
t = t .. "\n* Count begin coders: " .. viewers.ta("n", lua_table.level_count(counter) ) .. viewers.rough_view(counter)
local counter = lua_table.count_values(langs, "lang")
t = t .. "\n* Count begin langs: " .. viewers.ta("n", lua_table.level_count(counter) ) .. viewers.rough_view(counter)
local counter = lua_table.count_values(projects, "lang")
t = t .. "\n* Count begin projects: " .. viewers.ta("n", lua_table.level_count(counter) ) .. viewers.rough_view(counter)
local counter = lua_table.count_values(versions, "lang")
t = t .. "\n* Count begin versions: " .. viewers.ta("n", lua_table.level_count(counter) ) .. viewers.rough_view(counter)
viewers.restore_configs(memo, "activity.begin_central_modules_support") -- Restore global configurations after eventual changes.
return t
end -- t = t .. activity.begin_central_modules_support(t) -- Survey the current state of sub tasks to debug. len
 
function activity.central_module_descriptor(wiki, selector) -- Begin to adapt the main central module version to a wiki.
local mwuri = mw.uri.new()
local hostPort = mwuri.hostPort
local actual_wiki = false
if type(selector ~= "string") then selector = hostPort end -- Adapt to actual wiki as default
-- wiki.doc_full = wiki.version_full .. "/" .. wiki.doc -- fr.wikisource.org/wiki/Module:Centralizer-s-fr/Documentation
if not CMD then CMD = tracker.initadd({ ["name"] = "CMD", ["limit"] = 2 }) end -- Initialize a track
wiki.actual_wiki = actual_wiki -- Is this wiki selected?
if (type(wiki.doc_full) == "string") then -- fr.wikisource.org/wiki/Module:Centralizer-s-fr/Documentation
local points = string.gsub(wiki.doc_full, "/", ".") -- fr.wikisource.org.wiki.Module:Centralizer-s-fr.Documentation
local points = string.gsub(points, ":", ".") -- fr.wikisource.org.wiki.Module.Central-s-fr.Documentation
local s = mw.text.split(points, '.', true)-- { "fr", "wikisource", "org", "wiki", "Module", "Central-s-fr", "Documentation" }
wiki.url_ref = "https://fr.wikisource.org/wiki/Module:Centralizer-s-fr/Documentation"
wiki.protocol = "https://" -- https://
wiki.lang_project_org = s[1] .. "." .. s[2] .. "." .. s[3]
if (type(wiki.enforce_main_version) == "string") then wiki.lang_project_org = wiki.enforce_main_version end
wiki.doc_full = string.gsub(wiki.doc_full, wiki.lang_project_org, wiki.enforce_main_version)
-- fr.wikisource.org.wiki.Module.Central-s-fr.Documentation
local points = string.gsub(wiki.doc_full, "/", ".") -- fr.wikisource.org.wiki.Module:Centralizer-s-fr.Documentation
local points = string.gsub(points, ":", ".") -- fr.wikisource.org.wiki.Module.Central-s-fr.Documentation
local s = mw.text.split(points, '.', true)-- s= { "fr", "wikisource", "org", "wiki", "Module", "Central-s-fr", "Documentation" }
wiki.lang = s[1] -- fr
wiki.project = s[2] -- wikisource
if wiki.project =="MediaWiki" then wiki.lang = "en" end
wiki.proj = activity.kiwis_names[wiki.project] or "proj" -- s in brief for wikisource
wiki.org = s[3] -- org
wiki.lang_project_org = wiki.lang .. "." .. wiki.project .. "." .. wiki.org -- fr.wikisource.org
if wiki.lang_project_org == hostPort then actual_wiki = true ; wiki.actual_wiki = actual_wiki end
if wiki.actual_wiki then
wiki.admins = tostring(mw.site.stats.usersInGroup("sysop"))
wiki.assets = tostring(mw.site.stats.activeUsers)
wiki.found = true -- This wiki is selected
CMD.add(CMD, 1, "descriptor admins assets hostPort", { ["admins"] = wiki.admins, ["assets"] = wiki.assets, ["actual_wiki"] = wiki.actual_wiki, ["lang_project_org"] = wiki.lang_project_org, } )
else
wiki.admins = wiki.admins
wiki.assets = wiki.assets
wiki.actual_wiki = wiki.actual_wiki -- This wiki is selected
CMD.add(CMD, 1, "descriptor admins assets else", { ["admins"] = wiki.admins, ["assets"] = wiki.assets, ["actual_wiki"] = wiki.actual_wiki, ["lang_project_org"] = wiki.lang_project_org, } )
end
CMD.add(CMD, 1, "descriptor wikis_to_begin", { ["i"] = i, ["s"] = s, ["wiki.lang"] = wiki.lang, ["wiki.lang_project_org"] = wiki.lang_project_org, } )
wiki.wiki = s[4] -- wiki
wiki.transmodule = s[5] -- Module
wiki.version = "Central-" .. wiki.proj .. "-" .. wiki.lang -- Central-s-fr
wiki.modulename = wiki.version -- s[6] -- Module
wiki.version_full = wiki.lang_project_org .. "/" .. wiki.wiki .. "/" .. wiki.transmodule .. ":" .. wiki.version
wiki.version_url = wiki.protocol .. wiki.lang_project_org .. "/" .. wiki.wiki .. "/" .. wiki.transmodule .. ":" .. wiki.version
wiki.version_link = "[" .. wiki.version_url .. " " .. wiki.version .. "]" -- To link to the central version
wiki.doc = s[7] -- Documentation
wiki.doc_full = wiki.version_full .. "/" .. wiki.doc -- fr.wikisource.org/wiki/Module:Centralizer-s-fr/Documentation
wiki.doc_url = wiki.protocol .. wiki.doc_full -- https://fr.wikisource.org/wiki/Module:Centralizer-s-fr/Documentation
wiki.doc_link = "[" .. wiki.doc_url .. " " .. wiki.doc .. "]" -- To link to the documentation of the central version
CMD.add(CMD, 1, "activity.descriptor links", { ["wiki.lang_project_org"] = wiki.lang_project_org, ["wiki.version"] = wiki.version, ["version_link"] = wiki.version_link, ["doc_link"] = wiki.doc_link, } )
end
-- CMD.t = "\n* <b>:activity.central_module_descriptor()</b> END."
return wiki
end -- function activity.central_module_descriptor(wiki, selector)
 
function lua_table.to_sort(tab, sortfield, sortorder) -- To sort any table and convert in sequence if needed.
local t = viewers.ta("\n* Begin tab", tab ) .. viewers.ta("sortfield", sortfield) .. viewers.ta("sortorder", sortorder)
local tab = tab or {}
if (type(tab) == "string") then
tab = mw.text.split(tostring(tab), ';') -- table to sort
end
t = t .. versions.sorted_libraries_list
t = t .. viewers.ta("\n* Count of central libraries", lua_table.level_count(versions.sorted_libraries) )
if (type(tab) ~= "table") then tab = {} end
if not ( (type(sortfield) == "number") or (type(sortfield) == "string") ) then sortfield = 1 end
if (type(sortorder) ~= "string") then sortorder = "<" end
local sorted, i = {}, 0
for key, elem in pairs(tab) do
i = i + 1
table.insert(sorted, elem)
end
if (type(sortfield) == "string") then
table.sort(sorted, function (a, b) return ( ( a[sortfield or "a"] ) < ( b[sortfield or "b"] ) ) end ) -- Sort libraries
end
if (type(sortfield) == "number") then
-- table.sort(sorted, function (a, b) return ( ( a[sortfield or 1] ) < ( b[sortfield or 1] ) ) end ) -- Sort libraries
end
t = t .. viewers.ta("\n* End tab", tab ) .. viewers.ta("sortfield", sortfield) .. viewers.ta("sortorder", sortorder)
return sorted, (t or "lua_table.to_sort()")
end -- local sorted = lua_table.to_sort(tab, sortfield, sortorder) -- To sort any table and convert in sequence if needed.
 
local ftd = ";"
ftd = ftd .. "activity.phabricator_tasks_report;activity.rough_date_days;"
ftd = ftd .. "activity.central_subtasks_report;activity.describe_central_libraries;activity.init_selected_wiki;activity.begin_central_modules_support;"
ftd = ftd .. "activity.begin_central_modules_support;activity.central_functions_report;activity.central_subtasks_report;"
ftd = ftd .. "activity.MW_Versions_report;activity.phabricator_tasks_report;"
ftd = ftd .. "central_library.binded_in;central_library.new;"
ftd = ftd .. "datas.get_image;datas.get_item;datas.get_item_report;datas.property;drop_box.new;"
ftd = ftd .. "events.add_cat;events.add_cat_group;events.add_err;events.add_wng;events.all_kinds_test;"
ftd = ftd .. "events.categories_lister;events.errors_lister;events.gener_categories;"
ftd = ftd .. "langs.dummy_languages;langs.init_content_page_user_lang;langs.list_MediaWiki_languages;langs.main_i18n_languages_list;"
ftd = ftd .. "langs.missing_translations;langs.translations_counts;"
ftd = ftd .. "lua_table.count_all;lua_table.count_tests;lua_table.count_types;lua_table.count_values;"
ftd = ftd .. "lua_table.from_subnames_object;lua_table.from_subnames_table;lua_table.level_count;lua_table.level_get;"
ftd = ftd .. "lua_table.level_list;lua_table.named_sub_counts;lua_table.obj_from_subnames;lua_table.sort_onkey;"
ftd = ftd .. "lua_table.sort_types;lua_table.structure;lua_table.structure_recursive_report;lua_table.tab_from_subnames;"
ftd = ftd .. "lua_table.to_list;lua_table.to_list_tests;lua_table.to_table;lua_table.to_table_test;"
ftd = ftd .. "mathroman.int2roman;mathroman.int2roman_test;mathroman.roman2int;mathroman.roman2int_tests;"
ftd = ftd .. "modes.all_categories_list;modes.all_errors_list;modes.get_args;modes.get_args_report;modes.levenshtein;"
ftd = ftd .. "modes.multiple_selection_tests;modes.options_from_args_tests;modes.recursive_normal;modes.recursive_normal_tests;"
ftd = ftd .. "modes.similar_args_list;"
ftd = ftd .. "tableview.form_one_case;tableview.new;"
ftd = ftd .. "version descriptor;versions.all_G_and_loaded_list;versions.get_one_module_or_library;versions.setup_central_libraries;"
ftd = ftd .. "viewers.day_to_stamp;viewers.day_to_UTC;viewers.discreet_main_version;viewers.doc_group;viewers.doc_internal;"
ftd = ftd .. "viewers.doc_module;viewers.doc_page;viewers.doc_section;viewers.form99content;viewers.form99page;"
ftd = ftd .. "viewers.form99user;viewers.form9content;viewers.form9en;viewers.form9page;viewers.form9user;viewers.form9user_test;"
ftd = ftd .. "viewers.form_image;viewers.is_in;viewers.is_in_sp;viewers.main_view;viewers.restore_configs;viewers.rough_view;"
ftd = ftd .. "viewers.rough_view_test;viewers.save_configs;viewers.save_restore_balance_report;viewers.simple_list;"
ftd = ftd .. "viewers.simple_list_test;viewers.styles_small_caps;viewers.ta;viewers.tam;viewers.table_col;viewers.table_dat;"
ftd = ftd .. "viewers.table_end;viewers.table_head;viewers.table_row;viewers.styles_color_add;viewers.styles_color_colargs;"
ftd = ftd .. "viewers.styles_color_delete;viewers.styles_color_discreet;viewers.styles_color_error;viewers.styles_color_mask;"
ftd = ftd .. "viewers.styles_color_normal;viewers.styles_color_warning;viewers.styles_color_wikidata;viewers.usual_color;"
 
activity.functions_to_doc = ftd
 
function activity.to_sort(tab, sortfield, sortorder) -- To sort any table and convert in sequence if needed.
local t = viewers.ta("\n* Begin tab", tab ) .. viewers.ta("sortfield", sortfield) .. viewers.ta("sortorder", sortorder)
local tab = tab or {}
if (type(tab) == "string") then
tab = mw.text.split(tostring(tab), ';') -- table to sort
end
t = t .. viewers.ta("\n* Count of central libraries", lua_table.level_count(libname_libraries) )
if (type(tab) ~= "table") then tab = {} end
if not ( (type(sortfield) == "number") or (type(sortfield) == "string") ) then sortfield = 1 end
if (type(sortorder) ~= "string") then sortorder = "<" end
local sorted, i = {}, 0
for key, elem in pairs(tab) do
i = i + 1
table.insert(sorted, elem)
end
if (type(sortfield) == "string") then
table.sort(sorted, function (a, b) return ( ( a[sortfield or "a"] ) < ( b[sortfield or "b"] ) ) end ) -- Sort libraries
end
if (type(sortfield) == "number") then
-- table.sort(sorted, function (a, b) return ( ( a[sortfield or 1] ) < ( b[sortfield or 1] ) ) end ) -- Sort libraries
end
t = t .. viewers.ta("\n* End tab", tab ) .. viewers.ta("sortfield", sortfield) .. viewers.ta("sortorder", sortorder)
return sorted, (t or "activity.to_sort()")
end -- local sorted = activity.to_sort(tab, sortfield, sortorder) -- To sort any table and convert in sequence if needed.
 
function activity.sort_central_libraries_functions(sorted_central_libraries) -- Select and sort central libraries and functions
local sorted_central_libraries = sorted_central_libraries or {} -- To sort any table and convert in sequence if needed.
local sorted_functions, libname, libname_funcname = {}
for libname, lib in pairs(package.loaded) do -- search directly in package.loaded
if(type(lib) == "table") and (type(lib.i18n) == "table") and (type(libname) == "string") -- Select central i18n objects
and (not string.find(libname, ":") ) then -- Avoid central modules
lib.libname = libname
table.insert(sorted_central_libraries, lib)
for funcname, func in pairs(lib) do -- search directly in package.loaded Rical 20180321
if (type(func) == "function") then -- select central libraries
libname_funcname = libname .. "." .. funcname
table.insert(sorted_functions, { ["libname"] = libname, ["funcname"] = funcname, ["libname_funcname"] = libname_funcname } )
end
end
end
end
table.sort(sorted_central_libraries, function (a, b) return ( a.libname < b.libname ) end ) -- Sort libraries
table.sort(sorted_functions, function (a, b) return ( (a.libname_funcname < b.libname_funcname ) ) end ) -- Sort libraries
activity.sorted_central_libraries = sorted_central_libraries
activity.sorted_functions = sorted_functions
return sorted_central_libraries, sorted_functions
end -- local sorted_central_libraries, sorted_functions = activity.sort_central_libraries_functions() -- Select and sort central libraries and functions
 
-- Last
function activity.central_functions_report(t) -- Lists actual functions for documentations.
local t = t or "\n* <b>activity.central_functions_report(t)</b> List all actual functions."
t = t .. '\n* Selected functions come from: <b>activity.functions_to_doc</b> = "<b>;activity.central_functions_report;events.add_cat;</b>"'
t = t .. "\n* The fonctions to document are in bold like <b>activity.central_functions_report</b>"
local sorted_central_libraries, sorted_functions = activity.sort_central_libraries_functions() -- Select and sort central libraries and functions
local libname, funcname, libname_funcname, asterisk = "", "", "", ""
t = t .. viewers.ta("\n* Count of central libraries", lua_table.level_count(sorted_central_libraries) )
local nlibfunc, nallfunc, nlibdoc, nalldoc = 0, 0, 0, 0
local sorted_to_autodoc = {}
local UPPER = ""
for i, lib in pairs(sorted_central_libraries) do
nlibfunc = 0
nlibdoc = 0
lib.libname = (lib.libname or lib.name or "libname")
t = t .. "\n* <b>Library " .. libname .. "</b>: "
for i, func_record in pairs(sorted_functions) do -- search all functions
if func_record.libname == lib.libname then
nallfunc = nallfunc + 1
nlibfunc = nlibfunc + 1
libname_funcname = tostring(func_record.libname_funcname)
asterisk = ""
if string.find(activity.functions_to_doc, libname_funcname, 1, true) then --OK
nlibdoc = nlibdoc + 1
nalldoc = nalldoc + 1
if string.lower(libname_funcname) ~= libname_funcname then UPPER = UPPER .. libname_funcname .. ", " end -- funcname with uppercase
t = t .. " <b>" .. libname_funcname .. "</b>, "
table.insert(sorted_to_autodoc, { ["name"] = name, ["funcname"] = funcname, ["libname_funcname"] = libname_funcname } )
else
t = t .. libname_funcname .. ", "
end
end
end
table.insert(sorted_functions, { ["name"] = name, ["funcname"] = funcname, ["libname_funcname"] = libname_funcname } )
t = t .. viewers.ta("* <i>Count of functions in this library</i>", nlibfunc) .. viewers.ta("<i>to document</i>", nlibdoc)
end
table.sort(sorted_functions, function (a, b) return ( (a.libname_funcname < b.libname_funcname ) ) end ) -- Sort libraries
t = t .. viewers.ta("\n* <i>Count of functions in all libraries</i>", nallfunc)
t = t .. viewers.ta("<i>functions to doc</i>", lua_table.level_count(sorted_to_autodoc) )
t = t .. viewers.ta("<i>functions with doc</i>", nalldoc)
t = t .. viewers.ta("\n* <b>Count of sorted functions: </b>", lua_table.level_count(sorted_functions) )
t = t .. viewers.ta("\n* <b>List of functions with uppercase in funcname</b>: ", UPPER )
activity.sorted_functions = sorted_functions
activity.sorted_to_autodoc = sorted_to_autodoc
return t
end -- function activity.central_functions_report(t)
-- Last
 
function activity.central_libraries_autodoc(t, sorted_functions) -- Formats a basic documentation for sorted functions.
local t = t or "\n* <b>activity.central_libraries_autodoc(t)</b> Formats a basic documentation for sorted functions."
t = t .. "\n*"
local sorted_functions = sorted_functions or activity.sorted_functions
local one_autodoc = "<br>[[= = = %1 = = =]]<br> "
for i, lib_func in pairs(activity.sorted_to_autodoc) do -- form one_autodoc
t = t .. viewers.form9user(one_autodoc, lib_func.libname_funcname)
end
t = string.gsub(tostring(t), "= = =", "===")
t = string.gsub(tostring(t), "= =", "==")
return t
end -- function activity.central_libraries_autodoc(t, sorted_functions)
 
activity.report_subtasks_list = { -- List of subtasks to report. See "NOW",
-- Begin later below
--loadData
-- DUPLICATE NOWNOW, in change. toDoc
{ "---", "---", "---", "---", "---", "DUPLICATE NOW, in change", },
{ "20180721", "20180729", "NOW", "Rical", "S180721pj7", "Begin: search 7 Projects : MediaWikis wikidata wikipedia wikisource wikiquote meta test2 ?", },
{ "20180721", "20180729", "NOW", "Rical", "S180721lg7", "Begin: search 7 Languages : br, de, en, es, fr, hu, vi ?", },
{ "20180708", "20180729", "NOW", "Rical", "S180708bc7", "Begin: Rical invite 7 Lua-coders : Tpt, Zolo, Od1n, Julien1978, Daehan, VIGNERON ?", },
{ "20180722", "20180722", "NOW", "Rical", "S180722ust", "Module:Centralizer update subtasks list", },
--
-- Automatic shift of below "todo" subtasks.
{ "---", "---", "---", "---", "---", "Automatic shift of below todo subtasks", },
{ "20180108", "20180109", "todo", "Rical", "S180108wtd", "Restore old function datas.wikidata_time_details()", },
{ "20180108", "20180109", "todo", "Rical", "S180108blg", "For each wikidata search the better lang in userlang, userlang2, pagelang, contentlang", },
{ "20180106", "20180108", "todo", "Rical", "S180106arg", "new Object:args form known arguments to import, complete from datas and finalize", },
{ "20171019", "20171022", "todo", "Rical", "S171019ime", "include Lua modules in extensions like Wikibase/client/includes/DataAccess/Scribunto/mw.wikibase.lua, see phabtask T41610.", },
{ "20171015", "20171018", "todo", "Rical", "S171015trk", "add a method tracker:trk(self, ...) from tracker.add(opt, ...). see Lua_reference_manual#Function_declaration_statements", }, --
{ "20171001", "20171002", "todo", "Rical", "S170801cvG", "put MW versions and Central versions in _G and CentralData", },
{ "20171001", "20171002", "todo", "Rical", "S170801tcG", "put tests_groups versions in _G and CentralData", },
{ "20171001", "20171002", "todo", "Rical", "S170801cCD", "Create Special:PageData/CentralData (change from MW only)", },
{ "20171001", "20171002", "todo", "Rical", "S170801cCD", "Create MediaWiki:Scribunto/CentralData (change from admin only)", },
{ "20171001", "20171002", "todo", "Rical", "S170801cCD", "Create Central/PageData/CentralData (change from any user)", },
{ "20170915", "20170917", "todo", "Rical", "S170915ajb", "phabtask extend tests_groups.subdiffs() to lua_table.trees.all_jobs", },
{ "20170910", "20170914", "todo", "Rical", "S170910wpw", "Use: wikidata = { property = 'P84',... syntax like {{Wikidata}} for wikidata", },
-- see 4.2 Paramètre "wikidata" https://fr.wikipedia.org/wiki/Aide:Infobox_en_Lua#Param.C3.A8tre_.22wikidata.22
{ "20170910", "20170914", "todo", "Rical", "S170910bob", "Create a button object for boxes, like drop_box with: n, states, shapes, keywords, colors", },
{ "20170910", "20170914", "todo", "Rical", "S170910ssb", "Restructure for a soft structure in viewers.boxviews.form()", },
{ "20170906", "20170909", "todo", "Rical", "S170906tbe", "restructure for a Table of Box Elements in viewers.boxviews.form()", },
{ "20170828", "20170905", "todo", "Rical", "S170828dut", "delete unused tracker in _G : ARGS, IAMO, MAMO, tests_groups", },
{ "20170828", "20170905", "todo", "Rical", "S170820vtg", "try graphics in viewers.try_graph() -- see Macron", },
{ "20170828", "20170905", "todo", "Rical", "S170723obv", "make object viewers.boxviews.form(cssView)", },
{ "20170816", "20170823", "todo", "Rical", "S170901adl", "automatize langs.dummy_languages() using isSupportedLanguage(xx)", },
{ "20170816", "20170823", "todo", "Rical", "S170901sas", "debug modes.similar_args_search() Test des mots proches similaires", },
{ "20170816", "20170823", "todo", "Rical", "S170901mMW", "use Special:PageData CentralData T163923+T168726 in activity.MW_Versions_report()", },
{ "20170816", "20170823", "todo", "Rical", "S170729eli", "easy https://en.wikisource.org/wiki/Template:Lorem_ipsum", },
{ "20170816", "20170823", "todo", "Rical", "S170728acr", "debug versions.anti_crash() + tests", },
{ "20170816", "20170823", "todo", "Rical", "S170801uPD", "automatize PageData change in datas.update_PageData(t) for activity.MW_Versions_report()", },
{ "20170811", "20170815", "todo", "Rical", "S170716tac", "langs.abnormal_char_in_text() fails", },
{ "20170811", "20170815", "todo", "Rical", "S170705dbf", "Debug all functions tests in Dropboxes", },
{ "20170811", "20170815", "todo", "Rical", "S170615css", "use Conventional css parameters cssview in edit, content, drop_box, infobox, tableview ... ", },
{ "20170811", "20170815", "todo", "Rical", "S170720diw", "Enhance datas.get_item() from 20170403 ModuleCentral 6a clean display.lua", },
{ "20170811", "20170815", "todo", "Rical", "S170718FLI", "Propose Firstname, Lastname and Initial in wikidata", },
{ "20170811", "20170815", "todo", "Rical", "S170718FLI", "lua_table.4_diffs(A, B) Detect 4 first diffs of tables A/B and B/A, in-deep/in-next with limits", },
{ "20170811", "20170815", "todo", "Rical", "S170811uMD", "After 'Begin' fully use Module:drop_box from es.wikipedia.org/wiki/Módulo:Lista_plegable", },
-- S170718FLI : in https://www.wikidata.org/wiki/Wikidata:Property_proposal/Person#Noms().", },
-- S170718FLI : T53657 is Close : Firstname and Lastname properties
-- S170718FLI : T53657 to re Open : Firstname and Lastname properties. Follow Aklapper comment on Jul 19 2013, 12:51
{ "20170810", "20170811", "todo", "Rical", "S180311a2c", "if _i_cat or _u_cat add 2 categories: detailed and ( internal or usage )", },
-- if viewers.is_in("_i_cat", key) then key = "versions_with_internal_error" -- = "Module with internal error",
-- elseif viewers.is_in("_u_cat", key) then key = "versions_with_usage_error" -- = "Module with usage error",
{ "20170810", "20170811", "todo", "Rical", "S180810lts", "continue function lua_table.to_sort(tab, ...) To convert any table in sequence, and sort it.", },
{ "20180410", "20180414", "todo", "Rical", "S180410ilp", "After 'Begin' T20180621 Enough inform Central modules for jumps to lang.project URI.", },
{ "20180410", "20180414", "todo", "Rical", "S180410alp", "After 'Begin' T20180621 Automatic adapt Central modules for lang.project URI.", },
{ "20180407", "20180410", "todo", "Rical", "S180407rlv", "After 'Begin' Fully report modules and libraries versions.", },
{ "20180407", "20180409", "todo", "Rical", "S180407ruc", "After 'Begin' report all viewers.usual_color(t)", },
{ "20170810", "20170811", "todo", "Rical", "S180306vdf", "debug function versions.deprecated_function() nil table : mask it on 20180306", },
{ "20170810", "20170811", "todo", "Rical", "S170617rpd", "debug modes.recursive_normal() test", },
{ "20170810", "20170811", "todo", "Rical", "S170630alr", "debug antiLoop() modules libraries runTestsCases limit counts init time tables", },
{ "20170810", "20170811", "todo", "Rical", "S170614tva", "Use tableview.new() for all tables, search .table_end()", }, --
{ "20170810", "20170811", "todo", "Rical", "S170813lll", "debug lua_table.level_list(mw) for all uses", }, --
{ "20170808", "20170810", "todo", "Rical", "S170707icc", "Begin: begin to integrate changes from other coders", },
{ "20170808", "20170810", "todo", "Rical", "S170707icc", "Begin: update important Phabricator tasks to activate their availability", },
-- Inform after 'Create Begin'
{ "20170805", "20170807", "todo", "Rical", "S170702cJP", "Begin: Lua coders Utilisateur:JackPotte [[:fr:Utilisateur:JackPotte|JackPotte fr de es en]]", },
{ "20170805", "20170807", "todo", "Rical", "S170702wvm", "Begin: announce Meet coders throught Wikis video meeting France SWEL-fr https://meet.jit.si/swel-fr", },
{ "20170805", "20170807", "todo", "Rical", "S170702atr", "Begin: Ask translations in meta [https://meta.wikimedia.org/wiki/Translation_requests Translation_requests]", },
{ "20170805", "20170807", "todo", "Rical", "S170604iTN", "Begin: inform [https://meta.wikimedia.org/wiki/Tech/News#contribute Tech News] about central modules begin phase", },
-- S170604iTN : Tech/News#contribute : central, begin to use, efficiency, ask lua coders ?
-- Debug to support Create Begin's group
-- Automatic shift of behind "todo" subtasks.
-- Begin later behind
--
-- NOWNOW, in change. toDoc
{ "---", "---", "---", "---", "---", "NOW, in change", },
{ "20180721", "20180729", "NOW", "Rical", "S180721pj7", "Begin: search 7 Projects : MediaWikis wikidata wikipedia wikisource wikiquote meta test2 ?", },
{ "20180721", "20180729", "NOW", "Rical", "S180721lg7", "Begin: search 7 Languages : br, de, en, es, fr, hu, vi ?", },
{ "20180708", "20180729", "NOW", "Rical", "S180708bc7", "Begin: Rical invite 7 Lua-coders : Tpt, Zolo, Od1n, Julien1978, Daehan, VIGNERON ?", },
{ "20180722", "20180722", "NOW", "Rical", "S180722ust", "Module:Centralizer update subtasks list", },
-- Already done
{ "---", "~sort~", "---", "---", "---", "Already done", },
{ "20180708", "20180715", "done", "Rical", "S180708Ric", "Begin: Rical start with Auteur2Tpt ... until 7 Lua-coders, in 7 projects, in 7 Languages.", },
{ "20180708", "20180708", "done", "Rical", "S170826ust", "Module:Centralizer update subtasks list", },
{ "20180701", "20180714", "done", "Rical", "S180718Ric", "Begin: Rical continue with Auteur2Tpt to complete translations.", },
{ "20180625", "20180625", "done", "Rical", "S180625ALC", "Begin: Ask Lua coders: Zolo, Zebulon84, Hlm Z., Cantons-de-l'Est, Thibaut120094, Daehan", },
{ "20180625", "20180625", "done", "Rical", "S180621new", "For 'Begin' complete translations in Module:Centralizer/I18N.lua.", },
{ "20180625", "20180625", "done", "Rical", "S180625btu", "Begin: Create phab task T198107 Begin to use central modules", },
{ "20180624", "20180625", "done", "Rical", "S180624cMA", "Begin: for Rical : convert Module:Auteur2 to central, from Tpt", },
{ "20170824", "20170825", "done", "Rical", "S170620dcm", "Begin: announce and description in Discussion MediaWiki:Scribunto/Central manual", },
{ "20180621", "20180625", "done", "Rical", "S180621new", "For 'Begin' document Module:Centralizer/I18N.lua. Do not really help.", },
{ "20180619", "20180619", "done", "Rical", "S180619icm", "For 'Begin' Install the Central-s-fr last version in s-br s-de w-es s-es s-fr s-es w-hu w-vi", },
{ "20180619", "20180619", "done", "Rical", "S180619tMI", "For 'Begin' group all translations in Module:Centralizer/I18N.lua", },
{ "20170727", "20170612", "done", "Rical", "S171210arg", "Avoid upercase in near all fucntions names", },
{ "20170724", "20170610", "done", "Rical", "S180128lit", "Show details link to internal error cat ending _i_cat, _u_cat in events.add_record()", },
{ "20180607", "20180608", "done", "Rical", "S180607uts", "After 'Begin' Update all important tasks to support central modules", },
{ "20180601", "20180606", "done", "Rical", "S180617upt", "For 'Begin' Update all phabtask in activity.phabricator_tasks_Group{}", },
{ "20180601", "20180604", "done", "Rical", "S180617ufc", "For 'Begin' update Central-s-fr functions comments from Central manual.", },
{ "20180604", "20180604", "done", "Rical", "S180604crm", "For 'Begin' T20180604 Update Central modules reference manual. DONE", },
{ "20180518", "20180518", "done", "Rical", "S180518ust", "Module:Centralizer update subtasks list", },
{ "20180421", "20180421", "done", "Rical", "S180421CGL", "For 'Begin' renew CentralGuideline from CentralModules and CentralManual", },
{ "20180419", "20180420", "done", "Rical", "S180419aCv", "add Central version in running_times", },
{ "20180414", "20180414", "done", "Rical", "S180414ust", "Module:Centralizer update subtasks list", },
{ "20180413", "20180416", "done", "Rical", "S180413uia", "Update modes.get_args()=args_known +source +template +import +... with priorities", },
{ "---", "---", "---", "---", "---", "STOP the display of this table", },
{ "20170729", "20170729", "done", "STOP", STOP = "STOP", }, -- STOP the display of this table
{ "20180329", "20180407", "done", "Rical", "S180329uma", "For 'Begin' Update ModuleAuthor3.lua.", },
{ "20180322", "20180323", "done", "Rical", "S180322crm", "For 'Begin' Update Stability in Central modules reference manual", },
{ "20180307", "20180326", "done", "Rical", "S180307clr", "For 'Begin' debug function activity.central_functions_report look OK", },
{ "20180317", "20180317", "done", "Rical", "S180317ttD", "transfer activity.central_libraries_autodoc() to Module:Draft.lua", },
{ "20180313", "20180316", "done", "Rical", "S180313clr", "For 'Begin' Update actual functions for documentations in activity.central_functions_report", },
{ "20180307", "20180308", "done", "Rical", "S180307vmr", "For 'Begin' small debug function versions.versions_management_report() ok else val", },
{ "20180306", "20180306", "done", "Rical", "S180303zzz", "For 'Begin' small debug function viewers.save_restore_balance_report(t) nil", },
{ "20180304", "20180305", "done", "Rical", "S180303bas", "For 'Begin' small debug function versions.bind_all_sub_modules() nil", },
{ "20180304", "20180305", "done", "Rical", "S180303sas", "For 'Begin' small debug function modes.similar_args_search() no known args", },
{ "20180304", "20180304", "done", "Rical", "S180128ust", "Module:Centralizer update subtasks list", },
{ "20180303", "20180304", "done", "Rical", "S180303dgi", "For 'Begin' small debug function datas.get_item() Test de Wikidata accès arbitraire", },
{ "20180303", "20180304", "done", "Rical", "S180303rom", "For 'Begin' small debug function mathroman.roman2int() + mathroman.int2roman()", },
{ "20180303", "20180304", "done", "Rical", "S180303akr", "For 'Begin' small debug function modes.args_known_report(t) empty table", },
{ "20180128", "20180128", "done", "Rical", "S180128ust", "Module:Centralizer update subtasks list", },
{ "20180122", "20180122", "done", "Rical", "S180122mka", "Report of main known args in modes.args_known_report(t)", },
{ "20180111", "20180111", "done", "Rical", "S180111pfs", "Made a generic object obji18n. to support others. need phabtask T135845", },
{ "20171209", "20171209", "done", "Rical", "S171209ust", "Module:Centralizer update subtasks list", },
{ "20171205", "20171208", "done", "Rical", "S171205dtt", "Debug translations in langs.trans9vars()", },
{ "20171130", "20171209", "done", "Rical", "S171130esr", "check equilibrium save/restore of configs in viewers.save_restore_balance_report()", },
{ "20171128", "20171129", "done", "Rical", "S171128laf", "For doc central_functions_report().", },
{ "20171127", "20171128", "done", "Rical", "S171127dip", "debug init_content_page_user_lang().", },
{ "20171126", "20171127", "done", "Rical", "S171126ecl", "list available all_errors_list() and all_categories_list()", },
{ "20171120", "20171125", "done", "Rical", "S171120", "missing and changing infos in langs.missing_translations().", },
{ "20171111", "20171111", "done", "Rical", "S170918ust", "Module:Centralizer update subtasks list", },
{ "20171110", "20171111", "done", "Rical", "S170620csc", "make versions.central_library() for easier descriptions of libraries and modules.", },
{ "20171104", "20171105", "done", "Rical", "S170620csc", "For 'Begin' count Lua-coders, langs, projects in function lua_table.level_list().", },
{ "20171102", "20171102", "done", "Rical", "S170918ust", "ModuleCentral size 20171102=1413 k, 20170803=1340 k, 20170501=1226 k, 20170204=1016 k, 1.5 k/j", },
{ "20171026", "20171103", "done", "Rical", "S171026mdl", "For 'Begin' record central_module_descriptor() in ModuleCentral-s-fr 5d activity.central_module_descriptor OK", },
{ "20171024", "20171025", "done", "Rical", "S170706s10", "For 'Begin' link to 7 wikis/langages in function activity.central_module_descriptor()", },
{ "20171024", "20171024", "done", "Rical", "S170918ust", "Module:Centralizer update subtasks list", },
{ "20171001", "20171024", "done", "Rical", "S170918dtr", "debug tests_groups.resultdiffs() in ModuleCentral-s-fr 5d resultdiffs near ok", },
{ "20170925", "20170928", "done", "Rical", "S170918uPD", "debug update_PageData() in ModuleCentral-s-fr 4c update_PageData ok 20170928-1639.pdf", },
{ "20170918", "20170918", "done", "Rical", "S170918ust", "Module:Centralizer update subtasks list", },
{ "20170902", "20170918", "done", "Rical", "S170902cnt", "Begin: improve stability of tests_groups in tests_groups.getTestProvider()", },
{ "20170906", "20170907", "done", "Rical", "S170907dcm", "For 'Begin' Update doc MediaWiki:Scribunto/Central modules", },
{ "20170903", "20170904", "done", "Rical", "S170903dif", "For tests_groups and stability, tests_groups.subdiffs() Report differences between 2 tables", },
{ "20170801", "20170902", "done", "Rical", "S170801rtc", "Begin: improve stability of tests_groups in tests_groups.recursive_tests()", },
{ "20170901", "20170902", "done", "Rical", "S170902crm", "For 'Begin' Update doc MediaWiki:Scribunto/Central modules reference manual", },
{ "20170822", "20170822", "done", "Rical", "S170706tcG", "first test of PageData in datas.update_PageData() Share DATAS between modules?", },
{ "20170821", "20170821", "done", "Rical", "S170821sty", "Short story of Central modules from modes on 20130125 to boxviews on 20170723", },
{ "20170819", "20170820", "done", "Rical", "S170820crm", "For 'Begin' Update doc MediaWiki:Scribunto/Central modules reference manual", },
{ "20170806", "20170808", "done", "Rical", "S170806ass", "Automatic shift of todo subtasks in activity.central_subtasks_report(t)", },
{ "20170801", "20170807", "done", "Rical", "S170820crm", "For 'Begin' Update doc MediaWiki:Scribunto/Central modules reference manual", },
{ "20170802", "20170804", "done", "Rical", "S170802mct", "Library langs : debug missing and changing_translations().", },
{ "20170801", "20170801", "done", "Rical", "S170711ust", "Module:Centralizer update subtasks list", },
{ "20170723", "20170724", "done", "Rical", "S170723vbv", "make an easy box builder viewers.boxviews.form(txt, css)", },
{ "20170723", "20170723", "done", "Rical", "S170711ust", "Module:Centralizer update subtasks list", },
{ "20170720", "20170720", "done", "Rical", "S170720t_G", "for months, var 't' to debug in versions.all_G_and_loaded_list() after line 4303", },
{ "20170718", "20170719", "done", "Rical", "S170703amo", "debug modes.import_arguments() in modes.import_args_mode_options()", },
{ "20170717", "20170717", "done", "Rical", "S170717iwi", "update and activate datas.get_item()", },
{ "20170703", "20170705", "done", "Rical", "S170703ust", "Module:Centralizer update subtasks list", },
{ "20170703", "20170704", "done", "Rical", "S170703wtA", "Module:Centralizer-s-fr 5c viewers.tracker.ARGS ok", },
{ "20170629", "20170703", "done", "Rical", "S170629alc", "debug add and list categories.", },
{ "20170629", "20170702", "done", "Rical", "S170701cpu", "debug langs.init_content_page_user_lang() import from modes.args_source.", },
{ "20170701", "20170701", "done", "Rical", "S170701ial", "debug langs.init_content_page_user_lang() activate languages.", },
{ "20170629", "20170629", "done", "Rical", "S170629mct", "debug events.all_categories_test() Test: Creation of categories in some languages.", },
{ "20170625", "20170629", "done", "Rical", "S170625ust", "ModuleCentral update subtasks", },
{ "20170626", "20170628", "done", "Rical", "S170626rev", "Rebuild events.add_new()", },
{ "20170628", "20170628", "done", "Rical", "S170626trk", "viewers.tracker = tracker -- Object for parametrable tracks.", },
{ "20170626", "20170626", "done", "Rical", "S170606rmn", "roman2int_tests+int2roman error form9usernil in function events.add_err()", },
{ "20170618", "20170625", "done", "Rical", "S170625ste", "lua_table.from_subnames_table() last sub-table from its sub-names.", },
{ "20170618", "20170625", "done", "Rical", "S170618ltc", "langs.translations_counts(t) limit counts", },
{ "20170625", "20170625", "done", "Rical", "S170625bx1", "simpler options from modes in form_result() box1 ok", },
{ "20170617", "20170617", "done", "Rical", "S170618slk", "sort langs keys search .i18n.es", },
} -- activity.report_subtasks_list = { -- List of subtasks to monitor.
 
-- See tasks in activity.phabricator_tasks_report() and sub-tasks in activity.central_subtasks_report(t)
function activity.central_subtasks_report(t) -- Reports the current state of subtasks defined by Lua-coders. See "NOW",
local memo = viewers.save_configs("activity.central_subtasks_report") -- Save global configuration before eventual changes.
local t = t or '\n* <b>activity.central_subtasks_report()</b> Report the current state of subtasks. Automaticaly shifts tasks to do later, See "NOW".'
local tab_view = { -- Group datas and options for a table view with lines and columns.
test_group = activity.report_subtasks_list, -- List of subtasks to monitor.
title_memo = "activity_report_subtasks_title", -- "activity.central_subtasks_report(t) Report the current state of subtasks, See "NOW".",
headers = " start; end; state; user; sub id; bug description; duration ",
headers_class = "wikitable alternative center sortable",
-- track_on = true,
ccc = {}, -- To communicate and compute between cases
rowGroup = {},
}
local function tab_view_rough_shifter(tab_view) -- Monitor and shift tasks.
tab_view.ccc.now = os.date("%Y%m%d")
tab_view.ccc.now_days = activity.rough_date_days(tab_view.ccc.now)
local stop_min_days, delay_min = 999999, 999999, 999999
tab_view.ccc.shift_days = 999999
tab_view.ccc.stop_min = "99999999"
for i, bug in pairs(tab_view.test_group) do -- First: Compute how to shift subtasks.
bug.track = ""
local now = tab_view.ccc.now
tab_view.ccc.now_days = activity.rough_date_days(tab_view.ccc.now)
bug.start = bug[1]
bug.stop = bug[2]
bug.plan = bug[3]
local y2 = tonumber(string.sub(bug.stop,1,4))
local m2 = tonumber(string.sub(bug.stop,5,6))
local d2 = tonumber(string.sub(bug.stop,7,8))
local date_days, y2, m2, d2, years, months, days = activity.rough_date_days(bug.stop) -- Rough date days of a time stamp, from 0000-01-01.
bug.start_days = activity.rough_date_days(bug.start)
bug.stop_days = activity.rough_date_days(bug.stop)
bug.duration = bug.stop_days - bug.start_days
if (type(bug.start) == "string") and (type(bug.stop) == "string") and (bug.plan == "todo") then
if bug.stop < tab_view.ccc.stop_min then
tab_view.ccc.stop_min = bug.stop
tab_view.ccc.stop_min_days = activity.rough_date_days(tab_view.ccc.stop_min)
if tab_view.ccc.stop_min_days < tab_view.ccc.now_days then tab_view.ccc.stop_min_days = tab_view.ccc.now_days end
tab_view.ccc.shift_days = (tab_view.ccc.stop_min_days + 2) - bug.stop_days
end
bug.track = bug.track.."<br/>"..viewers.ta("now", now)..viewers.ta("y2", y2)..viewers.ta("m2", m2)..viewers.ta("d2", d2)
bug.track = bug.track.."<br/>"..viewers.ta("stop", bug.stop)..viewers.ta("delay", bug.duration)..viewers.ta("date_days", date_days)
end
end
for i, bug in pairs(tab_view.test_group) do -- After: really shift subtasks.
bug.start = bug[1]
bug.stop = bug[2]
bug.plan = bug[3]
bug.start = bug.start --.. "+3 " .. bug.start
if bug.plan == "todo" then -- Only for todo tasks
bug.start_days = activity.rough_date_days(bug.start)
bug.start = activity.rough_days_timestamp(bug.start_days + tab_view.ccc.shift_days) -- Rough time stamp from date days, like "20170806".
bug.stop_days = activity.rough_date_days(bug.stop)
bug.stop = activity.rough_days_timestamp(bug.stop_days + tab_view.ccc.shift_days) -- Rough time stamp from date days, like "20170806".
end
end
end -- function tab_view_rough_shifter(tab_view) -- Shift todo tasks.
function tab_view.form_one_case(bug, tab_view) -- Convert a case from test_group to rowGroup.
bug.start = bug.start or bug[1] or "---"
bug.stop = bug.stop or bug[2] or "---"
bug.plan = bug.plan or bug[3] or "---"
if bug.plan == "todo" then -- Display one row whole in bold.
bug[6] = bug[6] -- .. bug.track
end
if bug.plan == "NOW" then -- Display one row whole in bold.
bug.start = "<b>" .. bug.start .. "</b>"
bug.stop = "<b>" .. bug.stop .. "</b>"
bug.plan = "<b>" .. bug.plan .. "</b>"
bug[4] = "<b>" .. bug[4] .. "</b>"
bug[5] = "<b>" .. bug[5] .. "</b>"
bug[6] = "<b>" .. bug[6] .. "</b>"
bug.duration = "<b>" .. bug.duration .. "</b>"
end
return { bug.start, bug.stop, bug.plan, bug[4], bug[5], bug[6], bug.duration, }
end
tab_view_rough_shifter(tab_view) -- Monitor and shift tasks.
t = t .. tableview.new(tab_view) -- Formats a table view with lines and columns.
viewers.restore_configs(memo, "activity.central_subtasks_report") -- Restore global configurations after eventual changes.
return t
end -- t = function activity.central_subtasks_report(t) -- Report the current state of subtasks, See "NOW".
 
activity.phabricator_tasks_Group = { -- toDoc
-- Importance: Important
{ 102, "Important", "20180412", "T185557", 0, "Open", "Create the easy function mw.wikibase.property('P21', 'Q8023', 'en')", },
--[[ new phabtask T185557 : (property, QITEM, language)
-- on 20180123 : Rical Description :
This function gets the sought property from any available item and language.
Examples:
local prop1 = mw.wikibase.property('P21') -- Simplest use
local prop2 = mw.wikibase.property('lastname') -- Named pseudo property
local prop3 = mw.wikibase.property('label', 'Q', { 'user', 'page', 'content', 'en', 'de', 'es', } ) -- Default values
local prop4 = mw.wikibase.property('description', 'Nelson Mandela', { 'user', 'fr', } ) -- other case
--]]
{ 106, "Important", "20170703", "T20170703", 0, "ToCreate", "Standardize content, page and user langages availability", "Standardize languages", },
-- T20170703 : Rename T68051 : "Central modules need the user language to display errors and category names"
-- T20170703 : Standardize content, page and user langages availability
-- T20170703 : Content, page and user langages are not available nor defined in the same ways for scribunto modules.
-- T20170703 : That complicate modules which use them. Similar ways could enhance efficiency and reduce the development tasks.
{ 110, "Important", "20170325", "T20170325", 0, "ToCreate", "Centralize and share central datas about central modules", "share central datas", },
-- T20170325 : Centralize datas as MediaWiki versions installations in each lang-project, uses of central modules (helpers, projects, languages ...).
{ 114, "Important", "20180626", "T135845", 0, "Assigned", "Convert any module as central or centralisable", "Convert as central", },
{ 116, "Important", "20160822", "T53660", 0, "Open", "Detect the edit state for modules which help users and helpers", "edit state", },
{ 118, "Important", "20180620", "T4085", 0, "Open", "Add a {{USERLANGUAGE}}/{{USERLANG}} magic word", "USERLANGUAGE", },
-- T173207: Implement Lua alternative to {{int:Lang}}.
{ 119, "Important", "20180629", "T107119", 0, "Open", "Provide a Lua method mw.loadTemplateData()", }, -- See PageData
{ 120, "Important", "20170613", "T163923", 0, "Resolved", "Create Special:PageData as a canonical entry point for machine readable page data.", "Special:PageData done", },
-- T163923: Permit at modules to change PageData (for stat, modules versions, mw versions...).
{ 122, "Important", "20180606", "T149532", 0, "Resolved", "Why Multi-Content-Revisions? Use cases and requirements.", "Special:PageData done", },
{ 124, "Important", "20180530", "T168726", 0, "Open", "Create syntax documentation page for Special:PageData.", "Special:PageData doc", },
{ 126, "Important", "20170907", "T68051", 1, "Open", "Central modules need the user language to display errors and category names", "user language for errors", },
{ 132, "Important", "20180603", "T85461", 0, "Resolved", "Lua error: too many language codes requested", "too many language", },
-- T85461 https://meta.wikimedia.org/wiki/Module:Assemble_multilingual_message
-- T85461 https://meta.wikimedia.org/w/index.php?title=Module:Assemble_multilingual_message&action=edit#mw-ce-l46
{ 134, "Important", "20170309", "T159322", 0, "Open", "Central categories and alerts for central modules", "Central categories/alerts", },
-- T159322 : Does the community agree to implement central categories and alerts for central modules?
-- T159322 : This enhances the efficiency of the detection and the correction of errors, in some ways:
{ 136, "Important", "20160522", "T85419", 0, "Open", "User groups should be exposed to Scribunto", "user groups", },
-- T85419: to adapt errors and warning for administrators or modules coders
{ 138, "Important", "20180413", "T142093", 0, "Open", "Decide how to do usage tracking for strings_c used to lookup entities (page titles, external ids, …)", "how to link entities/titles", },
{ 140, "Important", "20170211", "T20170211", 1, "ToCreate", "In mw.language.fetchLanguageNames( 'fr' ) some languages names are not in French", "French languages names", },
-- T20161220 : ToDo: test: local getContentLanguage = mw.language.getContentLanguage().code -- default content_lang
{ 146, "Important", "20170921", "T176362", 0, "Declined", "Implement ClassNameTests in Scribunto to enhance central modules stability", },
-- T176362 : phabtask : Implement getTestProvider in Scribunto to enhance central modules stability
-- T176362 : phabtask : proposed functions in MediaWiki:
-- T176362 : phabtask : mw.getTestProvider(mw_tests, nmaxi) -- To initialise, to limit all tests in time and to limit cases to nmaxi.
-- T176362 : phabtask : mw.ClassNameCase(case, n), used inside mw.getTestProvider() to run each test case of number 1 to nmaxi.
-- T176362 : phabtask : The case object contains fields: count, OK="OK"..., n, name, type, args{}, expect{}, NameTest{}, func(), provide(), run()
-- T176362 : phabtask : Functions used in central modules: tests_groups.getTestProvider(), .init(), .gettestsgroups(), .getcases(), .subdiffs(), .normalcase(case), viewers.form9en()
-- T176362 : phabtask : In the tests_groups library, tests cases are in recursive groups of groups of cases. Groups levels: main module, sub modules or libraries, functions and their tests cases.
{ 148, "Important", "20170121", "T122752", 1, "Open", "#invoke do not record the main module in package.loaded", "invoke# main not loaded", },
-- T122752: 20161202 18:25 See example https://fr.wikisource.org/wiki/Module:Phab.TestpackG : detect "in " "_G" or package.loaded
-- T122752: 20160102 22:46 See example https://fr.wikisource.org/wiki/Module:TestRequire
-- T122752: To locate and to debug the bug T122752 in time, Rical lists here the versions of fr.wikisource.org/wiki/Module:ControlArgs1
-- T122752: Oldest research of "Replace the missing of record of the module by" : ModuleControlArgs 6 tools...lua 2016-01-16
-- T122752: (actu | diff) 2015-11-25T11:43:11‎ Rical (discussion | contributions | bloquer)‎ . . (261 314 octets) (-3 519)‎ . . (The versions management seems OK) (annuler)
-- T122752: (actu | diff) 2015-11-28T09:55:37‎ Rical (discussion | contributions | bloquer)‎ . . (267 472 octets) (+5 809)‎ . . (find_main_module)
-- T122752: (actu | diff) 2015-12-01T14:18:22‎ Rical (discussion | contributions | bloquer)‎ . . (268 956 octets) (+1 614)‎ . . (find_main_module OK ?)
-- T122752: (actu | diff) 2016-01-18T02:09:45‎ Rical (discussion | contributions | bloquer)‎ . . (319 599 octets) (+10 183)‎ . . (translate library.i18n first)
-- T122752: 2016-01-02 phabricator: T122752 Rical created this task. Sat, Jan 2, 2016-01-02 23:08
{ 156, "Important", "20180508", "T63958", 0, "Assigned", "Use existing $dateFormats to format dates on Wikidata", "$dateFormats on Wikidata", },
{ 160, "Important", "20170521", "T67687", 0, "Resolved", "mw.load_data can be used to pass data between #invoke's by reading frame arguments", },
--
-- Importance: Central
{ 202, "Central", "20180625", "T198107", 0, "Open", "Begin to use central modules in 7 wikis S180625btu", "Begin use central", },
{ 206, "Central", "20171106", "T20171106", 0, "ToCreate", "Lua-coders could better report bugs with recent MediaWiki versions for each wiki", "wikis MediaWiki_version", },
{ 210, "Central", "20180326", "T121470", 0, "Open", "Central Global Repository for Templates, Lua modules, and Gadgets", "central repository", },
{ 214, "Central", "20180321", "T52329", 0, "Stalled", "We need a common repository for Scribunto modules and templates", "common repository", },
{ 218, "Central", "20180312", "T41610", 0, "Open", "Scribunto should support global module invocations", "global invocations", },
-- T41610: subscriber: kaldari 2017-05-20, 16:03
-- T41610: You can include Lua modules in extensions and then register them with Scribunto as global modules.
-- T41610: Wikibase, for example, includes 2 Lua modules:
-- T41610: Wikibase/client/includes/DataAccess/Scribunto/mw.wikibase.entity.lua
-- T41610: Wikibase/client/includes/DataAccess/Scribunto/mw.wikibase.lua
{ 224, "Central", "20170301", "T20170301", 0, "ToCreate", "Phabricator tasks states for easier versions management of modules", "Phabricator tasks states", },
-- datas to get for each query: Task number, title, state, priority, Authored By and date, Last event date, number of subscribers, Assigned.
{ 228, "Central", "20170225", "T20170225", 0, "ToCreate", "? Report MediaWiki changes for the versions management, and use {{subst:}}", "MediaWiki changes", },
-- T20170225: The gerrit team needs the date of a bug and the dates of mw install in each wiki to debug mw.
-- T20170225: We could detect, record and report all date-time changes of MediaWiki, for some weeks.
-- T20170225: We could use {{subst:}} in 2 ways. See https://www.MediaWiki.org/wiki/Manual:Substitution
-- T20170225: duplicate of T121470: Central Global Repository for Templates, Lua modules, and Gadgets.
{ 230, "Central", "20170314", "T1238", 0, "Close", "Central Code Repository for code used on wikis (Templates, Lua modules, Gadgets)", "Code Repository", },
--
-- Importance: Other
{ 302, "Other", "20180320", "T147618", 0, "Open", "Localize one or more major WMF software products related to new editor retention to hu.wikipedia", "Localize new editor retention", },
{ 304, "Other", "20180320", "T132308", 0, "Open", "Internationalise citoid dates", "Deal non standard dates", },
{ 306, "Other", "20180320", "T142906", 1, "Close", "Data access in user language doesn't obey the uselang get parameter", "User language not OK", },
--[[ T142906 Data access in user language do not obey the uselang get parameter / Apparently
We use the former as an optimization in
Scribunto_LuaWikibaseLibrary::getLanguage and
Scribunto_LuaWikibaseEntityLibrary::getLanguage to only split the parser cache when actually needed. --]]
{ 308, "Other", "20170427", "T104109", 0, "Close", "No syntax highlight for large JavaScript/CSS/Lua/API pages", "highlight for large Lua", },
--[[ T104109: Have you the same bug?
Where could this effect coming from?
- My user:vector.css or common.css? But I have them only in fr.wikisource.org and not in vi.wikipedia.org
- A step to prepare T121470 Central Global Repository?
- A step to prepare T156048 syntax highlighting?
- A change in my Module:Centralizer itself, which formats many viewers, always inside <div>...</div> ? But I edit with the edit-panel first, up in the page, and the result of the module below, later. Also these <div> tags are, in the page, in other tags which protect them to interfere.
- A mix of these origins?
Small or large modules edit panels lost their syntax highlighting and line numbers.
Tech News: 2017-15 : replacement of HTML_Tidy, Extension:ParserMigration, see https://meta.wikimedia.org/wiki/Tech/News/2017/15
T104109 --]]
{ 310, "Other", "20170427", "T162877", 0, "Close", "CodeEditor default changed if you have never used the toggle", "CodeEditor default if never", },
{ 312, "Other", "20170427", "T161875", 0, "Close", "CodeEditor is always enabled when starting an edit on a page containing code", "CodeEditor enabled on code", },
-- T161875: Actual: It is enabled, though mw.user.options.get('usecodeeditor') correctly gives 0.
{ 314, "Other", "20160520", "T85412", 0, "Open", "The formatPropertyValues needs an option to format data from date-time, angle or geographic coordinates", "format date-time", },
{ 316, "Other", "20170517", "T156048", 0, "Open", "Add syntax highlighting to wiki diff of source code pages (like Gerrit)", "syntax highlighting", },
{ 318, "Other", "20170313", "T107119", 0, "Open", "Provide a Lua method mw.loadTemplateData()", "loadTemplateData", },
{ 320, "Other", "20170524", "T166202", 0, "Open", "Strings defined as long comments give a Lua modules syntax error", "Strings as comments error", },
--
-- Other, ToCreate or not
{ 321, "Other", "20170213", "T20170213", 0, "ToCreate", "Some languages have not French names in French language", "languages in stranger names", },
{ 322, "Other", "20151215", "T20151215", 0, "ToCreate", "In some cases the box of the drop_box is not displayed", "drop_box not displayed", },
-- T20151215: .. "\n------ " -- This code interact with drop_box and debug the task T20151215 2016-11-13 17:57.
-- T20151215: if there is "\n------ " before editDocBox and then the editDocBox <div> is only a bar of 1 em hight, and its content is after the <div>. Rical 2016-10-24 08:15.
{ 326, "Other", "20160616", "T20160616", 0, "ToCreate", "? Add module and library types in scribunto ?", "module and library types?", },
-- T20160616: get.is_library = ( true ) -- true if the object is a library
{ 328, "Other", "20171007", "T155624", 0, "Open", "Special:Version not showing SHA info for MediaWiki version on fr.wikisource", "MediaWiki version?", },
-- UTC-20170407-20:21 : reported in T155624 Special:Version not showing SHA info for MediaWiki version on fr.wikisource
--
-- Importance: Obsolete: Do not create, these functions come from mw... libraries.
{ 428, "Obsolete", "20161022", "T20161022", 0, "ToCreate", "? Scribunto functions are out of package.loaded", "Lua functions out of package.loaded", },
-- T20161022: -- Found in Lua_reference_manual but not in Module:Centralizer-s-fr :
-- T20161022: -- 2016-10-22 15:45 : versions.all_G_and_loaded_list() : Variables in _G global space without libraries and modules in packageloaded. ,
-- xpcall = function , tostring = function , _VERSION = Lua 5.1 , unpack = function , require = function , pairs = function , next = function ,
-- assert = function , ipairs = function , rawequal = function , getmetatable = function , rawset = function , pcall = function , type = function ,
-- selector = function , rawget = function , tonumber = function , error = function , setmetatable = function
{ 430, "Obsolete", "20170324", "T133498", 1, "Declined", "Detect and extend known title <-> entity links in a semi-automatic way", "semi-automatic wikidata QITEM", },
{ 432, "Obsolete", "20161128", "T151715", 0, "Invalid", 'string.gsub( s, "%%1", repl) fails as "invalid capture index"', 'string.gsub(s,"%%1",r) fails', },
{ 434, "Obsolete", "20170110", "T154769", 0, "Invalid", 'When "Erreur Lua : attempt to call a string value", where?', "Error Lua call a string where?", },
-- T154769: Rical 2017-01-08 My main mistake was to write xpcall() where pcall() is right.
-- T154769: Tests are there https://fr.wikisource.org/wiki/Module:Phab.T154769.Test
-- T154769: versions.anti_crash() preserve pages against residual errors which can crash pages.
{ 436, "Obsolete", "20170202", "T155898", 0, "Invalid", "Preview change from external local editors", "Change from local", },
-- T155898: OK, I will continue to search in JEdit plugins. Perhaps I will ask them an adapted solution.
{ 438, "Obsolete", "20160424", "T67507", 0, "Resolved", "It should be possible to get entity id from page title", "entity id from title", },
{ 440, "Obsolete", "20160524", "T119978", 0, "Invalid", "Get name and record-time of all modules to better manage their versions", "own module name", },
{ 442, "Obsolete", "20160813", "T75460", 0, "Resolved", "[Story] Make Lua functions default to the user's language on multilingual wikis", "multilingual wikis", },
} -- activity.phabricator_tasks_Group = {...}
 
function activity.phabricator_tasks_report(t, short) -- Reports the Phabricator tasks linked with central modules.
local memo = viewers.save_configs("activity.phabricator_tasks_report") -- Save global configuration before eventual changes.
local t = t or "\n* <b>activity.phabricator_tasks_report()</b> Monitor states of known phabricator tasks,"
t = t .. "\n* How to well report a task like in <b><big>[[phab:T149532#2878699|that task]]</big></b> :"
t = t .. "\n* 1) <b>What happens in brief</b> 2) <b>Type of activity</b> 3) <b>What is the problem</b>"
t = t .. "\n* 4) <b>Dedicated test case without ambiguity.</b> "
t = t .. "\n* 5) <b>Expected outcome</b> 6) <b>Proposed solution</b>"
t = t .. "\n* 7) <b>Where and when to use the proposed solution</b>"
t = t .. "\n* 8) <b>Who would benefit + your name.</b> 9) <b>Current status of the discussion</b>"
t = t .. "\n* 10) <b>Links</b> 11) <b>Your name linked to your MediaWiki URL, or profile elsewhere on the internet</b>"
local mwtitle = mw.title.getCurrentTitle()
local tasks_Group = activity.phabricator_tasks_Group
local sort_importance = "Obsolete;Other;Important;Central"
local split_importance = mw.text.split(sort_importance, ';') -- table of words
local sort_import, split_n, split_import = {}, 1, "Open"
for i, task in pairs(tasks_Group) do
task.iii = tostring(task[1]) ; task.importance = tostring(task[2])
task.lastdate = tostring(task[3]) ; task.phab = tostring(task[4])
task.detect = tostring(task[5]) ; task.status = tostring(task[6])
task.title = tostring(task[7]) ; task.shortext = tostring(task[8])
task.sort = "s"
for split_n, split_import in pairs(split_importance) do
if task.importance == split_import then -- to sort on importance then lastdate
task.sort = task.sort .. split_n .. task.lastdate .. task.phab
end
end
table.insert(sort_import, task)
end
table.sort(sort_import, function (a, b) return ( a.sort > b.sort ) end ) -- to sort on importance then lastdate
table.sort(sort_import, function (a, b) return ( a.lastdate > b.lastdate ) end ) -- to sort on importance then lastdate
local tab_view = { -- Group datas and options for a table view with lines and columns.
test_group = sort_import, -- = sorted activity.phabricator_tasks_Group,
title_memo = "activity_phabricator_tasks_title", -- "activity.phabricator_tasks_report() Monitor states of known phabricator tasks",
headers = "Importance; modified on; Task; Status; Title",
headers = "activity_phabricator_tasks_headers", -- "Importance; modified on; Task; Status; Title"
headers_class = "wikitable alternative center sortable",
rowGroup = {},
-- track_on = true,
}
function tab_view.form_one_case(task) -- Convert a task from test_group to rowGroup.
task.phab = "[[phab:" .. task.phab .. "|" .. task.phab .. "]]"
local usual = "discreet"
if viewers.is_in(task.status, "ToCreate, Declined, Invalid, ") then usual = "discreet"
elseif viewers.is_in(task.status, "Open, Assigned, Gerrit") then usual = "normal"
elseif viewers.is_in(task.status, "Resolved") then usual = "invoke"
else usual = "discreet" end -- All states : ToCreate, Open, Stalled, Assigned, Resolved, Declined, Invalid, Gerrit
task.title = viewers.usual_color(task.title, usual)
if task.detect == 1 then task.title = task.title .. " - ( detected state )" end
-- headers = "Importance; modified on; Task; Status; Title" -- "Importance, modifiée le, Tâche, Etat, Titre"
local importance = task.importance .. viewers.styles_color_discreet(" on " .. task.lastdate)
return { importance , task.phab, task.status, task.title, } -- task.sort, task.shortext }
end -- function tab_view.form_one_case(task)
t = t .. "<br>Used colors: "
.. viewers.ta("ToCreate, Declined, Invalid", viewers.usual_color("task to create or activate", "discreet") )
.. viewers.ta("Open, Assigned, Gerrit", viewers.usual_color("task in way to Resolved", "normal") )
.. viewers.ta("Resolved", viewers.usual_color("task already Resolved", "invoke") )
.. viewers.ta("Other", viewers.usual_color("other tasks or track objects", "discreet") )
t = t .. tableview.new(tab_view) -- Formats a table view with lines and columns.
viewers.restore_configs(memo, "activity.phabricator_tasks_report") -- Restore global configurations after eventual changes.
return t
end -- function activity.phabricator_tasks_report(t, short)
 
function activity.rough_delay_timestamps(stamp1, stamp2) -- Rough delay between two time stamps, like 31.
local delay, years, months, days = 0, 0, 0, 0
if (type(stamp1) ~= "string") or (type(stamp2) ~= "string") then return delay end
local y1 = tonumber(string.sub(stamp1,1,4))
local y2 = tonumber(string.sub(stamp2,1,4))
if y1 and y2 then years = y2 - y1 end
local m1 = tonumber(string.sub(stamp1,5,6))
local m2 = tonumber(string.sub(stamp2,5,6))
if m1 and m2 then months = m2 - m1 end
local d1 = tonumber(string.sub(stamp1,7,8))
local d2 = tonumber(string.sub(stamp2,7,8))
if d1 and d2 then days = d2 - d1 end
delay = years * 365 + months * 30 + days
return delay
end
 
function activity.rough_date_days(stamp1) -- Rough date days of a time stamp, like 736447.
local date_days, years, months, days = 0, 0, 0, 0
if (type(stamp1) ~= "string") then return delay end
local y1 = tonumber(string.sub(stamp1,1,4)) or 2001
local m1 = tonumber(string.sub(stamp1,5,6)) or 1
local d1 = tonumber(string.sub(stamp1,7,8)) or 1
years = y1 * 365
months = m1 * 30
days = d1
date_days = years + months + days
return date_days, y1, m1, d1, years, months, days
end
 
function activity.rough_days_timestamp(date_days) -- Rough time stamp from date days, like "20170806".
local timestamp = "no timestamp"
if (type(date_days) ~= "number") then return timestamp end
local year = math.floor(date_days / 365)
local day = date_days - (year * 365)
local month = math.floor(day / 30)
local day = day - (month * 30)
local yyyy = string.sub( ("0000" .. tostring(year) ), -4, -1)
local mm = string.sub( ("0000" .. tostring(month) ), -2, -1)
local dd = string.sub( ("0000" .. tostring(day) ), -2, -1)
timestamp = yyyy .. mm .. dd
return timestamp
end
 
function activity.MW_Versions_report(t) -- Reports versions of MediaWiki for 3 months.
local memo = viewers.save_configs("activity.MW_Versions_report") -- Save global configuration before eventual changes.
local t = t or "\n* <b>activity.MW_Versions_report()</b> Monitor MediaWiki versions."
-- t = t .. activity.MediaWiki_Versions_code(versions.MediaWiki_Versions, ">") -- First on begin, Last on end
-- t = t .. activity.MediaWiki_Versions_code(versions.MediaWiki_Versions, "<") -- First on end, Last on begin
table.sort(versions.MediaWiki_Versions, function (a, b) return (a["verstime"] > b["verstime"]) end )
local tab_view = { -- Group datas and options for a table view with lines and columns.
test_group = versions.MediaWiki_Versions,
title_memo = "activity_MW_Versions_report_title", -- "<b>activity.MW_Versions_report()</b> Monitor MediaWiki versions.",
headers = " verstime; versid; site; seen_time ",
-- local case = { version.MW, version.versid, version.site, version.seen_time, }
headers_class = "wikitable alternative center sortable",
rowGroup = {},
-- track_on = true,
}
-- from MediaWiki 1.30.0-wmf.4 (3248a17) 22:41, 7 June 2017
-- See ISO 8601 time format like : 1977-04-22T01:00:00-05:00 (5 heures de décalage) = 1977-04-22T06:00:00Z local time
function tab_view.form_one_case(version, all_cases) -- Convert a case from test_group to rowGroup.
local example =
{ site = "fr.wikisource", verstime = "2017-12-15T23:35:09", versid = "1.31.0-wmf.16 (a31d45c)", seen_time = "2018-01-12T07:43:00",
task = "T155624", title = "In wikisource/Spécial:Version:wmf.15 (0953700) but Central module mw = 1.31.0-wmf.16 (a31d45c) seen by Rical.", }
if version.task then version.versid = version.versid .. "<br/>" .. "[[phab:" .. version.task .. "|" .. version.task .. "]]" end
if version.title then version.seen_time = version.seen_time .. "<br/>" .. version.title end
return { version.site, version.verstime, version.versid, version.seen_time, }
-- function versions.detect_MediaWiki_changes() display only 3 last months
end
t = t .. tableview.new(tab_view) -- Formats a table view with lines and columns.
t = t .. "\n* Counts of MW_Versions_report: "
t = t .. viewers.ta("#test_group", lua_table.level_count(tab_view.test_group) ) .. viewers.ta("#rowGroup", lua_table.level_count(tab_view.rowGroup) )
local list, count_done, level, split = lua_table.level_list(tab_view.rowGroup, "string", "MediaWiki", 3)
local list, count_now, level, split = lua_table.level_list(tab_view.rowGroup, "string", "wikisource", 3) -- function lua_table.level_list(
local list, count_later, level, split = lua_table.level_list(tab_view.rowGroup, "string", "2017-08", 1) -- subtasks S170813lll
t = t .. viewers.ta("MW_Versions MediaWiki count_done", count_done) .. viewers.ta("MW_Versions wikisource count_now", count_now) .. viewers.ta("MW_Versions 2017-08 count_later", count_later)
-- Counts of selected and sorted sub-tasks: , #test_group = 52 , #rowGroup = 0
-- { "20170529", "20170530", "done", "Rical", "S170530mwv", "versions.MediaWiki_Versions in Module:MediaWikiVersions for activity.MW_Versions_report()", },
viewers.restore_configs(memo, "activity.MW_Versions_report") -- Restore global configurations after eventual changes.
return t
end -- t = activity.MW_Versions_report(t)
 
function activity.MediaWiki_Versions_code(MediaWiki_Versions, sort) -- Re_form the Lua code of versions.MediaWiki_Versions{}.
local MediaWiki_Versions = MediaWiki_Versions or versions.MediaWiki_Versions
if (type(MediaWiki_Versions) ~= "table") then MediaWiki_Versions = {} end
local MediaWiki_Versions_example = { -- Example only
{ site = "fr.wikisource", verstime = "2017-05-11T00:48:00", versid = "1.29.0-wmf.21 (d6c07d1)", seen_time = "2017-05-11T00:48:00-00:00",
task = "T165000", title = "The version date of MW 1.29.0-wmf.21 (d6c07d1) is in the future !",
report = "Rical: Schedule in https://www.MediaWiki.org/wiki/MediaWiki_1.29/Roadmap", },
}
-- alphabetic sort vesions on verstime
local sort = sort
if (type(sort) ~= "string") then sort = activity.MediaWiki_Versions_sort end
if sort == ">" then table.sort(MediaWiki_Versions, function (a, b) return (a["verstime"] > b["verstime"]) end ) end -- First on begin, Last on end
if sort == "<" then table.sort(MediaWiki_Versions, function (a, b) return (a["verstime"] < b["verstime"]) end ) end -- First on end, Last on begin
local code = '\n* activity.MediaWiki_Versions_sort = "' .. sort .. '"'
code = code .. "\n* versions.MediaWiki_Versions = {"
for i, version in ipairs(MediaWiki_Versions) do
-- See ISO 8601 time format like : 1977-04-22T01:00:00-05:00 (5 heures de décalage) = 1977-04-22T06:00:00Z local time
code = code .. '<br/> { site = "' .. version.site
code = code .. '", verstime = "' .. version.verstime
code = code .. '", versid = "' .. version.versid
code = code .. '", seen_time = "' .. version.seen_time
if (type(version.task) == "string") then code = code .. '", task = "' .. version.task end
if (type(version.title) == "string") then code = code .. '", title = "' .. version.title end
if (type(version.report) == "string") then code = code .. '", report = "' .. version.report end
code = code .. '", },' -- end of line
end
code = code .. "<br/>}<br/>"
return code
end -- t = t .. activity.MediaWiki_Versions_code(MediaWiki_Versions, sort)
 
function activity.extract_MW_Versions() -- Extract MediaWiki versions from the page.
local memo = viewers.save_configs("activity.extract_MW_Versions") -- Save global configuration before eventual changes.
local t = t or "\n* <b>activity.extract_MW_Versions()</b> Report the current state of subtasks the current state of subtasks the current state of subtasks."
local actual_title = mw.title.getCurrentTitle() -- Returns the title object for the current page.
local actual_content = actual_title:getContent() -- Returns the (unparsed) content of the page, or nil if there is no page. The page will be recorded as a transclusion.
local i = string.find(actual_content, "Central Normal mode example")
if i then t = t .. "\n* " .. string.sub(actual_content, i, i + 222) end
viewers.restore_configs(memo, "activity.extract_MW_Versions") -- Restore global configurations after eventual changes.
return t
end -- t = activity.extract_MW_Versions() -- Extract MediaWiki versions from the page.
 
function central_library.binded_in(object, name) -- Detects if the object is binded in _G space or in package.loaded.
local binded_in = "xx"
if _G[name] == object then binded_in = "_G" end
if package.loaded[name] == object then binded_in = "LD" end
return binded_in
-- 20161202 18:25 See example https://fr.wikisource.org/wiki/Module:Phab.TestpackG : detect "in " "_G" or package.loaded
end -- binded_in = central_library.binded_in(object, name)
 
function central_library.new(name, library, options) -- Installs a library in package.loaded. The new library must be a Lua table.
-- Installs only a table as a new library.
-- RunOnce : Do not repeat this function to not disturb subsequent processes.
-- A Sribunto library can be a table, a string or a function, not a nil.
-- Modules can only install libraries in tables.
options = options or {}
options.err = ""
options.name = options.name or name
options.library = options.library or library
if (type(options.library) == "table") then
options.library.libname = options.name
elseif (type(options.library) ~= "table") then
options.err = "library~=table"
return library
end
if (type(options.name) ~= "string") then return options.library end
local object = library
local php = nil
function object.setupInterface(options)
-- Remove setup function
if options.library then options.library.setupInterface = nil end
-- Copy the PHP callbacks to a local variable, and remove the global
php = mw_interface
mw_interface = nil
-- Do any other setup here
-- Install into the mw global
mw = mw or {}
mw.ext = mw.ext or {}
mw.ext[options.name] = options.library
-- Indicate that we're loaded
package.loaded[options.name] = options.library
options.err = ""
end
object = object.setupInterface(options)
central_library.i18n_libraries_list = central_library.i18n_libraries_list or {} -- Build a list of central libraries
central_library.i18n_libraries_list[options.name] = object
options.binded_in = central_library.binded_in(object, options.name)
return package.loaded[options.name], options.err
end -- return object, err = function central_library.new(name, library, options)
 
-- cut_libraries
 
-- - - - ------------------ - - - - ---------------------------------
-- - - - ------------------ - - - - ---------------------------------
-- The Library:datas imports datas of Wikidata from mw.wikibase
-- see Extension:Wikibase Client/Lua
-- see Extension:Scribunto/Lua reference manual : class nameTest extends Scribunto_LuaEngineTestBase
-- - - - ------------------ - - - - ---------------------------------
-- - - - ------------------ - - - - ---------------------------------
 
 
datas.default_item = "Q34743" -- Rudyard Kipling
datas.default_name = "Rudyard Kipling" -- Rudyard Kipling
 
-- datas = {} -- already declared by Scribunto, see central_library.new() -- Record a library in package.loaded
-- Translations for datas library
datas.i18n = {}
-- datas = {} -- already declared by Scribunto, see central_library.new() -- Record a library in package.loaded
-- Translations for datas library
datas.i18n.br = {
-- Pour traduire, les langues de référence sont l'anglais et le français.
-- Pour traduire, ne traduisez pas des parties comme celles-ci : <b>%1</b> ; <b>%1</b> = <b>%2</b> (%3) ; <code>Q535</code> ; <br/> ; \n* ; _G.
-- Wikidata
datas_Wikidata_header = "Données : ",
datas_known_Datas_header = "Données connues : ",
datas_sougth_Datas_header = "Données souhaitées : ",
datas_needed_Datas_header = "Données nécessaires : ",
datas_Wikidata_wikibase_err = "Erreur : Wikibase n'est pas disponible.",
datas_Wikidata_getEntity_err = "Erreur : getEntity Wikidata n'est pas disponible.",
datas_Wikidata_getEntityObject_err = "Erreur : L'élément <b>%1</b> de Wikidata n'est pas trouvé.",
datas_Wikidata_property_err = "Erreur : La propriété <b>%1</b> de Wikidata n'est pas trouvée.",
datas_Wikidata_error_err = "Erreur Wikidata : <b>%1</b> ",
-- datas_Wikidata_cat_err = "modes_no_source_arguments_cat",
datas_Wikidata_cat_err = "Module with internal error", -- modes_no_source_arguments_cat
datas_structured_data_txt = 'Données de Wikidata',
datas_Wikidata_any_page_title = "Wikidata pour une autre page :",
datas_Wikidata_details_test_title = "Tests et données importées de Wikidata",
datas_Wikidata_arbitrary_tests_title = "datas.get_item() Test de Wikidata accès arbitraire",
datas_Wikidata_arbitrary_access_text = "Wikidata pour un titre : ",
datas_Wikidata_time_details_title = "datas.Wikidata_time_details{} Wikidata propriétés de temps pour plus de détails",
datas_update_Special_PageData_title = "datas.update_PageData() Partager des DATA entre modules en Special:PageData",
datas_update_Special_PageData_header = "site; temps de version; identificateur de version; heure de vue",
datas_get_item_report_title = "datas.get_item_report() Rapporte les données de mw.wikibase pour la page ou tout autre élément.",
-- Messages et erreurs divers
datas_no_args_Wikidata_err = "Erreur interne : Module sans table d'arguments Wikidata.",
datas_sources_of_datas = "Informations de : /Wikidata, /modèle ou module, /autres, /warning, /erreur",
} -- datas.i18n.br
datas.i18n.de = {
-- Zum Übersetzen sind die Referenzsprachen Englisch und Französisch.
-- Übersetze keine Teile wie diese: <b>%1</b> ; <b>%1</b> = <b>%2</b> (%3) ; <code>Q535</code> ; <br/> ; \n* ; _G.
datas_Wikidata_header = "Daten: ",
datas_known_Datas_header = "Bekannte Daten: ",
datas_sougth_Datas_header = "Gewünschte Daten: ",
datas_needed_Datas_header = "Daten benötigt: ",
datas_Wikidata_wikibase_err = "Fehler: Wikibase ist nicht verfügbar.",
datas_Wikidata_getEntity_err = "Fehler: getEntity Wikidata ist nicht verfügbar.",
datas_Wikidata_getEntityObject_err = "Fehler: Der Eintrag <b>%1</b> von Wikidata wurde nicht gefunden.",
datas_Wikidata_property_err = "Fehler: Die Wikidata <b>%1</b> Eigenschaft wurde nicht gefunden.",
datas_Wikidata_error_err = "Wikidata-Fehler: <b>%1</b> ",
-- datas_Wikidata_cat_err = "modes_no_source_arguments_cat",
datas_Wikidata_cat_err = "Modul mit internem Fehler", -- modes_no_source_arguments_cat
datas_structured_data_txt = 'Wikidata daten',
datas_Wikidata_any_page_title = "Wikidata für eine andere Seite:",
datas_Wikidata_details_test_title = "Tests und Daten, die aus Wikidata importiert wurden",
datas_Wikidata_arbitrary_tests_title = "datas.get_item() Wikidata Test beliebiger Zugriff",
datas_Wikidata_arbitrary_access_text = "Wikidata für einen Titel: ",
datas_Wikidata_time_details_title = "datas.Wikidata_time_details{} Wikidata Zeiteigenschaften für weitere Details",
datas_update_Special_PageData_title = "datas.update_PageData() Partager des DATA entre modules en Special:PageData",
datas_update_Special_PageData_header = "Ort; Versionszeit; Versionskennung; Stunde der Sicht",
datas_get_item_report_title = "datas.get_item_report() Gibt mw.wikibase-Daten für die Seite oder einen anderen Artikel aus.",
-- Verschiedene Nachrichten und Fehler
datas_no_args_Wikidata_err = "Interner Fehler: Modul ohne Wikidata-Argumenttabelle.",
datas_sources_of_datas = "Informationen von: / Wikidata, / Modell oder Modul, / andere, / Warnung, / Fehler",
} -- datas.i18n.de
datas.i18n.en = {
-- To translate, referral languages are English and French.
-- To translate, do not translate parts like these: <b>%1</b> ; <b>%1</b> = <b>%2</b> (%3) ; <code>Q535</code> ; <br/> ; \n* ; _G.
datas_Wikidata_header = "Datas: ",
datas_known_Datas_header = "Known datas: ",
datas_sougth_Datas_header = "Sougth datas: ",
datas_needed_Datas_header = "Needed datas: ",
datas_Wikidata_wikibase_err = "Error: Wikibase is not available.",
datas_Wikidata_getEntity_err = "Error: getEntity Wikidata is not available.",
datas_Wikidata_getEntityObject_err = "Error: Element Wikidata <b>%1</b> is not found.",
datas_Wikidata_property_err = "Error: Wikidata property <b>%1</b> is not found.",
datas_Wikidata_error_err = "Error Wikidata: <b>%1</b> ",
-- datas_Wikidata_cat_err = "Error Wikidata",
datas_Wikidata_cat_err = "Module with internal error", -- modes_no_source_arguments_cat
datas_structured_data_txt = 'Datas from Wikidata',
datas_Wikidata_any_page_title = "Wikidata for any page:",
datas_Wikidata_details_test_title = "Tests and imported datas from Wikidata",
datas_Wikidata_arbitrary_tests_title = "datas.get_item() Test of Wikidata arbitrary access",
datas_Wikidata_arbitrary_access_text = "Wikidata for Title: ",
datas_Wikidata_time_details_title = "datas.Wikidata_time_details{} Wikidata time properties for more details",
datas_update_Special_PageData_title = "datas.update_PageData() Share DATAS between modules in Special:PageData",
datas_update_Special_PageData_header = "site; version time; version identifier; seen hour",
datas_get_item_report_title = "datas.get_item_report() Reports datas from mw.wikibase for the page or any other item.",
-- Miscellaneous warnings and errors
datas_no_args_Wikidata_err = "Error: Module without Wikidata arguments table.",
datas_sources_of_datas = "Informations from: /Wikidata, /template or module, /other, /warning, /error",
} -- datas.i18n.en
datas.i18n.es = {
-- Para traducir, los idiomas de referencia son inglés y francés.
-- Para traducir, no traduzca partes como estas: <b>%1</b> ; <b>%1</b> = <b>%2</b> (%3) ; <code>Q535</code> ; <br/> ; \n* ; _G.
-- Wikidata
datas_Wikidata_header = "Datos: ",
datas_known_Datas_header = "Datos conocidas: ",
datas_sougth_Datas_header = "Datos deseados: ",
datas_needed_Datas_header = "Datos necesarios: ",
datas_Wikidata_wikibase_err = "Error: Wikibase no está disponible.",
datas_Wikidata_getEntity_err = "Error: getEntity Wikidata no está disponible.",
datas_Wikidata_getEntityObject_err = "Error: Elemento <b>%1</b> de Wikidata no se encuentra.",
datas_Wikidata_property_err = "Error: La propiedad <b>%1</b> de Wikidata no se encuentra.",
datas_Wikidata_error_err = "Error Wikidata : <b>%1</b> ",
datas_Wikidata_cat_err = "Módulo con error interno", -- modes_no_source_arguments_cat
datas_structured_data_txt = 'Datos de Wikidata',
datas_Wikidata_any_page_title = "Wikidata para cualquier página:",
datas_Wikidata_details_test_title = "Pruebas y datos importados de Wikidata",
datas_Wikidata_arbitrary_tests_title = "datas.get_item() Prueba de Wikidata acceso arbitrario",
datas_Wikidata_arbitrary_access_text = "Wikidata por título: ",
datas_Wikidata_time_details_title = "datas.Wikidata_time_details{} Wikidata propiedades de tiempo para más detalles",
datas_update_Special_PageData_title = "datas.update_PageData() Compartir DATOS entre módulos en Special:PageData",
datas_update_Special_PageData_header = "sitio; tiempo de versión; identificador de versión; tiempo visto",
datas_get_item_report_title = "datas.get_item_report() Informes de datos de mw.wikibase para la página o cualquier otro elemento.",
-- Diversos mensajes y errores
datas_no_args_Wikidata_err = "Error: Módulo sin argumentos Wikidata tabla.",
datas_sources_of_datas = "Informaciones de: /Wikidata, /template o module, /other, /warning, /error",
} -- datas.i18n.es
datas.i18n.fr = {
-- Pour traduire, les langues de référence sont l'anglais et le français.
-- Pour traduire, ne traduisez pas des parties comme celles-ci : <b>%1</b> ; <b>%1</b> = <b>%2</b> (%3) ; <code>Q535</code> ; <br/> ; \n* ; _G.
-- Wikidata
datas_Wikidata_header = "Données : ",
datas_known_Datas_header = "Données connues : ",
datas_sougth_Datas_header = "Données souhaitées : ",
datas_needed_Datas_header = "Données nécessaires : ",
datas_Wikidata_wikibase_err = "Erreur : Wikibase n'est pas disponible.",
datas_Wikidata_getEntity_err = "Erreur : getEntity Wikidata n'est pas disponible.",
datas_Wikidata_getEntityObject_err = "Erreur : L'élément <b>%1</b> de Wikidata n'est pas trouvé.",
datas_Wikidata_property_err = "Erreur : La propriété <b>%1</b> de Wikidata n'est pas trouvée.",
datas_Wikidata_error_err = "Erreur Wikidata : <b>%1</b> ",
-- datas_Wikidata_cat_err = "modes_no_source_arguments_cat",
datas_Wikidata_cat_err = "Module with internal error", -- modes_no_source_arguments_cat
datas_structured_data_txt = 'Données de Wikidata',
datas_Wikidata_any_page_title = "Wikidata pour une autre page :",
datas_Wikidata_details_test_title = "Tests et données importées de Wikidata",
datas_Wikidata_arbitrary_tests_title = "datas.get_item() Test de Wikidata accès arbitraire",
datas_Wikidata_arbitrary_access_text = "Wikidata pour un titre : ",
datas_Wikidata_time_details_title = "datas.Wikidata_time_details{} Wikidata propriétés de temps pour plus de détails",
datas_update_Special_PageData_title = "datas.update_PageData() Partager des DATA entre modules en Special:PageData",
datas_update_Special_PageData_header = "site; temps de version; identificateur de version; heure de vue",
datas_get_item_report_title = "datas.get_item_report() Rapporte les données de mw.wikibase pour la page ou tout autre élément.",
-- Messages et erreurs divers
datas_no_args_Wikidata_err = "Erreur interne : Module sans table d'arguments Wikidata.",
datas_sources_of_datas = "Informations de : /Wikidata, /modèle ou module, /autres, /warning, /erreur",
} -- datas.i18n.fr
datas.i18n.hu = {
-- Zum Übersetzen sind die Referenzsprachen Englisch und Französisch.
-- Übersetzen Sie keine Teile wie diese: <b>%1</b> ; <b>%1</b> = <b>%2</b> (%3) ; <code>Q535</code> ; <br/> ; \n* ; _G.
datas_Wikidata_header = "Adat: ",
datas_known_Datas_header = "Ismert adatok: ",
datas_sougth_Datas_header = "Kívánt adatokat: ",
datas_needed_Datas_header = "Szükséges adatok: ",
datas_Wikidata_getEntity_err = "Hiba: a getEntity Wikidata nem érhető el.",
datas_Wikidata_getEntityObject_err = "Lỗi: Không tìm thấy mục <b>%1</b> để Wikidata.",
datas_Wikidata_property_err = "Erreur : La propriété <b>%1</b> de Wikidata n'est pas trouvée.",
datas_Wikidata_error_err = "Lỗi Wikidata : <b>%1</b> ",
datas_Wikidata_cat_err = "Mô-đun có lỗi nội bộ",
datas_structured_data_txt = 'Dữ liệu Wikidata',
datas_Wikidata_any_page_title = "Wikidata cho một trang khác:",
datas_Wikidata_details_test_title = "Kiểm tra và dữ liệu được nhập từ Wikidata",
datas_Wikidata_arbitrary_tests_title = "datas.get_item() Wikidata kiểm tra truy cập tùy ý",
datas_Wikidata_arbitrary_access_text = "Wikidata cho một tiêu đề : ",
datas_Wikidata_time_details_title = "datas.Wikidata_time_details{} Wikidata thuộc tính thời gian để biết thêm chi tiết",
datas_update_Special_PageData_title = "datas.update_PageData() Megosztja a DATA-t a speciális modulok között: Special:PageData",
datas_update_Special_PageData_header = "webhely; verzióidő; verzióazonosító; látott órát",
datas_get_item_report_title = "datas.get_item_report() Rapporte les données de mw.wikibase pour la page ou tout autre élément.",
-- Messages et erreurs divers
datas_no_args_Wikidata_err = "Erreur interne : Module sans table d'arguments Wikidata.",
datas_sources_of_datas = "Informations de : /Wikidata, /modèle ou module, /autres, /warning, /erreur",
} -- datas.i18n.hu
datas.i18n.vi = {
-- Để dịch, các ngôn ngữ giới thiệu là tiếng Anh và tiếng Pháp.
-- Để dịch, không dịch các phần như thế này: <b>%1</b> ; <b>%2</b> = <b>%3</b> (<b>%4</b>) ; <code>Q535</code> ; <br/> ; <br/> ; \n* ; _G.
datas_Wikidata_header = "Dữ liệu: ",
datas_known_Datas_header = "Dữ liệu nổi tiếng: ",
datas_sougth_Datas_header = "Dữ liệu mong muốn: ",
datas_needed_Datas_header = "Dữ liệu cần thiết : ",
datas_Wikidata_wikibase_err = "Lỗi: Wikibase không khả dụng.",
datas_Wikidata_getEntity_err = "Lỗi: getEntity Wikidata không khả dụng.",
datas_Wikidata_getEntityObject_err = "Lỗi: Không tìm thấy mục <b>%1</b> để Wikidata.",
datas_Wikidata_property_err = "Lỗi: Không tìm thấy thuộc tính Wikidata <b>%1</b>.",
datas_Wikidata_error_err = "Lỗi Wikidata: <b>%1</b> ",
-- datas_Wikidata_cat_err = "modes_no_source_arguments_cat",
datas_Wikidata_cat_err = "Mô-đun có lỗi nội bộ", -- modes_no_source_arguments_cat
datas_structured_data_txt = 'Dữ liệu Wikidata',
datas_Wikidata_any_page_title = "Wikidata cho một trang khác:",
datas_Wikidata_details_test_title = "Các bài kiểm tra và dữ liệu được nhập từ Wikidata",
datas_Wikidata_arbitrary_tests_title = "datas.get_item() Wikidata kiểm tra truy cập tùy ý",
datas_Wikidata_arbitrary_access_text = "Wikidata cho một tiêu đề: ",
datas_Wikidata_time_details_title = "datas.Wikidata_time_details{} Các thuộc tính thời gian để Wikidata để biết thêm chi tiết",
datas_update_Special_PageData_title = "datas.update_PageData() Chia sẻ DATA giữa các mô-đun trong Special:PageData",
datas_update_Special_PageData_header = "địa điểm; thời gian phiên bản; định danh phiên bản; thấy giờ",
datas_get_item_report_title = "datas.get_item_report() Báo cáo dữ liệu mw.wikibase cho trang hoặc bất kỳ mục nào khác.",
-- Các thông báo và lỗi khác nhau
datas_no_args_Wikidata_err = "Lỗi nội bộ: Mô-đun không có bảng đối số Wikidata.",
datas_sources_of_datas = "Thông tin từ: /Wikidata, /mô hình hoặc mô-đun, /người khác, /cảnh báo, /lỗi",
} -- datas.i18n.vi
 
function datas.getDateFromTimeStatement(statement, field)
local struct = {
year = nil,
century = nil,
text = nil,
precision = 0
}
local snak = statement.mainsnak
if snak.snaktype == 'novalue' then
return struct
end
if snak.snaktype == 'somevalue' then
struct.text = '??'
return struct
end
struct = parseWbTime(snak.datavalue.value)
local prefix = ''
if struct.precision == 8 then
prefix = 'vers '
end
--Extract circa
if statement.qualifiers ~= nil and statement.qualifiers.P1480 ~= nil then
for _,qualifier in pairs(statement.qualifiers.P1480) do
if qualifier.datavalue.value.id == 'Q5727902' then
prefix = 'circa '
struct.precision = 8 --TODO: hacky
end
end
end
--Use before and after if precision <= century
if statement.qualifiers ~= nil and struct.precision <= 7 then
if statement.qualifiers.P1319 ~= nil then
for _,qualifier in pairs(statement.qualifiers.P1319) do
struct = parseWbTime(qualifier.datavalue.value)
prefix = 'après '
struct.precision = 8 --TODO: hacky
end
elseif statement.qualifiers.P1326 ~= nil then
for _,qualifier in pairs(statement.qualifiers.P1326) do
struct = parseWbTime(qualifier.datavalue.value)
prefix = 'avant '
struct.precision = 8 --TODO: hacky
end
elseif statement.qualifiers.P1317 ~= nil then
for _,qualifier in pairs(statement.qualifiers.P1317) do
struct = parseWbTime(qualifier.datavalue.value)
prefix = 'floruit '
struct.precision = 8 --TODO: hacky
end
end
end
--Create text
if struct.precision >= 9 then
struct.text = prefix .. getTextForYear(struct.year)
elseif struct.precision == 8 then
struct.text = prefix .. getTextForYear(struct.year)
elseif struct.precision == 7 then
struct.text = prefix .. getTextForCentury(struct.century, true)
else
struct.text = errorMessage('La date de ' .. field .. ' a une précision trop faible sur Wikidata')
end
return struct
end
 
datas.track_val = datas.track_val or ""
function datas.tv(line, prop, what, val) -- track a property in datas.get_item
datas.track_val = datas.track_val or "" -- birthyear=P569
if prop == "P569" then
local line = "L" .. tostring(line)
local prop = tostring(prop)
local what = tostring(what)
local val = tostring(val)
datas.track_val = datas.track_val .. viewers.ta(line .. "-" .. prop .. ":" .. what, val)
end
return datas.track_val
end -- datas.track_val = datas.tv(line, prop, what, val)
 
function datas.get_uri(prop, better, lang) -- Get props.uri for the page.
local mwuri, uri = mw.uri.new(), "-" -- Server mw.uri.new for path like = /wiki/Utilisateur:Rical/Nelson_Mandela
local sub_parts = mw.text.split(mwuri.path, '/') ; for k, part in pairs(sub_parts) do uri = part end -- last text after /
uri = string.gsub(uri, "_", " ") ; return uri
end
 
function datas.get_image(prop, QITEM, lang) -- T185557 Gets the sought image name for the page, or some others for galeries.
-- see phabtask T185557 Authored By Rical on 20180123 : Create the easy function mw.wikibase.property('P21', 'Q8023', 'en')
if type(prop) ~= "string" then prop = "P18" end
if (prop == "image") then prop = "P18" end
local image = image or datas.props.image or datas.props.P18 or "Victor Hugo.jpg" or (datas.get_uri() .. ".jpg")
return image -- image = image or prop or "Victor Hugo.jpg" --
end
 
function datas.property(argmt) -- Get datas from mwwikibase for one property of the page.
argmt = mw.clone(argmt) -- avoid any interaction with other properties.
datas.QITEM = mw.wikibase.getEntityIdForCurrentPage() -- use props.QITEM Returns the Item id as string, like "Q42"
local QITEM = datas.QITEM or datas.default_item
datas.item = mw.wikibase.getEntity(QITEM)
local loc = {}
local label = nil
local val = nil
if argmt.prop then -- Admit any type of keyword and prop.
argmt.keyword = argmt.keyword or argmt.key or argmt.prop
argmt.prop = argmt.prop -- Get datas from mwwikibase for one property of the page.
if argmt.prop == "QITEM" then val = mw.wikibase.getEntityIdForCurrentPage() -- use props.QITEM Returns the Item id as string, like "Q42"
elseif argmt.prop == "label" then val = datas.item:getLabel(QITEM) ; label = label or val -- use props.label Returns a string, like "Berlin" with 'de'
elseif argmt.prop == "sitelink" then val = datas.item:getSitelink() -- use props.sitelink like Author:Aristotel
elseif argmt.prop == "labelwithlang" then val = mw.wikibase.entity:getLabelWithLang() -- use props.labelwithlang -- Returns a string like "Berlin" and a language like
elseif argmt.prop == "description" then val = mw.wikibase.description(QITEM) -- use props.description -- ric : Description of the QITEM page
elseif argmt.prop == "labelcontent" then val = mw.wikibase.getLabelByLang(QITEM, langs.content_lang) ; label = label or val -- use props.labelcontent -- Returns the content_lang label of the item
elseif argmt.prop == "labelpage" then val = mw.wikibase.getLabelByLang(QITEM, langs.page_lang) ; label = label or val -- use props.description -- Returns the content_lang label of the item
elseif argmt.prop == "labeluser" then val = mw.wikibase.getLabelByLang(QITEM, langs.user_lang or "es") ; label = label or val -- use props.description -- Returns the content_lang label of the item
elseif argmt.prop == "labelbylang" then val = mw.wikibase.getLabelByLang(QITEM, langs.user_lang or "it") ; label = label or val -- use props.labelbylang -- see use by props.user props.page props.content props.content
-- mw.wikibase.getLabelByLang( 'Q42', 'es' ) -- Returns the Spanish label of the item as a string, like "Berlín".
else -- ric (p.box1)
loc.formatPropertyValues = datas.item:formatPropertyValues( argmt.prop ) -- like "P123"
-- Returns a table like: { value = "Formatted claim value", label = "Label of the Property" }
if loc.wd_RANK_TRUTH then
loc.formatPropertyValues = datas.item:formatPropertyValues( argmt, { loc.wd_RANK_TRUTH } )
end
if loc.wd_claimRanks then
loc.formatPropertyValues = datas.item:formatPropertyValues( argmt, { loc.wd_claimRanks } )
end
val = loc.formatPropertyValues.value
end
val = tostring(val)
if argmt.format == "year" then val = mw.ustring.sub( val, -4, -1 ) end
val = tostring(val)
argmt.val = val
end --function modes.get_args(
argmt.label = label or argmt.label or argmt.labeluser or argmt.labelcontent or argmt.labelpage or argmt.labelbylang
argmt = mw.clone(argmt) -- avoid any interaction with other properties.
return argmt
end -- argmt = datas.property(argmt) -- Get datas from mwwikibase for one property of the page.
 
function datas.get_item(args_known, QITEM) -- Get datas from mw.wikibase for the page.
-- from 2016-08-16 ModuleCentral 3a lua_table.to_list.lua
local args_known = args_known or modes.args_known or p.args_known or {} -- optional value from p.args_known = {...}
local t = "\n* <b>datas.get_item(args_known, QITEM)</b>: Get datas from mw.wikibase for the page."
local Title, Label, prop, lang, description, val, label, adr, proplabel
local QITEM = QITEM or mw.wikibase.getEntityIdForCurrentPage() or datas.default_item
datas.QITEM = QITEM
datas.item = mw.wikibase.getEntity(datas.QITEM or "Q34743") -- Rudyard Kipling
local props = {} -- All properties form args_known with argmt.prop.
local prop = {} -- to collect properties
local loc = {} -- local values
for key, argmt in pairs(args_known) do -- For all known parameters
if type(argmt) == "table" then
argmt.key = key
argmt.syn = argmt.syn or 0
argmt = datas.property(argmt) -- Get datas from mwwikibase for one property of the page. function datas.property(
if argmt.keyword == "QITEM" then argmt.val = QITEM end
if argmt.prop then -- Admit any type of keyword and prop.
props[argmt.keyword] = mw.clone(argmt)
prop[argmt.keyword] = argmt.val -- ric (p.box1)
end
end
end
prop.countall = tostring( lua_table.level_count(prop) )
props.countall = tostring( lua_table.level_count(props) )
datas.props = props
datas.prop = prop
return prop, props
end -- local prop, props = datas.get_item(args_known, QITEM) -- Get datas from mw.wikibase for the page.
 
function datas.get_item_report(t) -- datas.get_item() Report datas from mw.wikibase for the page **
local memo = viewers.save_configs("datas.get_item_report") -- Save global configuration before eventual changes.
local t = t or "\n* <b>datas.get_item_report(t)</b>: Report datas from mw.wikibase for the page **"
local args_known = args_known or modes.args_known or p.args_known or {} -- modes.args_known = { -- p.args_known = { -- }
local prop, props = datas.get_item(args_known, QITEM) -- Get datas from mw.wikibase for the page. ric
local countprops = tostring( lua_table.level_count(props) ) -- do not follow one_prop structure
local countallprops = tostring( lua_table.level_count(props) ) -- do not follow one_prop structure
t = t .. viewers.ta("\n* countprops", countprops) .. viewers.ta("\n* countallprops", countallprops)
local sortprops = {} -- to sort properties in alphabetic order
for key, val in pairs(props) do -- from list all fond datas
t = t .. "\n* get_item: " .. viewers.ta("key", key) .. viewers.ta("val", val)
table.insert(sortprops, props[key])
end
table.sort(sortprops, function (a, b) return ( tostring(a.keyword or a.prop) < tostring(b.keyword or b.prop)) end ) -- alphabetic sort of properties
local tab_view = { -- Group datas and options for a table view with lines and columns.
test_group = sortprops, -- Use default cases.
rowGroup = {},
-- title_memo = "datas.get_item_report() Reports datas from mw.wikibase for the page or any other item.",
title_memo = "datas_get_item_report_title",
form_one_case = function(case) -- Convert a case from test_group to rowGroup.
return { case.key, case.val, case.typ, case.need, case.keyword, case.syn, case.prop, case.format, } end,
headers = "key; val; typ; need; keyword; syn; prop; format",
}
t = t .. tableview.new(tab_view) -- Formats a table view with lines and columns.
t = t .. viewers.ta("#test_group", lua_table.level_count(tab_view.test_group) )
t = t .. viewers.ta("#rowGroup", lua_table.level_count(tab_view.rowGroup) )
t = t .. "\n* <b>datas.get_item_report(t)</b>: end"
viewers.restore_configs(memo, "datas.get_item_report") -- Restore global configurations after eventual changes.
return t
end -- local t = datas.get_item_report(t) -- datas.get_item() Report datas from mw.wikibase for the page **
 
function datas.prot(prop) -- form a string to show a prop value
datas.props = datas.props or {}
local prop = prop
if type(prop) ~= "string"then prop = "prop" end
local t = prop
if type(prop) == "string" and not string.find(prop, "%s", 1, true) then t = datas.props[prop] or prop end
return t
end
 
function datas.PageData_to_table(datext) -- Convert a PageData in JSON to a table.
return "To do later : datas.PageData_to_table(datext) -- Convert a PageData in JSON to a table."
end -- local tab = datas.PageData_to_table(datext)
 
function datas.table_to_PageData(tab) -- Convert a table to JSON for PageData.
return datext
end -- local datext = datas.table_to_PageData(tab)
 
function datas.update_PageData(t, datext) -- Try to share INFOS between a group of modules in Module:Main/INFOS
local memo = viewers.save_configs("datas.update_PageData") -- Save global configuration before eventual changes.
local t = t or "\n* datas.update_PageData() Share DATAS between modules in Special:PageData for modules." -- PageData from 20170822
local tab = datas.PageData_to_table(datext)
local datext = datas.table_to_PageData(tab)
local Help_Tabular_DataExample = [=[{
"license": "CC0-1.0",
"description": {
"en": "Some good fruits for you",
"es": "Algunas buenas frutas para ti"
},
"sources": "http://example.com and [[Data]] page",
"schema": {
"fields": [
{ "name": "id", "type": "string", "title": { "en": "Fruit ID", "fr": "ID de fruit" }},
{ "name": "count", "type": "number", "title": { "en": "Count" }},
{ "name": "liked", "type": "boolean", "title": { "en": "Do I like it?" }},
{ "name": "description", "type": "localized", "title": { "en": "Fruit name", "fr": "Nom du fruit" }}
]
},
"data": [
[
"peaches",
100,
true,
{
"en": "Magnificent but a bit artificial sweet peaches",
"es": "esto puede estar en español",
"fr": "this could be in french"
}
],
]
}]=]
local lua_content = mw.text.jsonDecode(Help_Tabular_DataExample)
local json_content = mw.text.jsonEncode(lua_content)
local table_to_code = activity.wikis_names --[[ see activity.wikis_names
["b"] = "wikibooks", ["cm"] = "commons", ["meta"] = "meta", ["mw"] = "MediaWiki",
["n"] = "wikinews", ["p"] = "wiki", ["q"] = "wikiquote", ["s"] = "wikisource",
["species"] = "species", ["t"] = "wiktionary", ["test"] = "test", ["test2"] = "test2",
["v"] = "wikiversity", ["w"] = "wikipedia", ["wm"] = "wikimedia", ["y"] = "wikivoyage",
} -- activity.wikis_names
--]]
local table_json = mw.text.jsonEncode(table_to_code)
local table_lua = mw.text.jsonDecode(table_json)
local final_table = {}
for key, val in pairs(table_lua) do final_table[key] = val end
local tab_view = { -- Group datas and options for a table view with lines and columns.
test_group = final_table, -- Use default cases.
title_memo = "datas_update_Special_PageData_title", -- "events.all_kinds_test() Test: all kinds of events (err, wng, cat)",
headers = "key;val",
rowGroup = {},
}
function tab_view.form_one_case(case) -- Convert a case from test_group to rowGroup.
return { case.key, case.val }
end
t = t .. tableview.new(tab_view) -- Formats a table view with lines and columns.
t = t .. viewers.ta("#test_group", lua_table.level_count(tab_view.test_group) )
t = t .. viewers.ta("#rowGroup", lua_table.level_count(tab_view.rowGroup) )
viewers.restore_configs(memo, "datas.update_PageData") -- Restore global configurations after eventual changes.
return t
end -- function datas.update_PageData(t)
 
function datas.load_data(t, datext) -- Pass data between #invoke's
local T67687 = "phabtask : mw.load_data can be used to pass data between #invoke's by reading frame arguments"
if false then
-- Create the following as Module:LoadData:
local p = {}
function p.main(frame)
return mw.load_data('Module:LoadData/data')[1]
end
return p
end
if false then
-- Create the following as Module:LoadData/data:
return { mw.getCurrentFrame().args[1] }
end
if false then
end
end -- function datas.load_data(t, datext) -- Pass data between #invoke's
 
-- cut_libraries
 
-- - - - ------------------ - - - - ------------------ - - - - -----------------------------
-- - - - ------------------ - - - - ------------------ - - - - -----------------------------
-- The Library:events support events of types erros, warnings and categories.
-- viewers.save_configs("events.save_configs" memo, tab_view, group ) -- Init a new events group
-- events.add_err(key, ... ) -- Add an error in the actual table of events.
-- events.add_cat_group(groupCat, groupList) -- Add some categories in the actual table of events.
-- events.form(evt) -- Format events types
-- events.all_categories_test(t) -- test categories
-- - - - ------------------ - - - - ---------------------------------
-- - - - ------------------ - - - - ---------------------------------
 
 
-- events = {} -- already declared by Scribunto, see central_library.new() -- Record a library in package.loadedS
-- Translations for Library:events
events.i18n = {}
events.i18n.br = {
events_test_tests_title = "List a table, test with limits:",
events_test_resTest_title = "List a table, test with limits:",
events_test_projects_title = "Test and display tests events for projects",
events_test_projects_headers = "Type;Key;Name test and values;result of the test",
events_test_MediaWiki_title = "Test and display tests events for MediaWiki",
events_test_MediaWiki_headers = "Type;Key;Name test and values;result of the test",
events_test_categ_Test_title = "Tester categ_Test : catégories dans quelques langues",
events_all_kinds_tests_title = "events.all_kinds_test() Test: toutes les sortes d'événements (err, wng, cat)",
events_all_kinds_tests_headers = "typ;key;idargs;result",
events_add_cat_deprecated = "Fonction obsolète dans le module principal.",
events_close_without_memo_err = "viewers.restore_configs(memo, where) sans <b>memo</b> dans le module <b>%1</b>.",
events_antiCrash_protect_err = "La fonction antiCrash() protège cette page contre un effondrement complet dû à une erreur interne : %1.",
} -- events.i18n.br
events.i18n.en = {
events_test_tests_title = "List a table, test with limits:",
events_test_resTest_title = "List a table, test with limits:",
events_test_projects_title = "Test and display tests events for projects",
events_test_projects_headers = "Type;Key;Name test and values;result of the test",
events_test_MediaWiki_title = "Test and display tests events for MediaWiki",
events_test_MediaWiki_headers = "Type;Key;Name test and values;result of the test",
events_test_categ_Test_title = "categ_Test test : classes in some languages",
events_all_kinds_tests_title = "events.all_kinds_test() Test: all kinds of events (err, wng, cat)",
events_all_kinds_tests_headers = "typ;key;idargs;result",
events_close_without_memo_err = "viewers.restore_configs(memo, where) without <b>memo</b> in module <b>%1</b>.",
events_antiCrash_protect_err = "The antiCrash() function protects this page against a complete crash due to an internal error: %1.",
} -- events.i18n.en
events.i18n.es = {
events_test_tests_title = "List a table, test with limits:",
events_test_resTest_title = "List a table, test with limits:",
events_test_projects_title = "Test and display tests events for projects",
events_test_projects_headers = "Type;Key;Name test and values;result of the test",
events_test_MediaWiki_title = "Test and display tests events for MediaWiki",
events_test_MediaWiki_headers = "Type;Key;Name test and values;result of the test",
events_test_categ_Test_title = "Prueba categ_Test: clases en algunos lenguajes",
events_all_kinds_tests_title = "events.all_kinds_test() Prueba: todo tipo de eventos (err, wng, cat)",
events_all_kinds_tests_headers = "typ;key;idargs;result",
events_add_cat_deprecated = "Función obsoleto en módulo principal.",
events_close_without_memo_err = "viewers.restore_configs(memo, where) sin <b>memo</b> en el módulo <b>%1</b>.",
events_antiCrash_protect_err = "La función antiCrash() protege esta página contra un colapso completo debido a un error interna: %1.",
} -- events.i18n.es
events.i18n.fr = {
events_test_tests_title = "List a table, test with limits:",
events_test_resTest_title = "List a table, test with limits:",
events_test_projects_title = "Test and display tests events for projects",
events_test_projects_headers = "Type;Key;Name test and values;result of the test",
events_test_MediaWiki_title = "Test and display tests events for MediaWiki",
events_test_MediaWiki_headers = "Type;Key;Name test and values;result of the test",
events_test_categ_Test_title = "Tester categ_Test : catégories dans quelques langues",
events_all_kinds_tests_title = "events.all_kinds_test() Test: toutes les sortes d'événements (err, wng, cat)",
events_all_kinds_tests_headers = "typ;key;idargs;result",
events_add_cat_deprecated = "Fonction obsolète dans le module principal.",
events_close_without_memo_err = "viewers.restore_configs(memo, where) sans <b>memo</b> dans le module <b>%1</b>.",
events_antiCrash_protect_err = "La fonction antiCrash() protège cette page contre un effondrement complet dû à une erreur interne : %1.",
} -- events.i18n.fr
events.i18n.hu = {
events_test_tests_title = "List a table, test with limits:",
events_test_resTest_title = "List a table, test with limits:",
events_test_projects_title = "Test and display tests events for projects",
events_test_projects_headers = "Type;Key;Name test and values;result of the test",
events_test_MediaWiki_title = "Test and display tests events for MediaWiki",
events_test_MediaWiki_headers = "Type;Key;Name test and values;result of the test",
events_test_categ_Test_title = "Tester categ_Test : catégories dans quelques langues",
events_all_kinds_tests_title = "events.all_kinds_test() Test: toutes les sortes d'événements (err, wng, cat)",
events_all_kinds_tests_headers = "typ;key;idargs;result",
events_add_cat_deprecated = "Fonction obsolète dans le module principal.",
events_close_without_memo_err = "viewers.restore_configs(memo, where) sans <b>memo</b> dans le module <b>%1</b>.",
events_antiCrash_protect_err = "La fonction antiCrash() protège cette page contre un effondrement complet dû à une erreur interne : %1.",
} -- events.i18n.hu
events.i18n.vi = {
events_test_tests_title = "List a table, test with limits:",
events_test_resTest_title = "List a table, test with limits:",
events_test_projects_title = "Test and display tests events for projects",
events_test_projects_headers = "Type;Key;Name test and values;result of the test",
events_test_MediaWiki_title = "Test and display tests events for MediaWiki",
events_test_MediaWiki_headers = "Type;Key;Name test and values;result of the test",
events_test_categ_Test_title = "Tester categ_Test : catégories dans quelques langues",
events_all_kinds_tests_title = "events.all_kinds_test() Test: toutes les sortes d'événements (err, wng, cat)",
events_all_kinds_tests_headers = "typ;key;idargs;result",
events_add_cat_deprecated = "Fonction obsolète dans le module principal.",
events_close_without_memo_err = "viewers.restore_configs(memo, where) sans <b>memo</b> dans le module <b>%1</b>.",
events_antiCrash_protect_err = "La fonction antiCrash() protège cette page contre un effondrement complet dû à une erreur interne : %1.",
} -- events.i18n.vi
 
events.test_group = {}
events.rowGroup = {}
events.tab_view = {}
events.tab_view.test_group = {}
events.tab_view.rowGroup = {}
 
function events.add_cat(key, ... ) -- Add a category in the actual table of events.
return events.add_record("cat", key, ...) -- Add a error, warning or category in the lists. S170626rev
end
 
function events.add_err(key, ... ) -- Add an error in the actual table of events.
return events.add_record("err", key, ...) -- Add a error, warning or category in the lists. S170626rev
end
 
function events.add_wng(key, ... ) -- Add a warning in the actual table of events.
return events.add_record("wng", key, ...) -- Add a error, warning or category in the lists. S170626rev
end
 
function events.form_cat(evt, txt, lnk, c, space)
local space = space or (mw.site.namespaces.Category.name .. ":")
local c = c or evt.ccc or ":"
if evt.typ == "cat" then -- Format a category to display or activate
evt.content_wkt = viewers.form9content(evt.key, lua_table.to_list( evt.vals ) )
evt.page_wkt = viewers.form9page(evt.key, lua_table.to_list( evt.vals ) )
evt.user_wkt = viewers.form9user(evt.key, lua_table.to_list( evt.vals ) )
return " [[" .. c .. space .. (evt.content_wkt or lnk) .. "|" .. (evt.user_wkt or txt) .. "]] "
else
return ""
end
end
 
events.list_all_events = {} -- Table to collect all events types "err", "wng" and "cat".
 
function events.new(typ, key, ...) -- Initialize and finalize a new event.
local evt = {} -- default event
if type(typ) == "table" then
evt = typ -- Use a predefined event
else -- To finalize an existing event.
evt.typ = typ
evt.key = key
end -- Finalize all events
evt.typ = evt.typ or typ -- Type of event: err, wng, cat
evt.key = evt.key or key -- Translation key, simple or extended by name
if type(typ) ~= "string" then typ = "notyp" end -- To debug abnormal type of event
if type(key) ~= "string" then key = "nokey" end -- To debug abnormal translation key
evt.name = evt.typ or evt.key or "name" -- Translation key, simple or extended by name
evt.vals = evt.vals or { ... } -- table of arguments values
evt.catview = evt.catview or ":" -- Default value for eventual use
-- Check, yes or no, to form an event, in special cases
if (evt.typ == "cat") then
evt.res, evt = events.form( evt ) -- Formats the resulting wikitext, can be re-form later
elseif (evt.typ == "err") then
evt.res, evt = events.form( evt ) -- Formats the resulting wikitext, can be re-form later
elseif (evt.typ == "wng") then
evt.res, evt = events.form( evt ) -- Formats the resulting wikitext, can be re-form later
end
return evt
end -- function events.new(typ, key, ...)
 
function events.add_new(evt) -- Add a error, warning or category in the lists. S170626rev
-- Select only new events
if type(evt) ~= "table" then evt = {} end
local new_evt = viewers.form9tests( tostring(evt.key), lua_table.to_list( evt.vals ) )
for i, event in pairs(events.list_all_events) do
local old_evt = viewers.form9tests( tostring(event.key), lua_table.to_list( event.vals ) )
if new_evt == old_evt then new_evt = nil ; break end -- Add only new events. Reject already seen events.
end
-- events.add_wng("modes_auto_val_warning_wng", langs.user_translations[key], val) -- form_result
if new_evt then table.insert(events.list_all_events, evt) end
return evt
end -- function events.add_new(typ, ref, ...)
 
function events.add_record(typ, key, ... ) -- Add a new error, warning or category in a list.
-- Guide line: all events are in a single table, including categories, without duplication.
-- Guide line: without duplication: events differ if the type, the key or any value of any argument differs.
-- Guide line: We can view or categorize categories.
local intern_or_use = versions.memo_i18n["en"][key]
local evt = events.new(typ, key, ...) -- Initialize and finalize a new event.
local evt = events.add_new(evt) -- Add an error, warning or category in the lists. S170626rev
local res, evt = events.form(evt, c) -- Format an event as an error, warning or category.
return res, evt
end -- local res, evt = events.add_record(typ, key, ... )
 
function events.form(evt, c) -- Format an event as an error, warning or category.
evt.res = tostring(evt.res) .. "? form " .. viewers.form9tests(".form evt.key=%1, evt.res=%2, ", evt.key, evt.res )
local evt = mw.clone(evt) -- do not disturb input event
if type(evt) ~= "table" then
evt.res = viewers.rough_view(evt)
return evt.res, evt
end
if (evt.typ ~= "cat") and (evt.typ ~= "wng") and (evt.typ ~= "err") then
evt.res = viewers.rough_view(evt)
return evt.res, evt
end
evt.tableStyle = evt.tableStyle or "" -- Could change the style of the wikitext. Not available on 20160916
if type(evt.name) ~= "string" then evt.name = ""
elseif evt.name ~= "" then evt.name = evt.name .. "_" end
evt.idargs = evt.name .. tostring( viewers.form9user( tostring(evt.key), lua_table.to_list( evt.vals ) ) )
-- Each type of event formats its own type of wikitext
evt.content_wkt = viewers.form9content(evt.key, lua_table.to_list( evt.vals ) )
evt.page_wkt = viewers.form9page(evt.key, lua_table.to_list( evt.vals ) )
evt.user_wkt = viewers.form9user(evt.key, lua_table.to_list( evt.vals ) )
evt.res = "" -- multilingual
if evt.typ == "err" then evt.res = viewers.styles_color_error(evt.user_wkt) end
if evt.typ == "wng" then evt.res = viewers.styles_color_warning(evt.user_wkt) end
evt.ccc = c or evt.catview or events.catview or ":"
evt.content_catspace = mw.site.namespaces.Category.name -- name: Local namespace name.
if evt.typ == "cat" then -- Format a category to display or activate
evt.res = events.form_cat(evt)
if viewers.is_in("_i_cat", key) then -- If needed, add a second "Category:Module with internal error"
res = res .. events.add_cat("versions_with_internal_error")
end
if viewers.is_in("_u_cat", key) then -- If needed, add a second "Category:Module with user error"
res = res .. events.add_cat("versions_with_user_error")
end
end
return evt.res, evt
end -- function events.form(evt, c)
 
events.all_kinds_test_test_group = {
{ "abc", "langs_form9user_all_types_values", { "pi = ", "circle / diameter", 3.14, }, },
{ "equation", "langs_form9user_all_types_values", { 11, 7, 3.14, }, },
{ "Matrix:", "langs_form9user_all_types_values", { "2.1.0", "v4-6, ISO_8601, FC14 h6", }, },
{ "pi = ", "langs_form9user_all_types_values", { "circle / diameter", 3.14, }, },
{ "quadrature", "langs_form9user_all_types_values", { function() end, "convert a square to a circle", }, },
}
-- langs_form9user_all_types_values = "Test: string=%1 number=%2 nil=%3 function=%4 table=%5.",
function events.all_kinds_test(t) -- Test: all kinds of events (err, wng, cat)
local memo = viewers.save_configs("events.all_kinds_test") -- Save global configuration before eventual changes.
events.all_kinds_trck = "\n* events.all_kinds_trck: "
local t = t or ""
t = t .. "\n* events.all_kinds_test(t) -- Test: all kinds of events (err, wng, cat): "
t = t .. events.all_kinds_trck
local tab_view = { -- Group datas and options for a table view with lines and columns.
test_group = events.all_kinds_test_test_group, -- Use default cases.
title_memo = "events_all_kinds_tests_title", -- "events.all_kinds_test() Test: all kinds of events (err, wng, cat)",
headers = "events_all_kinds_tests_headers", -- "typ;key;idargs;result",
rowGroup = {},
}
function tab_view.form_one_case(evt) -- Convert a case from test_group to rowGroup.
return { evt.typ or "t", evt.key or "k", evt.idargs or "i", evt.res or "r" }
end
t = t .. tableview.new(tab_view) -- Formats a table view with lines and columns.
t = t .. viewers.ta("end #test_group *2", lua_table.level_count(tab_view.test_group) ) -- function tableview.new( nil bug170602
t = t .. viewers.ta("end #rowGroup *2", lua_table.level_count(tab_view.rowGroup) ) -- function tableview.new( nil bug170602
t = t .. events.all_kinds_trck
viewers.restore_configs(memo, "events.all_kinds_test") -- Restore global configurations after eventual changes.
return t
end -- function events.all_kinds_test(t)
 
function events.add_cat_group(groupCat, groupList) -- Add some categories in the actual table of events. Separated by ";".
-- catGroup("Country %1", "France,Italia") -> [[Category:Country France]] [[Category:Country Italia]]
if type(groupCat) ~= "string" then groupCat = "%1" end
if type(groupList) ~= "string" then return "" end
local cats = ""
for i, str in mw.text.gsplit(groupList, ";", true) do
local wkt = viewers.form9user(groupCat, str)
cats = cats .. events.add_cat(groupCat, wkt)
end
local res, evt = events.add("catGroup", groupCat, cats) -- Add an event to a group.
evt.trc = evt.trc .. viewers.form9user("\n* add_cat evt.typ=%1, evt.key=%2, ", evt.typ, evt.key)
return res, evt
end -- function events.add_cat_group(groupCat, groupList)
 
function events.select_typ(typ) -- Select events by one type
local is = {}
for i, evt in pairs(events.test_group) do
if evt.typ == typ then table.insert( is, evt.idargs ) end
end
return is
end
 
function events.sort_typ() -- Sort events by type in wng, err, cat.
local wng, err, cat = {}, {}, {}
for i, evt in pairs(events.test_group) do
if evt.typ == "wng" then table.insert( wng, evt ) end
if evt.typ == "err" then table.insert( err, evt ) end
if evt.typ == "cat" then table.insert( cat, evt ) end
end
return wng, err, cat
end -- function events.sort_typ()
 
function events.selector( tab_view, evt )
if type(evt) ~= "table" then
evt = { -- options for tableview.new() -- Formats a table with lines and columns.
headers = "typ;key;selector-name;wkt",
style = "",
typ = "err",
rowGroup = {},
}
else
evt.headers = evt.headers or "typ;key;else-name;wkt"
evt.tableStyle = evt.tableStyle or ""
evt.name = evt.name or "_"
evt.typ = evt.typ or "nil"
end
if (type(tab_view) == "table") and (type(tab_view.typ) == "string") and (tab_view.typ == evt.typ) then
table.insert( tab_view.test_group, { evt.typ, evt.key, evt.name, evt.wkt } )
elseif (type(tab_view) == "table") and (type(tab_view.typ) == "string") and (tab_view.typ == "v") then
table.insert( tab_view.test_group, { evt.typ, evt.key, evt.name, evt.wkt } )
else
tab_view = {}
table.insert( tab_view.test_group, { evt.typ, evt.key, evt.name, evt.wkt } )
end
end -- function events.selector( tab_view, evt )
 
function events.all_kinds_test_test(t) -- Test: all kinds of events (err, wng, cat)
local memo = viewers.save_configs("events.all_categories_test") -- Save global configuration before eventual changes.
local t = t or "\n* <b>events.all_kinds_test()</b> Test: all kinds of events (err, wng, cat)"
local tab_view = { -- Group datas and options for a table view with lines and columns.
test_group = nil, -- Use default cases.
title_memo = "events_all_kinds_tests_title", -- "events.all_kinds_test() Test: all kinds of events (err, wng, cat)",
headers = "events_all_kinds_tests_headers", -- "typ;key;idargs;result",
}
function tab_view.form_one_case(evt) -- Convert a case from test_group to rowGroup.
return { evt.typ, evt.key, evt.idargs, evt.res }
end
t = t .. tableview.new(tab_view) -- Form a table view with lines and columns.
viewers.restore_configs(memo, "events.all_kinds_test_test") -- Restore global configurations after eventual changes.
return t --, errors -- langs_missing_translations_title
end -- function events.all_kinds_test_test(t)
 
events.errors_list = {} -- Deprecated: Table to collect errors and warnings
events.erron = true -- Activated or not errors. Errores activado o no. Erreurs activées ou non.
events.categories_list = {} -- Table to collect all categories to generate in wikitext
 
function events.errors_lister(title, v1, v2, v3, v4, v5, v6, v7, v8, v9)
local res, msgref = "", ""
local mwtitle = mw.title.getCurrentTitle()
local page = tostring(mwtitle.nsText) .. ":" .. tostring(mwtitle.text)
if type(title) ~= "string" then title = "modes_error_list_header_err" end
res = res .. '\n*' .. viewers.form9user(title, page, v1, v2, v3, v4, v5, v6, v7, v8, v9) -- .. ' - ' .. page
local n = 0
for k, wng in ipairs(events.errors_list) do
msgref = viewers.form9user(wng.ref, wng.v1, wng.v2, wng.v3, wng.v4, wng.v5, wng.v6, wng.v7, wng.v8, wng.v9) -- texte traduit ou direct
if wng.typ == "wng" then
res = res .. '<br>⦁ ' .. viewers.styles_color_warning(msgref)
end
end
for k, wng in ipairs(events.errors_list) do
msgref = viewers.form9user(wng.ref, wng.v1, wng.v2, wng.v3, wng.v4, wng.v5, wng.v6, wng.v7, wng.v8, wng.v9) -- texte traduit ou direct
if wng.typ == "err" then
res = res .. '<br>⦁ ' .. viewers.styles_color_error(msgref)
n = n + 1
end
end
if n > 0 then
events.add_cat("versions_module_with_error_err")
end
return res
end -- function events.errors_lister(title, v1, v2, v3, v4, v5, v6, v7, v8, v9)
 
function events.gener_categories(args_final) -- Only for this library, form categories without activate them
local args_final = args_final
if type(args_final) ~= "table" then args_final = modes.args_final end
if args_final.birthyear then
events.add_cat("p_authors_birthyear_cat", args_final.birthyear)
end
if args_final.deathyear then
events.add_cat("p_authors_deathyear_cat", args_final.deathyear)
end
if args_final.description then
-- events.add_cat("p_authors_deathyear_cat", args_final.description)
end
return
end -- function events.gener_categories(args_final)
 
function events.categories_lister(c) -- Categorize categories, or view categories if c=":".
local res = ""
modes.options_to_cat_view()
-- c can replace cat_view to enforce the documentation or the categorisation
c = c or modes.cat_view or ""
for k, evt in pairs(events.list_all_events) do
if (evt.typ == "cat") then
local keyuser = viewers.form9user(evt.key)
local keycontent = viewers.form9content(evt.key)
res = res .. events.form_cat(evt, keyuser, keycontent, c)
end
end
return res
end -- function events.categories_lister(c)
 
-- cut_libraries
 
-- - - - ------------------ - - - - ------------------ - - - - -----------------------------
-- - - - ------------------ - - - - ------------------ - - - - -----------------------------
-- The Library:langs supports i18n translations.
-- - - - ------------------ - - - - ------------------ - - - - -----------------------------
-- - - - ------------------ - - - - ------------------ - - - - -----------------------------
 
-- These Module:Centralizer/I18N translations for langs library update and complete Module:Centralizer translations.
langs.i18n = {}
langs.i18n.br = {
language = 'langue',
langs_translations_counts_title = "langs.translations_counts() Comptages des traductions en tables",
langs_translations_stats_report_title = "Traductions: nombres par langues et par librairies ou modules.",
langs_translations_stats_report_headers = "En-têtes calculés",
langs_form9user_tests_title = "viewers.form9user() Test: Remplacer <b>%1</b> à %9 par tostring( argN ) à partir des arguments",
langs_form9user_all_types_values = "Résultats de test: string=<b>%1</b> number=<b>%2</b> nil=<b>%3</b> function=<b>%4</b> table=%5.",
langs_form99user_tests_title = "viewers.form99user() Test: Remplacer %01 à %99 par tostring( argN ) à partir des arguments",
langs_form99user_all_types_values = "en viewers.form99user() Valeurs de tous types : <b>%1</b>, <b>%2</b>, <b>%3</b>, <b>%4</b>, %5.",
langs_translations_key_missing = "Erreur interne: Clé de traduction manquante ou anormale dans viewers.trans9vars()",
langs_form99user_no_tranlation = "en viewers.form99user() Manque de traduction.",
langs_form99user_a_value_is_table = "en viewers.form99user() Une valeur est une table.",
langs_lang_not_exist_err = "Erreur : La langue <b>%1</b> n'est pas disponible.",
langs_abnormal_char_in_text_title = "langs.abnormal_char_in_text() Test: Détecter les caractères anormaux dans un texte unilingue.",
langs_abnormal_char_in_alphabet = "abcdefghabklmnopqrstuvwxyz ABCDEFGHABKLMNOPQRSTUVWXYZ 013456789 àéèêëiouüœ ÀÉÈÊËIOUÜŒ ,;.:!?",
langs_list_MediaWiki_languages_title = "langs.list_MediaWiki_languages() Liste de toutes les langues de MediaWiki.",
-- Principaux textes, erreurs et catégories des outils
langs_first_tests_languages = "Documentation des premières langues",
langs_content_page_user_lang_msg = "Langues : content: <b>%1</b>, page: <b>%2</b>, user: <b>%3</b>.",
langs_without_translation_err = "Argument connu, mais non traduit : <b>%1</b>.",
langs_without_translation_N_err = "Il y a <b>%1</b> arguments non traduits.",
langs_main_i18n_languages_count = "Ce module peut traduire <b>%1</b> phrases en <b>%2</b> langues : ",
langs_table_can_translate_counts = "La table <b>%1</b> peut traduire <b>%2</b> phrases en <b>%3</b> langues.",
langs_mw_language_fetchLanguageName = "<b>%1</b>(%2=%3), ",
langs_counts_translations_headers = "*; Nom de la table; Textes; Tables; Commentaire",
langs_i18n_list_all_string = "Cette liste montre tous les textes, mais ne peut remplacer les déclarations originales.",
langs_languages_nbr_and_list = "\n* Il y a <b>%1</b> tables de traductions dans ces langues : <b>%2</b> <br>",
langs_string_translated_in_langs = "Il y a <b>%1</b> textes traduits en <b>%2</b> langues.",
langs_no_wiki_translations_err = "Erreur interne : Module sans table d'arguments traduits.",
langs_list_in_translated_lang = "<b>%1</b> traductions en langage <b>%2</b> : <b>%3</b> : <b>%4</b>",
langs_changing_translations_title = "langs.changing_translations() Changements de traduction dans les tables i18n",
langs_changing_translations_headers = "Module; Langue; Clé i18n; Traduction précédente; Traduction changeante",
langs_missing_translations_title = "langs.missing_translations() Traductions manquantes dans les tables i18n.",
langs_missing_translations_headers = "Langue; clé i18n; Traduction précédente; Nouvelle traduction; Module",
langs_changing_translations_help = "Voir aussi <b>%1</b> pour demander de l'aide pour traduire.",
langs_mixed_translations_title = "Tables de traductions i18n combinées :",
langs_dummy_languages_title = "langs.dummy_languages() Caractéristiques de quelques langues:",
langs_Module_Central_version = "Central-w-fr",
langs_selectLang_tests_title = "langs.select_lang() Tests: Select a language for tests or other",
langs_selectLang_test_headers = "Wiki language; User language; Sought language; Selected language; Example",
langs_selectLang_test_example = "Language: content = <b>%1</b>, user = <b>%2</b>, selected = <b>%3</b>.",
langs_selectLang_test_err = "Internal error : langs.select_lang(lang) has no tests table.",
langs_selectLang_test_cat = "Module avec erreur interne",
langs_missing_one_translation_err = "Traduction manquante, clé <b>%1</b> en langue <b>%2</b>",
langs_missing_one_translation_i_cat = "Traduction manquante, au moins une", -- + "Module with internal error",
} -- langs.i18n.br
langs.i18n.de = {
language = 'Sprache',
langs_translations_counts_title = "langs.translations_counts() Übersetzungen in Tabellen zählen",
langs_translations_stats_report_title = "Übersetzungen: Zahlen nach Sprachen und nach Bibliotheken oder Modulen.",
langs_translations_stats_report_headers = "Berechnete Kopfzeilen",
langs_form9user_tests_title = "viewers.form9user() Test: Ersetzen Sie <b>%1</b> bis %9 durch tostring(argN) von den Argumenten",
langs_form9user_all_types_values = "Testergebnisse: string=<b>%1</b> number=<b>%2</b> nil=<b>%3</b> function=<b>%4</b> table=%5.",
langs_form99user_tests_title = "viewers.form99user() Test: Ersetzen Sie %01 bis %99 durch tostring(argN) von den Argumenten",
langs_form99user_all_types_values = "en viewers.form99user() Werte aller Arten: <b>%1</b>, <b>%2</b>, <b>%3</b>, <b>%4</b>, %5.",
langs_translations_key_missing = "Interner Fehler: Fehlender oder abnormaler Übersetzungsschlüssel viewers.trans9vars()",
langs_form99user_no_tranlation = "in viewers.form99user() Mangel an Übersetzung.",
langs_form99user_a_value_is_table = "in viewers.form99user() Ein Wert ist eine Tabelle.",
langs_lang_not_exist_err = "Fehler: <b>%1</b> Sprache ist nicht verfügbar.",
langs_abnormal_char_in_text_title = "langs.abnormal_char_in_text() Test: Ermitteln Sie abnormale Zeichen in einem einsprachigen Text.",
langs_abnormal_char_in_alphabet = "abcdefghabklmnopqrstuvwxyz ABCDEFGHABKLMNOPQRSTUVWXYZ 013456789 àéèêëiouüœ ÀÉÈÊËIOUÜŒ ,;.:!?",
langs_list_MediaWiki_languages_title = "langs.list_MediaWiki_languages() Liste aller MediaWiki-Sprachen.",
-- Haupttexte, Fehler und Kategorien von Werkzeugen
langs_first_tests_languages = "Dokumentation der ersten Sprachen",
langs_content_page_user_lang_msg = "Sprachen: content: <b>%1</b>, page: <b>%2</b>, user: <b>%3</b>.",
langs_without_translation_err = "Bekannt, aber nicht übersetzt: <b>%1</b>.",
langs_without_translation_N_err = "Es gibt <b>%1</b> nicht übersetzte Argumente.",
langs_main_i18n_languages_count = "Dieses Modul kann <b>%1</b> Sätze in <b>%2</b> Sprachen übersetzen.",
langs_table_can_translate_counts = "LaDie Tabelle <b>%1</b> kann <b>%2</b> Sätze in <b>%3</b> Sprachen übersetzen.",
langs_mw_language_fetchLanguageName = "<b>%1</b>(<b>%2</b>=<b>%3</b>), ",
langs_counts_translations_headers = "*; Name der Tabelle; Texte; Tabellen; Kommentar",
langs_i18n_list_all_string = "Diese Liste zeigt alle Texte, kann aber die ursprünglichen Aussagen nicht ersetzen.",
langs_languages_nbr_and_list = "\n* Es gibt <b>%1</b> Übersetzungstabellen in diesen Sprachen: <b>%2</b> <br>",
langs_string_translated_in_langs = "Es sind <b>%1</b> Texte in <b>%2</b> Sprachen übersetzt.",
langs_no_wiki_translations_err = "Interner Fehler: Modul ohne übersetzte Argumententabelle.",
langs_list_in_translated_lang = "<b>%1</b> Sprachübersetzungen <b>%2</b> : <b>%3</b> : <b>%4</b>",
langs_changing_translations_title = "langs.changing_translations() Übersetzungsänderungen in i18n-Tabellen",
langs_changing_translations_headers = "Modul; Sprache; Schlüssel i18n; Vorherige Übersetzung; Ändern der Übersetzung",
langs_missing_translations_title = "langs.missing_translations() Fehlende Übersetzungen in i18n-Tabellen.",
langs_missing_translations_headers = "Sprache; i18n Schlüssel; Vorherige Übersetzung Neue Übersetzung Modul",
langs_changing_translations_help = "Siehe auch <b>%1</b> für die Hilfe beim Übersetzen.",
langs_mixed_translations_title = "i18n Übersetzungstabellen kombiniert:",
langs_dummy_languages_title = "langs.dummy_languages() Eigenschaften einiger Sprachen:",
langs_Module_Central_version = "Central-w-de",
langs_selectLang_tests_title = "langs.select_lang() Tests: Wählen Sie eine Sprache für Tests oder andere Tests aus",
langs_selectLang_test_headers = "Wiki-Sprache; Benutzersprache; Gesuchte Sprache; Ausgewählte Sprache; Beispiel",
langs_selectLang_test_example = "Sprache: content = <b>%1</b>, user = <b>%2</b>, selected = <b>%3</b>.",
langs_selectLang_test_err = "Internal error : langs.select_lang(lang) has hat keine Testtabelle.",
langs_selectLang_test_cat = "Modul mit internem Fehler",
langs_missing_one_translation_err = "Fehlende Übersetzung, Schlüssel <b>%1</b> in Sprache <b>%2</b>",
langs_missing_one_translation_i_cat = "Fehlende Übersetzung, mindestens eine", -- + "Module with internal error",
} -- langs.i18n.de
langs.i18n.en = {
language = 'language',
langs_translations_counts_title = "langs.translations_counts() Counts of translations into tables",
langs_translations_stats_report_title = "Translations: numbers by language and by libraries or modules.",
langs_translations_stats_report_headers = "Computed headers",
langs_form9user_tests_title = "viewers.form9user() Test: Replace <b>%1</b> to %9 by tostring( argN ) from arguments",
langs_form9user_all_types_values = "Résultats de test: string=<b>%1</b> number=<b>%2</b> nil=<b>%3</b> function=<b>%4</b> table=%5.",
langs_form99user_tests_title = "in viewers.form99user() Test: Replace %01 to %99 by tostring( argN ) from arguments",
langs_form99user_all_types_values = "in viewers.form99user() Values of all types: <b>%1</b>, <b>%2</b>, <b>%3</b>, <b>%4</b>, %5.",
langs_form99user_no_tranlation = "in viewers.form99user() Lack of translation.",
langs_form99user_a_value_is_table = "in viewers.form99user() A value is a table.",
langs_translations_key_missing = "Internal error: Translations key missing or abnormal in viewers.trans9vars()",
langs_lang_not_exist_err = "Error: The language <b>%1</b> is not available.",
langs_abnormal_char_in_text_title = "langs.abnormal_char_in_text() Test: Detect abnormal characters in an unilingual text.",
langs_abnormal_char_in_alphabet = "abcdefghabklmnopqrstuvwxyz ABCDEFGHABKLMNOPQRSTUVWXYZ 013456789 ,;.:!?",
langs_list_MediaWiki_languages_title = "langs.list_MediaWiki_languages() List all MediaWiki languages.",
-- Main string, errors and categories of tools
langs_first_tests_languages = "Documentation of first languages",
langs_content_page_user_lang_msg = "Languages: content: <b>%1</b>, page: <b>%2</b>, user: <b>%3</b>.",
langs_without_translation_err = "Known argument, but not translated: <b>%1</b>.",
langs_without_translation_N_err = "There are <b>%1</b> arguments untranslated.",
langs_main_i18n_languages_count = "This module can translate <b>%1</b> sentences into <b>%2</b> languages: ",
langs_table_can_translate_counts = "The table <b>%1</b> can translate <b>%2</b> sentences into <b>%3</b> languages.",
langs_mw_language_fetchLanguageName = "<b>%1</b>(%2=%3), ",
langs_counts_translations_headers = "*; Table name; Texts; Tables; Comment",
langs_i18n_list_all_string = "This list show all the string, but cannot replace the original declarations.",
langs_languages_nbr_and_list = "\n* There are <b>%1</b> tables of translations in these languages : <b>%2</b> <br>",
-- Miscellaneous warnings and errors
langs_string_translated_in_langs = "There are <b>%1</b> string translated in <b>%2</b> languages.",
langs_no_wiki_translations_err = "Error: Module without translated arguments table.",
langs_list_in_translated_lang = "<b>%1</b> translations in language <b>%2</b> : <b>%3</b> : <b>%4</b>",
langs_transdiff_wanted_error_err = "Wanted error for minimal test of langs.missing_translations().",
langs_missing_translations_title = "langs.missing_translations() Missing translations in i18n tables.",
langs_missing_translations_headers = "Language; i18n Key; Previous translation; New translation; Module",
langs_changing_translations_headers = "Language; i18n Key; Previous translation; New translation; Module",
langs_changing_translations_help = "See also <b>%1</b> to ask for help to langs.",
langs_mixed_translations_title = "langs.i18n_lister() Combined i18n translations tables:",
langs_dummy_languages_title = "langs.dummy_languages() Characteristics of some languages:",
langs_Module_Central_version = "Central-w-en",
langs_selectLang_tests_title = "langs.select_lang() Tests: Select a language for tests or other",
langs_selectLang_test_headers = "Wiki language; User language; Sought language; Selected language; Example",
langs_selectLang_test_example = "Language: content = <b>%1</b>, user = <b>%2</b>, selected = <b>%3</b>.",
langs_selectLang_test_err = "Internal error : langs.select_lang(lang) has no tests table.",
langs_selectLang_test_cat = "Module with internal error",
langs_missing_one_translation_err = "Missing translation key <b>%1</b> in <b>%2</b> language",
langs_missing_one_translation_i_cat = "Missing at least one translation", -- + "Module with internal error",
} -- langs.i18n.en
langs.i18n.es = { -- ¿Quién es?
language = 'lenguaje',
langs_translations_counts_title = "langs.translations_counts() Condes des traducciones en tablas",
langs_translations_stats_report_title = "Traducciones: números por idioma y por bibliotecas o módulos.",
langs_translations_stats_report_headers = "Encabezados calculados",
langs_form9user_tests_title = "viewers.form9user() Prueba: Reemplazar <b>%1</b> a %9 por tostring( argN ) a partir de argumentos",
langs_form9user_all_types_values = "Résultats de test: string=<b>%1</b> number=<b>%2</b> nil=<b>%3</b> function=<b>%4</b> table=%5.",
langs_form99user_tests_title = "en viewers.form99user() Prueba: Reemplazar %01 a %99 por tostring( argN ) a partir de argumentos",
langs_form99user_all_types_values = "en viewers.form99user() Valores de todos los tipos: <b>%1</b>, <b>%2</b>, <b>%3</b>, <b>%4</b>, %5.",
langs_form99user_no_tranlation = "en viewers.form99user() Falta de traducción.",
langs_form99user_a_value_is_table = "en viewers.form99user() Un valor es una tabla.",
langs_translations_key_missing = "Error interno: Traducciones clave que falta o anormal en viewers.trans9vars()",
langs_lang_not_exist_err = "Error: El lenguaje <b>%1</b> no está disponible.",
langs_abnormal_char_in_text_title = "langs.abnormal_char_in_text() Prueba: Detectar caracteres anormales en un texto monolingüe.",
langs_abnormal_char_in_alphabet = "abcdefghabklmnopqrstuvwxyz ABCDEFGHABKLMNOPQRSTUVWXYZ 013456789 àéèêëiouüœ ÀÉÈÊËIOUÜŒ ,;.:!?",
langs_list_MediaWiki_languages_title = "langs.list_MediaWiki_languages() Lista de todos los idiomas de MediaWiki.",
-- Textos principales, errores y categorías de instrumentos
langs_first_tests_languages = "Documentación de las primeras idiomas",
langs_content_page_user_lang_msg = "Idiomas: content: <b>%1</b>, page: <b>%2</b>, user: <b>%3</b>.",
langs_without_translation_err = "Argumento conocido, pero no traducido: <b>%1</b>.",
langs_without_translation_N_err = "Hay <b>%1</b> argumentos no traducidos.",
-- Diversos mensajes y errores
langs_main_i18n_languages_count = "Este módulo puede traducir <b>%1</b> frases en <b>%2</b> idiomas: ",
langs_table_can_translate_counts = "Tabla <b>%1</b> puede traducir <b>%2</b> frases en <b>%3</b> idiomas.",
langs_mw_language_fetchLanguageName = "<b>%1</b>( <b>%2</b> = <b>%3</b> ), ",
langs_counts_translations_headers = "*; Nombre de la tabla; Textos; Mesas; Comentario",
langs_languages_nbr_and_list = "\n* Hay <b>%1</b> mesas de traducciones en estas idiomas: <b>%2</b> <br>",
langs_string_translated_in_langs = "Hay <b>%1</b> textos traducidos en <b>%2</b> idiomas.",
langs_no_wiki_translations_err = "Error: Módulo sin argumentos traducidos tabla.",
langs_i18n_list_all_string = "Esta lista muestra todos los textos, pero no puede sustituir a las declaraciones originales.",
langs_list_in_translated_lang = "<b>%1</b> traducciones en idioma <b>%1</b>:<b>%2</b>:<b>%3</b> <b>%4</b> ",
langs_missing_translations_title = "langs.missing_translations() Faltan traducciones en las tablas i18n.",
langs_missing_translations_headers = "Idioma; llave i18n; Traducción previa; Nueva traducción; Módulo",
langs_changing_translations_title = "langs.changing_translations() Changing (or missing) translations in i18n tables.",
langs_changing_translations_title = "langs.changing_translations() Traducciones que cambian (o falta de) en las tablas i18n.",
langs_changing_translations_headers = "Idioma; Clave i18n; Traducción anterior; Nueva traducción; Módulo",
langs_changing_translations_help = "Consulte también <b>%1</b> para solicitar ayuda para traducir.",
langs_mixed_translations_title = "Tablas traducciones i18n combinadas:",
langs_dummy_languages_title = "langs.dummy_languages() Características de algunos idiomas:",
langs_Module_Central_version = "Central-w-es",
langs_selectLang_tests_title = "langs.select_lang() Tests: Select a language for tests or other",
langs_selectLang_test_headers = "Wiki language; User language; Sought language; Selected language; Example",
langs_selectLang_test_example = "Language: content = <b>%1</b>, user = <b>%2</b>, selected = <b>%3</b>.",
langs_selectLang_test_err = "Internal error : langs.select_lang(lang) has no tests table.",
langs_selectLang_test_cat = "Module with internal error",
langs_missing_one_translation_err = "Falta traducción, clave <b>%1</b> en el idioma <b>%2</b>",
langs_missing_one_translation_i_cat = "Falta la traducción, al menos uno", -- + "Module with internal error",
} -- langs.i18n.es
langs.i18n.fr = {
language = 'langue',
langs_translations_counts_title = "langs.translations_counts() Comptages des traductions en tables",
langs_translations_stats_report_title = "Traductions: nombres par langues et par librairies ou modules.",
langs_translations_stats_report_headers = "En-têtes calculés",
langs_form9user_tests_title = "viewers.form9user() Test: Remplacer <b>%1</b> à %9 par tostring( argN ) à partir des arguments",
langs_form9user_all_types_values = "Résultats de test: string=<b>%1</b> number=<b>%2</b> nil=<b>%3</b> function=<b>%4</b> table=%5.",
langs_form99user_tests_title = "viewers.form99user() Test: Remplacer %01 à %99 par tostring( argN ) à partir des arguments",
langs_form99user_all_types_values = "en viewers.form99user() Valeurs de tous types : <b>%1</b>, <b>%2</b>, <b>%3</b>, <b>%4</b>, %5.",
langs_translations_key_missing = "Erreur interne: Clé de traduction manquante ou anormale dans viewers.trans9vars()",
langs_form99user_no_tranlation = "en viewers.form99user() Manque de traduction.",
langs_form99user_a_value_is_table = "en viewers.form99user() Une valeur est une table.",
langs_lang_not_exist_err = "Erreur : La langue <b>%1</b> n'est pas disponible.",
langs_abnormal_char_in_text_title = "langs.abnormal_char_in_text() Test: Détecter les caractères anormaux dans un texte unilingue.",
langs_abnormal_char_in_alphabet = "abcdefghabklmnopqrstuvwxyz ABCDEFGHABKLMNOPQRSTUVWXYZ 013456789 àéèêëiouüœ ÀÉÈÊËIOUÜŒ ,;.:!?",
langs_list_MediaWiki_languages_title = "langs.list_MediaWiki_languages() Liste de toutes les langues de MediaWiki.",
-- Principaux textes, erreurs et catégories des outils
langs_first_tests_languages = "Documentation des premières langues",
langs_content_page_user_lang_msg = "Langues : content: <b>%1</b>, page: <b>%2</b>, user: <b>%3</b>.",
langs_without_translation_err = "Argument connu, mais non traduit : <b>%1</b>.",
langs_without_translation_N_err = "Il y a <b>%1</b> arguments non traduits.",
langs_main_i18n_languages_count = "Ce module peut traduire <b>%1</b> phrases en <b>%2</b> langues : ",
langs_table_can_translate_counts = "La table <b>%1</b> peut traduire <b>%2</b> phrases en <b>%3</b> langues.",
langs_mw_language_fetchLanguageName = "<b>%1</b>(%2=%3), ",
langs_counts_translations_headers = "*; Nom de la table; Textes; Tables; Commentaire",
langs_i18n_list_all_string = "Cette liste montre tous les textes, mais ne peut remplacer les déclarations originales.",
langs_languages_nbr_and_list = "\n* Il y a <b>%1</b> tables de traductions dans ces langues : <b>%2</b> <br>",
langs_string_translated_in_langs = "Il y a <b>%1</b> textes traduits en <b>%2</b> langues.",
langs_no_wiki_translations_err = "Erreur interne : Module sans table d'arguments traduits.",
langs_list_in_translated_lang = "<b>%1</b> traductions en langage <b>%2</b> : <b>%3</b> : <b>%4</b>",
langs_changing_translations_title = "langs.changing_translations() Changements de traduction dans les tables i18n",
langs_changing_translations_headers = "Module; Langue; Clé i18n; Traduction précédente; Traduction changeante",
langs_missing_translations_title = "langs.missing_translations() Traductions manquantes dans les tables i18n.",
langs_missing_translations_headers = "Langue; clé i18n; Traduction précédente; Nouvelle traduction; Module",
langs_changing_translations_help = "Voir aussi <b>%1</b> pour demander de l'aide pour traduire.",
langs_mixed_translations_title = "Tables de traductions i18n combinées :",
langs_dummy_languages_title = "langs.dummy_languages() Caractéristiques de quelques langues:",
langs_Module_Central_version = "Central-w-fr",
langs_selectLang_tests_title = "langs.select_lang() Tests: Select a language for tests or other",
langs_selectLang_test_headers = "Wiki language; User language; Sought language; Selected language; Example",
langs_selectLang_test_example = "Language: content = <b>%1</b>, user = <b>%2</b>, selected = <b>%3</b>.",
langs_selectLang_test_err = "Internal error : langs.select_lang(lang) has no tests table.",
langs_selectLang_test_cat = "Module avec erreur interne",
langs_missing_one_translation_err = "Traduction manquante, clé <b>%1</b> en langue <b>%2</b>",
langs_missing_one_translation_i_cat = "Traduction manquante, au moins une", -- + "Module with internal error",
} -- langs.i18n.fr
langs.i18n.hu = {
language = 'nyelv',
langs_translations_counts_title = "langs.translations_counts() Fordítások a táblázatokba",
langs_translations_stats_report_title = "Fordítások: számok nyelv és könyvtárak vagy modulok szerint.",
langs_translations_stats_report_headers = "Számított fejlécek",
langs_form9user_tests_title = "viewers.form9user() Teszt: Az argumentumokból tostring(argN) helyett <b>%1</b> - %9 helyettesítse",
langs_form9user_all_types_values = "Teszt: string=<b>%1</b> number=<b>%2</b> nil=<b>%3</b> function=<b>%4</b> table=%5.",
langs_form99user_tests_title = "viewers.form99user() Teszt: Az argumentumokból tostring(argN) helyett %01 - %99 helyettesítse",
langs_form99user_all_types_values = "Teszt: string=<b>%1</b> number=<b>%2</b> nil=<b>%3</b> function=<b>%4</b> table=%5.",
langs_form99user_all_types_values = "xx-ben minden típusú értékek: <b>%1</b>, <b>%2</b>, <b>%3</b>, <b>%4</b>, %5.",
langs_translations_key_missing = "Belső hiba: hiányzik vagy abnormális fordítási kulcs van viewers.trans9vars()",
langs_form99user_no_tranlation = "in viewers.form99user() A fordítás hiánya.",
langs_form99user_a_value_is_table = "in viewers.form99user() Az érték egy táblázat.",
langs_lang_not_exist_err = "Hiba: A (z) <b>%1</b> nyelv nem érhető el.",
langs_abnormal_char_in_text_title = "langs.abnormal_char_in_text() Teszt: A kóros karaktereket egynyelvű szövegben ismeri fel.",
langs_abnormal_char_in_alphabet = "abcdefghabklmnopqrstuvwxyz ABCDEFGHABKLMNOPQRSTUVWXYZ 013456789 àéèêëiouüœ ÀÉÈÊËIOUÜŒ ,;.:!?",
langs_list_MediaWiki_languages_title = "langs.list_MediaWiki_languages() Az összes MediaWiki nyelv listája.",
-- Fő szövegek, hibák és eszközök kategóriái
langs_first_tests_languages = "Az első nyelvek dokumentálása",
langs_content_page_user_lang_msg = "Nyelveken: content: <b>%1</b>, page: <b>%2</b>, user: <b>%3</b>.",
langs_without_translation_err = "Ismert, de nem lefordított: <b>%1</b>.",
langs_without_translation_N_err = "<b>%1</b> nem fordított argumentum van.",
langs_main_i18n_languages_count = "Ez a modul lefordíthat <b>%1</b> mondatokat <b>%2</b> nyelvekre: ",
langs_table_can_translate_counts = "A <b>%1</b> táblázat <b>%2</b> mondatokat lefordíthat <b>%3</b> nyelvekre.",
langs_mw_language_fetchLanguageName = "<b>%1</b>(%2=%3), ",
langs_counts_translations_headers = "*; A táblázat neve; szövegek; asztalok; megjegyzés",
langs_i18n_list_all_string = "Ez a lista az összes szöveget mutatja, de nem helyettesítheti az eredeti állításokat.",
langs_languages_nbr_and_list = "\n* Ezek a nyelvek <b>%1</b> fordítási táblázatok vannak: <b>%2</b> ",
langs_string_translated_in_langs = "<b>%1</b> szövegek <b>%2</b> nyelvre lettek lefordítva.",
langs_no_wiki_translations_err = "Belső hiba: Modul fordítás nélküli táblázat nélkül.",
langs_list_in_translated_lang = "<b>%1</b> nyelvi fordítások <b>%2</b> : <b>%3</b> : <b>%4</b>",
langs_changing_translations_title = "langs.changing_translations() Fordítások a táblázatokban i18n",
langs_changing_translations_headers = "modul; nyelv; I18n kulcs; Korábbi fordítás; A fordítás megváltoztatása",
langs_missing_translations_title = "langs.missing_translations() A táblázatokban hiányzik a fordítás i18n.",
langs_missing_translations_headers = "nyelv; i18n kulcs; Korábbi fordítás; Új fordítás modul",
langs_changing_translations_help = "Voir aussi <b>%1</b> pour demander de l'aide pour traduire.",
langs_mixed_translations_title = "Tables de traductions i18n combinées :",
langs_dummy_languages_title = "langs.dummy_languages() Caractéristiques de quelques langues:",
langs_Module_Central_version = "Central-w-fr",
langs_selectLang_tests_title = "langs.select_lang() Tests: Select a language for tests or other",
langs_selectLang_test_headers = "Wiki language; User language; Sought language; Selected language; Example",
langs_selectLang_test_example = "Language: content = <b>%1</b>, user = <b>%2</b>, selected = <b>%3</b>.",
langs_selectLang_test_err = "Internal error : langs.select_lang(lang) has no tests table.",
langs_selectLang_test_cat = "Module avec erreur interne",
langs_missing_one_translation_err = "Traduction manquante, clé <b>%1</b> en langue <b>%2</b>",
langs_missing_one_translation_i_cat = "Traduction manquante, au moins une", -- + "Module with internal error",
} -- langs.i18n.hu
langs.i18n.vi = {
language = 'langue',
langs_translations_counts_title = "langs.translations_counts() Số bản dịch vào các bảng",
langs_translations_stats_report_title = "Bản dịch: số theo ngôn ngữ và theo thư viện hoặc mô-đun.",
langs_translations_stats_report_headers = "Tiêu đề được tính toán",
langs_form9user_tests_title = "viewers.form9user() Test: Remplacer <b>%1</b> à %9 par tostring( argN ) à partir des arguments",
langs_form9user_all_types_values = "Test: string=<b>%1</b> number=<b>%2</b> nil=<b>%3</b> function=<b>%4</b> table=%5.",
langs_form99user_tests_title = "viewers.form99user() Test: Remplacer %01 à %99 par tostring( argN ) à partir des arguments",
langs_form99user_all_types_values = "en viewers.form99user() Valeurs de tous types : <b>%1</b>, <b>%2</b>, <b>%3</b>, <b>%4</b>, %5.",
langs_translations_key_missing = "Erreur interne: Clé de traduction manquante ou anormale dans viewers.trans9vars()",
langs_form99user_no_tranlation = "en viewers.form99user() Manque de traduction.",
langs_form99user_a_value_is_table = "en viewers.form99user() Une valeur est une table.",
langs_lang_not_exist_err = "Erreur : La langue <b>%1</b> n'est pas disponible.",
langs_abnormal_char_in_text_title = "langs.abnormal_char_in_text() Test: Détecter les caractères anormaux dans un texte unilingue.",
langs_abnormal_char_in_alphabet = "abcdefghabklmnopqrstuvwxyz ABCDEFGHABKLMNOPQRSTUVWXYZ 013456789 àéèêëiouüœ ÀÉÈÊËIOUÜŒ ,;.:!?",
langs_list_MediaWiki_languages_title = "langs.list_MediaWiki_languages() Liste de toutes les langues de MediaWiki.",
-- Principaux textes, erreurs et catégories des outils
langs_first_tests_languages = "Documentation des premières langues",
langs_content_page_user_lang_msg = "Langues : content: <b>%1</b>, page: <b>%2</b>, user: <b>%3</b>.",
langs_without_translation_err = "Argument connu, mais non traduit : <b>%1</b>.",
langs_without_translation_N_err = "Il y a <b>%1</b> arguments non traduits.",
langs_main_i18n_languages_count = "Ce module peut traduire <b>%1</b> phrases en <b>%2</b> langues : ",
langs_i18n_list_all_string = "Cette liste montre tous les textes, mais ne peut remplacer les déclarations originales.",
langs_languages_nbr_and_list = "\n* Il y a <b>%1</b> tables de traductions dans ces langues : <b>%2</b> <br>",
langs_string_translated_in_langs = "Il y a <b>%1</b> textes traduits en <b>%2</b> langues.",
langs_no_wiki_translations_err = "Erreur interne : Module sans table d'arguments traduits.",
langs_list_in_translated_lang = "<b>%1</b> traductions en langage <b>%2</b> : <b>%3</b> : <b>%4</b>",
langs_changing_translations_help = "Voir aussi <b>%1</b> pour demander de l'aide pour traduire.",
langs_mixed_translations_title = "Tables de traductions i18n combinées :",
langs_dummy_languages_title = "langs.dummy_languages() Caractéristiques de quelques langues:",
langs_Module_Central_version = "Central-w-fr",
langs_selectLang_tests_title = "langs.select_lang() Tests: Select a language for tests or other",
langs_selectLang_test_headers = "Wiki language; User language; Sought language; Selected language; Example",
langs_selectLang_test_example = "Language: content = <b>%1</b>, user = <b>%2</b>, selected = <b>%3</b>.",
langs_selectLang_test_err = "Internal error : langs.select_lang(lang) has no tests table.",
langs_selectLang_test_cat = "Module avec erreur interne",
langs_missing_one_translation_err = "Traduction manquante, clé <b>%1</b> en langue <b>%2</b>",
langs_missing_one_translation_i_cat = "Traduction manquante, au moins une", -- + "Module with internal error",
--
langs_counts_translations_headers = "*; Tên bảng; Văn bản; Những cái bàn; Bình luận",
langs_table_can_translate_counts = "Bảng <b>%1</b> có thể dịch thành <b>%2</b> câu <b>%3</b> ngôn ngữ.",
langs_mw_language_fetchLanguageName = "<b>%1</b>(%2=%3), ",
langs_changing_translations_title = "langs.changing_translations() Các bản dịch trong i18n tables",
langs_changing_translations_headers = "Mô đun; Ngôn ngữ;, Khóa i18n; Bản dịch trước; Thay đổi bản dịch",
langs_missing_translations_title = "langs.missing_translations() Thiếu bản dịch trong bảng i18n.",
langs_missing_translations_headers = "Ngôn ngữ; i18n Key; Bản dịch trước; Bản dịch mới; Mô-đun",
langs_missing_one_translation_err = "Thiếu phím dịch <b>%1</b> bằng ngôn ngữ <b>%2</b>",
langs_missing_one_translation_i_cat = "Thiếu bản dịch, ít nhất một", -- + "Module with internal error",
} -- langs.i18n.vi
 
langs.MetaSupportedLanguages = { "ja", "es", "ru", "de", "nl", "tr", "fr", "pt", "ko", "en", "it", "oc",
"pl", "fa", "ar", "vi", "arz", "hi", "sv", "diq", "pt-br", "zh", "th", "bg", "hu", "uk", "en-gb",
"sh", "id", "bn", "az", "fi", "be", "he", "eo", "el", "sd", "kn", "ro", "yue", "sr", "mk", "ta",
"pa", "hy", "lb", "tt", "si", "yi", "ne", "cs", "sk", "ms", "eu", "mr", "sa", "tl", "eml",
-- https://meta.wikimedia.org/wiki/Special:SupportedLanguages on 20170629 Rical
} -- 58 languages in total.
 
function langs.i18n_sub_counts(subnames_in, key_form, lang) -- Count i18n in the last sub-table from its sub-names.
-- local t, strings_c, tables_c, strs_on_tabs, subnames = langs.i18n_sub_counts(subnames_in, key_form, lang)
local subnames_in, key_form, lang = subnames_in, key_form, lang
if (type(subnames_in) ~= "string") then subnames_in = "" end
local t, strings_c, tables_c, strs_on_tabs, subnames = "", 0, 0, 0, ""
local sub_names = mw.text.split(subnames_in, '%.') -- table of words
local in_i18n, i18n_i, subnames_, sub_tab, all_strings, strs_on_tabs, separ
local i18n_counts, i18n_strings_c, i18n_tables_c
local lang_counts, lang_strings_c, lang_tables_c = {}
if (type(sub_names) == "table") then
subnames_ = ""
separ = ""
in_i18n = nil
i18n_i = 0
for i, sub_name in ipairs(sub_names) do
subnames_ = subnames_ .. separ .. sub_name
separ = "."
subnames = subnames_ -- string.sub(subnames_, 2, -1) -- like modes.i16n.fr
if viewers.is_in("i18n", sub_name) then -- In a i18n table
i18n_i = i
sub_tab = lua_table.from_subnames_table(subnames) -- Get the last sub-table from its sub-names.
i18n_counts = lua_table.count_types(sub_tab)
i18n_strings_c = i18n_counts.string or "0"
i18n_tables_c = i18n_counts.table or 0
tables_c = i18n_tables_c
all_strings = 0
for key, val in pairs(sub_tab) do -- ModuleCentral-s-es (begin to try in Spanish wikisource)
if (type(val) == "table") then
all_strings = all_strings + lua_table.count_all(val)
end
end
strs_on_tabs = math.floor( (all_strings + 0.49) / math.min(tables_c, 1) )
strings_c = strs_on_tabs
elseif i > i18n_i then -- In a language sub-table
sub_tab = lua_table.from_subnames_table(subnames) -- Get the last sub-table from its sub-names.
lang_counts = lua_table.count_types(sub_tab)
lang_strings_c = lang_counts.string
lang_tables_c = lang_counts.table
strings_c = lang_strings_c
tables_c = 1
end
end
end
-- This module can translate... = langs_main_i18n_languages_count
local strings_c = strings_c or 0 -- or lang_counts.strings_c
local tables_c = tables_c or 0 -- or i18n_tables_c.tables_c
local strs_on_tabs = strs_on_tabs or 0
-- Formats resulting text
if (type(lang) ~= "string") then lang = "user"
elseif lang == "c" then lang = "content"
elseif lang == "p" then lang = "page"
elseif lang == "u" then lang = "user" end
if (type(key_form) ~= "string") then key_form = "langs_table_can_translate_counts" end
local t = viewers.form9user(key_form, subnames, strings_c, tables_c)
if lang == "page" then t = viewers.form9page(key_form, subnames, strings_c, tables_c) end
if lang == "content" then t = viewers.form9content(key_form, subnames, strings_c, tables_c) end
return t, strings_c, tables_c, strs_on_tabs, subnames
-- local t, strings_c, tables_c, strs_on_tabs, subnames = langs.i18n_sub_counts(subnames_in, key_form, lang)
end -- function langs.i18n_sub_counts(subnames_in, key_form, lang)
 
function langs.translations_counts(t) -- Counts of contents of some tables, from their names. -- S170618ltc
local memo = viewers.save_configs("langs.translations_counts") -- Save global configuration before eventual changes.
local t = t or '\n* langs.translations_counts("activity.i18n") Counts of contents of some tables, from their names: '
local selector = "br;es;vi;modes;begin;translate;" -- Select a reduces table view.
local object_loaded, counts, pre_counts, tables_c, sub_string_count
local tabname, subnames, tt, lang
local trans_Group, trans_counts = {}, {}
local libname_total = 0
local select_track = "-" -- nil
local trans_counts = {}
for libname, library in pairs(package.loaded) do
if (type(library.i18n) == "table") then -- Select all libraries with i18n tables.
tabname = libname .. ".i18n"
table.insert(trans_Group, { tabname } ) -- Build a table with translations counts.
end
end
table.sort(trans_counts, function (row_x, row_y) return ( row_x[1] < row_x[1] ) end ) -- Sort based on [1]=tabname
local test_tables = "versions.memo_i18n;begin.i18n.de;begin.i18n.hu;begin.i18n.vi;modes.i18n.fr" -- Select a reduces table view.
local test_tables_tab = mw.text.split(test_tables, ';') -- table of words
for i, subnames_in in ipairs(test_tables_tab) do -- list all used names, only one each, in alphabetic order
table.insert(trans_Group, { ["subnames_in"] = subnames_in, ["i"] = i } ) -- Build a table with translations counts.
end
local tab_view = { -- Group datas and options for a table view with lines and columns.
-- test_group = trans_Group,
test_group = {
{ i = 1, subnames_in = "activity.i18n.hu", },
{ i = 2, subnames_in = "versions.i18n.hu", },
{ i = 3, subnames_in = "versions.i18n.en", },
{ i = 4, subnames_in = "versions.memo_i18n.en", },
{ i = 5, subnames_in = "versions.memo_i18n.hu", },
{ i = 6, subnames_in = "versions.memo_i18n.vi", },
{ i = 7, subnames_in = "versions.memo_i18n", },
},
title_memo = "langs_translations_counts_title", -- "langs.translations_counts() Counts of translations in tables",
headers = "langs_counts_translations_headers", -- "*; Table name; Texts; Tables; Comment",en
headers_class = "wikitable alternative center sortable",
rowselect = selector,
rowGroup = {}, -- tests or tab_view.test_group or
}
function tab_view.form_one_case(case) -- Convert a case from test_group to rowGroup.
case.subnames_in = case.subnames_in or "subnames_in"
case.sub_names = lua_table.from_subnames_table(case.subnames_in, case.base_table) -- Get the last sub-table from its sub-names.
case.i = case.i or 33
case.t, case.strings_c, case.tables_c, case.strs_on_tabs, case.subnames = langs.i18n_sub_counts(case.subnames_in, "langs_table_can_translate_counts", "user")
case.comment = viewers.form9user("langs_table_can_translate_counts", case.subnames, case.strings_c, case.tables_c)
return { case.i, case.subnames_in, case.strings_c, case.tables_c, case.t, } -- .. comment .. trk
end
t = t .. tableview.new(tab_view) -- Formats a table view with lines and columns.
viewers.restore_configs(memo, "langs.translations_counts") -- Restore global configurations after eventual changes.
return t
end -- t = function langs.translations_counts(t)
 
function langs.translations_statistics_report(t) -- Reports statistics on translations.
local memo = viewers.save_configs("langs.translations_statistics_report") -- Save global configuration before eventual changes.
local t = t or "\n* <b>langs.translations_statistics_report(t)</b> Statistical report on translations by languages and libraries."
t = t .. "\n* Guideline for this stat : Count lists of translations by languages and libraries, then convert in a 2D table, then format and report them."
t = t .. "\n* <b>Normal result: Counts are similar in all languages.</b>"
local args_known = args_known or modes.args_known or p.args_known or {} -- modes.args_known = { -- p.args_known = { -- }
local translate_i18n = versions.memo_i18n
local all_stats = {} -- all_stats + Total
local trans_count, case, i18n_group, total_stat, total_stats = 0
-- Guideline for this stat : Collect counts of translations by languages and libraries, then put them in a 2D table, then format and report them.RIC
for libname, vers in pairs(package.loaded) do -- in reverse order bind_libra
total_stat = { ["libr"] = tostring(vers.libname), ["code"] = "en", ["content"] = 0, ["page"] = 0, ["user"] = 0, ["n_langs"] = 0, ["total"] = 0, }
if (type(vers) == "table") and (type(vers.i18n) == "table") then
local case = { ["libr"] = tostring(vers.libname), ["code"] = "en", ["content"] = 0, ["page"] = 0, ["user"] = 0, ["n_langs"] = 0, ["total"] = 0, }
for code_lang, available_translations in pairs(vers.i18n) do -- import and mix known args and properties
case.code = code_lang
case.count = lua_table.level_count(available_translations)
-- case.i18n = vers.i18n
case.total_stat = { ["libr"] = tostring(vers.libname), ["code"] = "en", ["content"] = 0, ["page"] = 0, ["user"] = 0, ["n_langs"] = 0, ["total"] = 0, }
if case.code == langs.content_lang then case.content = case.count ; total_stat.content = total_stat.content + case.count end
if case.code == langs.page_lang then case.page = case.count ; total_stat.page = total_stat.page + case.count end
if case.code == langs.user_lang then case.user = case.count ; total_stat.user = total_stat.user + case.count end
-- total_stat.code = (total_stat.code or 0) + 1
total_stat.n_langs = (total_stat.n_langs or 0) + 1
case = { ["libr"] = tostring(vers.libname), ["code"] = case.code,
["content"] = case.content or 0, ["page"] = case.page or 0, ["user"] = case.user or 0, ["n_langs"] = 1, ["total"] = 0, }
end
table.insert( all_stats, case )
end
end
local list_case_libname = {} -- list of libnames
langs.list_case_libname = list_case_libname
for i, case in pairs(all_stats) do table.insert(langs.list_case_libname, case.libr) end
table.sort(langs.list_case_libname, function (a, b) return ( tostring(a) < tostring(b) ) end ) -- sort found langcodes
local headers = "langcode" -- and add list of libnames
for x, libname in pairs(langs.list_case_libname) do headers = headers .. ";" .. tostring(libname) end
headers = string.gsub(headers, versions.ModuleNS, "")
local libraries = {}
local langcodes = {} -- langcodes collection
local libnames = { "langcode" } -- libnames collection
for title, obj in pairs(package.loaded) do -- Get all libraries and libnames names.
local get = versions.bind_main_and_sub_modules_get[title]
if get and get.is_library and (type(get.i18n) == "table") then -- select libraries only
local libname = tostring(get.title)
table.insert( libnames, libname )
end
end
for i, libname in pairs(libnames) do -- for all objects
local get = versions.bind_main_and_sub_modules_get[libname]
if get and get.is_library and (type(get.module) == "table") and (type(get.title) == "string") then -- select libraries only
libname = get.title -- for all libraries
local lib = get.module
for langcode, trans_tab in pairs(lib.i18n) do -- To collect all langcode
if type(langcode) == "string" then langcodes[langcode] = langcode end -- add the langcode
end
end
end
local list_case_langcode = {} -- list of found langcodes
langs.list_case_langcode = list_case_langcode
for x, langcode in pairs(langcodes) do table.insert(list_case_langcode, langcode) end
table.sort(list_case_langcode, function (a, b) return ( tostring(a) < tostring(b) ) end ) -- sort found langcodes
local langcode_libname_2D = {}
local list_trans = {} -- list of number of translations in one library.
for i, langcode in pairs(list_case_langcode) do -- Structure a 2D table : libraries in langcodes.
local lib_tab = { langcode }
for j, libname in pairs(list_case_libname) do -- List all package.loaded objects.
local lib = package.loaded[tostring(libname)]
table.insert( lib_tab, lua_table.level_count(lib.i18n[tostring(langcode)]) )
end
table.insert(langcode_libname_2D, lib_tab)
end
local tab_view = { -- Group datas and options for a table view with lines and columns.
test_group = langcode_libname_2D,
title_memo = "langs_translations_stats_report_title",
form_one_case = function(case) -- Convert a case from test_group to row_group.
return case
end,
["headers"] = headers, -- ~= "Lang;activity;datas;langs;events;lua_table;mathroman;modes",
row_group = {},
}
t = t .. "<br/>" .. tableview.new(tab_view) -- Formats a table view with lines and columns.
viewers.restore_configs(memo, "langs.translations_statistics_report") -- Restore global configurations after eventual changes.
return t
end -- res = res .. langs.translations_statistics_report(t)
 
function langs.key(key, lang) -- Translate the key in user, wiki and content languages.
if (type(key) ~= "string") then key = "translate_missing_key_err" end
if (type(lang) ~= "string") then lang = nil end
local translate_i18n = versions.memo_i18n
function translate_one_key(translate_i18n, key, lang)
if lang and (type(translate_i18n) == "table") then translate_i18n = translate_i18n[lang] end
if key and (type(translate_i18n) == "table") then translate_i18n = translate_i18n[key] end
return translate_i18n
end
translate_i18n = translate_one_key(translate_i18n, key, lang)
if (type(lang) == "string") then -- Only the selected language
return translate_i18n
else
return translate_one_key(translate_i18n, key, langs.user_lang),
translate_one_key(translate_i18n, key, langs.content_lang),
translate_one_key(translate_i18n, key, langs.page_lang)
end
-- local user, wiki, page = langs.key(key, lang) -- Examples of uses
end -- function langs.key(key, lang)
 
function langs.main_i18n_languages_list() -- List available translations and languages
local main_i18n = versions.memo_i18n or {}
local xxx, strings_c, tables_c, strs_on_tabs, subnames = langs.i18n_sub_counts("versions.memo_i18n", "langs_main_i18n_languages_count", "user")
local tab_to_sort = {}
for lang, modname in pairs(main_i18n) do
table.insert(tab_to_sort, lang) -- build a table with only languages codes
end
table.sort(tab_to_sort, function (a, b) -- sort the languages codes in stable alphabetic order
return ( a < b )
end )
strs_on_tabs = math.floor(strs_on_tabs / tables_c)
local t = viewers.form9user("langs_main_i18n_languages_count", strs_on_tabs, tables_c)
for i, lang in pairs(tab_to_sort) do -- Name and count translations in each language
local langi18n = "langs.main_i18n." .. lang
local xxx, strings_c, tables_c, strs_on_tabs, subnames = langs.i18n_sub_counts(langi18n, "langs_main_i18n_languages_count", "user")
t = t .. "<b>" .. strings_c .. "</b>-"
local nativename = mw.language.fetchLanguageName(lang)
local englishname = mw.language.fetchLanguageName(lang, "en")
local englishname = mw.language.fetchLanguageName(lang, "en")
t = t .. viewers.form9user("langs_mw_language_fetchLanguageName", nativename, lang, englishname) -- "<b>%1</b>(%2=%3), "
if i > 12 then t = t .. "<b> ...</b>" ; break end
end -- see langs.select_lang
return t
end -- function langs.main_i18n_languages_list()
 
langs.Central_version = "Central-s-fr" -- To adapt the version of Module:Centralizer in any translated text.
langs.default_user_lang = "en" -- To adapt the version of Module:Centralizer in any translated text.
-- waiting T68051 Central modules need the user language to display errors and category names
 
function langs.init_content_page_user_lang(content_lang, page_lang, user_lang)
-- Initialize or change the content, the page and the user languages and their translations tables.
-- Guide line: decreasing priority, for each of these 3 languages, is : argument, else MediaWiki, else default values.
-- See also https://meta.wikimedia.org/wiki/Translate_extension and [[Special:PageLanguage]] 2016-12-19
local main_i18n = versions.memo_i18n or langs.main_i18n or versions.main_i18n
local t = "" -- internal track
local lg = {}
local modesCont, modesPage, modesUser = nil, nil, nil
if modes.args_source then -- and modes.args_source.userlang Does module arguments ask a content_lang?
local modes_args = modes.args_final or modes.args_source -- work after full init or before
modesCont = modes_args.contentlang
modesPage = modes_args.pagelang
modesUser = modes_args.userlang
end
modes.frame = mw.getCurrentFrame()
local get_content_lang = mw.getContentLanguage().code -- Returns the default content language.
local get_page_lang = modes.frame:preprocess("{{PAGELANGUAGE}}") -- Returns the default page language.
local get_user_lang = modes.frame:preprocess( "{{int:Lang}}" )
-- waiting T68051 Central modules need the user language to display errors and category names
-- Activate these languages for all uses.
if type(main_i18n) ~= "table" then main_i18n = {} end -- default empty main_i18n. Only for languages
langs.content_lang = content_lang or get_content_lang or "en"
langs.content_translations = main_i18n[langs.content_lang]
langs.page_lang = page_lang or get_page_lang or "en"
langs.page_translations = main_i18n[langs.page_lang]
langs.user_lang = user_lang or get_user_lang or langs.default_user_lang or "en"
langs.user_translations = main_i18n[langs.user_lang]
langs.main_i18n = main_i18n
versions.main_i18n = main_i18n
return t
end -- function langs.init_content_page_user_lang(content_lang, page_lang, user_lang) -- _new
 
function langs.select_lang( lang ) -- Select a language for tests or other purpose.
if type(lang) ~= "string" then lang = "user_lang" end -- default is user language
-- Select between : user_lang content_lang tests en es fr or any available in i18n.
if lang == "tests" then lang = "tests"
elseif versions.memo_i18n and versions.memo_i18n[lang] then lang = lang -- available in i18n
elseif lang == "user_lang" then lang = langs.user_lang
elseif lang == "content_lang" then lang = langs.content_lang
else lang = langs.user_lang end -- default is user language
return lang
end -- function langs.select_lang( lang )
 
function langs.select_lang_test(t) -- Tests: Select a language for tests or other purpose.
local memo = viewers.save_configs("langs.select_lang_test") -- Save global configuration before eventual changes.
local t = t or "\n* Test <b>langs.select_lang()</b> :" -- langs_selectLang_tests_title
local tab_view = { -- Group datas and options for a table view with lines and columns.
test_group = { -- events.test_group
{ content_lang = "en", user_lang = "fr", sought = "content_lang", },
{ content_lang = "en", user_lang = "es", sought = "user_lang", },
{ content_lang = "en", user_lang = nil , sought = "content_lang", },
{ content_lang = nil , user_lang = "es", sought = "user_lang", },
{ content_lang = "fr", user_lang = "es", sought = "tests", },
},
headers = "langs_selectLang_test_headers"
-- headers = "Wiki language; User language; Sought language; Selected language; Example",
}
function tab_view.form_one_case(case) -- Convert a case from test_group to rowGroup.
local selected = langs.select_lang( lang )
local example = viewers.form9user("langs_selectLang_test_example")
if selected == "tests" then example = viewers.form9tests("selectLang", case.content_lang, case.user_lang, case.sought) end
return { tostring(case.content_lang), tostring(case.user_lang), tostring(case.sought), tostring(selected), tostring(example), }
end
t = t .. tableview.new(tab_view) -- Formats a table view with lines and columns.
viewers.restore_configs(memo, "langs.select_lang_test") -- Restore global configurations after eventual changes.
return t
end -- langs.select_lang_test(t)
 
function langs.list_MediaWiki_languages(t, lang) -- List all MediaWiki languages.
local memo = viewers.save_configs("langs.list_MediaWiki_languages") -- Save global configuration before eventual changes.
if type(t) ~= "string" then t = "\n* <b>langs.list_MediaWiki_languages()</b> List all known MediaWiki languages:" end
local interwikiMap = mw.site.interwikiMap("local") local lang = mw.language.new( langs.user_lang or "en" )
local LangCode = lang:getFallbackLanguages()
local lang_code_name = mw.language.fetchLanguageNames() -- inLanguage, 'mwfile' )
local toSort, t2 = {}, ""
local t = (t or "") .. "\n* Infos lang_code_name: " .. viewers.ta("#lang_code_name", lua_table.level_count(lang_code_name) )
for code, name in pairs(lang_code_name) do -- make a true table in rough order
table.insert(toSort, { code, name } )
-- insert detail { [1]=code, [2]=name } )
end
table.sort(toSort, function (row_x, row_y) return ( row_x[1] < row_x[1] ) end ) -- Sort based on [1]=code
table.sort(toSort, function (row_x, row_y) return ( row_x[2] < row_x[2] ) end ) -- Sort based on [2]=name
t = t .. "\n* List of <b>known</b> languages of MediaWiki lang_code_name: <br/>" .. t2
t = t .. "\n* Infos: " .. viewers.ta("#lang_code_name", lua_table.level_count(lang_code_name) ) .. viewers.ta("#toSort", lua_table.level_count(toSort) ) .. viewers.ta("user_lang", langs.user_lang)
t2 = ""
for i, lang in pairs(toSort) do
local ok = 1 or langs.abnormal_char_in_text(lang[2], langs.user_lang) -- Detect abnormal characters in an unilingual text.
local lang_2 = lang[2]
if not ok then lang_2 = viewers.styles_color_error(lang_2) end
t2 = t2 .. viewers.ta( lang[1], lang_2 ) -- .. "\n* "
end
t = t .. "\n* List of <b>known</b> languages of MediaWiki: <br/>" .. t2
viewers.restore_configs(memo, "langs.list_MediaWiki_languages") -- Restore global configurations after eventual changes.
return t
end -- function langs.list_MediaWiki_languages(t, lang)
 
function langs.abnormal_char_in_text(t) -- Test: Detect abnormal characters in an unilingual text.
if type(t) ~= "string" then return false end -- langs_abnormal_char_in_text_title
-- local ok, normal = true, "ABCDEFGHABKLMNOPQRSTUVWXYZ 013456789 abcdefghabklmnopqrstuvwxyz àéèêëiouüœ ÀÉÈÊËIOUÜŒ ,;.:!?"
local ok, normal = true, viewers.form9user("langs_abnormal_char_in_alphabet")
local letter, nn = "x", string.len(t .. " abcdef") - 3
for i = 1, nn do -- for all chars in t
letter = string.byte(t, i)
if not viewers.is_in(letter, normal) then ok = false ; break end
end
return ok
end -- function langs.abnormal_char_in_text(t)
 
function langs.changing_translations(t) -- List all changing translations
local memo = viewers.save_configs("langs.changing_translations") -- Save global configuration before eventual changes.
local t = t or "\n* <b>langs.changing_translations()</b>: List all changing translations:"
local i18n = versions.memo_i18n
langs.translations_differences = langs.translations_differences or {}
local nerr, errors, trans, err = 0, "*", "", ""
local nbr, nbr_in_lang, list = 0, 0, ""
local nbr_in_lang_limit = 4
local prev_i18n, next_i18n, prev_table, next_table, max, nkeys = {}, {}, {}, {}, 0, 0
local strnew, lang, prev_lang, refer_lang, cats = "strnew", "", "", "", "", ""
-- change means a different text in the main module relative to the text inside each central library, based on the same keyi18n.
local changingGroup, libraries = {}, {}
for title, obj in pairs(package.loaded) do -- For libraries only
local get = versions.bind_main_and_sub_modules_get[title]
if get and get.is_library and (type(get.i18n) == "table") then
prev_lang = refer_lang
prev_i18n = get.i18n
next_i18n = i18n
table.insert(libraries, get.module)
end
end
local lib_langs_keys = {} -- To mix libraries their langs and keys and vals
for title, onelibrary in pairs(libraries) do -- For all libraries only
for onelang, lang_table in pairs(onelibrary.i18n) do -- For all languages in each library
lib_langs_keys[onelang] = lib_langs_keys[onelang] or {}
for key, val in pairs(lang_table) do -- For all keys in each language
lib_langs_keys[onelang][key] = val
end
end
end
for refer_lang, next_table in pairs(libraries) do -- For all languages and texts to translate
list = list .. refer_lang .. ", "
nbr = nbr + 1
if type(next_table) == "table" then -- For each pair of languages to compare
nkeys = 0
nbr_in_lang = 0
local all_txts = {}
if type(next_table) == "table" then -- For each language to compare
for keyi18n, stri18n in pairs(next_table) do -- List all texts translated in at least one language
all_txts[keyi18n] = stri18n
end
for keyi18n, stri18n in pairs(all_txts) do -- Look at all translations in one language, but check them only from 1 to nbr_in_lang_limit.
nbr_in_lang = nbr_in_lang + 1
nkeys = nkeys + 1
if (type(keyi18n) == "string") then -- only translations, not positional arguments
keyi18n, stri18n = tostring(keyi18n), tostring(stri18n)
local cut = string.find(tostring(keyi18n) .. "_", "_")
local modul = string.sub(keyi18n, 1, cut - 1)
if (nbr_in_lang == nbr_in_lang_limit) then -- for the last changing
-- local strnew = i18n[refer_lang][keyi18n] or "strnew"
if i18n[refer_lang] then
strnew = i18n[refer_lang][keyi18n] or "strnew"
end
table.insert( changingGroup, { ["lang"] = refer_lang, ["keyi18n"] = keyi18n, ["stri18n"] = stri18n, ["strnew"] = strnew,
["counts"] = viewers.styles_color_error("changing limit = " .. nbr_in_lang_limit), ["modul"] = modul} )
-- nerr = nerr + 1
elseif (nbr_in_lang < nbr_in_lang_limit) then -- for changing before the last
-- headers = "Language; i18n Key; Previous translation; New translation; Module",
if i18n[refer_lang] then
strnew = i18n[refer_lang][keyi18n] or "strnew"
end
table.insert( changingGroup, { ["lang"] = refer_lang, ["keyi18n"] = keyi18n, ["stri18n"] = stri18n, ["strnew"] = strnew,
["counts"] = "changing: " .. nkeys .. " / " .. nerr, ["modul"] = modul} )
nerr = nerr + 1
end
end
end
end
if nkeys > max then max = nkeys end
end
prev_lang = refer_lang
prev_table = next_table
end
if nerr > 0 then
err = events.add_err("versions_module_miss_i18n_count_err", nerr, max)
t = t .. "<br>" .. err .. " "
errors = errors .. err
cats = cats .. events.add_cat("versions_err_module_miss_i18n_cat")
else
errors = errors .. " no errors "
-- err = events.add_wng("versions_module_miss_i18n_none_err")
end
local tab_view = { -- Group datas and options for a table view with lines and columns.
test_group = changingGroup,
langs_changing_translations_title = "langs.changing_translations() Changing (or missing) translations in i18n tables.",
langs_changing_translations_headers = "Language; i18n Key; Previous translation; New translation; Module",
title_memo = "langs_changing_translations_title",
headers = "Language; Key; Translation; N errs / N keys, Module",
headers = "langs_changing_translations_headers", -- CHANGING headers = "Language; Key; Previous translation; New translation; Module",
headers = "Language; i18n Key; Previous translation; New translation; counts; Module",
kind = "projects", -- MediaWiki or projects
typ = "err",
rowGroup = {}, -- tests or tab_view.test_group or
}
function tab_view.form_one_case(case) -- Convert a case from test_group to rowGroup.
return { case.lang, case.keyi18n, case.stri18n, case.strnew, case.counts, case.modul, }-- "Language; Key; Previous translation; New translation; Module"
end
t = t .. tableview.new(tab_view) -- Formats a table view with lines and columns.
errors = errors or " no errors "
if errors ~= "" then errors = viewers.styles_color_error(errors) end
t = t .. viewers.ta("#tab_view.rowGroup", lua_table.level_count(tab_view.rowGroup) ) -- Formats a table with lines and columns.
viewers.restore_configs(memo, "langs.changing_translations") -- Close a cats and errors table. For one test or main module.
return t --, errors -- translate_missing_translations_title
end -- function langs.changing_translations(t)
 
function langs.missing_translations_init(t) -- Initialize the list of known translations, and their counts.
local t = t or ""
langs.known_translations = langs.known_translations or {}
local i18n = versions.memo_i18n
langs.known_langs = i18n
langs.known_texts = {}
langs.known_langs_maxi = 0
langs.known_texts_maxi = 0
for refer_lang, next_table in pairs(i18n) do -- For all languages and texts to translate
if (type(other_trans) == "table") then
langs.known_langs[refer_lang] = refer_lang
t = t .. "\n* for refer_lang : " .. viewers.ta("refer_lang", refer_lang) .. viewers.ta("#next_table", lua_table.level_count(next_table) )
for name, txt in pairs(next_table) do -- mix translations for 1 language in 1 library
-- table.insert( langs.known_texts, { name = txt } )
langs.known_texts[name] = txt
end
t = t .. " end for : " .. viewers.ta("#langs.known_texts", lua_table.level_count(langs.known_texts) )
end
end
t = t .. "\n* i18n end: " .. viewers.ta("#langs.known_langs", lua_table.level_count(langs.known_langs) ) .. viewers.ta("#langs.known_texts", lua_table.level_count(langs.known_texts) )
if (langs.known_langs_maxi < lua_table.level_count(i18n) ) then langs.known_langs_maxi = lua_table.level_count(i18n) end -- Maximum number of languages
return t
end
 
function langs.missing_translations(t) -- List all missing translations
local memo = viewers.save_configs("langs.missing_translations") -- Save global configuration before eventual changes.
local t = t or "\n* <b>langs.missing_translations()</b>: List all missing translations: "
local i18n = versions.memo_i18n
local errors = "*"
local changingGroup = {}
local missingGroup = {}
langs.translations_differences = langs.translations_differences or {}
local nerr, trans, err = 0, "", ""
local nbr, nbr_in_lang, list = 0, 1, ""
local nbr_in_lang_limit = 4
local prev_table, next_table, max, nkeys = {}, {}, 0, 0
local lang, prev_lang, refer_lang, cats = "", "", "", ""
local refer_stri18n, other_stri18n = "-"
local count_known_texts = lua_table.level_count(langs.known_texts)
local count_changingGroup = lua_table.level_count(changingGroup)
local count_missingGroup
t = t .. langs.missing_translations_init(t) -- Initialize the list of known translations, and their counts.
t = t .. "\n* Insure next_table is OK: "
nkeys = 0
local err_in_refer_lang, err_in_other_lang, err_in_refer_lang_limit = 0, 0, 5
for refer_lang, refer_trans in pairs(langs.known_langs) do -- for all languages
if not ( (refer_lang == "en") or (refer_lang == "es") or (refer_lang == "fr") ) then -- small langs for tests debug
t = t .. ", L=" .. refer_lang ..": n=".. lua_table.level_count(refer_trans)
refer_trans = i18n[refer_lang]
for other_lang, other_trans in pairs(langs.known_langs) do -- Look at all translations in one language, but check them only from 1 to nbr_in_lang_limit.
if not ( (other_lang == "en") or (other_lang == "es") or (other_lang == "fr") ) then -- small langs for tests debug
t = t .. ", O=" .. other_lang ..": n=".. lua_table.level_count(other_trans)
if (type(other_trans) == "table") then -- if the translations in the alternate language is ok
t = t .. ", nlt=" .. refer_lang
for keyi18n, stri18n in pairs(refer_trans) do -- Look at all translations
local cut = string.find(tostring(keyi18n) .. "_", "_")
local modul = string.sub(keyi18n, 1, cut - 1)
refer_stri18n = i18n[refer_lang][keyi18n]
other_stri18n = i18n[other_lang][keyi18n]
count_known_texts = lua_table.level_count(langs.known_texts)
count_changingGroup = lua_table.level_count(changingGroup)
if (not other_stri18n) and (err_in_refer_lang < err_in_refer_lang_limit) then -- if missing
err_in_refer_lang = err_in_refer_lang + 1
count_missingGroup = lua_table.level_count(missingGroup) + 1
local missing_case = { ["refer_lang"] = refer_lang, ["other_lang"] = other_lang, ["keyi18n"] = keyi18n,
["refer_stri18n"] = refer_stri18n, ["counts"] = viewers.form9user("counts missing=%1 / changing=%2 (err n=%3)",
count_missingGroup, count_changingGroup, count_known_texts, err_in_refer_lang), ["modul"] = modul, }
table.insert( missingGroup, missing_case )
t = t .. viewers.form9user(
"\n* missing err: refer_lang=%1, other_lang=%2, missing=%3 / changing=%4, keyi18n=%5",
refer_lang, other_lang, count_missingGroup, count_changingGroup, keyi18n)
elseif (other_stri18n ~= refer_stri18n) and (err_in_other_lang < err_in_refer_lang_limit) then -- if changing
err_in_other_lang = err_in_other_lang + 1
count_changingGroup = lua_table.level_count(changingGroup) + 1
local counts = viewers.form9user("refer_lang=%1, other_lang=%2, counts changing=%1 / missing=%2, texts=%3",
refer_lang, other_lang, count_changingGroup, count_missingGroup, count_known_texts, err_in_other_lang)
local changing_case = { ["refer_lang"] = refer_lang, ["other_lang"] = other_lang, ["keyi18n"] = keyi18n,
["refer_stri18n"] = refer_stri18n, ["other_stri18n"] = other_stri18n, ["counts"] = counts, ["modul"] = modul, }
table.insert( changingGroup, changing_case )
t = t .. viewers.form9user(
"\n* changing err: refer_lang=%1, other_lang=%2, changing=%3 / missing=%4, keyi18n=%5",
refer_lang, other_lang, count_changingGroup, count_missingGroup, keyi18n)
end
end
end
end -- small langs for tests debug
end
end -- small langs for tests debug
end
local tab_view = { -- Group datas and options for a table view with lines and columns.
test_group = missingGroup,
langs_missing_translations_title = "langs.missing_translations() Missing translations in i18n tables.",
langs_missing_translations_headers = "Language; i18n Key; Previous translation; New translation; Module",
title_memo = "langs_missing_translations_title",
headers = "langs_missing_translations_headers", -- MISSING "Language; i18n Key; Previous translation; New translation; Module",
headers = "Languages; missing Key; Previous translation; New translation; Module",
kind = "projects", -- MediaWiki or projects
typ = "err",
rowGroup = {}, -- tests or tab_view.test_group or
}
function tab_view.form_one_case(case) -- Convert a case from test_group to rowGroup.
--[[table.insert( missingGroup, { ["lang"] = refer_lang, ["keyi18n"] = keyi18n, ["refer_stri18n"] = refer_stri18n, ["modul"] = modul,
["counts"] = viewers.form9user("counts missing=%1 / changing=%2 (err n=%3)", count_missingGroup, count_changingGroup, count_known_texts, err_in_refer_lang), } ) --]]
return { (case.modul or "modul") .." : ".. (case.refer_lang or "lang") .."/".. (case.other_lang or "lang"),
case.keyi18n, case.refer_stri18n, case.other_stri18n, (case.counts or "counts"), }
-- headers = "Language; missing Key; Previous translation; New translation; Counts Module",
end
t = t .. tableview.new(tab_view) -- Formats a table view with lines and columns.
tab_view.test_group = changingGroup
tab_view.rowGroup = {}
tab_view.headers = "Language; changing Key; Previous translation; New translation; Counts Module"
function tab_view.form_one_case(case) -- Convert a case from test_group to rowGroup.
--[[table.insert( changingGroup, { ["lang"] = refer_lang, ["keyi18n"] = keyi18n, ["stri18n"] = stri18n, ["modul"] = modul,
["counts"] = viewers.form9user("lang=%1, other_lang=%2, counts changing=%1 / missing=%2, texts=%3",
count_changingGroup, count_missingGroup, count_known_texts, err_in_other_lang), } ) --]]
local modul_refer_other = (case.modul or "modul") .." : ".. (case.refer_lang or "refer_lang") .."/".. (case.other_lang or "other_lang")
return { modul_refer_other, case.keyi18n, case.other_stri18n, case.refer_stri18n, (case.counts or "counts"), }
end
t = t .. tableview.new(tab_view) -- Formats a table view with lines and columns.
viewers.restore_configs(memo, "langs.missing_translations") -- Restore global configurations after eventual changes.
return t --, errors -- langs_missing_translations_title
end -- function langs.missing_translations(t)
 
function langs.i18n_lister(t, i18n_tables)
if type(i18n_tables) ~= "table" then i18n_tables = versions.memo_i18n end
local t = t or "\n* <b>i18n_lister</b> :"
t = t .. viewers.styles_color_error("\n* <b>This list show all the string, but cannot replace the original declarations.</b> ")
t = t .. viewers.styles_color_error("\n* <b>" .. viewers.form9user("langs_i18n_list_all_string") .. " </b> " )
for lang, lang_table in pairs(i18n_tables) do
t = t .. "\np.i18n." .. lang .. ' = { '
if type(lang_table) == "table" then
for key, text in pairs(lang_table) do
if key and text then
t = t .. "\n:" .. key .. ' = "' .. text .. '",'
end
end
end
t = t .. "\n}\n"
end
return t
end -- function langs.i18n_lister(t, i18n_tables)
 
-- - - - ------------------ - - - - ---------------------------------
-- Manage translations of arguments and warnings
-- Gestione traducciones de argumentos y advertencias
-- Gérer les traductions des arguments et warnings
-- - - - ------------------ - - - - ---------------------------------
 
function langs.dummy_languages() -- Test dummy languages S170614tva
-- https://fr.wikipedia.org/wiki/%C3%89tiquette_d%27identification_de_langues_IETF
-- https://fr.wikipedia.org/wiki/Module:Langue/Data
-- pour convertir en code de langue IETF les noms français de langues
-- https://www.MediaWiki.org/wiki/Manual:$wgDummyLanguageCodes
-- List of language codes that have been renamed to new (correct) codes, or don't correspond to an actual interface language.
-- array( 'als' => 'gsw', 'bat-smg' => 'sgs', 'be-x-old' => 'be-tarask', 'bh' => 'bho'...
langs.MetaSupportedLanguages = { "ja", "es", "ru", "de", "nl", "tr", "fr", "pt", "ko", "en", "it", "oc",
"pl", "fa", "ar", "vi", "arz", "hi", "sv", "diq", "pt-br", "zh", "th", "bg", "hu", "uk", "en-gb",
"sh", "id", "bn", "az", "fi", "be", "he", "eo", "el", "sd", "kn", "ro", "yue", "sr", "mk", "ta",
"pa", "hy", "lb", "tt", "si", "yi", "ne", "cs", "sk", "ms", "eu", "mr", "sa", "tl", "eml",
-- https://meta.wikimedia.org/wiki/Special:SupportedLanguages on 20170629 Rical
} -- 58 languages in total.
local dummy_i18n = {
en = "Module:Centralizer/I18N", -- english
es = "Modul:Central/I18N", -- spanish
fr = "Module:Centralizer/I18N", -- french
Fr = "Module:Centralizer/I18N", -- error test
als = "Modulen:Central/I18N", -- alemanish
gsw = "Mod-gsw:Central/I18N", -- unknown
["bat-smg"] = "Mod-bat-smg:Central/I18N", -- alemanish
sgs = "Mod-sgs:Central/I18N", -- unknown
}
local t = '\n* langs.dummy_languages() : ' .. viewers.ta("isTag", "isKnownLanguageTag(xx)") .. viewers.ta("isLang", "isSupportedLanguage(xx)") .. viewers.ta("isBuilt", "isValidBuiltInCode(xx)")
local tab_view = { -- Group datas and options for a table view with lines and columns.
test_group = {
{ "en", "Module:Centralizer/I18N", }, -- english
{ "es", "Modul:Central/I18N", }, -- spanish
{ "fr", "Module:Centralizer/I18N", }, -- french
{ "Fr", "Module:Centralizer/I18N", }, -- error test
{ "als", "Modulen:Central/I18N", }, -- alemanish
{ "gsw", "Mod-gsw:Central/I18N", }, -- unknown
{ "bat-smg", "Mod-bat-smg:Central/I18N", }, -- alemanish
{ "sgs", "Mod-sgs:Central/I18N", }, -- unknown
},
title_memo = "langs_dummy_languages_title", -- "lua_table.to_list() Return a list from a Lua table.",
headers = "langs_dummy_languages_headers", --
headers = " lang; isTag; isLang; isBuilt; langname; native ", --
rowGroup = {},
}
function tab_view.form_one_case(case) -- Convert a case from test_group to rowGroup.
local lang, modname = case[1], case[2]
if (type(lang) ~= "string") then lang = "-" end
local isTag = mw.language.isKnownLanguageTag(lang)
local langname = mw.language.fetchLanguageName(lang, "en") -- see langs.select_lang
local native = mw.language.fetchLanguageName(lang)
-- local isLang = mw.language.isSupportedLanguage(lang)
local isBuilt = mw.language.isValidBuiltInCode(lang)
local space_name = tostring(mw.site.namespaces.Module.name)
return { lang, isTag, tostring(isLang), isBuilt, langname, native, space_name, }
end
t = t .. tableview.new(tab_view) -- Formats a table view with lines and columns.
return t
end -- function langs.dummy_languages()
 
-- cut_libraries
 
-- - - - ------------------ - - - - ------------------ - - - - -----------------------------
-- - - - ------------------ - - - - ------------------ - - - - -----------------------------
-- The Library:lua_table enhances the support of previous table library from Lua.
-- "lua_table" avoids ambiguities with other kind of tables.
-- To enhance, we could write here : lua_table = table.
-- see Extension:Scribunto/Lua reference manual : class nameTest extends Scribunto_LuaEngineTestBase
-- - - - ------------------ - - - - ---------------------------------
-- - - - ------------------ - - - - ---------------------------------
 
-- lua_table = {} -- already declared by Scribunto, see central_library.new() -- Record a library in package.loaded
-- Translations for lua_table library
-- These Module:Centralizer/I18N translations for lua_table library update and complete Module:Centralizer translations.
lua_table.i18n = {}
lua_table.i18n.br = {
luaTable_recursive_luaTable_title = "MediaWiki lua_table récursive",
luaTable_rough_view_tests_title = "viewers.rough_view() Test: Former un code Lua grossier d'une table",
luaTable_structure_level_maxi = "Limite de niveau recursif = <b>%1</b> ",
luaTable_table_listlimit_max_n = "Limite de longueur max_n = <b>%1</b> ",
lua_table_structure_recursive_report= "lua_table.structure() Lister une table, test avec ou sans limites :",
luaTable_toList_tests_title = "lua_table.to_list() Retourne une liste à partir d'une table Lua.",
luaTable_toList_tests_headers = "Cas testé; Table à lister, vue brute; Liste de sortie",
luaTable_toTable_tests_title = "lua_table.to_table() Test: convertir une phrase en table de mots",
luatable_form_subcounts_subtables = "La table <b>%1</b> compte <b>%2</b> variables, <b>%3</b> sous-tables, <b>%4</b> fonctions.",
luaTable_fromsubnames_base_err = "Erreur interne: dans langs.sub_i18n_counts(), base indisponible pour la table subnames <b>%1</b>.",
luaTable_fromsubnames_subtable_err = "Erreur interne: dans langs.sub_i18n_counts(), <b>%1</b> n'est pas une sous-table dans subnames <b>%2</b>.",
luaTable_form_sub_counts_type_err = "Un <b>%1</b> remplace la table : <b>%2</b>.",
-- luaTable_fromsubnames_missing_err = "Erreur interne : in lua_table.form_sub_counts() La recherche de cette sous-table <b>%1</b> n'a trouvé que celle-ci <b>%2</b>.", obsolete
luaTable_fromsubnames_tests_headers = "Sous-nom; Table de base; Taille de la table; Entrée viewers.rough_view",
luaTable_table_dont_exists_err = "La table <b>%1</b> n'existe pas.",
luaTable_table_args_source_title = "lua_table.structure() Table des arguments reçus, args_source :",
luaTable_tables_differences_title = "tests_groups.resultdiffs() signaler les différences entre 2 tables.",
} -- lua_table.i18n.br
lua_table.i18n.de = {
luaTable_recursive_luaTable_title = "MediaWiki lua_table rekursive",
luaTable_rough_view_tests_title = "viewers.rough_view() Test: Bilden Sie einen groben Lua-Code aus einer Tabelle",
luaTable_structure_level_maxi = "Rekursives Level-Limit = <b>%1</b> ",
luaTable_table_listlimit_max_n = "Längenbegrenzung max_n = <b>%1</b> ",
lua_table_structure_recursive_report= "lua_table.structure() Listen Sie eine Tabelle auf, testen Sie mit oder ohne Grenzen:",
luaTable_toList_tests_title = "lua_table.to_list() Gibt eine Liste aus einer Lua-Tabelle zurück.",
luaTable_toList_tests_headers = "Fall getestet; Tabelle zu Liste, grobe Ansicht; Freigabeliste",
luaTable_toTable_tests_title = "lua_table.to_table() Test: Konvertiere einen Satz in eine Worttabelle",
luatable_form_subcounts_subtables = "Die Tabelle <b>%1</b> zählt <b>%2</b> Variablen, <b>%3</b> Untertabellen, <b>%4</b> Funktionen.",
luaTable_fromsubnames_base_err = "Interner Fehler: in langs.sub_i18n_counts(), Basis für die Tabelle der Unternamen nicht verfügbar <b>%1</b>.",
luaTable_fromsubnames_subtable_err = "Interner Fehler: In langs.sub_i18n_counts(), ist <b>%1</b> keine Untertabelle in Unternamen <b>%2</b>.",
luaTable_fromsubnames_subtable_err = "Interner Fehler: In langs.sub_i18n_counts(), <b>%1</b> ist keine Untertabelle in Unternamen <b>%2</b>.",
luaTable_form_sub_counts_type_err = "Ein <b>%1</b> ersetzt die Tabelle: <b>%2</b>.",
luaTable_fromsubnames_tests_headers = "Teilname; Basistabelle; Größe des Tisches; Eintrag viewers.rough_view",
luaTable_table_dont_exists_err = "Tabelle <b>%1</b> existiert nicht.",
luaTable_table_args_source_title = "lua_table.structure() Tabelle der Argumente erhaltenTabelle der Argumente erhalten, args_source:",
luaTable_tables_differences_title = "tests_groups.resultdiffs() berichten Sie die Unterschiede zwischen 2 Tabellen.",
} -- lua_table.i18n.de
lua_table.i18n.en = {
luaTable_recursive_luaTable_title = "MediaWiki recursive lua_table",
luaTable_rough_view_tests_title = "viewers.rough_view() Test: Formats a rough Lua code of a table",
luaTable_structure_level_maxi = "Recursive level limit = <b>%1</b> ",
luaTable_table_listlimit_max_n = "Length limit max_n = <b>%1</b> ",
lua_table_structure_recursive_report= "lua_table.structure() List a table, test with or without limits:",
luaTable_toList_tests_title = "lua_table.to_list() Return a list from a Lua table.",
luaTable_toList_tests_headers = "Tested case; Input table, rough_view; Output list",
luaTable_toTable_tests_title = "lua_table.to_table() Test: convert a string to a table of words",
luatable_form_subcounts_subtables = "The table <b>%1</b> counts <b>%2</b> values, <b>%3</b> sub-tables and <b>%4</b> functions.",
luaTable_fromsubnames_base_err = "Internal error: in langs.sub_i18n_counts(), base unavailable for the subnames table <b>%1</b>.",
luaTable_fromsubnames_subtable_err = "Internal error: in langs.sub_i18n_counts(), <b>%1</b> is not a sub-table in subnames <b>%2</b>.",
luaTable_form_sub_counts_type_err = "A <b>%1</b> replaces the table: <b>%2</b>.",
-- luaTable_fromsubnames_missing_err = "Internal error: in lua_table.form_sub_counts() The search for this sub-table <b>%1</b> found only this one <b>%2</b>.", obsolete
luaTable_fromsubnames_tests_headers = "Sub name; Base table; Table count; Input viewers.rough_view",
luaTable_table_dont_exists_err = "The table <b>%1</b> does not exist.",
luaTable_table_args_source_title = "lua_table.structure() Table of received arguments, args_source:",
luaTable_tables_differences_title = "tests_groups.resultdiffs() report differences between 2 tables.",
} -- lua_table.i18n.en
lua_table.i18n.es = {
luaTable_recursive_luaTable_title = "MediaWiki lua_table recursiva",
luaTable_rough_view_tests_title = "viewers.rough_view() Prueba: Formar un código de Lua grueso de una tabla",
luaTable_structure_level_maxi = "Límite de nivel recursivo = <b>%1</b> ",
luaTable_table_listlimit_max_n = "Límite de longitud max_n = <b>%1</b> ",
lua_table_structure_recursive_report= "lua_table.structure() Enumerar una tabla, prueba con o sin límites:",
luaTable_toList_tests_title = "lua_table.to_list() Devolver una lista de una tabla Lua.",
luaTable_toList_tests_headers = "Probados casos; Tabla a listar, ver prima; lista de salida",
luaTable_toTable_tests_title = "Prueba: convertir una cadena en una tabla de palabras",
luatable_form_subcounts_subtables = "La tabla <b>%1</b> cuenta <b>%2</b> valores, <b>%3</b> sub-tablas y <b>%4</b> funciones.",
luaTable_fromsubnames_base_err = "Error interno: en langs.sub_i18n_counts(), base no disponible para la tabla subnames <b>%1</b>.",
luaTable_fromsubnames_subtable_err = "Error interno: en langs.sub_i18n_counts(), <b>%1</b> no es una sub-tabla en subnames <b>%2</b>.",
luaTable_form_sub_counts_type_err = "Un <b>%1</b> reemplaza la tabla: <b>%2</b>.",
-- luaTable_fromsubnames_missing_err = "Error interno: in lua_table.form_sub_counts() La búsqueda de este subtabla <b>%1</b> encontró que <b>%2</b>.", obsolete
luaTable_fromsubnames_tests_headers = "Sub nombre; Mesa base; Tamaño de la mesa; viewers.rough_view de entrada",
luaTable_table_dont_exists_err = "La tabla <b>%1</b> no existe.",
luaTable_table_args_source_title = "lua_table.structure() Tabla de argumentos recibido, args_source:",
luaTable_tables_differences_title = "tests_groups.resultdiffs() reportar diferencias entre 2 tablas.",
} -- lua_table.i18n.es
lua_table.i18n.fr = {
luaTable_recursive_luaTable_title = "MediaWiki lua_table récursive",
luaTable_rough_view_tests_title = "viewers.rough_view() Test: Former un code Lua grossier d'une table",
luaTable_structure_level_maxi = "Limite de niveau recursif = <b>%1</b> ",
luaTable_table_listlimit_max_n = "Limite de longueur max_n = <b>%1</b> ",
lua_table_structure_recursive_report= "lua_table.structure() Lister une table, test avec ou sans limites :",
luaTable_toList_tests_title = "lua_table.to_list() Retourne une liste à partir d'une table Lua.",
luaTable_toList_tests_headers = "Cas testé; Table à lister, vue brute; Liste de sortie",
luaTable_toTable_tests_title = "lua_table.to_table() Test: convertir une phrase en table de mots",
luatable_form_subcounts_subtables = "La table <b>%1</b> compte <b>%2</b> variables, <b>%3</b> sous-tables, <b>%4</b> fonctions.",
luaTable_fromsubnames_base_err = "Erreur interne: dans langs.sub_i18n_counts(), base indisponible pour la table subnames <b>%1</b>.",
luaTable_fromsubnames_subtable_err = "Erreur interne: dans langs.sub_i18n_counts(), <b>%1</b> n'est pas une sous-table dans subnames <b>%2</b>.",
luaTable_form_sub_counts_type_err = "Un <b>%1</b> remplace la table : <b>%2</b>.",
-- luaTable_fromsubnames_missing_err = "Erreur interne : in lua_table.form_sub_counts() La recherche de cette sous-table <b>%1</b> n'a trouvé que celle-ci <b>%2</b>.", obsolete
luaTable_fromsubnames_tests_headers = "Sous-nom; Table de base; Taille de la table; Entrée viewers.rough_view",
luaTable_table_dont_exists_err = "La table <b>%1</b> n'existe pas.",
luaTable_table_args_source_title = "lua_table.structure() Table des arguments reçus, args_source :",
luaTable_tables_differences_title = "tests_groups.resultdiffs() signaler les différences entre 2 tables.",
} -- lua_table.i18n.fr
lua_table.i18n.hu = {
luaTable_recursive_luaTable_title = "MediaWiki lua_table rekurzív",
luaTable_rough_view_tests_title = "viewers.rough_view() Teszt: Formázz egy durva Lua kódot egy asztaltól",
luaTable_structure_level_maxi = "Rekurzív szintű határérték = <b>%1</b> ",
luaTable_table_listlimit_max_n = "Hossza határ max_n = <b>%1</b> ",
lua_table_structure_recursive_report= "lua_table.structure() Sorolja fel a táblázatot, próbálkozzon korlátozásokkal vagy anélkül :",
luaTable_toList_tests_title = "lua_table.to_list() Visszaad egy listát egy Lua asztalról.",
luaTable_toList_tests_headers = "Esettanulmány; Táblázat lista, durva nézet; Kiadási lista",
luaTable_toTable_tests_title = "lua_table.to_table() Teszt: egy mondatot egy szótáblára konvertál",
luatable_form_subcounts_subtables = "A <b>%1</b> táblázatok <b>%2</b> változókat, <b>%3</b> al-táblákat, <b>%4</b>.",
luaTable_fromsubnames_base_err = "Belső hiba: be langs.sub_i18n_counts(), alap nem áll rendelkezésre az almenük táblázata számára <b>%1</b>.",
luaTable_fromsubnames_subtable_err = "Belső hiba: be langs.sub_i18n_counts(), A <b>%1</b> nem alatti név az almenekben <b>%2</b>.",
luaTable_form_sub_counts_type_err = "A <b>%1</b> táblázat helyettesíti az asztalt: <b>%2</b>.",
luaTable_fromsubnames_tests_headers = "Sub-név; Base asztal; A táblázat mérete; belépés viewers.rough_view",
luaTable_table_dont_exists_err = "A <b>%1</b> táblázat nem létezik.",
luaTable_table_args_source_title = "lua_table.structure() A kapott érvek táblázata, args_source :",
luaTable_tables_differences_title = "tests_groups.resultdiffs() jelenteni a különbségeket a két táblázat között.",
} -- lua_table.i18n.hu
lua_table.i18n.vi = {
luaTable_recursive_luaTable_title = "MediaWiki lua_table đệ quy",
luaTable_rough_view_tests_title = "viewers.rough_view() Kiểm tra: Tạo thành một mã Lua thô từ một bảng",
luaTable_structure_level_maxi = "Giới hạn mức đệ quy = <b>%1</b> ",
luaTable_table_listlimit_max_n = "Giới hạn độ dài max_n = <b>%1</b> ",
lua_table_structure_recursive_report= "lua_table.structure() Liệt kê một bảng, kiểm tra có hoặc không có giới hạn:",
luaTable_toList_tests_title = "lua_table.to_list() Trả về danh sách từ bảng Lua.",
luaTable_toList_tests_headers = "Trường hợp được kiểm tra; Bảng vào danh sách, xem thô; Danh sách phát hành",
luaTable_toTable_tests_title = "lua_table.to_table() Kiểm tra: chuyển đổi một câu thành một bảng từ",
luatable_form_subcounts_subtables = "Bảng <b>%1</b> đếm <b>%2</b> biến, <b>%3</b> bảng phụ, <b>%4</b> chức năng.",
luaTable_fromsubnames_base_err = "Lỗi nội bộ: trong ngôn langs.sub_i18n_counts(), cơ sở không có sẵn cho bảng subnames <b>%1</b>.",
luaTable_fromsubnames_subtable_err = "Lỗi nội bộ: trong ngôn langs.sub_i18n_counts(), <b>%1</b> không phải là một bảng phụ trong subnames <b>%2</b>.",
luaTable_form_sub_counts_type_err = "Một <b>%1</b> thay thế bảng: <b>%2</b>.",
luaTable_fromsubnames_tests_headers = "Sub-tên; Bảng cơ sở; Kích thước để bảng; lối vào viewers.rough_view",
luaTable_table_dont_exists_err = "Bảng <b>%1</b> không tồn tại.",
luaTable_table_args_source_title = "lua_table.structure() Bảng đối số nhận được, args_source:",
luaTable_tables_differences_title = "tests_groups.resultdiffs() báo cáo sự khác biệt giữa 2 bảng.",
} -- lua_table.i18n.vi
 
function lua_table.from_subnames_object(sub_names, base_table) -- Get the last sub-object from its sub-names, but not a table.
local sub_obj = nil
if (type(base_table) ~= "table")then base_table = package.loaded end
local sub_names = mw.text.split(sub_names, '%.') -- table of words
local sub_tab, sub_obj = base_table, nil
for i, sub_name in ipairs(sub_names) do
sub_obj = sub_tab[sub_name]
if (type(sub_obj) == "table") -- the search continue in sub tables and cannot search a table
then sub_tab = sub_obj
else break end -- get the last object which is not a table
end
return sub_obj
end
 
function lua_table.from_subnames_table(sub_names, base_table) -- Get the last sub-table from its sub-names.
-- S170625ste sub_tab is bad, but it run
if (type(base_table) ~= "table")then base_table = package.loaded end
local sub_names = mw.text.split(sub_names, '%.') -- table of words
local sub_tab = base_table
for i, sub_name in ipairs(sub_names) do
if (type(sub_tab) == "table") and (type(sub_tab[sub_name]) == "table")
then sub_tab = sub_tab[sub_name]
else sub_tab = nil end
end
return sub_tab
end
 
function lua_table.named_sub_counts(subnames_in, base_table) -- Count all objects of all types in all levels, in the sub-tables from their sub-names.
local t = "\n* lua_table.named_sub_counts() Count all objects of all types in all levels"
if (type(subnames_in) ~= "string") then subnames_in = "." end
-- Default base_table for libraries and modules.
local base_table = base_table -- Do not disturb other processes through an external pointer.
if (type(base_table) ~= "table") then base_table = package.loaded end
-- luaTable_fromsubnames_base_err = "Internal error: in langs.sub_i18n_counts(), base unavailable for the subnames table %1.",
local subnames, k = "", ""
local count, pre_count, errs = 0, 0, ", errs: "
local subnames_tab = mw.text.split(subnames_in, '.', true)
local subnames_1 = subnames_tab[1]
-- Default base_table for not loaded libraries.
if (type(base_table) ~= "table") and (type(subnames_1) == "string") and (type(_G[subnames_1]) == "table") then base_table = _G end
local sub_table, object_loaded = base_table, sub_table
local obj_typ, count, pre_count = "string", 0, 0
local counts, all_counts = {}, {}
local pre_counts = nil
local functions_c, numbers_c, strings_c, tables_c, last_count, all_strings, sub_tables_count = 0, 0, 0, 0, 0, 0, 0, 0
local isi18n, endi18n, to_break = false, false
local max_string_count, max_tables_count, missing_trans = 0, 0, 0, 0
local loop = 1
for i, partname in pairs(subnames_tab) do
loop = loop + 1
subnames = subnames .. "." .. partname
object_loaded = sub_table[partname]
obj_typ = type(object_loaded)
all_strings = 0
functions_c, numbers_c, strings_c, tables_c, sub_tables_count = 0, 0, 0, 0, 0
endi18n = string.sub(subnames, -4, -1) -- Is this an i18n table?
isi18n = (endi18n == "i18n") -- Is this an i18n table?
if (type(object_loaded) == "table") then -- Count languages tables.
if isi18n then -- Count languages tables.
for key, val in pairs(object_loaded) do
if (type(val) == "table") then tables_c = tables_c + 1 end
loop = loop + 1
if loop > 99 then break end
end
sub_tables_count = 0
for key, val in pairs(object_loaded) do
if (type(val) == "table") then
sub_tables_count = sub_tables_count + 1
all_strings = all_strings + lua_table.count_all(val)
end
end
else -- Count translations in this table.
for key, val in pairs(object_loaded) do
if (type(val) == "string") then
strings_c = strings_c + 1
if strings_c > max_string_count then max_string_count = strings_c end
elseif (type(val) == "number") then
numbers_c = numbers_c + 1
elseif (type(val) == "function") then
functions_c = functions_c + 1
end
loop = loop + 1
if loop > 99 then break end
end
end
-- local strs_on_tabs = all_strings / tables_c, ["subnames"] = subnames, obj = object_loaded, typ = obj_typ,
local strs_on_tabs = math.floor( (all_strings + 0.49) / math.min(sub_tables_count, 1) )
-- 1/1 = 1.4/1 = 1 3/3 = 3.4/3 = 1.13 = 1 10/2 = 10.5/2 = 5.25 = 5
counts = { ["i"] = i, ["partname"] = partname, ["subnames"] = subnames,
["object_loaded"] = object_loaded, ["obj_typ"] = obj_typ, ["isi18n"] = isi18n, ["endi18n"] = endi18n,
["tables_c"] = tables_c, ["strings_c"] = strings_c, ["numbers_c"] = numbers_c,
["functions_c"] = functions_c, ["booleans_c"] = booleans_c,
["all_strings"] = all_strings, ["max_string_count"] = max_string_count,
["pre_counts"] = pre_counts, ["all_counts"] = all_counts,
-- details:
["strs_on_tabs"] = strs_on_tabs, ["missing_trans"] = missing_trans, -- special langs, remove here
["sub_tables_count"] = sub_tables_count, -- special langs, remove here, obsolete, replaced by pre_counts
["to_break"] = to_break, ["loop"] = loop, -- internal, anticrash and tests only
}
table.insert(all_counts, counts) -- Build a table with translations counts.
if (type(pre_counts) == "table") and (type(counts) == "table") then
counts.pre_counts = pre_counts
pre_counts.post_counts = counts
end
pre_counts = counts
counts.tt = viewers.form9user( "\n* counts: %1, %2, %3, %4, %5, %6.", counts.i, counts.partname, counts.endi18n, counts.strings_c, counts.tables_c, counts.all_strings)
if loop > 99 then break end
end
t = (t or "t") .. (counts.tt or "counts.tt")
end
local strs_on_tabs = math.floor( (strings_c + 0.49999) / math.min(tables_c, 1) )
counts.t = (t or "t")
return strings_c, tables_c, strs_on_tabs, subnames, counts, all_counts, counts.t
-- local strings_c, tables_c, strs_on_tabs, subnames, counts, all_counts, t = lua_table.named_sub_counts(subnames_in, base_table)
end -- function lua_table.named_sub_counts(subnames_in, base_table)
 
function lua_table.count_all(tab) -- Count all objects in the table.
local count = 0
for key, elem in pairs(tab or {}) do count = count + 1 end
return count
end
 
function lua_table.count_types(tab) -- Count in the table, for each type, the number of objects of the this type.
local types_counts = {} -- S170620csc
for key, obj in pairs(tab or {}) do
types_counts[type(obj)] = (types_counts[type(obj)] or 0) + 1
end
return types_counts
end
 
function lua_table.count_values(tab) -- Count in the table, for each value, the number of objects of the this value.
local values_counts = {}
for key, obj in pairs(tab or {}) do
values_counts[obj] = (values_counts[obj] or 0) + 1
end
return values_counts
end
 
function lua_table.counts(obj, opt) -- Counts in object types
local t = t or "\n* <b>lua_table.counts()</b>: Counts in object types, where, what, how, sort." -- to_debug_on_20170503
tab_view.t = tab_view.t or "-"
t = t .. viewers.ta("count_done", count_done) .. viewers.ta("count_now", count_now) .. viewers.ta("count_later", count_later)
local counts_fields = { -- define counts : caracterize available counts
where_to_count = { "string table numbers function", }, -- Detect object type to count. Convert from function.
where_to_count = { "tostring totable tonumbers", }, -- Convert asked totable() or tostring() or tonumber()
which_part = { "coli coln colname rowi rown rowname", }, -- in which object part to count : column i, named row
what_to_count = { "column_i column_n row_i row_n word_i word_n group_i group_n", }, -- count in the column_i. count column_n = the number of columns
how_to_count = { "group_i group_n", }, -- group_i = number of objects in which_part
how_to_sort = { "nosort 0to9 9to0 atoz ztoa", }, -- sort or no, in alpha or digital, increasing decreasing or none
example_1 = { opt = "tostring ztoa", }, -- Count words in a string. Sort in reverse order.
example_3 = { opt = "totable column_n", }, -- Convert to table or insure that. Count the number of columns.
example_2 = { opt = "totable colname group_n 9to0", }, -- Convert to table. Count in column colname. Count in each group_n of values. Sort decreasing.
}
return count, t -- count can be a number, a list, a simple table, an array table of counts
end -- count, t = lua_table.counts(obj, opt) -- Counts in object types
 
function lua_table.to_list(tab, ...) -- Return a list from any Lua table.
-- This function is the reverse of func( ... )
if (type(tab) ~= "table") then tab = {} end
local tab = mw.clone(tab) -- to not disturb original table
local maxn = lua_table.count_all(tab)
local function tabN_to_list1(tab, n, ...)
local max_tab = lua_table.count_all(tab)
local listab = {...}
local max_list = lua_table.count_all(listab)
local tab_last = tab[n] -- last element, even a table to not delete below
local tab_last_string = type(tab_last) -- tostring(tab_last)
if (type(tab_last) ~= "nil") and (n <= max_tab) then
if (type(tab) == "table") then
return tab_last, tabN_to_list1(tab, n + 1, ...)
else
tab_last = tostring(tab_last)
end
else return end
end
return tabN_to_list1(tab, 1, ...)
end -- function lua_table.to_list(tab, ...)
 
function lua_table.to_list_tests(t) -- Return a list from a Lua table.
local memo = viewers.save_configs("lua_table.to_list_tests") -- Save global configuration before eventual changes.
local t = t or "\n* <b>events.all_kinds_test()</b> Test: all kinds of events (err, wng, cat)"
local tab_view = { -- Group datas and options for a table view with lines and columns.
test_group = {
{ "Simple table", { 123, "abc", key = "txt" }, },
{ "All types transmited", { "name", 111, true, false, { 789, "xyz"}, function()end }, },
{ "10 values in the table", { "a", "b", "c", "d", "e", "f", "g", "h", "i9", "j10" }, },
{ "Any number of values", {
"a", "b", "c", "d", "e", "f", "g", "h", "i09", "j10",
"a", "b", "c", "d", "e", "f", "g", "h", "i19", "j20",
"a", "b", "c", "d", "e", "f", "g", "h", "i29", "j30",
"a", "b", "c", "d", "e", "f", "g", "h", "i39", "j40",
"a", "b", "c", "d", "e", "f", "g", "h", "i49", "j50",
"a", "b", "c", "d", "e", "f", "g", "h", "i59", "j60" }, },
},
title_memo = "luaTable_toList_tests_title", -- "lua_table.to_list() Return a list from a Lua table.",
headers = "luaTable_toList_tests_headers", -- "Tested case; Input table, rough_view; Output list",
}
function tab_view.form_one_case(case) -- Convert a case from test_group to rowGroup.
local descript = case[1]
local tabview = viewers.rough_view( case[2] )
local tab_list = { lua_table.to_list( case[2] ) }
local t1 = ""
for i, elem in ipairs(tab_list) do
t1 = t1 .. viewers.ta( "[" .. i .. "]", tostring(elem) )
end
return { descript, tabview, t1, }
end
local t = tableview.new(tab_view) -- Formats a table view with lines and columns.
viewers.restore_configs(memo, "lua_table.to_list_tests") -- Restore global configurations after eventual changes.
return t --, errors -- langs_missing_translations_title
end -- function lua_table.to_list_tests(t)
 
function lua_table.to_table(stringList, pattern, plain) -- convert a string to a table of words
if type(stringList) ~= "string" then stringList = "" end
if type(pattern) ~= "string" then pattern = "" end
if plain then plain = true else plain = false end
local tab = mw.text.split(stringList, pattern, plain)
local tab2 = {}
for i, word in ipairs(tab) do -- for all names
word = mw.text.trim(word) -- clean spaces in each name
tab2[word] = word -- not table.insert(tab2, name)
end
return tab2
end
 
function lua_table.to_table_test(t) -- Test: convert a string to a table of words
local memo = viewers.save_configs("lua_table.to_table_test") -- Save global configuration before eventual changes.
local stringList = ""
local t = t or "\n* lua_table.to_table_test(t) -- Test: convert a string to a table of words"
local tab_view = { -- Group datas and options for a table view with lines and columns.
test_group = {
{ stringList = "docview nocatview : tests docline", pattern = nil, },
{ stringList = "docview nocatview : tests docline", pattern = " ", plain = nil, },
{ stringList = "docview,nocatview, : ,tests docline", pattern = ",", plain = true, },
{ stringList = "docview docline : tests", pattern = " ", plain = true, },
{ stringList = "docview; nocatview; : tests; docline", pattern = ";", plain = false, },
{ stringList = "abc ; ; def.;ghi;,jkl", pattern = ";", },
},
headers = "langs_selectLang_test_headers", -- "stringList; pattern; plain; result"
headers = "stringList; pattern; plain; result",
}
function tab_view.form_one_case(case) -- Convert a case from test_group to rowGroup.
local tab = lua_table.to_table(case.stringList, case.pattern, case.plain)
local t1 = ""
for key, elem in pairs(tab) do
t1 = t1 .. viewers.ta("[" .. viewers.value(key) .. "]", elem)
end
return { case.stringList, case.pattern, case.plain, t1, }
end
t = t .. tableview.new(tab_view) -- Formats a table view with lines and columns.
viewers.restore_configs(memo, "lua_table.to_table_test") -- Restore global configurations after eventual changes.
return t
end -- function lua_table.to_table_test(t)
 
function lua_table.old_to_sort(tab, sortfield, sortorder) -- To sort any table and convert in sequence if needed. "20180307", "NOW", "Rical", "S180810lts", "new function
local opt = opt or {}
if (type(tab) ~= "table") then tab = {} end
if (type(sortfield) ~= "string") then sortfield = "" end
if (type(sortorder) ~= "string") then sortorder = "" end
local sorted, i = {}, 0
for key, elem in pairs(tab) do
i = i + 1
table.insert(sorted, elem)
end
return sorted
end -- local sorted = lua_table.to_sort(tab, sortfield, sortorder) -- To sort any table and convert in sequence if needed.
 
function lua_table.to_sort_tests(t) -- To sort any table and convert in sequence if needed.
local t = t or "\n* lua_table.to_sort(tab, sortfield, sortorder) Test to sort any table and convert in sequence if needed."
local opt = opt or {}
local sorted = lua_table.to_sort(tab, sortfield, sortorder) -- To sort any table and convert in sequence if needed.
local sorted, i = {}, 0
for key, elem in pairs(tab) do
i = i + 1
elem[sortfield] = i
table.insert(sorted, elem)
end
t = t .. "\n* " .. viewers.ta("tab count", lua_table.level_count(tab) )
t = t .. "\n* " .. viewers.ta("sorted count", lua_table.level_count(sorted) )
return t
end -- local sorted = lua_table.to_sort(tab, sortfield, sortorder) -- To sort any table and convert in sequence if needed.
 
-- local tot_vars, tot_tabs, tot_func, vr_tb = lua_table.sub_counts(tablebase, tabname, opt, recursiveLevel)
function lua_table.sub_counts(tablebase, tabname, opt, recursiveLevel) -- In a table, recursive counts of vars, sub-tables and functions.
local opt = opt or {}
opt.recursiveLevel = recursiveLevel or opt.recursiveLevel
opt.recursiveLevel, opt.recursive_limit, opt.recursiveLevel_err = modes.recursive_normal(opt.recursiveLevel, modes.recursive_limit)
local isempty = true
local tot_vars, tot_tabs, tot_func = opt.tot_vars or 0, opt.tot_tabs or 0, opt.tot_func or 0
-- lua_table.sub_counts(get.i18n, get.pagename) -- : attempt to index local 'opt' (a nil value).
local nbr_vars, nbr_tabs, nbr_func = 0, 0, 0
local txt, vr, tb, fn, vrtb, vr_tb = "", 0, 0, 0, 0, 0
local case = ""
if (type(tablebase) == "table") and (type(tabname) == "string") then -- for any tables
-- normal case OK, do nothing
case = " tab+name"
elseif (type(tablebase) == "table") and (type(tabname) ~= "string") then -- for abnormal or missing tabname
tabname = "tabname=" .. tostring(tablebase) .. "?"
tabname = viewers.styles_color_error(tabname)
case = " tab+noname"
elseif (type(tablebase) ~= "table") and (type(tabname) == "string") then -- for abnormal table
tabname = "tabname=" .. tostring(tabname) .. "?"
tabname = viewers.styles_color_error(tabname)
case = " notab+name"
elseif type(tablebase) == "string" then -- for viewers.tables
tabname = "package.loaded." .. tablebase
case = " tab=name"
else
tabname = "tabname=" .. tostring(tablebase) .. "?"
tabname = viewers.styles_color_error(tabname)
case = " notab+noname"
end
if (type(tablebase) == "table") and (type(tabname) == "string") then -- for normal cases
for key, var in pairs(tablebase) do -- List and count vars, functions and sub tables
local sub_tabname = tostring(key)
if type(var) == "table" then
local sub_tablebase = var
nbr_tabs = nbr_tabs + 1
if (opt.recursiveLevel < opt.recursive_limit) then
-- if (opt.recursiveLevel > 0) and (opt.recursiveLevel < opt.recursive_limit) then
-- vr, tb, fn, vrtb, opt.recursiveLevel = lua_table.sub_counts(var, tabname, opt)
opt.recursiveLevel = opt.recursiveLevel + 111
vr, tb, fn, vrtb = lua_table.sub_counts(sub_tablebase, sub_tabname, opt, opt.recursiveLevel)
tot_vars = tot_vars + vr
tot_tabs = tot_tabs + tb + 1
tot_func = tot_func + fn
end
elseif type(var) == "function" then
nbr_func = nbr_func + 1
tot_func = tot_func + 1
isempty = false
else -- type(var) == other
nbr_vars = nbr_vars + 1
tot_vars = tot_vars + 1
isempty = false
end
end
end
local vr_tb = 0
if tot_tabs == 0 then
vr_tb = tot_vars -- string number in all languages
else -- How many translations in each language? Approximative if not equal.
vr_tb = tot_vars / tot_tabs -- string number in one language, like + 33.49
vr_tb = math.floor( vr_tb ) -- digital string number in each language
end
opt.tot_vars = tot_vars -- total number of variables in the table
opt.tot_tabs = tot_tabs -- total number of sub-tables in the table
opt.tot_func = tot_func -- total number of functions in the table
opt.vr_tb = vr_tb -- digital string number in each language
return tot_vars, tot_tabs, tot_func, vr_tb -- , opt.recursiveLevel
end -- local tot_vars, tot_tabs, tot_func, vr_tb = lua_table.sub_counts(tablebase, tabname, opt, recursiveLevel)
 
function lua_table.level_count(tab) -- Count all objects in the table, or 0 if tab is not a table.
local count = 0
if (type(tab) ~= "table") then return count end
for k,v in pairs(tab) do
count = count + 1
end
return count
end -- c = lua_table.level_count(tab)
 
function lua_table.level_get(tab, typ) -- Get only the first level of the table. Get only one key type if asked.
local level = {}
local count = 0
if (type(tab) ~= "table") then return level, count end
for key, val in pairs(tab) do
if (type(typ) == "string") and (type(val) == typ)
then level[key] = val ; count = count + 1
else level[key] = val ; count = count + 1 end
end
return level, count
end -- function lua_table.level_get(tab, typ)
 
function lua_table.level_list(tab, typ, select, field) -- Collect and count selected or all keys, in the first level of the table -- subtasks S170813lll
-- typ = "key;val;keys;vals;sort;boolean;function;number;string;table;"
-- Get only the first level of the table. Select only keys containing select. Select the field as key if defined.
-- Collects and counts the selected keys, or all, in recording order
-- Count the key of the typ type
local list, count, level, split, ok = "", 0, {}, {}, false
local sort, keyval = typ, ""
if (type(tab) ~= "table") then return list, count, level, split end
for key, val in pairs(tab) do
table.insert(level, val)
ok = false
if (typ == "key") then -- Count and list keys from select and field.
sort, keyval = false, key
if viewers.is_in(keyval, select) then ok = true end -- Select a value if the val is in select.
elseif (typ == "val") then -- Count and list values...
sort, keyval = false, val
if viewers.is_in(keyval, select) then ok = true end -- Select a value if the val is in select.
elseif (typ == "keys") then -- Count and sort keys...
sort, keyval = true, key
if viewers.is_in(keyval, select) then ok = true end -- Select a value if the val is in select.
elseif (typ == "vals") then -- Count and sort values...
sort, keyval = true, val
if viewers.is_in(keyval, select) then ok = true end -- Select a value if the val is in select.
elseif (typ == "sort") then -- Sort all values...
sort, keyval = true, tab[field or 1]
if viewers.is_in( tostring(keyval), tostring(select) ) then ok = true end -- Select a value if the val is in select.
else -- lua_table.count_values()
local typ2 = type(typ) -- To select a type or the type of a variable.
if (typ2 == "boolean") or (typ == "boolean") then -- Count only these types.
if viewers.is_in(keyval, select) then ok = true end -- Select a value if the val is in select.
elseif (typ2 == "function") or (typ == "function") then
if viewers.is_in(keyval, select) then ok = true end -- Select a value if the val is in select.
elseif (typ2 == "number") or (typ == "number") then
if viewers.is_in(keyval, select) then ok = true end -- Select a value if the val is in select.
elseif (typ2 == "string") or (typ == "string") then
if viewers.is_in(keyval, select) then ok = true end -- Select a value if the val is in select.
elseif (typ2 == "table") or (typ == "table") then
if viewers.is_in(keyval, select) then ok = true end -- Select a value if the val is in select.
end
end
if ok then
table.insert(split, keyval) -- Collect the selected keys, or all, in recording order
count = count + 1 -- Count the key of the typ type
list = list .. tostring(keyval) .. ", " -- List values
end
end
if (sort == "sort") or (sort == true) then table.sort( split ) end -- in alphabetic order -- , function (a, b) end
list = table.concat(split, ", ")
return list, count, level, split
end -- local list, count, level, split = lua_table.level_list(tab, typ, select, field) lua_table.level_list_tests(
 
function lua_table.count_tests(t) -- Count all objects or types or values in the table
local memo = viewers.save_configs("lua_table.count_tests") -- Save global configuration before eventual changes.
local t = t or "\n* <b>lua_table.count_values()</b> Tests: Count all objects or types or values."
local test_table = { "name", 111, "other", function() return 2 end, true, false, { 789, "xyz"}, function() return 1 end }
local tab_view = { -- Group datas and options for a table view with lines and columns.
test_group = {
{ "count_all", { "name", 111, "other", function() end, true, false, { 33 }, function() end }, },
{ "count_types", { "name", 111, "other", function() end, true, false, { 33 }, function() end }, },
{ "count_values", { "name", 111, "other", function() end, true, false, { 33 }, function() end }, },
{ "count_all", { a = "abc", 11, z = "xyz", t = true, false, n = nil, min = 11, 33, nil, 33, max = 55, "abc", }, },
{ "count_types", { a = "abc", 11, z = "xyz", t = true, false, n = nil, min = 11, 33, nil, 33, max = 55, "abc", }, },
{ "count_values", { "abc", 11, "xyz", true, false, nil, 11, 33, nil, 33, 55, "abc", }, },
{ "level_list", { "abc", 11, "xyz", true, false, nil, 11, 33, nil, 33, 55, "abc", }, "key", "3", },
{ "level_list", { "abc", 11, "xyz", true, false, nil, 11, 33, nil, 33, 55, "abc", }, "val", "3", },
{ "level_list", { "abc", 11, "xyz", true, false, nil, 11, 33, nil, 33, 55, "abc", }, "keys", "3", },
{ "level_list", { "abc", "bcd", "xyz", "bcbc", nil, 11, 33, nil, 33, 55, "abc", }, "vals", "bc", },
{ "level_list", { "name", 111, "other", function() end, true, false, { 33 }, function() end }, "sort", },
-- local list, count, level, split = lua_table.level_list(tab, typ, select, field)
-- typ = "key;val;keys;vals;sort;boolean;function;number;string;table;"
{ "level_list", { "abc", "bcd", "xyz", "bcbc", nil, 11, 33, nil, 33, 55, "abc", }, "boolean", "bc", },
{ "level_list", { "abc", "bcd", "xyz", "bcbc", nil, 11, 33, nil, 33, 55, "abc", }, "function", "bc", },
{ "level_list", { "abc", "bcd", "xyz", "bcbc", nil, 11, 33, nil, 33, 55, "abc", }, "number", "bc", },
{ "level_list", { "abc", "bcd", "xyz", "bcbc", nil, 11, 33, nil, 33, 55, "abc", }, "string", "bc", },
{ "level_list", { "abc", { "bcbc", nil }, "bcd", "xyz", { "tab1", "tab2" }, "abc", }, "table", "bc", },
{ "level_list", "abcdefg", "table", "bc", },
{ "level_list", 12345, "table", "bc", },
},
title_memo = "lua_table_count_all_values_title", -- "lua_table.count_values() Count all objects or types or values in the table.",
headers = "luaTables_count_all_types_values_headers", -- "Tested case; Input table, rough_view; Output list",
headers = "Tested table; Function to count; Kind of count; Resulting counts",
}
function tab_view.form_one_case(case) -- Convert a case from test_group to rowGroup RIC05900470
local func_name = case[1]
local test_table = case[2]
local count_kind = case[3]
if (type(test_table) ~= "table") then test_table = { test_table } end
-- if (type(func_name) ~= "string") then test_table = { test_table } end
local values_counts = lua_table[func_name](test_table) -- Select the function to test
if (type(values_counts) ~= "table") then values_counts = { values_counts } end
local tests_view = ""
for key, val in pairs(test_table) do
val = tostring(val)
tests_view = tests_view .. viewers.ta(key, val)
end
local counts_view = ""
for key, val in pairs(values_counts) do
val = tostring(val)
counts_view = counts_view .. viewers.ta(key, val)
end
return { tests_view, func_name, count_kind, counts_view }
end
t = t .. tableview.new(tab_view) -- Formats a table view with lines and columns.
viewers.restore_configs(memo, "lua_table.count_tests") -- Restore global configurations after eventual changes.
return t
end -- function lua_table.count_tests(t)
 
-- opt = { drop_opt.drop_opt = "drop_opt", level_maxi = 3, max_n = 2, exclude1 = "hou" } ) -- example of use , {width = "88%", tc1 = "blue"}
function lua_table.normal_options(opt, recursiveLevel, recursive_limit) -- Normalize lua_table options.
if type(opt) ~= "table" then opt = {} end
if type(opt.level_maxi) ~= "number" then opt.level_maxi = 111 end
if type(opt.max_n) ~= "number" then opt.max_n = 9999 end
opt.max_n = opt.max_n or 9999
opt.recursiveLevel = recursiveLevel or opt.recursiveLevel or 1
opt.recursive_limit = recursive_limit or opt.recursiveLevel or 111
opt.exclude1 = opt.exclude1 or ""
opt.exclude2 = opt.exclude2 or ""
opt.exclude3 = opt.exclude3 or ""
opt.countonly = opt.countonly and true
return opt
end
 
function viewers.rough_view(table) -- Formats a string to describe a value like: true, 123.456, "abcd", func(), table{}
if type(table) ~= "table" then return viewers.value(table) end
local opt = option
if type(opt) ~= "table" then opt = {} end
opt.level = (opt.level or 1)
opt.recursive_limit = tonumber(opt.recursive_limit) or 11111
opt.max_n = tonumber(opt.max_n) or 11111
local shift = "\n" .. string.rep(":", opt.level)
local t = ""
local n = 0
local continue = true
if opt.level > opt.recursive_limit then -- Limit the number of levels of sub-tables to opt.recursive_limit
local col = viewers.styles_color_warning( viewers.form9user( '%1 = %2', "recursive_limit", opt.recursive_limit) )
t = t .. viewers.form9user( '{ %1 }', col )
else
shift = "\n" .. string.rep(":", opt.level)
for k, v in pairs(table) do
n = n + 1
if n > opt.max_n then -- Limit the number of elements in each-subtable to opt.max_n.
local col = viewers.styles_color_warning( viewers.form9user( '%1 = %2', "max_n", opt.max_n ) )
continue = false
end
if continue then
if (type(k) == "string")
then t = t .. viewers.form9user( '["%1"] = %2, ', k, tostring(v), shift )
else t = t .. viewers.form9user( '[%1] = %2, ', tostring(k), tostring(v), shift ) end
end
end
for k, v in pairs(table) do
n = n + 1
if n > opt.max_n then
local col = viewers.styles_color_warning( viewers.form9user( '%1 = %2', "max_n", opt.max_n ) )
continue = false
end
if continue then -- Do not list if exclude1, exclude2 or exclude3 are in the table name.
if (type(v) == "table") and (k ~= opt.exclude1) and (k ~= opt.exclude2) and (k ~= opt.exclude3) then
opt.level = (opt.level or 1) + 1
shift = "\n" .. string.rep(":", opt.level)
local tt = viewers.rough_view(v, opt)
opt.level = (opt.level or 1) - 1
shift = "\n" .. string.rep(":", opt.level)
t = t .. viewers.form9user( '%3 ["%1"] = %2 ', k, tt, shift )
elseif (type(v) == "function") then
t = t .. viewers.form9user( '%3 ["%1"] = %2() ', k, "function", shift )
elseif (type(v) == "nil") then
t = t .. viewers.form9user( '%3 %1 = %2() ', k, "nil", shift )
end
end
end
end
t = "{ " .. t .. " }"
return t
end -- t = viewers.rough_view(table) -- Formats a string to describe a value like: true, 123.456, "abcd", func(), table{}
 
function lua_table.rough_view(table) -- Formats a string to describe a value like: true, 123.456, "abcd", func(), table{}
versions.deprecated_function("lua_table.rough_view", "viewers.rough_view")
return viewers.rough_view(table) end
 
function viewers.rough_view_test(t) -- Formats a rough Lua code of the table structure.
local memo = viewers.save_configs("viewers.rough_view_test") -- Save global configuration before eventual changes.
local t = t or "viewers.rough_view_test(t) : From a Lua table, re-form a string roughly equivalent to the table."
local table_key = { "A table used as key.", key = "string", bar = "bartxt", }
local table_value = { "A table used as value is expended in the main table.", abc = "ABC", [5] = "five", ghi = "JKL", }
local tae_val = "A table used as value is expended in the main table."
local function funcView() return "A function result in this string." end
local test_table = {
key = "string",
"string one without key",
[12] = "number key twelve",
["12"] = "string key twelve in brace",
sub_table = { [4] = "four", abc = "ABC", [5] = "five", ghi = "JKL", },
func = funcView(),
"string two without key",
[tonumber] = "A function used as key.",
[true] = "A Lua reserved value used as key.",
}
local t = t .. viewers.rough_view(test_table)
viewers.restore_configs(memo, "viewers.rough_view_test") -- Restore global configurations after eventual changes.
return t
end -- function viewers.rough_view_test(t)
 
function lua_table.sort_onkey(tab, key) -- Sort a table with any types of keys.
local key = key or "keyword"
return table.sort(tab, function (a, b)
if (type(a[key]) == type(b[key])) then return ( a[key] < b[key] ) -- any translated arguments of same types
else return ( tostring(a[key]) < tostring(b[key]) ) end -- alphabetic sort of translated arguments
end )
end
 
function lua_table.sort_types(tab, key, decrease) -- Sort a table, with any types of fields, even of differents types as strings.
if (type(tab) ~= "table") then return tab end
if (type(key) ~= "string") then key = "keyword" end
if decrease == ">" then -- sort in decreasing order
table.sort(tab, function (a, b)
if ( type(a[key]) == type(b[key]) )
then return ( a[key] > b[key] ) -- Sort same types
else return (tostring(a[key]) > tostring(b[key]) ) end -- Sort differents types as strings
end )
else -- sort in increasing order
table.sort(tab, function (a, b)
if ( type(a[key]) == type(b[key]) )
then return ( a[key] < b[key] ) -- Sort same types
else return (tostring(a[key]) < tostring(b[key]) ) end -- Sort differents types as strings
end )
end
end -- function lua_table.sort_types(tab, key, decrease)
 
function lua_table.structure_recursive(tbl, uppername, name, recursiveLevel, opt) -- countonly, level_maxi, max_n, exclude1, exclude2, exclude3)
if type(tbl) ~= "table" then tbl = {} end
if type(uppername) ~= "string" then name = "uppername" end
if type(name) ~= "string" then name = "table" end
local res, newname, part, shift = "", "", "", ""
local sep, N = ", ", 0
local isempty = true
local levelname = uppername .. "." .. name
local tot_vars, tot_func, tot_tabs = 0, 0, 0
local nbr_vars, lst_vars = 0, ""
local nbr_func, lst_func = 0, ""
local nbr_tabs, lst_tabs = 0, ""
local max, lst_subtabs = 0, ""
local st, vr, fn, tb = "", 0, 0, 0
local list = not opt.countonly
if recursiveLevel > opt.level_maxi then -- limit the number of the level of sub-tables
local t_levelmaxi = viewers.form9user("luaTable_structure_level_maxi", recursiveLevel)
return viewers.styles_color_warning( tostring(t_levelmaxi ) ), tot_vars, tot_func, tot_tabs
end
opt.max_n = tonumber(opt.max_n) or 11111
shift = string.rep("*", recursiveLevel)
-- Do not list if exclude1, exclude2 or exclude3 is in the table name.
if type(opt.exclude1) == "string" and opt.exclude1 ~= "" and string.find(name, opt.exclude1) ~= nil
then return "", tot_vars, tot_func, tot_tabs end
if type(opt.exclude2) == "string" and opt.exclude2 ~= "" and string.find(name, opt.exclude2) ~= nil
then return "", tot_vars, tot_func, tot_tabs end
if type(opt.exclude3) == "string" and opt.exclude3 ~= "" and string.find(name, opt.exclude3) ~= nil
then return "", tot_vars, tot_func, tot_tabs end
if type(tbl) ~= "table" then -- display table error
return '<br>The variable "' .. tostring(name) .. '" is not a table.<br>', tot_vars, tot_func, tot_tabs
end
for k, v in pairs(tbl) do -- List and count vars, functions and sub tables
k = tostring(k)
if type(v) == "table" then
lst_tabs = lst_tabs .. k .. sep
nbr_tabs = nbr_tabs + 1
isempty = false
newname = tostring(k)
max = max + 1
if recursiveLevel <= opt.level_maxi then -- List recursively each sub-table
st, vr, fn, tb = lua_table.structure_recursive(v, levelname, newname, recursiveLevel + 1, opt) -- countonly, level_maxi, max_n, exclude1, exclude2, exclude3)
tot_vars = tot_vars + vr
tot_func = tot_func + fn
tot_tabs = tot_tabs + tb + 1
if list then lst_subtabs = lst_subtabs .. st end
else
local t_levelmaxi = viewers.form9user("luaTable_structure_level_maxi", recursiveLevel)
if list then res = res .. " " .. viewers.styles_color_warning( t_levelmaxi ) end
end
local sep = ""
if max == opt.max_n then
local luaTable_table_listlimit_max_n = viewers.form9user("luaTable_table_listlimit_max_n", opt.max_n)
if list then res = res .. "\n" .. shift .. " Table <b>" .. levelname .. "</b> " .. viewers.styles_color_warning(luaTable_table_listlimit_max_n) end
break
end
elseif type(v) == "function" then
nbr_func = nbr_func + 1
tot_func = tot_func + 1
isempty = false
if list then lst_func = lst_func .. k .. sep end
else -- type(v) == other
nbr_vars = nbr_vars + 1
tot_vars = tot_vars + 1
isempty = false
if list then lst_vars = lst_vars .. type(v) .. " - <b>" .. tostring(k) .. "</b> = " .. tostring(v) .. " " .. sep end
end
end
if list then res = res .. "\n" .. shift .. " Table <b>" .. levelname .. "</b>, " .. tostring(nbr_vars) .. " vars: " .. lst_vars end
if list then res = res .. "\n" .. shift .. " Table <b>" .. levelname .. "</b>, " .. tostring(nbr_func) .. " functions: " .. lst_func end
if list then res = res .. "\n" .. shift .. " Table <b>" .. levelname .. "</b>, " .. tostring(nbr_tabs) .. " tables: " .. lst_tabs .. lst_subtabs end
return res, tot_vars, tot_func, tot_tabs
end -- function lua_table.structure_recursive(tbl, uppername, name, recursiveLevel, opt) -- countonly, level_maxi, max_n, exclude1, exclude2, exclude3)
 
-- - - - ------------------ - - - - ---------------------------------
-- Document the tables and their structures. List a table content, with formating.
-- Documentar las tablas y sus estructuras. Lista de un contenido de la tabla, con el formateo.
-- Documenter les tables et leurs structures. Lister un contenu de la table, avec le formatage.
-- - - - ------------------ - - - - ---------------------------------
-- Dump and format the content of a table and its sub-tables ; with limits in length, deep and exceptions.
-- Listar y formatar le contento de una tabla y su sub-tablas.
-- Lister et formater le contenu d'une table et ses sous-tables ; avec des limites en longueur, profondeur et exceptions.
-- For each (sub)table, list : in first vars, then functions, then sub-tables list, then sub-tables contents
 
-- Auto test of limits of the table list.
-- Auto test des limites de liste de table.
lua_table.tablim = { "one", "two", max1 = "MAX1", max2 = "MAX2", max3 = "MAX3"}
lua_table.tablim.life = { animal = "dog", vegetal = { big = "tree", small = "flower"} }
lua_table.tablim.life.animals = { "turtle"}
lua_table.tablim.comfort = { "tv", mobile = "car", sub2 = { "phone", fix = "wall", sub3 = { "bed", up = "roof", sub4 = { "ball"} } } }
lua_table.tablim.house = { "kitcheen", "bedroom"}
lua_table.tablim.house.garden = { flower = "rose", nature = "river"}
-- opt = { drop_opt.drop_opt = "drop_opt", level_maxi = 3, max_n = 2, exclude1 = "hou" } ) -- , {width = "88%", tc1 = "blue"}
 
function lua_table.structure(table, tablename, opt)
-- luaTable_structure_limits_title = "List a table, test with limits:",
local memo = viewers.save_configs("lua_table.structure") -- Save global configuration before eventual changes.
local recursiveLevel, recursive_limit, recursiveLevel_err = 1, 1111, ""
local res = "\n* Content of the <b>" .. tostring(tablename) .. "</b> table, begin:"
if not opt then opt = { recursive_limit = 11111 } end
local recursiveLevel = opt.recursiveLevel or 1
if langs.main_i18n_complete then
recursiveLevel, recursive_limit, recursiveLevel_err = modes.recursive_normal(recursiveLevel, modes.recursive_limit)
end
-- local recursiveLevel, recursive_limit, recursiveLevel_err = modes.recursive_normal(recursiveLevel, modes.recursive_limit)
if type(opt.level_maxi) ~= "number" then opt.level_maxi = 222 end
-- opt.level_maxi = opt.level_maxi or 222
if type(opt.max_n) ~= "number" then opt.max_n = 3333 end
opt.max_n = opt.max_n or 3333
opt.recursiveLevel = opt.recursiveLevel or recursiveLevel or 1
opt.exclude1 = opt.exclude1 or ""
opt.exclude2 = opt.exclude2 or ""
opt.exclude3 = opt.exclude3 or ""
opt.countonly = opt.countonly and true
local tot_vars, tot_func, tot_tabs = 0, 0, 0
if recursiveLevel > opt.level_maxi then -- even for abnormal limit -- Erreur Lua dans Module:Centralizer-s-fr à la ligne 7271 : attempt to compare number with nil.
return "", tot_vars, tot_func, tot_tabs
end
local st, vr, fn, tb = lua_table.structure_recursive(table, "", tablename, 1, opt) -- countonly, level_maxi, max_n, exclude1, exclude2, exclude3)
res = res .. st
tot_vars = tot_vars + vr
tot_func = tot_func + fn
tot_tabs = tot_tabs + tb
res = res .. "\n* Content of the <b>" .. tostring(tablename) .. "</b> table, end: "
res = res .. viewers.form9user(" %1 variables, %2 functions, %3 sub-tables.\n", vr, fn, tb)
viewers.restore_configs(memo, "lua_table.structure") -- Restore global configurations after eventual changes.
return res, tot_vars, tot_func, tot_tabs
end -- function lua_table.structure(table, tablename, opt)
 
function lua_table.structure_recursive_report(t) -- List the structure of a table, with or without limits
local t = t or "\n* <b>lua_table.structure()</b> List the structure of a table, with or without limits"
local t = t .. "\n* lua_table.structure() List a table, <b>test with limits</b>:"
local opt = { ["drop_opt"] = "drop_opt", ["level_maxi"] = 3, ["max_n"] = 2, ["exclude1"] = "hou" }
local res, tot_vars, tot_func, tot_tabs = lua_table.structure(lua_table.tablim, "lua_table.tablim", opt)
local t = t .. res -- luaTable_structure_limits_title
local t = t .. "\n* ."
local t = t .. "\n* lua_table.structure() List a table, <b>test without limits</b>:"
local res, tot_vars, tot_func, tot_tabs = lua_table.structure(lua_table.tablim, "lua_table.tablim", nil)
local t = t .. res -- luaTable_structure_nolimits_title
return t
end -- local t = lua_table.structure_recursive_report(t)
 
-- cut_libraries
 
-- - - - ------------------ - - - - ------------------ - - - - -----------------------------
-- - - - ------------------ - - - - ------------------ - - - - -----------------------------
-- The Library:mathroman is here as an example of very small central library. It becomes central using the central modules system.
-- function mathroman.roman2int(rm, testcase) -- Convert a roman number to decimal
-- function mathroman.int2roman(i, testcase) -- Convert a integer number to roman
-- - - - ------------------ - - - - ------------------ - - - - -----------------------------
-- - - - ------------------ - - - - ------------------ - - - - -----------------------------
 
 
-- These Module:Centralizer/I18N translations for mathroman library update and complete Module:Centralizer translations.
mathroman.i18n = {} -- translations tables known in the module
mathroman.i18n.br = {
mathroman_errors_head_err = "Erreur : ",
mathroman_roman_err = "Erreur de romain : ",
mathroman_value_error_err = "Erreur de valeur : ",
mathroman_J_before_end_err = "Caractère J avant la fin",
mathroman_char_X_in_N_err = "Caractère <b>%1</b> en <b>%2</b>",
mathroman_char_increase_err = "3 caractères croissants",
mathroman_greater_4999_err = "Valeur > 4999",
mathroman_null_value_err = "Valeur nulle",
mathroman_rom2dig_value_err = "Erreur de valeur de nombre romain",
mathroman_dig2rom_value_err = "Erreur de valeur décimale",
mathroman_roman2int_tests_title = "mathroman.roman2int() Test des nombres romains en nombres décimaux",
mathroman_roman2int_tests_headers = "Nombre romain; Valeur décimale; Correct; Erreur(s)",
mathroman_int2roman_test_title = "mathroman.int2roman() Test des nombres décimaux en nombres romains",
mathroman_int2roman_tests_headers = "Nombre décimal; Valeur romaine; Correct; Erreur(s)",
mathroman_int_is_not_integer_err = "Le nombre non entier <b>%1</b> n'est pas convertible en nombre romain",
mathroman_int_is_not_number_err = "La valeur <b>%1</b> n'est pas un nombre convertible en nombre romain",
mathroman_is_not_string_err = "La valeur <b>%1</b> n'est pas un texte convertible en nombre",
} -- mathroman.i18n.br
mathroman.i18n.de = {
mathroman_errors_head_err = "Fehler: ",
mathroman_roman_err = "Römischer Fehler: ",
mathroman_value_error_err = "Wert Fehler: ",
mathroman_J_before_end_err = "J Zeichen vor dem Ende",
mathroman_char_X_in_N_err = "Zeichen <b>%1</b> in <b>%2</b>",
mathroman_char_increase_err = "3 zunehmende Charaktere",
mathroman_greater_4999_err = "Wert > 4999",
mathroman_null_value_err = "Nullwert",
mathroman_rom2dig_value_err = "Roman Wert Fehler",
mathroman_dig2rom_value_err = "Dezimalwertfehler",
mathroman_roman2int_tests_title = "mathroman.roman2int() Test römischer Zahlen in Dezimalzahlen",
mathroman_roman2int_tests_headers = "Römische Nummer; Dezimalwert; Richtig; Error (s)",
mathroman_int2roman_test_title = "mathroman.int2roman() Test von Dezimalzahlen in römischen Zahlen",
mathroman_int2roman_tests_headers = "Dezimalzahl; Römischer Wert; Richtig; Error (s)",
mathroman_int_is_not_integer_err = "Das nicht ganzzahlige <b>%1</b> ist nicht in römische Zahl umwandelbar",
mathroman_int_is_not_number_err = "Der Wert <b>%1</b> ist keine Zahl, die in eine römische Zahl umgewandelt werden kann",
mathroman_is_not_string_err = "Der Wert <b>%1</b> ist kein konvertierbarer Text in der Zahl",
} -- mathroman.i18n.de
mathroman.i18n.en = {
mathroman_errors_head_err = "Error: ",
mathroman_roman_err = "Roman error: ",
mathroman_value_error_err = "Value error: ",
mathroman_J_before_end_err = "character J before the end",
mathroman_char_X_in_N_err = "character <b>%1</b> in <b>%2</b>",
mathroman_char_increase_err = "3 increasing characters",
mathroman_greater_4999_err = "value > 4999",
mathroman_null_value_err = "null value",
mathroman_rom2dig_value_err = "roman value error",
mathroman_dig2rom_value_err = "digital value error",
mathroman_roman2int_tests_title = "mathroman.roman2int() Test roman to digital numbers",
mathroman_roman2int_tests_headers = "Roman number; Digital value; Correct; Error(s)",
mathroman_int2roman_test_title = "mathroman.int2roman() Test digital numbers to roman numbers",
mathroman_int2roman_tests_headers = "Digital number; Roman value; Correct; Error(s)",
mathroman_int_is_not_integer_err = "The not integer number <b>%1</b> is not convertible to Roman numeral",
mathroman_int_is_not_number_err = "The value <b>%1</b> is not a convertible number to Roman numeral",
mathroman_is_not_string_err = "The value <b>%1</b> is not a text convertible to number"
} -- mathroman.i18n.en
mathroman.i18n.es = {
mathroman_errors_head_err = "Error: ",
mathroman_roman_err = "Error de romano: ",
mathroman_value_error_err = "Error de valor: ",
mathroman_J_before_end_err = "Carácter J antes del fin",
mathroman_char_X_in_N_err = "Carácter <b>%1</b> en <b>%2</b>",
mathroman_char_increase_err = "3 crecientes caracteres",
mathroman_greater_4999_err = "Valor > 4999",
mathroman_null_value_err = "Valor null",
mathroman_rom2dig_value_err = "Romano valor error",
mathroman_dig2rom_value_err = "Decimale valor error",
mathroman_roman2int_tests_title = "mathroman.roman2int() Prueba de números romanos a números decimales",
mathroman_roman2int_tests_headers = "Número romano; Valor digital; Corregido; Error(s)",
mathroman_int2roman_test_title = "mathroman.int2roman() Prueba de números decimales a números romanos",
mathroman_int2roman_tests_headers = "Número decimal, Valor romana; Correcto; Error(es),",
mathroman_int_is_not_integer_err = "El no entero <b>%1</b> no se puede convertir en número romano",
mathroman_int_is_not_number_err = "El valor <b>%1</b> no es un número y no se puede convertir en número romano",
mathroman_is_not_string_err = "El valor <b>%1</b> no es un texto y no se puede convertir en número",
} -- mathroman.i18n.es
mathroman.i18n.fr = {
mathroman_errors_head_err = "Erreur : ",
mathroman_roman_err = "Erreur de romain : ",
mathroman_value_error_err = "Erreur de valeur : ",
mathroman_J_before_end_err = "Caractère J avant la fin",
mathroman_char_X_in_N_err = "Caractère <b>%1</b> en <b>%2</b>",
mathroman_char_increase_err = "3 caractères croissants",
mathroman_greater_4999_err = "Valeur > 4999",
mathroman_null_value_err = "Valeur nulle",
mathroman_rom2dig_value_err = "Erreur de valeur de nombre romain",
mathroman_dig2rom_value_err = "Erreur de valeur décimale",
mathroman_roman2int_tests_title = "mathroman.roman2int() Test des nombres romains en nombres décimaux",
mathroman_roman2int_tests_headers = "Nombre romain; Valeur décimale; Correct; Erreur(s)",
mathroman_int2roman_test_title = "mathroman.int2roman() Test des nombres décimaux en nombres romains",
mathroman_int2roman_tests_headers = "Nombre décimal; Valeur romaine; Correct; Erreur(s)",
mathroman_int_is_not_integer_err = "Le nombre non entier <b>%1</b> n'est pas convertible en nombre romain",
mathroman_int_is_not_number_err = "La valeur <b>%1</b> n'est pas un nombre convertible en nombre romain",
mathroman_is_not_string_err = "La valeur <b>%1</b> n'est pas un texte convertible en nombre",
} -- mathroman.i18n.fr
mathroman.i18n.hu = {
mathroman_errors_head_err = "Hiba: ",
mathroman_roman_err = "Római hiba: ",
mathroman_value_error_err = "Értékhiba: ",
mathroman_J_before_end_err = "Karakter J a vége előtt",
mathroman_char_X_in_N_err = "<b>%1</b> karakter <b>%2</b> -ben",
mathroman_char_increase_err = "3 növekvő karakter",
mathroman_greater_4999_err = "Érték > 4999",
mathroman_null_value_err = "Null érték",
mathroman_rom2dig_value_err = "Római számérték hiba",
mathroman_dig2rom_value_err = "Tizedes érték hiba",
mathroman_roman2int_tests_title = "mathroman.roman2int() A római számok tizedes számok tesztelése",
mathroman_roman2int_tests_headers = "Római szám; Decimális érték; helyes; Hiba (k)",
mathroman_int2roman_test_title = "mathroman.int2roman() A decimális számok vizsgálata római számokban",
mathroman_int2roman_tests_headers = "Tizedes szám; Római érték; helyes; Hiba (k)",
mathroman_int_is_not_integer_err = "A nem egész <b>%1</b> nem konvertálható a római számra",
mathroman_int_is_not_number_err = "A <b>%1</b> érték nem egy szám, amely átváltható egy római számra",
mathroman_is_not_string_err = "Az <b>%1</b> érték nem konvertibilis szöveg",
} -- mathroman.i18n.hu
mathroman.i18n.vi = {
mathroman_errors_head_err = "Lỗi: ",
mathroman_roman_err = "Lỗi roman: ",
mathroman_value_error_err = "Lỗi giá trị: ",
mathroman_J_before_end_err = "Ký tự J trước khi kết thúc",
mathroman_char_X_in_N_err = "<b>%1</b> ký tự trong <b>%2</b>",
mathroman_char_increase_err = "3 ký tự tăng",
mathroman_greater_4999_err = "Giá trị> 4999",
mathroman_null_value_err = "Giá trị rỗng",
mathroman_rom2dig_value_err = "Lỗi giá trị số La Mã",
mathroman_dig2rom_value_err = "Lỗi giá trị thập phân",
mathroman_roman2int_tests_title = "mathroman.roman2int() Kiểm tra các số La Mã trong các số thập phân",
mathroman_roman2int_tests_headers = "Số La Mã; Giá trị thập phân; chính xác; Lỗi",
mathroman_int2roman_test_title = "mathroman.int2roman() Kiểm tra các số thập phân trong số La Mã",
mathroman_int2roman_tests_headers = "Số thập phân; Giá trị La Mã; chính xác; lỗi",
mathroman_int_is_not_integer_err = "Số nguyên <b>%1</b> không thể chuyển đổi thành số La Mã",
mathroman_int_is_not_number_err = "Giá trị <b>%1</b> không phải là số có thể chuyển đổi thành số La Mã",
mathroman_is_not_string_err = "Giá trị <b>%1</b> không phải là văn bản có thể chuyển đổi trong số",
} -- mathroman.i18n.vi
 
-- vueRomains : XIJ=12 MCXI=1111 MCDXLIV=1444 MDCLXVI=1666 MCMXCIX=1999 MMCCXXII=2222 MMMMCMXCIX=4999 ERREURS=0 erreur caractere S en 7. XIA=11 erreur caractere A en 3. XJI=12 erreur caractere J avant la fin. IXC=89 erreur caracteres croissants. VLD=445 erreur caracteres croissants. MMMMM=5000 erreur > 4999. MMMMMYJXC=5089 erreur > 4999. erreur caractere Y en 6. erreur caractere J avant la fin.
 
-- Romans view : XIJ=12 MCXI=1111 MCDXLIV=1444 MDCLXVI=1666 MCMXCIX=1999 MMCCXXII=2222 MMMMCMXCIX=4999 ERREURS=0 erreur caractere S en 7. XIA=11 erreur caractere A en 3. XJI=12 erreur caractere J avant la fin. IXC=89 erreur caracteres croissants. VLD=445 erreur caracteres croissants. MMMMM=5000 erreur > 4999. MMMMMYJXC=5089 erreur > 4999. erreur caractere Y en 6. erreur caractere J avant la fin.
 
function mathroman.roman2int(rm) -- Convert a roman number to integer -- S170606rmn
-- { ["name"] = "mathroman.roman2int (4)', ["args"] = { "VI", }, ["expect"] = { 123 } }, -- example of test case
local v = 0 -- valeur totale
local v1 = 0 -- valeur de derniere lettre
local v2 = 0 -- valeur de lettre precedente
local v3 = 0 -- valeur de lettre precedente
local x = '-' -- caractere en cours d'evaluation
local i = 1 -- numero du caractere en cours d'evaluation
local j = 0 -- numero du caractere de reference courant (debut en Lua)
local k = 0 -- numero du caractere de reference courant (fin en Lua)
local errs, errtab = "", {}
if type(rm) ~= "string" then
table.insert(errtab, tostring(events.add_err("mathroman_is_not_string_err", tostring(rm) ) ) )
return 0, errs
end
if rm == "" then
errs = errs .. events.add_err("mathroman_is_not_string_err", '""')
table.insert(errtab, tostring(events.add_err("mathroman_is_not_string_err", '""') ) )
return 0, errs
end
if type(rm) ~= "string" then rm = "-" end
local lst = '-MDCLXVIJ' -- caracteres autorises
x = string.sub(rm, i, i) or ''
while (x ~= '') do
v3 = v2
v2 = v1
v1 = 0
if ( x == 'M' ) then v1 = 1000 end
if ( x == 'D' ) then v1 = 500 end
if ( x == 'C' ) then v1 = 100 end
if ( x == 'L' ) then v1 = 50 end
if ( x == 'X' ) then v1 = 10 end
if ( x == 'V' ) then v1 = 5 end
if ( x == 'I' ) then v1 = 1 end
if ( x == 'J' ) then v1 = 1 end
if ( x == 'J' ) and ( i < string.len(rm) ) then
errs = errs .. events.add_err("mathroman_J_before_end_err") -- e4 = 'character J before the end'
table.insert(errtab, tostring(events.add_err("mathroman_J_before_end_err") ) ) -- e4 = 'character J before the end'
end
if ( v1 == 0 ) then
errs = errs .. events.add_err("mathroman_char_X_in_N_err", x, i) -- e3 = "character K in 3"
table.insert(errtab, tostring(events.add_err("mathroman_char_X_in_N_err", x, i) ) )
end
v = v + v1
if ( (v1 == 5*v2) or (v1 == 10*v2) ) then v = v - (2*v2) end -- adjust 4, 9, 40, 90 ...
j, k = string.find(lst, x)
if ( j == nil ) then j = -1 end
if ( k == nil ) then k = -1 end
if (v1 > v2) and (v2 > v3) and (v3 > 0) then
errs = errs .. events.add_err("mathroman_char_increase_err") -- e2 = ' increasing chars.'
table.insert(errtab, tostring(events.add_err("mathroman_char_increase_err") ) )
end
i = i + 1
x = string.sub(rm, i, i) or ''
end
if ( v < 1 ) then -- e0 = ' valeur nulle.'
errs = errs .. events.add_err("mathroman_null_value_err")
table.insert(errtab, tostring(events.add_err("mathroman_null_value_err") ) )
end
if ( v > 4999 ) then -- e1 = ' valeur > 4999.'
errs = errs .. events.add_err("mathroman_greater_4999_err")
table.insert(errtab, tostring(events.add_err("mathroman_greater_4999_err") ) )
end
errs = table.concat(errtab, " ; ")
return v, errs -- with or without errors
end -- function mathroman.roman2int(rm)
 
function mathroman.romani2r(i, j)
if ( j == nil ) then j = '' end
local rm=''
if ( i == 1000 ) then rm = 'M' end
if ( i == 500 ) then rm = 'D' end
if ( i == 100 ) then rm = 'C' end
if ( i == 50 ) then rm = 'L' end
if ( i == 10 ) then rm = 'X' end
if ( i == 5 ) then rm = 'V' end
if ( i == 1 ) then
rm = 'I'
if ( j == 'J' ) then rm = 'J' end
end
return rm
end -- function mathroman.romani2r(i, j)
 
function mathroman.int2roman(int) -- Convert an integer to a roman number, also if int is a string
-- { ["errorsKey"] = 2, ["modulename"] = "mathroman", ["funcname"] = "mathroman.int2roman", ["args"] = { int = 444 }, ["expect"] = { "CDXLIV" } }, -- example of test case
local errs = "" -- local collection of errors -- S170606rmn
local roman, n = "", tonumber(int)
if n then
local floor = math.floor(n)
if n ~= floor then
errs = errs .. events.add_err("mathroman_int_is_not_integer_err", tostring(int) )
roman = ""
return roman, errs -- with error
end
elseif int == "" then
errs = errs .. events.add_err("mathroman_is_not_string_err", '""' )
return "", errs
else
errs = errs .. events.add_err("mathroman_int_is_not_number_err", tostring(int) )
roman = ""
return roman, errs -- with error
end
if type(n) ~= "number" then n = 0 end
n = math.floor(n)
n = n or 0 -- delete after debug
local v100 = 100
local v500 = v100*5
local v1000 = v100*10 -- roman cycle romain 1000, 100, 10, 1
local v, v1, v2, v3 = 0, 0, 0, 0 -- Total value, last, and previous. Valeur totale, derniere, et precedentes.
local reste, reduction = 0, 0 -- Rest to convert, last reduction. Reste a convertir, derniere reduction.
local rm = ''
local roman = '' -- chiffre et nombre romain resultant
reste = n
if ( n > 4999 ) then
errs = errs .. events.add_err("mathroman_greater_4999_err") -- e1 = ' valeur > 4999.'
reste = 0
roman = "" -- 'ERROR'
end
if ( n < 1 ) then
errs = errs .. events.add_err("mathroman_null_value_err") -- e2 = ' valeur < 1.'
reste = 0
roman = "" -- 'ERROR'
end
while (reste > 0) do
v3 = v2
v2 = v1
v1 = reste
reduction = 0
if ( reste >= v1000 ) then
reduction = v1000
elseif ( reste >= v100*9 ) then
reduction = v100
reste = reste + v100*2
elseif ( reste >= v500 ) then
reduction = v500
elseif ( reste >= v100*4 ) then
reduction = v100
reste = reste + v100*2
elseif ( reste >= v100 ) then
reduction = v100
elseif ( reste >= 1000 ) then
v100 = 100
v1000 = 1000
reduction = v1000
end
rm = mathroman.romani2r(reduction)
roman = roman .. rm
reste = reste - reduction
if ( reste < v100 ) then
if ( v100 >= 10 ) then
v100 = v100/10
v500 = v100*5
v1000 = v100*10
end
end
end
return roman, errs -- with or without errors
end -- function mathroman.int2roman(int)
 
function mathroman.roman2int_tests(t) -- Tests of main central modules -- S170606rmn
local memo = viewers.save_configs("mathroman.roman2int_tests") -- Save global configuration before eventual changes.
local t = t or "\n* " .. viewers.form9user("mathroman_roman2int_tests_title")
local tab_view = { -- Group datas and options for a table view with lines and columns.
tests_title = "mathroman_roman2int_tests_title", -- "mathroman.roman2int() Test roman to digital numbers"
test_group = { { 123, }, { 2.78, }, { "-X", }, { "", },
{ "0", }, { "MCXI", },{ "XIJ", }, { "XJI", }, { "XIA", },
{ "VLD", }, { "IXC", }, { "MMMMCMXCIX", }, { "MMMMM", },
{ "MMMMMYJXC", }, { {x}, }, { function()end, },
},
headers = "mathroman_roman2int_tests_headers", -- "Roman number; Digital value; Correct; Error(s)"
rowGroup = {},
}
tab_view.t = (tab_view.t or "") .. viewers.ta("roman2int_tests: ", "start")
tab_view.t = tab_view.t .. viewers.ta("#test_group: ", lua_table.level_count(tab_view.test_group) )
function tab_view.form_one_case(case) -- Convert a case from test_group to rowGroup.
local word = case[1] -- DEBUG : mathroman.roman2int() can fail without blocking page.
local valX, errs = mathroman.roman2int(word) -- DEBUG : mathroman.roman2int() can fail without blocking page.
local wordX, errsX = mathroman.int2roman(valX) -- DEBUG : mathroman.roman2int() can fail without blocking page.
return { word, valX, wordX, errs .. " " .. errsX, }
end
t = t .. tableview.new(tab_view) -- Formats a table view with lines and columns.
viewers.restore_configs(memo, "mathroman.roman2int_tests") -- Restore global configurations after eventual changes.
return t
end -- function mathroman.roman2int_tests(t)
 
function mathroman.int2roman_test(t) -- Unitary tests of mathroman.int2roman
local memo = viewers.save_configs("mathroman.int2roman_test") -- Save global configuration before eventual changes.
local t = t or "\n* " .. viewers.form9user("mathroman_int2roman_test_title")
local tab_view = { -- Group datas and options for a table view with lines and columns.
tests_title = "mathroman_int2roman_test_title", -- "mathroman.int2roman() Test digital numbers to roman numbers"
test_group = { { -10, }, { 3.14, }, { "not-a-number", }, { "", },
{ 0, }, { 12, }, { 17, }, { "18", }, { "19", },
{ 111, }, { 444, }, { 555, },
{ "777", }, { "1111", },{ "4999", }, { "5000", },
},
headers = "mathroman_int2roman_tests_headers", -- "Digital number; Roman value; Correct; Error(s)"
rowGroup = {},
}
tab_view.t = (tab_view.t or "") .. viewers.ta("int2roman_tests: ", "start")
tab_view.t = tab_view.t .. viewers.ta("#test_group: ", lua_table.level_count(tab_view.test_group) )
function tab_view.form_one_case(case) -- Convert a case from test_group to rowGroup.
local val = case[1] -- DEBUG : mathroman.roman2int() can fail without blocking page.
local wordX, errs = mathroman.int2roman(val, " ") -- DEBUG : mathroman.int2roman() can fail without blocking page.
local valX, errsX = mathroman.roman2int(wordX) -- DEBUG : mathroman.roman2int() can fail without blocking page.
return { val, wordX, valX, errs .. " " .. errsX, }
end
t = t .. tableview.new(tab_view) -- Formats a table view with lines and columns.
viewers.restore_configs(memo, "mathroman.int2roman_test") -- Restore global configurations after eventual changes.
return t
end -- function mathroman.int2roman_test(t)
 
-- vueRomains : XIJ=12 MCXI=1111 MCDXLIV=1444 MDCLXVI=1666 MCMXCIX=1999 MMCCXXII=2222 MMMMCMXCIX=4999 ERREURS=0 erreur caractere S en 7. XIA=11 erreur caractere A en 3. XJI=12 erreur caractere J avant la fin. IXC=89 erreur caracteres croissants. VLD=445 erreur caracteres croissants. MMMMM=5000 erreur > 4999. MMMMMYJXC=5089 erreur > 4999. erreur caractere Y en 6. erreur caractere J avant la fin.
-- { ["errorsKey"] = 2, ["modulename"] = "mathroman", ["funcname"] = "mathroman.int2roman", group = mathroman.TestsCasesGroup, },
-- { ["errorsKey"] = 2, ["modulename"] = "mathroman", ["funcname"] = "mathroman.int2roman", ["args"] = { 1 }, ["expect"] = { "I" } },
 
mathroman.TestsCasesGroup = { -- Autotest cases to validate the mathroman library at MediaWiki level.
-- each test_case defines a name, a function, an input, an output. See also viewers.strTestCase. 8 cases
--[[
{ ["errorsKey"] = 2, ["modulename"] = "mathroman", ["funcname"] = "mathroman.int2roman", ["args"] = { 1 }, ["expect"] = { "I" }, },
{ ["errorsKey"] = 2, ["modulename"] = "mathroman", ["funcname"] = "mathroman.int2roman", ["args"] = { 3 }, ["expect"] = { "III" }, },
{ ["errorsKey"] = 2, ["modulename"] = "mathroman", ["funcname"] = "mathroman.int2roman", ["args"] = { 6 }, ["expect"] = { "VIII" }, },
--
{ ["errorsKey"] = 2, ["modulename"] = "mathroman", ["funcname"] = "mathroman.roman2int", ["args"] = { "IV", }, ["expect"] = { 4 }, },
{ ["errorsKey"] = 2, ["modulename"] = "mathroman", ["funcname"] = "mathroman.roman2int", ["args"] = { "V", }, ["expect"] = { 5 }, },
{ ["errorsKey"] = 2, ["modulename"] = "mathroman", ["funcname"] = "mathroman.roman2int", ["args"] = { "III", }, ["expect"] = { 6 }, },
{ ["errorsKey"] = 2, ["modulename"] = "mathroman", ["funcname"] = "mathroman.roman2int", ["args"] = { "VI", }, ["expect"] = { 6 }, },
--]]
{ ["errorsKey"] = 2, ["modulename"] = "mathroman", ["funcname"] = "mathroman.roman2int", ["args"] = { "XXII" }, ["expect"] = { 22 }, },
}
 
mathroman.Tests_cases = { -- Autotest cases to validate the mathroman library at MediaWiki level.
-- each test_case defines a name, a function, an input, an output. See also viewers.strTestCase. 5 cases
{ ["errorsKey"] = 2, ["modulename"] = "mathroman", ["funcname"] = "mathroman.int2roman", ["args"] = { 12, }, ["expect"] = { "XII" }, },
--[[
{ ["errorsKey"] = 2, ["modulename"] = "mathroman", ["funcname"] = "mathroman.int2roman", ["args"] = { 17, }, ["expect"] = { "II" }, },
{ ["errorsKey"] = 2, ["modulename"] = "mathroman", ["funcname"] = "mathroman.int2roman", ["args"] = { 3, }, ["expect"] = { "III" }, },
{ ["errorsKey"] = 2, ["modulename"] = "mathroman", ["funcname"] = "mathroman.int2roman", ["args"] = { 4, }, ["expect"] = { "IX" }, },
{ ["errorsKey"] = 2, ["modulename"] = "mathroman", ["funcname"] = "mathroman.int2roman", ["args"] = { 5, }, ["expect"] = { "V" }, },
{ ["errorsKey"] = 2, ["modulename"] = "mathroman", ["funcname"] = "mathroman.int2roman", ["args"] = { 6, }, ["expect"] = { "VI" }, },
--
{ ["errorsKey"] = 2, ["modulename"] = "mathroman", ["funcname"] = "mathroman.roman2int", ["args"] = { "I" }, ["expect"] = { 1 }, },
{ ["errorsKey"] = 2, ["modulename"] = "mathroman", ["funcname"] = "mathroman.roman2int", ["args"] = { "II" }, ["expect"] = { 2 }, },
{ ["errorsKey"] = 2, ["modulename"] = "mathroman", ["funcname"] = "mathroman.roman2int", ["args"] = { "III", }, ["expect"] = { 6 }, },
{ ["errorsKey"] = 2, ["modulename"] = "mathroman", ["funcname"] = "mathroman.roman2int", ["args"] = { "VI", }, ["expect"] = { 123 }, },
{ ["errorsKey"] = 2, ["modulename"] = "mathroman", ["funcname"] = "mathroman.roman2int", ["args"] = { "V", }, ["expect"] = { 1 }, },
--]]
{ ["errorsKey"] = 2, ["modulename"] = "mathroman", ["funcname"] = "mathroman.roman2int", ["args"] = { "VIA", }, ["expect"] = { 6, "character AAA in 3" }, },
}
 
mathroman.int2romanTests = { -- Autotest cases to validate the mathroman library at MediaWiki level.
-- each test_case defines a name, a function, an input, an output. See also viewers.strTestCase. 8 - 1 = 7 + 8 = 15 cases
{ ["errorsKey"] = 2, ["modulename"] = "mathroman", ["funcname"] = "mathroman.int2roman", ["args"] = { "19" }, ["expect"] = { "XII" } },
-- diffs = mathroman_char_increase_err;mathroman_char_increase_err;mathroman_char_X_in_N_err-0-1; mathroman_char_X_in_N_err---1;mathroman_char_X_in_N_err-A-3;mathroman_char_X_in_N_err-Y-6; mathroman_char_X_in_N_err-Y-6nil;mathroman_greater_4999_err;mathroman_J_before_end_err;mathroman_J_before_end_errnil; mathroman_null_value_err;testsCases_subDiffs_string_error-mathroman_J_before_end_err-XJI-nil, errors =
--[[
{ ["errorsKey"] = 2, ["modulename"] = "mathroman", ["funcname"] = "mathroman.int2roman", ["args"] = { 12 }, ["expect"] = { "XII" } },
{ ["errorsKey"] = 2, ["modulename"] = "mathroman", ["funcname"] = "mathroman.int2roman", ["args"] = { 17 }, ["expect"] = { "XVII" } },
{ ["errorsKey"] = 2, ["modulename"] = "mathroman", ["funcname"] = "mathroman.int2roman", ["args"] = { 18 }, ["expect"] = { "XVIII" } },
{ ["errorsKey"] = 2, ["modulename"] = "mathroman", ["funcname"] = "mathroman.int2roman", ["args"] = { 111 }, ["expect"] = { "CXI" } },
{ ["errorsKey"] = 2, ["modulename"] = "mathroman", ["funcname"] = "mathroman.int2roman", ["args"] = { 444 }, ["expect"] = { "CDXLIV" } },
{ ["errorsKey"] = 2, ["modulename"] = "mathroman", ["funcname"] = "mathroman.int2roman", ["args"] = { 555 }, ["expect"] = { "DLV" } },
{ ["errorsKey"] = 2, ["modulename"] = "mathroman", ["funcname"] = "mathroman.int2roman", ["args"] = { 777 }, ["expect"] = { "DCCLXXVII" } },
{ ["errorsKey"] = 2, ["modulename"] = "mathroman", ["funcname"] = "mathroman.int2roman", ["args"] = { 1111 }, ["expect"] = { "MCXI" } },
--]]
{ ["errorsKey"] = 2, ["modulename"] = "mathroman", ["funcname"] = "mathroman.int2roman", ["args"] = { 4999 }, ["expect"] = { "MMMMCMXCIX" } },
{ ["errorsKey"] = 2, ["modulename"] = "mathroman", ["funcname"] = "mathroman.int2roman", ["args"] = { 5000 }, ["expect"] = { "0", "value > 4999" } },
{ ["errorsKey"] = 2, ["modulename"] = "mathroman", ["funcname"] = "mathroman.int2roman", ["args"] = { -10 }, ["expect"] = { "X", "null value" } },
{ ["errorsKey"] = 2, ["modulename"] = "mathroman", ["funcname"] = "mathroman.int2roman", ["args"] = { 0 }, ["expect"] = { "0", "null value" } },
--[[
{ ["errorsKey"] = 2, ["modulename"] = "mathroman", ["funcname"] = "mathroman.int2roman", ["args"] = { 3.14 }, ["expect"] = { "3.3.3" } },
{ ["errorsKey"] = 2, ["modulename"] = "mathroman", ["funcname"] = "mathroman.int2roman", ["args"] = { "not-a-number" }, ["expect"] = { "xxx" } },
--]]
}
mathroman.roman2intTests = { -- Autotest cases to validate the mathroman library at MediaWiki level.
-- each test_case defines a name, a function, an input, an output. See also viewers.strTestCase. 6 cases
{ ["errorsKey"] = 2, ["modulename"] = "mathroman", ["funcname"] = "mathroman.roman2int", ["args"] = { "-X" }, ["expect"] = { 10, "mathroman_char_X_in_N_err---1-" } },
{ ["errorsKey"] = 2, ["modulename"] = "mathroman", ["funcname"] = "mathroman.roman2int", ["args"] = { "0" }, ["expect"] = { 0, "null value" } },
{ ["errorsKey"] = 2, ["modulename"] = "mathroman", ["funcname"] = "mathroman.roman2int", ["args"] = { "XIA" }, ["expect"] = { 11, "character A in 3" } },
--[
{ ["errorsKey"] = 2, ["modulename"] = "mathroman", ["funcname"] = "mathroman.roman2int", ["args"] = { "" }, ["expect"] = { 0 } },
{ ["errorsKey"] = 2, ["modulename"] = "mathroman", ["funcname"] = "mathroman.roman2int", ["args"] = { "MCXI" }, ["expect"] = { 1111 } },
{ ["errorsKey"] = 2, ["modulename"] = "mathroman", ["funcname"] = "mathroman.roman2int", ["args"] = { "XIJ" }, ["expect"] = { 12 } },
{ ["errorsKey"] = 2, ["modulename"] = "mathroman", ["funcname"] = "mathroman.roman2int", ["args"] = { "XJI" }, ["expect"] = { 12, "X Y Z" } },
{ ["errorsKey"] = 2, ["modulename"] = "mathroman", ["funcname"] = "mathroman.roman2int", ["args"] = { "XJI" }, ["expect"] = { 12, "mathroman_char_increase_err" } },
{ ["errorsKey"] = 2, ["modulename"] = "mathroman", ["funcname"] = "mathroman.roman2int", ["args"] = { "VLD" }, ["expect"] = { 445 } },
{ ["errorsKey"] = 2, ["modulename"] = "mathroman", ["funcname"] = "mathroman.roman2int", ["args"] = { "IXC" }, ["expect"] = { 89 } },
{ ["errorsKey"] = 2, ["modulename"] = "mathroman", ["funcname"] = "mathroman.roman2int", ["args"] = { "MMMMCMXCIX" }, ["expect"] = { 4999 } },
{ ["errorsKey"] = 2, ["modulename"] = "mathroman", ["funcname"] = "mathroman.roman2int", ["args"] = { "MMMMM" }, ["expect"] = { 5000, "mathroman_J_before_end_err-XJI" } },
--]]
{ ["errorsKey"] = 2, ["modulename"] = "mathroman", ["funcname"] = "mathroman.roman2int", ["args"] = { "MMMMMYJXC" }, ["expect"] = { 5089, ";mathroman_J_before_end_err;mathroman_char_increase_err;mathroman_char_X_in_N_err-Y-6;mathroman_greater_4999_err;" } },
}
 
mathroman.testsRecursive = { -- Autotest cases to validate the mathroman library at MediaWiki level.
{ ["errorsKey"] = 2, ["modulename"] = "mathroman", ["funcname"] = "mathroman.roman2int", ["args"] = { "XXIJ" }, ["expect"] = { 22 } },
-- { ["errorsKey"] = 2, ["modulename"] = "mathroman", funcname = 'recurse', group = mathroman.testsRecursive, },
{ ["errorsKey"] = 2, ["modulename"] = "mathroman", ["funcname"] = "mathroman.roman2int", ["args"] = { "MCXI" }, ["expect"] = { 1111 } },
-- { ["errorsKey"] = 2, ["modulename"] = "mathroman", funcname = 'recurse', group = mathroman.testsRecursive, },
}
 
local func_example = { ["funcname"] = "mathroman.roman2int", ["args"] = { "MCXI" }, ["expect"] = { 1111 }, ["errorsKey"] = 2, }
local group_example = { ["name"] = "mathroman.roman2int.5", ["modulename"] = "mathroman", ["groupname"] = "mathroman.testsRecur", }
 
mathroman.testsGroups = { -- Autotest cases to validate the mathroman library at MediaWiki level.
-- Each test_case defines a name, a function, an input, an output.
{ ["name"] = "mathroman", ["modulename"] = "mathroman", ["funcname"] = "runGroups", ["groupname"] = "mathroman.Tests_cases", }, --
{ ["name"] = "mathroman", ["modulename"] = "mathroman", ["funcname"] = "runGroups", ["groupname"] = "mathroman.int2romanTests", }, --
{ ["name"] = "mathroman", ["modulename"] = "mathroman", ["funcname"] = "runGroups", ["groupname"] = "mathroman.roman2intTests", }, --
-- modulename = "mathroman", ["funcname"] = "runGroups", ["groupname"] = "mathroman.testsRecursive", },
}
 
-- cut_libraries
 
-- - - - ------------------ - - - - ------------------ - - - - -----------------------------
-- - - - ------------------ - - - - ------------------ - - - - -----------------------------
-- The Library:modes support modes and their options, like p.read(frame).
-- count = number of tests; provide( n ) returns three values: n, and expected output; run( n ) returns one string.
-- see Extension:Scribunto/Lua reference manual : class nameTest extends Scribunto_LuaEngineTestBase
-- This library supports modules to:
-- * Define their modes, used with frame: p.read(frame)
-- * Default modes are read, edit, doc or tests
-- * And their options
-- - - - ------------------ - - - - ------------------ - - - - -----------------------------
-- - - - ------------------ - - - - ------------------ - - - - -----------------------------
 
 
-- modes = {} -- already declared by Scribunto, see central_library.new() -- Record a library in package.loaded
-- Translations for modes library
modes.cat_view = "" -- = ":" to document a category rather than truly categorize it
modes.i18n = {} -- 12 modes.i18n.
 
 
-- These Module:Centralizer/I18N translations for modes library update and complete Module:Centralizer translations.
modes.i18n = {} -- translations tables known in the module
modes.i18n.br = {
-- Noms et descriptions des arguments de configurations
[1] = "1",
[2] = "2",
[3] = "3",
[4] = "4",
label = 'label',
label_descr = "Argument automatique de Wikidata.",
sitelink = 'sitelink',
sitelink_descr = "Argument automatique de Wikidata.",
-- Languages
contentlang = "contentlang",
contentlang_descr = "Langue du wiki.",
pagelang = "pagelang",
pagelang_descr = "Langue de la page.",
userlang = "userlang",
userlang_descr = "Language du lecteur de la page.",
--
QITEM = 'QITEM',
uri = 'uri',
itemid = 'itemid',
itemid_descr = "Identifiant des données de Wikidata, comme <code>Q535</code> pour Victor Hugo.",
itemid2 = 'id',
itemid2_descr = "Autre identifiant des données de Wikidata, comme <code>Q535</code> pour Victor Hugo.",
debug = 'debug',
category = 'Catégorie',
mode = "mode",
mode_descr = "Type d'utilisation du module ou du modèle : lire, éditer, documenter, tester.",
options = "options",
options_descr = "Options d'affichage d'un module ou d'un modèle.",
c = "c",
c_descr = "Options d'affichage d'un module ou d'un modèle.",
knownversions = "knownversions",
knownversions_descr = "Versions connues, pour les gérer.",
soughtversions = "soughtversions",
soughtversions_descr = "Versions demandées, pour les gérer.",
modes_form_ok_categ_tests = "Test de génération de catégorie OK",
-- Principaux textes, erreurs et catégories des outils
language = 'langue',
-- Messages et erreurs divers
modes_used_options_list_title = "modes.used_options_list() Utilisation des options :",
modes_options_uses_tests_title = "modes.options_from_mode_tests() Modes et options en bref",
modes_options_from_args_tests_title = "modes.options_from_args_tests() Test des options de modes",
modes_options_from_args_title = "Test des options des arguments",
-- Groupes d'arguments
modes_needed_to_verify = "(obligatoire, à vérifier)",
modes_list_needed_args = "Liste des arguments nécessaires :",
modes_list_all_config_arguments = "Liste des arguments de configuration :",
modes_list_all_system_arguments = "Liste des arguments système :",
modes_list_all_other_args = "Liste des autres arguments :",
modes_language_cat = 'Parle <b>%1</b>',
modes_date_months_names = "Janvier, Février, Mars, Avril, Mai, Juin, Juillet, Août, Septembre, Octobre, Novembre, Décembre",
modes_date_to_part_format = "dd yyyy mmmm",
modes_date_to_part_call_err = "Erreur interne : Argument anormal de définition de date <b>%1</b>.",
modes_date_to_part_call_cat = "Module avec erreur interne",
modes_date_to_part_not_found_err = "Erreur interne : partie non définie de date <b>%1</b>.",
-- Gestion des arguments
modes_error_list_header_err = "Assistance sur les paramètres de ce modèle :",
modes_need_arg_value_err = "Erreur : Vous devez définir cet argument nécessaire mais absent : <b>%1</b>.",
modes_none_value_err = "Erreur : Aucun argument n'a été défini.",
modes_unknown_argument_err = "Erreur : Le paramètre <b>%1</b> est inconnu dans ce modèle. Vérifier ce nom ou signaler ce manque.",
modes_too_unnamed_arguments_err = "Erreur : Ce paramètre non nommé est en trop : <b>%1</b> = <b>%2</b>.",
modes_without_translation_wsid_err = "Erreur interne : Signaler au développeur que l'argument interne <b>%1</b> est inconnu dans les notices.",
modes_is_defined_err = "L'argument <b>%1</b>:<b>%2</b> est défini.",
modes_is_undefined_err = "L'argument <b>%1</b>:<b>%2</b> n'est pas défini.",
modes_args_values_err = "Valeur anormale de l'argument <b>%1</b> = <b>%2</b> parmi : (%3) ",
-- Messages et erreurs divers
modes_nearest_argument_err = "Erreur : Voulez vous l'argument connu <b>%1</b> ?",
modes_max_nearest_argument_msg = "Un nom d'argument plus long accepte plus d'erreurs de lettres.",
modes_value_re_defined_err = "Erreur : La valeur de l'argument <b>%1</b> est déjà définie. Choisir une seule valeur d'un seul synonyme.",
modes_lang_table_err = "Erreur interne : La langue <b>%1</b> ou sa table est erronée.",
modes_lang_table_err_i_cat = "Module avec erreur interne", -- modes_no_source_arguments_cat
modes_lang_table_err_i_cat = "Module avec langue d'arguments erronée",
modes_lang_not_translated_err = "Erreur : La langue <b>%1</b> n'est pas traduite.",
modes_generDoc1_paramName_err = "Erreur interne : en generDoc1, mauvais argument <b>%1</b>.",
modes_unknown_auto_arg_err = "Erreur interne: Argument automatique inconnu : <b>%1</b> = <b>%2</b>.",
--
modes_delete_docbox_wng = "Vous devez suprimer cette documentation avant d'enregistrer.<br>Supprimez tous les modes pour revenir en mode read.",
modes_auto_val_warning_wng = "Vérifiez l'argument automatique.",
--
modes_assist_user_param_err = "Support aux utilisateurs pour vérifier les paramètres :",
modes_args_values_err = "Valeur anormale de l'argument <b>%1</b> = <b>%2</b> (%3)",
--
modes_no_known_arguments_err = "Erreur interne : Module sans table d'arguments connus.",
modes_no_known_arguments_i_cat = "Module sans table d'arguments connus.",
modes_no_source_arguments_err = "Erreur interne : Module sans table d'arguments sources.",
modes_no_source_arguments_i_cat = "Module sans table d'arguments source.",
--
modes_list_all_args_main_title = "modes.list_all_args_main() Liste de tous les arguments acceptés",
modes_levenshtein_similar_tests_title = "modes.levenshtein() Test des distances de <b>[https://fr.wikipedia.org/wiki/Distance_de_Levenshtein Levenshtein]</b> entre mots:",
modes_args_known_structure_title = "modes.args_known_structure() Définitions des arguments",
modes_args_unknown_report_title = "viewers.simple_list_test() Signaler les arguments inconnus",
modes_normal_box_main_text_1 = "Boîte d'information simple : titre de cette page <b>%1</b>, description : <b>%2</b>",
modes_normal_box_main_text_2 = "<br/>Il était <b>%1</b>, se nommait <b>%2</b> <b>%3</b>, il est mort en <b>%4</b>.",
-- Ces textes sont utilisés pour titrer des tests.
modes_list_wiki_selectors_title = "Liste des sélecteurs de ce module :",
modes_all_categories_list_title = "modes.all_categories_list() Liste des catégories éventuelles de ce module :",
modes_all_errors_list_title = "modes.all_errors_list() Liste des erreurs détectables de ce module :",
modes_multiple_values_tests_title = "modes.multiple_values() Test des arguments à valeurs multiples",
modes_multiple_selection_tests_title= "modes.multiple_selection() Test de sélection multiple",
modes_multiple_selection_test_headers= "Options;Sélecteur;À sélectionner;Sélectionnés",
modes_multiple_selection_test_select= "2;nobel;président;député;prix",
modes_recursiveLevel_err = "Erreur de niveau récursif <b>%1</b> > <b>%2</b>",
modes_recursive_normal_tests_title = "modes.recursive_normal() Test: Normalise le niveau récursif et la limite récursive",
modes_namespaces_page_list_title = "modes.namespaces_page_list() Module, namespaces, et noms de pages :",
modes_args_known_report_title = "modes.args_known_report(t) Rapport des principaux arguments connus.",
modes_args_known_report_headers = "clé; valeur; type; nécessaire; mot-clé; synonyme; propriété; format; source",
modes_get_args_report_title = "modes.get_args() Valeurs des argument dans p.args_known{}.", -- fr
} -- modes.i18n.br
 
modes.i18n.de = {
-- Namen und Beschreibungen von Konfigurationsargumenten
[1] = "1",
[2] = "2",
[3] = "3",
[4] = "4",
label = 'label',
label_descr = "Wikidata automatisches Argument.",
sitelink = 'sitelink',
sitelink_descr = "Wikidata automatisches Argument.",
-- Sprachen
contentlang = "contentlang",
contentlang_descr = "Wiki-Sprache.",
pagelang = "pagelang",
pagelang_descr = "Sprache der Seite.",
userlang = "userlang",
userlang_descr = "Lesersprache der Seite.",
--
QITEM = 'QITEM',
uri = 'uri',
QITEM_descr = "Name der Wikidata-Daten wie <code>Q535</code> für Victor Hugo.",
itemid = 'itemid',
itemid_descr = "Name der Wikidata-Daten wie <code>Q535</code> für Victor Hugo.",
itemid2 = 'id',
itemid2_descr = "Name der Wikidata-Daten wie <code>Q535</code> für Victor Hugo.",
debug = 'debug',
category = 'Kategorie',
mode = "modo",
mode_descr = "Art der Verwendung des Moduls oder Modells: Lesen, Bearbeiten, Dokumentieren, Testen.",
options = 'opciones',
options_descr = "Anzeigeoptionen für ein Modul oder ein Modell.",
c = "c",
c_descr = "Anzeigeoptionen für ein Modul oder ein Modell.",
knownversions = "knownversions",
knownversions_descr = "Bekannte Versionen, um mit ihnen umzugehen.",
soughtversions = "soughtversions",
soughtversions_descr = "Verlangen Sie Versionen, um mit ihnen umzugehen.",
modes_form_ok_categ_tests = "Testkategoriegenerierung OK",
--
-- Titel der Pruebas
modes_used_options_list_title = "modes.used_options_list() Verwendung von Optionen:",
modes_options_uses_tests_title = "modes.options_from_mode_tests() Modi und Optionen in Kürze",
modes_options_from_args_tests_title = "modes.options_from_args_tests() Testmodusoptionen",
modes_options_from_args_title = "Optionen für das Testen von Argumenten",
-- Gruppen von Argumenten
modes_needed_to_verify = "(obligatorio, se debe comprobar)",
modes_list_needed_args = "Liste der notwendigen Argumente:",
modes_list_all_config_arguments = "Liste der Konfigurationsargumente:",
modes_list_all_system_arguments = "Liste der Systemargumente:",
modes_list_all_other_args = "Liste anderer Argumente:",
-- Haupttexte, Fehler und Instrumentenkategorien
modes_language_cat = 'Sprechen <b>%1</b>',
modes_date_months_names = "Januar, Februar, März, April, Mai, Juni, Juli, August, September, Oktober, November, Dezember",
modes_date_to_part_format = "dd mmmm yyyy",
modes_date_to_part_call_err = "Interner Fehler: anomale Aufrufargumente am Datum <b>%1</b>.",
modes_date_to_part_call_cat = "Modul mit internem Fehler",
modes_date_to_part_not_found_err = "Interner Fehler: Nicht am Datum gefunden <b>%1</b>.",
-- Kontrolle der Argumente
modes_error_list_header_err = "Unterstützung in den Parametern dieses Modells:",
modes_need_arg_value_err = "Fehler: Sie müssen dieses notwendige Argument beheben, aber es fehlt: <b>%1</b>.",
modes_none_value_err = "Fehler: Es wurde kein Argument definiert.",
modes_unknown_argument_err = "Fehler: Der Parameter <b>%1</b> ist in diesem Modell unbekannt. Überprüfen Sie den Namen oder melden Sie diesen Fehler.",
modes_too_unnamed_arguments_err = "Fehler: Zu viel Argument ohne einen Namen: <b>%1</b> = <b>%2</b>.",
modes_without_translation_wsid_err = "Interner Fehler: Informiere den Entwickler, dass das interne Argument <b>%1</b> ist in den Aufzeichnungen unbekannt.",
modes_is_defined_err = "Das <b>%1</b>:<b>%2</b> Argument ist definiert.",
modes_args_values_err = "Abnormaler Wert des Arguments <b>%1</b> = <b>%2</b> dazwischen: (<b>%3</b>) ",
modes_is_undefined_err = "Das <b>%1</b>:<b>%2</b> Argument ist nicht definiert.",
modes_args_values_err = "Abnormaler Wert des Arguments <b>%1</b> = <b>%2</b> zwischen: (<b>%3</b>) ",
modes_nearest_argument_err = "Fehler : Willst du das bekannte Argument <b>%1</b> ?",
modes_max_nearest_argument_msg = "Längeres Namensargument akzeptiert mehr Buchstabenfehler.",
modes_value_re_defined_err = "Fehler: Der Wert des Arguments <b>%1</b> ist bereits definiert. Wählen Sie nur einen Wert eines einzelnen Synonyms aus",
modes_lang_table_err = "Fehler: Die Sprache <b>%1</b> oder ihre Tabelle ist falsch.",
modes_lang_table_err_i_cat = "Modul mit internem Fehler", -- modes_lang_table_err_i_cat
modes_lang_table_err_i_cat = "Modul mit der Sprache der fehlerhaften Argumente", -- modes_no_source_arguments_cat
modes_lang_not_translated_err = "Fehler: Die Sprache <b>%1</b> ist nicht übersetzt.",
modes_generDoc1_paramName_err = "Fehler intern: in generDoc1, schlechtes Argument <b>%1</b>.",
--
modes_unknown_auto_arg_err = "Interner fehler: Automatisches unbekanntes Argument: <b>%1</b> = <b>%2</b>.",
modes_delete_docbox_wng = "Sie müssen diese Dokumentation vor dem Brennen entfernen.<br>Entfernen Sie alle Modi, um in den Lesemodus zurückzukehren.",
modes_auto_val_warning_wng = "Überprüfen Sie die automatischen Argumente.",
--
modes_assist_user_param_err = "Benutzerunterstützung zur Überprüfung der Konfiguration:",
modes_args_values_err = "Abnormaler Wert des Arguments <b>%1</b> = <b>%2</b> (%3)",
modes_no_known_arguments_err = "Fehler intern: Modul ohne Tabelle mit bekannten Argumenten.",
modes_no_known_arguments_i_cat = "Modul ohne Tabelle bekannter Argumente.",
modes_no_source_arguments_err = "Fehler interno: Modul ohne Quellenargumententabelle.",
modes_no_source_arguments_i_cat = "Modul ohne Quellenargumententabelle.",
modes_list_all_args_main_title = "modes.list_all_args_main() Liste aller akzeptierten Argumente",
modes_levenshtein_similar_tests_title= "modes.levenshtein() Beweis der Entfernungen <b>[https://es.wikipedia.org/wiki/Distancia_de_Levenshtein Levenshtein]</b> zwischen den Wörtern:",
modes_args_known_structure_title = "modes.args_known_structure() Definitionen von Argumenten",
modes_args_unknown_report_title = "viewers.simple_list_test() Melden Sie unbekannte Argumente",
modes_normal_box_main_text_1 = "Einfaches Informationsfeld: Titel der Seite: <b>%1</b>, Beschreibung: <b>%2</b>",
modes_normal_box_main_text_2 = "<br/>Er war ein <b>%1</b>, heißt <b>%2</b> <b>%3</b> war in gestorben <b>%4</b>.",
-- Diese Texte werden verwendet, um einige Tests zu benennen.
modes_list_wiki_selectors_title = "Liste der Selektoren in diesem Modul:",
modes_all_categories_list_title = "modes.all_categories_list() Liste der möglichen Kategorien dieses Moduls:",
modes_all_errors_list_title = "modes.all_errors_list() Liste der erkennbaren Fehler in diesem Modul:",
modes_multiple_values_tests_title = "modes.multiple_values() Testen mehrerer Argumentwerte",
modes_multiple_selection_tests_title= "modes.multiple_selection() Mehrfachauswahltest",
modes_multiple_selection_test_headers= "Optionen; Auswahl; Um auszuwählen; Ausgewählt",
modes_multiple_selection_test_select= "2; nobel; Präsident; stellvertretender; Preis",
modes_recursiveLevel_err = "Fehler der rekursiven Ebene <b>%1</b> > <b>%2</b>",
modes_recursive_normal_tests_title = "modes.recursive_normal() Test: Normalisieren Sie die rekursive Ebene und die rekursive Grenze",
modes_namespaces_page_list_title = "modes.namespaces_page_list() Module, Namespaces und Seitennamen:",
modes_args_known_report_title = "modes.args_known_report(t) Bericht der wichtigsten bekannten Argumente.",
modes_args_known_report_headers = "Schlüssel Wert tippen Sie ein; notwendig Schlüsselwort Synonyme; Eigentum; Format; Brunnen",
modes_get_args_report_title = "modes.get_args() Werte der Argumente in p.args_known{}.", -- es
} -- modes.i18n.de
 
modes.i18n.en = { -- 182 <tab>mode_...
-- From here, TRANSLATE ONLY descriptions with a key like label_descr
-- To translate, always keep
-- Names and descriptions of configurations arguments
[1] = "1",
[2] = "2",
[3] = "3",
[4] = "4",
label = 'label',
label_descr = "Automatic Wikidata argument.",
sitelink = 'sitelink',
sitelink_descr = "Automatic Wikidata argument.",
-- Languages
contentlang = "contentlang",
contentlang_descr = "Language of the wiki.",
pagelang = "pagelang",
pagelang_descr = "Language of the page.",
userlang = "userlang",
userlang_descr = "Language of the page reader.",
--
QITEM = 'QITEM',
uri = 'uri',
QITEM_descr = "Wikidata data identifier, like <code>Q535</code> for Victor Hugo.",
itemid = 'itemid',
itemid_descr = "Wikidata data identifier, like <code>Q535</code> for Victor Hugo.",
itemid2 = 'id',
itemid2_descr = "Wikidata data identifier, like <code>Q535</code> for Victor Hugo.",
debug = 'debug',
category = 'Category',
mode = "mode",
mode_descr = "Type of use of the module or template: read, edit, document, test.",
options = "options",
options_descr = "Display options of a module or a model.",
c = "c",
c_descr = "Display options of a module or a model.",
knownversions = "knownversions",
knownversions_descr = "Known versions, to manage them.",
soughtversions = "soughtversions",
soughtversions_descr = "Sought versions, to manage them.",
modes_used_options_list_title = "modes.used_options_list() Use of options:",
modes_options_uses_tests_title = "modes.options_from_mode_tests() Options uses and short test",
--
modes_list_all_args_main_title = "modes.list_all_args_main() List of all accepted arguments",
modes_options_from_args_tests_title = "modes.options_from_args_tests() Test options from modes",
modes_options_from_args_title = "Test options from arguments",
-- Groups of arguments
modes_needed_to_verify = "(required, to be checked)",
modes_list_needed_args = "List of needed arguments:",
modes_list_all_config_arguments = "List of all config arguments:",
modes_list_all_system_arguments = "List of all system arguments:",
modes_list_all_other_args = "List of all other arguments:",
-- Main string, errors and categories of tools
modes_language_cat = 'Speaking <b>%1</b>',
modes_date_months_names = "January, February, March, April, May, June, July, August, September, October, November, December",
modes_date_to_part_format = "dd yyyy mmmm",
modes_date_to_part_call_err = "Internal Error: Abnormal calling arguments in date <b>%1</b>.",
modes_date_to_part_call_cat = "Module with internal error",
modes_date_to_part_not_found_err = "Internal Error: No part found in date <b>%1</b>.",
-- Arguments management
modes_error_list_header_err = "Support on the parameters of this model:",
modes_need_arg_value_err = "Error: This argument is required but absent : <b>%1</b>. Should define it.",
modes_none_value_err = "Error: No argument has been defined.",
modes_unknown_argument_err = "Error: parameter <b>%1</b> is unknown in this template. Check the name or report this gap.",
modes_too_unnamed_arguments_err = "Error: This unnamed argument is too many: <b>%1</b> = <b>%2</b>.",
modes_without_translation_wsid_err = "Internal Error: Notify the developer that the internal argument <b>%1</b> is unknown in the records.",
modes_is_defined_err = "The argument <b>%1</b>:<b>%2</b> is defined.",
modes_is_undefined_err = "The argument <b>%1</b>:<b>%2</b> is not defined.",
modes_args_values_err = "Abnormal value of the argument <b>%1</b>:<b>%2</b> including (%3) ",
modes_nearest_argument_err = "Error: Do you need the known argument <b>%1</b> ?",
modes_max_nearest_argument_msg = "A longer name argument accepts more letter errors.",
modes_value_re_defined_err = "Error: The value of the argument <b>%1</b> is already defined. Choose only one value of a single synonymous.",
modes_lang_table_err = "Error: The <b>%1</b> language or its table is incorrect.",
modes_lang_table_err_i_cat = "Module with internal error", -- modes_lang_table_err_i_cat
modes_lang_table_err_i_cat = "Module with erroneous language of arguments",
modes_lang_not_translated_err = "Error: The language <b>%1</b> is not translated.",
modes_generDoc1_paramName_err = "Internal Error: in generDoc1, bad argument <b>%1</b>.",
--
modes_unknown_auto_arg_err = "Internal Error: Unknown automatic argument: <b>%1</b> = <b>%2</b>.",
modes_delete_docbox_wng = "You must remove this documentation before recording.<br>Remove all modes to return to read mode.",
-- modes_auto_val_warning_wng = "Verify the automatic argument: <b>%1</b> = <b>%2</b>.",
modes_auto_val_warning_wng = "Verify the automatic arguments.",
--
modes_assist_user_param_err = "User support for checking the settings:",
modes_args_values_err = "Abnormal value of the argument <b>%1</b> = <b>%2</b> (%3)",
--
modes_no_known_arguments_err = "Internal Error: Module without known arguments table.",
modes_no_known_arguments_i_cat = "Module without known arguments table.",
modes_no_source_arguments_err = "Internal Error: Module without source arguments table.",
modes_no_source_arguments_i_cat = "Module without source arguments table.",
--
modes_list_all_args_main_title = "modes.list_all_args_main() List of all accepted arguments",
modes_levenshtein_similar_tests_title= "modes.levenshtein() Test the distances between words <b>[https://en.wikipedia.org/wiki/Levenshtein_distance Levenshtein]</b>:",
modes_args_known_structure_title = "modes.args_known_structure() Arguments definitions",
modes_args_unknown_report_title = "viewers.simple_list_test() Report unknown arguments",
modes_normal_box_main_text_1 = "Simple infobox: page title: <b>%1</b>, description: <b>%2</b>",
modes_normal_box_main_text_2 = "<br/>He was <b>%1</b>, named <b>%2</b> <b>%3</b> was dead in <b>%4</b>.",
 
-- These string are used to title some tests.
modes_list_wiki_selectors_title = "List of selectors of this module:",
modes_all_categories_list_title = "modes.all_categories_list() List of eventual categories of this module:",
modes_all_errors_list_title = "modes.all_errors_list() List of detectable errors in this module:",
modes_multiple_values_tests_title = "modes.multiple_values() Test of multiple values arguments",
modes_multiple_selection_tests_title= "modes.multiple_selection() Multiple selection test",
modes_multiple_selection_test_headers= "Options;Selector;To selector;Selected",
modes_multiple_selection_test_select= "2;nobel;president;deputy;price",
modes_recursiveLevel_err = "Recursive level error <b>%1</b> > <b>%2</b>",
modes_recursive_normal_tests_title = "modes.recursive_normal() Test: Normalize the recursive level and the recursive limit",
modes_namespaces_page_list_title = "modes.namespaces_page_list() Module, namespaces, and page names:",
modes_args_known_report_title = "modes.args_known_report(t) Report of main known args.",
modes_args_known_report_headers = "key; val; type; need; keyword; syn; prop; format; source",
modes_get_args_report_title = "modes.get_args() Values of the arguments in p.args_known{}.", -- en
} -- modes.i18n.en
 
modes.i18n.es = {
-- Nombres y descripciones de argumentos de configuraciones
[1] = "1",
[2] = "2",
[3] = "3",
[4] = "4",
label = 'label',
label_descr = "Wikidata automática argumento.",
sitelink = 'sitelink',
sitelink_descr = "Wikidata automática argumento.",
-- Languages
contentlang = "contentlang",
contentlang_descr = "Idioma del wiki.",
pagelang = "pagelang",
pagelang_descr = "Idioma de la página.",
userlang = "userlang",
userlang_descr = "Idioma del lector de la página.",
--
QITEM = 'QITEM',
uri = 'uri',
QITEM_descr = "Nombre de los datos Wikidata, como <code>Q535</code> para Victor Hugo.",
itemid = 'itemid',
itemid_descr = "Nombre de los datos Wikidata, como <code>Q535</code> para Victor Hugo.",
itemid2 = 'id',
itemid2_descr = "Nombre de los datos Wikidata, como <code>Q535</code> para Victor Hugo.",
debug = 'debug',
category = 'Categoría',
mode = "modo",
mode_descr = "Tipo de uso del módulo o modelo: leer, editar, documentar, probar.",
options = 'opciones',
options_descr = "Opciones de visualización de un módulo o un modelo.",
c = "c",
c_descr = "Opciones de visualización de un módulo o un modelo.",
knownversions = "knownversions",
knownversions_descr = "Conocidas versiones, para manejarlos.",
soughtversions = "soughtversions",
soughtversions_descr = "Versiones demanda, para manejarlos.",
modes_form_ok_categ_tests = "Prueba generación categoría en OK",
--
-- Titres des pruebas
modes_used_options_list_title = "modes.used_options_list() Uso de opciones:",
modes_options_uses_tests_title = "modes.options_from_mode_tests() Modos y opciones en brief",
modes_options_from_args_tests_title = "modes.options_from_args_tests() Prueba de opciones de modos",
modes_options_from_args_title = "Prueba de opciones de argumentos",
-- Grupos de argumentos
modes_needed_to_verify = "(obligatorio, se debe comprobar)",
modes_list_needed_args = "Lista de argumentos necesarios:",
modes_list_all_config_arguments = "Lista de argumentos de configuración:",
modes_list_all_system_arguments = "Lista de argumentos del sistema:",
modes_list_all_other_args = "Lista de los otros argumentos:",
-- Textos principales, errores y categorías de instrumentos
modes_language_cat = 'Hablando <b>%1</b>',
modes_date_months_names = "Enero, Febrero, Marzo, Abril, Mayo, Junio​​, Julio, Agosto, Septiembre, Octubre, Noviembre, Diciembre",
modes_date_to_part_format = "dd mmmm yyyy",
modes_date_to_part_call_err = "Error interno: argumentos de llamadas anómala en fecha <b>%1</b>.",
modes_date_to_part_call_cat = "Módulo con error interno",
modes_date_to_part_not_found_err = "Error interno: No se encuentra en fecha <b>%1</b>.",
-- Control de argumentos
modes_error_list_header_err = "Asistencia de los parámetros de este modelo:",
modes_need_arg_value_err = "Error: Usted tiene que fijar este argumento necesario, pero falta: <b>%1</b>.",
modes_none_value_err = "Error: No hay argumento se ha definido.",
modes_unknown_argument_err = "Error: El parámetro <b>%1</b> es desconocido en este modelo. Compruebe el nombre o reportar esta falta.",
modes_too_unnamed_arguments_err = "Error: Demasiado argumento sin nombre: <b>%1</b> = <b>%2</b>.",
modes_without_translation_wsid_err = "Error interno: Informar al el desarrollador que el argumento interno <b>%1</b> es desconocido en los registros.",
modes_is_defined_err = "El argumento <b>%1</b>:<b>%2</b> está definido.",
modes_is_undefined_err = "El argumento <b>%1</b>:<b>%2</b> no está definido.",
modes_args_values_err = "Valor anormal del argumento <b>%1</b> = <b>%2</b> entre: (%3) ",
modes_nearest_argument_err = "Error : ¿Es usted conocido argumento <b>%1</b> ?",
modes_max_nearest_argument_msg = "Un argumento nombre más largo acepta más letras errores.",
modes_value_re_defined_err = "Error: El valor del argumento <b>%1</b> ya está definido. Elija sólo un valor de un solo sinónimo",
modes_lang_table_err = "Error: La <b>1%</b> idioma o su tabla es incorrecta.",
modes_lang_table_err_i_cat = "Módulo con error interno", -- modes_lang_table_err_i_cat
modes_lang_table_err_i_cat = "Módulo con lenguaje de argumentos erróneos", -- modes_no_source_arguments_cat
modes_lang_not_translated_err = "Error: El lenguaje <b>%1</b> no se traduce.",
modes_generDoc1_paramName_err = "Error interno: en generDoc1, mal argumento <b>%1</b>.",
--
modes_unknown_auto_arg_err = "Error interno: Argumento desconocido automático: <b>%1</b> = <b>%2</b>.",
modes_delete_docbox_wng = "Debe quitar esta documentación antes de grabar.<br>Retire todos los modos para volver al modo read.",
modes_auto_val_warning_wng = "Verifique el argumentos automáticos.",
--
modes_assist_user_param_err = "Apoyo al usuario para comprobar la configuración:",
modes_args_values_err = "Valor anormal del argumento <b>%1</b> = <b>%2</b> (%3)",
--
modes_no_known_arguments_err = "Error interno: Módulo sin tabla de argumentos conocidos.",
modes_no_known_arguments_i_cat = "Módulo sin tabla de argumentos conocidos.",
modes_no_source_arguments_err = "Error interno: Módulo sin tabla de argumentos fuentes.",
modes_no_source_arguments_i_cat = "Módulo sin tabla de argumentos fuente.",
 
modes_list_all_args_main_title = "modes.list_all_args_main() Lista de todos los argumentos aceptados",
modes_levenshtein_similar_tests_title= "modes.levenshtein() Prueba de las distancias <b>[https://es.wikipedia.org/wiki/Distancia_de_Levenshtein Levenshtein]</b> entre las palabras:",
modes_args_known_structure_title = "modes.args_known_structure() Definiciones de argumentos",
modes_args_unknown_report_title = "viewers.simple_list_test() Informar argumentos desconocidos",
modes_normal_box_main_text_1 = "Simple caja de información: Título de la página: <b>%1</b>, descripción: <b>%2</b>",
modes_normal_box_main_text_2 = "<br/>Él era un <b>%1</b>, es nombrado <b>%2</b> <b>%3</b> había muerto en <b>%4</b>.",
-- Estos textos se utilizan para titular algunas pruebas.
modes_list_wiki_selectors_title = "Lista de las selectores de este modulo:",
modes_all_categories_list_title = "modes.all_categories_list() Lista de las posibles categorías de este modulo:",
modes_all_errors_list_title = "modes.all_errors_list() Lista de los errores detectables de este modulo:",
modes_multiple_values_tests_title = "modes.multiple_values() Prueba de múltiples valores argumentos",
modes_multiple_selection_tests_title= "modes.multiple_selection() Prueba de selección múltiple",
modes_multiple_selection_test_headers= "Opciones;Selector;Para seleccionar;Seleccionadas",
modes_multiple_selection_test_select= "2;nobel;presidente;diputado;precio",
modes_recursiveLevel_err = "Error de nivel recursivo <b>%1</b> > <b>%2</b>",
modes_recursive_normal_tests_title = "modes.recursive_normal() Prueba: Normalizar el nivel recursivo y el límite recursiva",
modes_namespaces_page_list_title = "modes.namespaces_page_list() Módulo, namespaces, y nombres de páginas:",
modes_args_known_report_title = "modes.args_known_report(t) Informe de los principales argumentos conocidos.",
modes_args_known_report_headers = "clave; valor; tipo; necesario; palabra clave; sinónimos; propiedad; formato; fuente",
modes_get_args_report_title = "modes.get_args() Valores de los argumentos en p.args_known{}.", -- es
} -- modes.i18n.es
 
modes.i18n.fr = {
-- Noms et descriptions des arguments de configurations
[1] = "1",
[2] = "2",
[3] = "3",
[4] = "4",
label = 'label',
label_descr = "Argument automatique de Wikidata.",
sitelink = 'sitelink',
sitelink_descr = "Argument automatique de Wikidata.",
-- Languages
contentlang = "contentlang",
contentlang_descr = "Langue du wiki.",
pagelang = "pagelang",
pagelang_descr = "Langue de la page.",
userlang = "userlang",
userlang_descr = "Language du lecteur de la page.",
--
QITEM = 'QITEM',
uri = 'uri',
itemid = 'itemid',
itemid_descr = "Identifiant des données de Wikidata, comme <code>Q535</code> pour Victor Hugo.",
itemid2 = 'id',
itemid2_descr = "Autre identifiant des données de Wikidata, comme <code>Q535</code> pour Victor Hugo.",
debug = 'debug',
category = 'Catégorie',
mode = "mode",
mode_descr = "Type d'utilisation du module ou du modèle : lire, éditer, documenter, tester.",
options = "options",
options_descr = "Options d'affichage d'un module ou d'un modèle.",
c = "c",
c_descr = "Options d'affichage d'un module ou d'un modèle.",
knownversions = "knownversions",
knownversions_descr = "Versions connues, pour les gérer.",
soughtversions = "soughtversions",
soughtversions_descr = "Versions demandées, pour les gérer.",
modes_form_ok_categ_tests = "Test de génération de catégorie OK",
-- Principaux textes, erreurs et catégories des outils
language = 'langue',
-- Messages et erreurs divers
modes_used_options_list_title = "modes.used_options_list() Utilisation des options :",
modes_options_uses_tests_title = "modes.options_from_mode_tests() Modes et options en bref",
modes_options_from_args_tests_title = "modes.options_from_args_tests() Test des options de modes",
modes_options_from_args_title = "Test des options des arguments",
-- Groupes d'arguments
modes_needed_to_verify = "(obligatoire, à vérifier)",
modes_list_needed_args = "Liste des arguments nécessaires :",
modes_list_all_config_arguments = "Liste des arguments de configuration :",
modes_list_all_system_arguments = "Liste des arguments système :",
modes_list_all_other_args = "Liste des autres arguments :",
modes_language_cat = 'Parle <b>%1</b>',
modes_date_months_names = "Janvier, Février, Mars, Avril, Mai, Juin, Juillet, Août, Septembre, Octobre, Novembre, Décembre",
modes_date_to_part_format = "dd yyyy mmmm",
modes_date_to_part_call_err = "Erreur interne : Argument anormal de définition de date <b>%1</b>.",
modes_date_to_part_call_cat = "Module avec erreur interne",
modes_date_to_part_not_found_err = "Erreur interne : partie non définie de date <b>%1</b>.",
-- Gestion des arguments
modes_error_list_header_err = "Assistance sur les paramètres de ce modèle :",
modes_need_arg_value_err = "Erreur : Vous devez définir cet argument nécessaire mais absent : <b>%1</b>.",
modes_none_value_err = "Erreur : Aucun argument n'a été défini.",
modes_unknown_argument_err = "Erreur : Le paramètre <b>%1</b> est inconnu dans ce modèle. Vérifier ce nom ou signaler ce manque.",
modes_too_unnamed_arguments_err = "Erreur : Ce paramètre non nommé est en trop : <b>%1</b> = <b>%2</b>.",
modes_without_translation_wsid_err = "Erreur interne : Signaler au développeur que l'argument interne <b>%1</b> est inconnu dans les notices.",
modes_is_defined_err = "L'argument <b>%1</b>:<b>%2</b> est défini.",
modes_is_undefined_err = "L'argument <b>%1</b>:<b>%2</b> n'est pas défini.",
modes_args_values_err = "Valeur anormale de l'argument <b>%1</b> = <b>%2</b> parmi : (%3) ",
-- Messages et erreurs divers
modes_nearest_argument_err = "Erreur : Voulez vous l'argument connu <b>%1</b> ?",
modes_max_nearest_argument_msg = "Un nom d'argument plus long accepte plus d'erreurs de lettres.",
modes_value_re_defined_err = "Erreur : La valeur de l'argument <b>%1</b> est déjà définie. Choisir une seule valeur d'un seul synonyme.",
modes_lang_table_err = "Erreur interne : La langue <b>%1</b> ou sa table est erronée.",
modes_lang_table_err_i_cat = "Module avec erreur interne", -- modes_no_source_arguments_cat
modes_lang_table_err_i_cat = "Module avec langue d'arguments erronée",
modes_lang_not_translated_err = "Erreur : La langue <b>%1</b> n'est pas traduite.",
modes_generDoc1_paramName_err = "Erreur interne : en generDoc1, mauvais argument <b>%1</b>.",
modes_unknown_auto_arg_err = "Erreur interne: Argument automatique inconnu : <b>%1</b> = <b>%2</b>.",
--
modes_delete_docbox_wng = "Vous devez suprimer cette documentation avant d'enregistrer.<br>Supprimez tous les modes pour revenir en mode read.",
modes_auto_val_warning_wng = "Vérifiez l'argument automatique.",
--
modes_assist_user_param_err = "Support aux utilisateurs pour vérifier les paramètres :",
modes_args_values_err = "Valeur anormale de l'argument <b>%1</b> = <b>%2</b> (%3)",
--
modes_no_known_arguments_err = "Erreur interne : Module sans table d'arguments connus.",
modes_no_known_arguments_i_cat = "Module sans table d'arguments connus.",
modes_no_source_arguments_err = "Erreur interne : Module sans table d'arguments sources.",
modes_no_source_arguments_i_cat = "Module sans table d'arguments source.",
--
modes_list_all_args_main_title = "modes.list_all_args_main() Liste de tous les arguments acceptés",
modes_levenshtein_similar_tests_title = "modes.levenshtein() Test des distances de <b>[https://fr.wikipedia.org/wiki/Distance_de_Levenshtein Levenshtein]</b> entre mots:",
modes_args_known_structure_title = "modes.args_known_structure() Définitions des arguments",
modes_args_unknown_report_title = "viewers.simple_list_test() Signaler les arguments inconnus",
modes_normal_box_main_text_1 = "Boîte d'information simple : titre de cette page <b>%1</b>, description : <b>%2</b>",
modes_normal_box_main_text_2 = "<br/>Il était <b>%1</b>, se nommait <b>%2</b> <b>%3</b>, il est mort en <b>%4</b>.",
-- Ces textes sont utilisés pour titrer des tests.
modes_list_wiki_selectors_title = "Liste des sélecteurs de ce module :",
modes_all_categories_list_title = "modes.all_categories_list() Liste des catégories éventuelles de ce module :",
modes_all_errors_list_title = "modes.all_errors_list() Liste des erreurs détectables de ce module :",
modes_multiple_values_tests_title = "modes.multiple_values() Test des arguments à valeurs multiples",
modes_multiple_selection_tests_title= "modes.multiple_selection() Test de sélection multiple",
modes_multiple_selection_test_headers= "Options;Sélecteur;À sélectionner;Sélectionnés",
modes_multiple_selection_test_select= "2;nobel;président;député;prix",
modes_recursiveLevel_err = "Erreur de niveau récursif <b>%1</b> > <b>%2</b>",
modes_recursive_normal_tests_title = "modes.recursive_normal() Test: Normalise le niveau récursif et la limite récursive",
modes_namespaces_page_list_title = "modes.namespaces_page_list() Module, namespaces, et noms de pages :",
modes_args_known_report_title = "modes.args_known_report(t) Rapport des principaux arguments connus.",
modes_args_known_report_headers = "clé; valeur; type; nécessaire; mot-clé; synonyme; propriété; format; source",
modes_get_args_report_title = "modes.get_args() Valeurs des argument dans p.args_known{}.", -- fr
} -- modes.i18n.fr
 
modes.i18n.hu = {
-- Nombres y descripciones de argumentos de configuraciones
[1] = "1",
[2] = "2",
[3] = "3",
[4] = "4",
label = 'label',
label_descr = "Automatikus Wikidata argumentum.",
sitelink = 'sitelink',
sitelink_descr = "Automatikus Wikidata argumentum.",
-- Languages
contentlang = "contentlang",
contentlang_descr = "Wiki nyelv.",
pagelang = "pagelang",
pagelang_descr = "Az oldal nyelve.",
userlang = "userlang",
userlang_descr = "Az oldal olvasó nyelve.",
--
QITEM = 'QITEM',
uri = 'uri',
QITEM_descr = "Wikidata adatok neve, például Victor Hugo kódja <code>Q535</code>.",
itemid = 'itemid',
itemid_descr = "Wikidata adatok neve, például Victor Hugo kódja <code>Q535</code>.",
itemid2 = 'id',
itemid2_descr = "Wikidata adatok neve, például Victor Hugo kódja <code>Q535</code>.",
debug = 'debug',
category = 'kategória',
mode = "modo",
mode_descr = "A modul vagy modell használata: olvasás, szerkesztés, dokumentum, tesztelés.",
options = 'opciones',
options_descr = "Egy modul vagy modell megjelenítési lehetőségei.",
c = "c",
c_descr = "Egy modul vagy modell megjelenítési lehetőségei.",
knownversions = "knownversions",
knownversions_descr = "Jól ismert verziók, kezelni őket.",
soughtversions = "soughtversions",
soughtversions_descr = "Kérjen változatokat, kezelni őket.",
-- Textos principales, errores y categorías de instrumentos
modes_form_ok_categ_tests = "OK kategória-generációs teszt",
--
-- Titres des pruebas
modes_used_options_list_title = "modes.used_options_list() Az opciók használata:",
modes_options_uses_tests_title = "modes.options_from_mode_tests() Módok és lehetőségek röviden",
modes_options_from_args_tests_title = "modes.options_from_args_tests() Tesztelési mód beállításai",
modes_options_from_args_title = "Tesztelési argumentum opciók",
-- Grupos de argumentos
modes_needed_to_verify = "(kötelező, ellenőrizze)",
modes_list_needed_args = "A szükséges érvek felsorolása:",
modes_list_all_config_arguments = "Konfigurációs argumentumok listája:",
modes_list_all_system_arguments = "Rendszer-érvek listája:",
modes_list_all_other_args = "Egyéb érvek felsorolása:",
-- Fő szövegek, hibák és műszerkategóriák
modes_language_cat = 'beszélő <b>%1</b>',
modes_date_months_names = "Január, február, március, április, május, június, július, augusztus, szeptember, október, november, december",
modes_date_to_part_format = "dd mmmm yyyy",
modes_date_to_part_call_err = "Belső hiba: anomáliás híváselméletek a dátumon <b>%1</b>.",
modes_date_to_part_call_cat = "Modul belső hibával",
modes_date_to_part_not_found_err = "Belső hiba: Nem található a dátumon <b>%1</b>.",
-- Control de argumentos
modes_error_list_header_err = "A modell paramétereinek támogatása:",
modes_need_arg_value_err = "Hiba: Meg kell oldanod ezt a szükséges érvet, de hiányzik: <b>%1</b>.",
modes_none_value_err = "Hiba: Nincs argumentum definiálva.",
modes_unknown_argument_err = "Hiba: A <b>%1</b> paraméter ismeretlen ebben a modellben. Ellenőrizze a nevet vagy jelezze ezt a hibát.",
modes_too_unnamed_arguments_err = "Hiba: túl sok argumentum a név nélkül: <b>%1</b> = <b>%2</b>.",
modes_without_translation_wsid_err = "Belső hiba: Tájékoztassa a fejlesztőt, hogy a <b>%1</b> belső argumentum ismeretlen a rekordokban.",
modes_is_defined_err = "A argumentum <b>%1</b>:<b>%2</b> definiálva van.",
modes_is_undefined_err = "A <b>%1</b>:<b>%2</b> argumentum nincs meghatározva.",
modes_args_values_err = "Az argumentum abnormális értéke <b>%1</b> = <b>%2</b> között: (<b>%3</b>) ",
modes_nearest_argument_err = "Hiba: Ismeretes az argumentum <b>%1</b> ?",
modes_max_nearest_argument_msg = "A hosszabb név argumentum több betűhibát is elfogad.",
modes_value_re_defined_err = "Hiba: Az <b>%1</b> argumentum értéke már definiált. Válasszon csak egyetlen értéket egy szinonimának",
modes_lang_table_err = "Hiba: A <b>%1</b> nyelv vagy annak táblája nem megfelelő.",
modes_lang_table_err_i_cat = "Modul belső hibával", -- modes_lang_table_err_i_cat
modes_lang_table_err_i_cat = "A téves érvek nyelvével rendelkező modul", -- modes_no_source_arguments_cat
modes_lang_not_translated_err = "Hiba: A nyelv <b>%1</b> nem fordított le.",
modes_generDoc1_paramName_err = "Belső hiba: generDoc1-ben, rossz érv <b>%1</b>.",
--
modes_unknown_auto_arg_err = "Belső hiba: Automatikus ismeretlen argumentum: <b>%1</b> = <b>%2</b>.",
modes_delete_docbox_wng = "Törölje a dokumentációt az égetés előtt.<br> Távolítsa el az összes módot, hogy visszatérjen az olvasási üzemmódba.",
modes_auto_val_warning_wng = "Ellenőrizze az automatikus érveket.",
--
modes_assist_user_param_err = "Felhasználói támogatás a konfiguráció ellenőrzéséhez:",
modes_args_values_err = "Az érv abnormális értéke <b>%1</b> = <b>%2</b> ( <b>%3</b> )",
--
modes_no_known_arguments_err = "Belső hiba: Az ismert argumentumok táblázata nélküli modul.",
modes_no_known_arguments_i_cat = "Modul tábla nélkül ismert érvekkel.",
modes_no_source_arguments_err = "Belső hiba: A tábla argumentum nélküli tábla nélküli modul.",
modes_no_source_arguments_i_cat = "Modul forrás argumentum táblázattal.Modul forrás argumentum táblázattal.",
 
modes_list_all_args_main_title = "modes.list_all_args_main() Az elfogadott érvek listája",
modes_levenshtein_similar_tests_title= "modes.levenshtein() A távolságok igazolása <b>[https://es.wikipedia.org/wiki/Distancia_de_Levenshtein Levenshtein]</b> entre las palabras:",
modes_args_known_structure_title = "modes.args_known_structure() Az érvek fogalommeghatározása",
modes_args_unknown_report_title = "viewers.simple_list_test() Ismeretlen érvek jelentése",
modes_normal_box_main_text_1 = "Egyszerű információs mező: Az oldal címe: <b>%1</b>, leírás: <b>%2</b>",
modes_normal_box_main_text_2 = "<br/><b>%1</b> névvel <b>%2</b> <b>%3</b> meghalt <b>%4</b>.",
-- Ezeket a szövegeket néhány teszt tesztelésére használják.
modes_list_wiki_selectors_title = "Ebben a modulban a szelektorkészletek listája:",
modes_all_categories_list_title = "modes.all_categories_list() A modul lehetséges kategóriái:",
modes_all_errors_list_title = "modes.all_errors_list() A modulban észlelhető hibák felsorolása:",
modes_multiple_values_tests_title = "modes.multiple_values() Több argumentum értékének vizsgálata",
modes_multiple_selection_tests_title= "modes.multiple_selection() Többszörös kiválasztási teszt",
modes_multiple_selection_test_headers= "Opciók; Kiválasztó; Kiválasztás; Kiválasztott",
modes_multiple_selection_test_select= "2; Nobel; elnök; helyettese; ár",
modes_recursiveLevel_err = "Rekurzív szint hiba <b>%1</b> > <b>%2</b>",
modes_recursive_normal_tests_title = "modes.recursive_normal() Teszt: Normalizálja a rekurzív szintet és a rekurzív határt",
modes_namespaces_page_list_title = "modes.namespaces_page_list() Modul, névterek és oldalnevek:",
modes_args_known_report_title = "modes.args_known_report(t) A legfontosabb ismert érvekről szóló jelentés.",
modes_args_known_report_headers = "kulcs; érték; írja; szükséges; kulcsszó; fordítása; tulajdon; formátumban; forrás",
modes_get_args_report_title = "modes.get_args() Az érvek értékei p.args_known{}.", -- es
} -- modes.i18n.hu
 
modes.i18n.vi = {
-- Noms et descriptions des arguments de configurations
[1] = "1",
[2] = "2",
[3] = "3",
[4] = "4",
label = 'label',
label_descr = "Đối số tự động để Wikidata.",
sitelink = 'sitelink',
sitelink_descr = "Đối số tự động để Wikidata.",
-- Languages
contentlang = "contentlang",
contentlang_descr = "Ngôn ngữ wiki.",
pagelang = "pagelang",
pagelang_descr = "Ngôn ngữ trang.",
userlang = "userlang",
userlang_descr = "Ngôn ngữ để người đọc trang.",
--
QITEM = 'QITEM',
uri = 'uri',
itemid = 'itemid',
itemid_descr = "Định danh dữ liệu Wikidata, chẳng hạn như <code>Q535</code> để Victor Hugo.",
itemid2 = 'id',
itemid2_descr = "Số nhận dạng khác để dữ liệu Wikidata, chẳng hạn như <code>Q535</code> để Victor Hugo.",
debug = 'gỡ lỗi',
category = 'Loại',
mode = "mode",
mode_descr = "Loại sử dụng mô-đun hoặc mô hình: đọc, chỉnh sửa, tài liệu, kiểm tra.",
options = "options",
options_descr = "Hiển thị tùy chọn mô-đun hoặc mô hình.",
c = "c",
c_descr = "Hiển thị tùy chọn mô-đun hoặc mô hình.",
knownversions = "knownversions",
knownversions_descr = "Các phiên bản đã biết, để quản lý chúng.",
soughtversions = "soughtversions",
soughtversions_descr = "Các phiên bản được yêu cầu, để quản lý chúng.",
-- Principaux textes, erreurs et catégories des outils
language = 'langue',
-- Messages et erreurs divers
modes_used_options_list_title = "modes.used_options_list() Sử dụng các tùy chọn:",
modes_options_uses_tests_title = "modes.options_from_mode_tests() Chế độ và tùy chọn trong ngắn hạn",
modes_options_from_args_tests_title = "modes.options_from_args_tests() Tùy chọn chế độ thử nghiệm",
modes_options_from_args_title = "Kiểm tra đối số tùy chọn",
-- Groupes d'arguments
modes_needed_to_verify = "(bắt buộc, phải được xác minh)",
modes_list_needed_args = "Danh sách các đối số cần thiết:",
modes_list_all_config_arguments = "Danh sách các đối số cấu hình:",
modes_list_all_system_arguments = "Danh sách các đối số hệ thống:",
modes_list_all_other_args = "Danh sách các đối số khác:",
modes_language_cat = 'Nói tiếng <b>%1</b>',
modes_date_months_names = "Tháng 1, tháng 2, tháng 3, tháng 4, tháng 5, tháng 6, tháng 7, tháng 9, tháng 10, tháng 11, tháng 12",
modes_date_to_part_format = "dd yyyy mmmm",
modes_date_to_part_call_err = "Lỗi nội bộ: Đối số định nghĩa ngày bất thường <b>%1</b>.",
modes_date_to_part_call_cat = "Mô-đun có lỗi nội bộ",
modes_date_to_part_not_found_err = "Lỗi nội bộ: phần không xác định để ngày <b>%1</b>.",
-- Gestion des arguments
modes_error_list_header_err = "Hỗ trợ các thông số để mô hình này:",
modes_need_arg_value_err = "Lỗi: Bạn phải đặt đối số cần thiết nhưng vắng mặt này: <b>%1</b>.",
modes_none_value_err = "Lỗi: Không có đối số nào được xác định.",
modes_unknown_argument_err = "Lỗi: Thông số <b>%1</b> không xác định trong mẫu này. Kiểm tra tên này hoặc báo cáo sự thiếu này.",
modes_too_unnamed_arguments_err = "Lỗi: Tham số chưa đặt tên này vượt quá: <b>%1</b> = <b>%2</b>.",
modes_without_translation_wsid_err = "Lỗi nội bộ: Báo cáo cho nhà phát triển rằng đối số nội bộ <b>%1</b> không xác định trong các bản ghi.",
modes_is_defined_err = "Đối số <b>%1</b>:<b>%2</b> được đặt.",
modes_is_undefined_err = "Đối số <b>%1</b>:<b>%2</b> không được xác định.",
modes_args_values_err = "Giá trị bất thường để đối số <b>%1</b> = <b>%2</b> từ: ( <b>%3</b> ) ",
-- Messages et erreurs divers
modes_nearest_argument_err = "Lỗi: Bạn có muốn đối số <b>%1</b> đã biết không?",
modes_max_nearest_argument_msg = "Tên đối số dài hơn chấp nhận nhiều lỗi thư hơn.",
modes_value_re_defined_err = "Lỗi: Giá trị để đối số <b>%1</b> đã được đặt. Chọn một giá trị duy nhất từ một từ đồng nghĩa duy nhất.",
modes_lang_table_err = "Lỗi nội bộ: Ngôn ngữ <b>%1</b> hoặc bảng để nó sai.", -- để=để
modes_lang_table_err_i_cat = "Mô-đun có lỗi nội bộ", -- modes_no_source_arguments_cat
modes_lang_table_err_i_cat = "Mô-đun với ngôn ngữ đối số sai",
modes_lang_not_translated_err = "Lỗi: Ngôn ngữ <b>%1</b> không được dịch.",
modes_generDoc1_paramName_err = "Lỗi nội bộ: trong generDoc1, đối số không hợp lệ <b>%1</b>.",
modes_unknown_auto_arg_err = "Lỗi nội bộ: Đối số tự động không xác định: <b>%1</b> = <b>%2</b>.",
--
modes_delete_docbox_wng = "Bạn phải xóa tài liệu này trước khi lưu.<br> Xóa tất cả các chế độ để trở về chế độ đọc.",
modes_auto_val_warning_wng = "Kiểm tra đối số tự động.",
--
modes_assist_user_param_err = "Hỗ trợ người dùng để kiểm tra cài đặt:",
modes_args_values_err = "Giá trị bất thường để đối số <b>%1</b> = <b>%2</b> ( <b>%3</b> )",
--
modes_no_known_arguments_err = "Lỗi nội bộ: Mô-đun không có bảng các đối số đã biết.",
modes_no_known_arguments_i_cat = "Mô-đun không có bảng các đối số đã biết.",
modes_no_source_arguments_err = "Lỗi nội bộ: Mô-đun không có bảng đối số nguồn.",
modes_no_source_arguments_i_cat = "Mô-đun không có bảng đối số nguồn.",
--
modes_list_all_args_main_title = "modes.list_all_args_main() Danh sách tất cả các đối số được chấp nhận",
modes_levenshtein_similar_tests_title = "modes.levenshtein() Kiểm tra khoảng cách <b>[https://fr.wikipedia.org/wiki/Distance_de_Levenshtein Levenshtein]</b> entre mots:",
modes_args_known_structure_title = "modes.args_known_structure() Định nghĩa đối số",
modes_args_unknown_report_title = "viewers.simple_list_test() Báo cáo đối số không xác định",
modes_normal_box_main_text_1 = "Hộp thông tin đơn giản: tiêu đề để trang này <b>%1</b>, mô tả: <b>%2</b>",
modes_normal_box_main_text_2 = "<br/>Anh ta <b>%1</b>, tên anh ta <b>%2</b> <b>%3</b>, anh ta đã chết <b>%4</b>.",
-- Ces textes sont utilisés pour titrer des tests.
modes_list_wiki_selectors_title = "Danh sách các bộ chọn để mô-đun này:",
modes_all_categories_list_title = "modes.all_categories_list() Danh sách các danh mục có thể có để mô-đun này:",
modes_all_errors_list_title = "modes.all_errors_list() Danh sách các lỗi có thể phát hiện trong mô-đun này:",
modes_multiple_values_tests_title = "modes.multiple_values() Thử nghiệm đối số nhiều giá trị",
modes_multiple_selection_tests_title= "modes.multiple_selection() Kiểm tra nhiều lựa chọn",
modes_multiple_selection_test_headers= "Tùy chọn; Bộ chọn; Để chọn; Đã chọn",
modes_multiple_selection_test_select= "2; nobel; chủ tịch; Phó; giá",
modes_recursiveLevel_err = "Lỗi mức đệ quy <b>%1</b> > <b>%2</b>",
modes_recursive_normal_tests_title = "modes.recursive_normal() Kiểm tra: Bình thường hóa mức đệ quy và giới hạn đệ quy",
modes_namespaces_page_list_title = "modes.namespaces_page_list() Mô-đun, namespaces, và tên trang:",
modes_args_known_report_title = "modes.args_known_report(t) Báo cáo để các đối số được biết đến chính.",
modes_args_known_report_headers = "chính; giá trị; loại; cần thiết; từ khóa; đồng nghĩa; bất động sản; định dạng; nguồn",
modes_get_args_report_title = "modes.get_args() Giá trị để các đối số trong p.args_known{}.",
} -- modes.i18n.vi
 
-- - - - ------------------ - - - - ---------------------------------
-- Support of the management of options. Sostén de la gestión de las opciones. Soutien de la gestion des options.
-- - - - ------------------ - - - - ---------------------------------
 
modes.options_for_modes = { -- default options_for_modes
read = " box1 ",
edit = " box1 docdef docline docsrc docdata catview docview : ",
doc = " nobox1 noerr nocatview ",
tests = " box1 docdef docline docsrc docdata catview docview : tests ",
-- List of parameters for module documentation
-- "docview" or ":" add the documentation panel
-- "docmin" list only some basic parameters
-- "docdef" list only the parameters defined, having a non-zero value
-- "docmax" list all known parameters
-- "docnotice" generate documentations of records
-- "docline" put all parameters on a single line
-- "docsrc" put the parameters in colors according to the sources
-- modes.options = " docdata docmin docdef docmax docline docview docafter docnotice docsrc : " -- for standard documentation
-- modes.options = " erron noerr nobox1 nocatview " -- do not form normal result
-- modes.options = " debug tests en es fr " -- enforce a language for debug
-- Option nocatview means "Do not categorize and do not show categories."
}
 
-- Manage Library:modes options. Administrar opciones. Gérer les options.
modes.template_options = "" -- Normal options from the template, like {{Bananas|options=docmax docdef}}.
modes.mode_options = "" -- Internal options from the mode.
modes.available_options = "" -- table to collect all available options, at any time.
modes.used_options = {} -- table to collect really or tested options then list them at end of tests.
 
mathroman.args_known = { -- Table of the definitions of all known arguments at module level.
-- Arguments in order without names, with their keyword for use as other arguments.
[1] = {need = 0, syn = 2, keyword = "mode"},
-- Special arguments to modify the fonctions and outputs of this module.
mode = {typ = "config", need = 0, keyword = "mode"},
c = {typ = "config", need = 0, keyword = "c"},
options = {typ = "config", need = 0, keyword = "options"},
-- The userlang argument permits at an administrator in his own langage (errors, warnings, catégories, tests) to help a wiki in any language.
contentlang = {typ = "config", need = 1, keyword = "contentlang"},
pagelang = {typ = "config", need = 2, keyword = "pagelang"},
userlang = {typ = "config", need = 0, keyword = "userlang"},
birthyear = {typ = "dat", need = 0, keyword = "birthyear", prop = "P569", format = "year"},
}
 
function modes.bind_args_known_props(args_known, args_new) -- Bind known args and their properties for central libraries. Later for modules.
local args_known = args_known or modes.args_known or p.args_known or {}
if (type(args_known) ~= "table") then return {} end
local args_known_one = {}
if (type(args_new) ~= "table") then return args_known end
for key, props in pairs(args_new) do -- import and mix known args and properties
if (type(props) == "table") then
args_known_one[key] = props or args_known[key]
props.key = key
end -- Add properties for a new argument
end
return args_known_one
end -- local args_known_props = modes.bind_args_known_props(args_known, args_new)
 
function modes.args_known_one_lib(args_known, args_new) -- Bind known args and their properties for central libraries. Later for modules.
local args_known = args_known or modes.args_known or p.args_known or {} -- modes.args_known = { -- p.args_known = { -- }
if (type(args_known) ~= "table") then return {} end
local args_known_props = {}
for key, one_lib in pairs(args_new) do -- import and mix known args and properties
if (type(one_lib) == "table") then
bind_args = modes.bind_args_known_props(args_known, args_new)
args_known_props = modes.bind_args_known_props(modes.args_known, args_new)
end
end
return args_known_props
end -- function modes.args_known_one_lib(args_known, args_new)
 
function modes.bind_args_known_one_lib_report(t) -- Report the binding of one library known args.
local memo = viewers.save_configs("modes.bind_args_known_one_lib_report") -- Save global configuration before eventual changes.
local t = t or "\n* mathroman.args_known_one_lib(t) Report the binding of one library known args."
local args_known = args_known or modes.args_known or p.args_known or {} -- modes.args_known = { -- p.args_known = { -- }
local args_known_props = modes.args_known_one_lib(modes.args_known, mathroman.args_known)
t = t .. "\n* " .. viewers.ta("#args_known_props", lua_table.level_count(args_known_props) )
if (type(args_known) ~= "table") then return args_known end
local tab_view = { -- Group datas and options for a table view with lines and columns.
test_group = args_known,
rowGroup = {},
form_one_case = function(case) -- Convert a case from test_group to rowGroup.
return { viewers.value(case.key), case.bind, case.typ, case.need, case.keyword, case.prop, case.format, }
end,
title_memo = "modes_bind_args_known_report_title",
title_memo = "modes.bind_args_known_one_lib_report(t) Report the binding of one library known args. **",
headers = "modes_bind_args_known_report_headers",
headers = "key;bind;typ;need;keyword;prop;format",
}
t = t .. "<br/>" .. tableview.new(tab_view) -- Formats a table view with lines and columns.
viewers.restore_configs(memo, "modes.bind_args_known_one_lib_report") -- Restore global configurations after eventual changes.
return t
end -- function modes.bind_args_known_one_lib_report(t)
 
function lua_table.sort_onkey(tab, key) -- Sort a table with any types of keys.
-- local tab = tab or {} -- keep table errors to permit to debug
local key = key or "keyword"
return table.sort(tab, function (a, b)
if (type(a[key]) == type(b[key])) then return ( a[key] < b[key] ) -- any translated arguments of same types
else return ( tostring(a[key]) < tostring(b[key]) ) end -- alphabetic sort of translated arguments
end )
end
 
function modes.args_known_report(t, args_known) -- Report of main known args.
local memo = viewers.save_configs("modes.args_known_report") -- Save global configuration before eventual changes.
local t = t or "\n* <b>modes.args_known_report(t)</b> Report of main known args."
local args_known = args_known or modes.args_known or p.args_known or {} -- modes.args_known = { -- p.args_known = { -- }
local args_group = {} -- modes.args_known = { -- p.args_known = { -- }
for key, tab in pairs(args_known) do -- import and mix known args and properties
table.insert( args_group, tab )
end
local prop, props = datas.get_item(args_known, QITEM) -- Get datas from mw.wikibase for the page. ric
table.sort(props, function (a, b) return ( (a.keyword or a.prop) < (b.keyword or b.prop)) end ) -- alphabetic sort of translated arguments
t = t .. "\n* " .. viewers.ta("args_known count", lua_table.level_count(args_known) )
local tab_view = { -- Group datas and options for a table view with lines and columns.
test_group = args_group, -- tab_view.test_group or
rowGroup = {},
title_memo = "modes.args_known_report(t) Report of main known args. **",
title_memo = "modes_args_known_report_title", -- "modes.args_known_report(t) Rapport des principaux arguments connus.",
headers = "modes_args_known_report_headers", -- headers = "key; val; type; need; keyword; syn; prop; format; source",
form_one_case = function(case) -- Convert a case from test_group to rowGroup. tab_view.form_one_case or
return { (case.keyword), (case.val or "-"), case.typ, case.need, case.keyword, case.syn, case.prop, case.format, case.src, }
end,
}
t = t .. "<br/>" .. tableview.new(tab_view) -- Formats a table view with lines and columns.
viewers.restore_configs(memo, "modes.args_known_report") -- Restore global configurations after eventual changes.
return t
end -- function modes.args_known_report(t, args_final)
 
function modes.init_options(template_options)
-- modes.template_options = modes.init_options(args.options)
-- modes.template_options = modes.init_options("fr params docview docmin docmax docdef docnotice docafter docline docsrc")
if (type(template_options) == "string") then modes.template_options = template_options end
if (type(modes.template_options) ~= "string") then modes.template_options = "" end
-- Early effects on options which modify other ones.
-- modes.options = " : docdata docmin docdef docmax docline docview docafter docnotice docsrc" -- for documentation
-- modes.options = " erron noerr nobox1 nocatview " -- without normal result
-- modes.options = " debug tests en es fr " -- for debug or enforce language
modes.options_to_cat_view()
if modes.option("noerr") then events.erron = false end
if modes.option("erron") then events.erron = true end
if modes.option("docolor") then modes.docolor = true end
-- If an option is a language, enable this language for the user.
-- Si una opción es un lenguaje, activar esta lengua para usuario.
-- Si une option est une langue, activer cette langue pour l'utilisateur.
for lang, tab in pairs(versions.i18n) do
if modes.option(lang) then
langs.init_content_page_user_lang(langs.content_lang, xx, yy, lang) -- langs.content_lang, langs.user_lang
end
end
return modes.template_options
end -- function modes.init_options(template_options)
 
function modes.options_from_mode(mode_name, options_for_modes)
modes.options_for_modes = options_for_modes or modes.options_for_modes
modes.mode_name = mode_name or modes.mode_name or "read"
if modes.options_for_modes and modes.options_for_modes[mode_name] then modes.mode_options = modes.options_for_modes[mode_name] end
return modes.mode_options, mode_name
end
 
function modes.option(key, opt) -- Is one option in available options?
-- Language identifiers allow to enforce some languages.
-- Errors appear only in Template or Module namespace, waiting the task T53660.
if type(key) ~= "string" then key = "" end
key = mw.text.trim(key)
if type(opt) ~= "string" then opt = "" end
opt = mw.text.trim(opt)
local available_options = (modes.template_options or "")
if available_options and modes.mode_options -- other param can replace modes.mode_options
then available_options = " " .. available_options .. " " .. modes.mode_options .. " "
elseif available_options and opt then available_options = " " .. available_options .. " " .. opt .. " " end
available_options = viewers.simple_list(available_options, " ")
-- The searched keyword is it among the options words? And not included in another word.
local ifyes = viewers.is_in_sp(key or "", available_options) -- and true
-- Collect options tested along the execution of the module
modes.used_options = modes.used_options or {}
if ifyes then modes.used_options[key] = "y"
else modes.used_options[key] = "n" end
local used = ""
for key, xx in pairs(modes.used_options) do
if xx == "y" then used = used .. ", <b>" .. tostring(key) .. "</b> " .. xx
else used = used .. " " .. tostring(key) .. ", " .. xx end
end
modes.available_options = available_options
modes.used_opts = used -- yes is not nil
return ifyes, used, available_options -- yes is not nil
end -- function modes.option(key, opt)
 
function modes.options_from_mode_tests(t)
local memo = viewers.save_configs("modes.options_from_mode_tests") -- Save global configuration before eventual changes.
local t = tostring(t)
local t = t or "options_from_mode_test:"
for md, opt in pairs(modes.options_for_modes) do t = t .. "<br>- " .. viewers.ta(md, opt) end
t = t .. viewers.table_head() .. viewers.table_col("Mode") .. viewers.table_col("List of options") .. viewers.table_col("noerr value") .. viewers.table_col("docview value") .. viewers.table_col("tests value")
local function test_options_from_mode(md, op1, op2, op3)
modes.available_options = ""
local opstest = modes.options_from_mode(md) or ""
return viewers.table_row() .. viewers.table_dat(md) .. viewers.table_dat(opstest) .. viewers.table_dat( modes.option(op1, opstest) )
.. viewers.table_dat(modes.option(op2, opstest)) .. viewers.table_dat(modes.option(op3, opstest))
end
t = t .. "<br>options_from_mode_test:"
t = t .. test_options_from_mode("read", "noerr", "docview", "tests")
t = t .. test_options_from_mode("edit", "noerr", "docview", "tests")
t = t .. test_options_from_mode("tests", "noerr", "docview", "tests")
t = t .. viewers.table_end()
viewers.restore_configs(memo, "modes.options_from_mode_tests") -- Restore global configurations after eventual changes.
return t
end -- function modes.options_from_mode_tests(t)
 
function modes.used_options_list(t, used_options)
local t = t or "List of modes:"
used_options = used_options or modes.used_options
modes.mode_name = mode_name or modes.mode_name or "read"
for md, opt in pairs(modes.options_for_modes) do t = t .. "<br>- " .. viewers.ta(md, opt) end
-- List of used options after collect them
t = t .. "\n* " .. viewers.form9user("langs_content_page_user_lang_msg", langs.user_lang, langs.content_lang)
t = t .. "\n* Actual mode used: <b>" .. modes.mode_name .. "</b>"
t = t .. "\n* Options read the last time in these tests, ones <b>activated</b> are in bold: "
t = t .. "\n* Options lues pour la dernière fois pendant ces tests, celles <b>activées</b> sont en gras : "
t = t .. "<br>"
local used = ""
for key, x in pairs(modes.used_options) do
if x == "y" then used = used .. ", <b>" .. tostring(key) .. "</b> "
else used = used .. ", " .. tostring(key) .. " " end
end
t = t .. used
return t, used
end
 
function modes.options_to_cat_view() -- Init or restaure modes.cat_view = modes.cat_view from options
if modes.option(":") or modes.option("catview") then modes.cat_view = ":" else modes.cat_view = "" end
return modes.cat_view
end -- function modes.options_to_cat_view()
 
function modes.options_from_args_tests(t)
local memo = viewers.save_configs("modes.options_from_args_tests") -- Save global configuration before eventual changes.
local mode_options_memo = modes.mode_options -- save
local template_options_memo = modes.template_options -- save
local used_options_memo = mw.clone(modes.used_options) -- save
modes.used_options = {} -- for test
local t = tostring(t)
t = t or "options_from_args_tests:"
t = t .. viewers.table_head() .. viewers.table_col("mode_options") .. viewers.table_col("template_options") .. viewers.table_col("opt can replace mode_options")
.. viewers.table_col("available options") .. viewers.table_col("option result") .. viewers.table_col("valid result")
local function options_from_args(mode_options, template_options, opt, key, verif)
modes.available_options = ""
modes.mode_options = mode_options or ""
modes.template_options = template_options or ""
local ifyes, available_options = modes.option(key, opt)
local testOK = ""
if tostring(ifyes) == tostring(verif) then testOK = "true" else testOK = "false" end
return viewers.table_row() .. viewers.table_dat( mode_options or "" ) .. viewers.table_dat( template_options or "" ) .. viewers.table_dat( opt or "" )
.. viewers.table_dat( modes.available_options ) .. viewers.table_dat( viewers.ta(key, ifyes) ) .. viewers.table_dat( testOK )
end
t = t .. options_from_args("nobox1 nocatview", "en docview", nil, "nobox1", "true")
t = t .. options_from_args("nobox1 nocatview", "en docview", nil, "nocatview", "true")
t = t .. options_from_args("nobox1 nocatview", "en docview", nil, "en", "true")
t = t .. options_from_args("nobox1 nocatview", "en docview", nil, "docview", "true")
t = t .. options_from_args("nobox1 nocatview", ": docview", nil, ":", "true")
t = t .. options_from_args("nobox1 nocatview", "en docview", "docline fr", "docline", "false")
t = t .. options_from_args("nobox1 nocatview", "en docview", "docline fr", "docline", "false")
t = t .. options_from_args(" ", nil, "docline fr", "docline", "false")
t = t .. options_from_args(" ", nil, "docline fr", "fr", "false")
t = t .. options_from_args(" ", "en docview", "docline fr", "en", "true")
t = t .. options_from_args("nobox1 nocatview", nil, "docline fr", "docline", "false")
t = t .. options_from_args("nobox1 nocatview", "en docview", "docline fr", nil, "true")
t = t .. options_from_args("nobox1 nocatview", "en docview", nil, "docline", "false")
t = t .. viewers.table_end()
t = t .. modes.used_options_list(nil, modes.used_options)
t = t .. "\n* After these tests, previous options are restored. Après ces tests, les options antérieures sont restaurés."
modes.mode_options = mode_options_memo -- restore
modes.template_options = template_options_memo -- restore
modes.used_options = used_options_memo -- restore
viewers.restore_configs(memo, "modes.options_from_args_tests") -- Restore global configurations after eventual changes.
return t
end -- function modes.options_from_args_tests(t)
 
--[[ Support of arguments and translations along their transformations :
datas.args_wikidata = {} -- Wikidata arguments, from Wikidata
events.errors_list = {} -- Errors list
events.categories_list = {} -- Categories lists
modes.args_known = {} -- Known arguments, at main module level
modes.args_template = {} -- Template arguments, at {{Template| ... }} level
modes.args_source = {} -- Source arguments = args_template
modes.args_unknown = {} -- Unknown arguments
modes.args_mixed = {} -- Mixed arguments
modes.args_import = {} -- Import arguments
modes.args_final = {} -- Final arguments, interactions in p.interact_args_final()
modes.args_selected = {} -- Selected arguments, in some modules
langs.content_translations = {} -- Wiki translations
langs.user_translations = {} -- User translations
versions.loaded_pack = {} -- loaded packages of modules and libraries
versions.loaded_vers = {} -- loaded versions of modules and libraries
--]]
 
function modes.change_itemid(id_in) -- Select a wikidata default item if needed.
local id = ""
if id_in then -- Local function parameter have priority.
id = id_in
else -- Else use the template arguments or inforce QITEM here.
id = modes.args_source.id
-- id = "Q535" -- (1802 – 1885) Victor Hugo
-- id = "Q8739" -- (near 287 av. J.-C. – 212 av. J.-C.) Archimède, Machine d'Archimède
-- id = "Q20882" -- (1832 – 1923) Gustave Eiffel
id = "Q1290" -- (1623 – 1662) Blaise Pascal
-- id = "Q41568" -- (1533 – 1592) Michel de Montaigne
-- id = "Q83428" -- (near 1493 – 1541) Paracelse
-- id = "Q131671" -- (VIe siècle av. J.-C. – Ve siècle av. J.-C.) Xénophane
-- id = "Q213330" -- (1330 – 1418) Nicolas Flamel
-- id = "Q21157618"-- ( – 1932) Charles Maumené
-- id = "Q9364" -- (1905 – 1980) Jean-Paul Sartre
end
local nst = 10 -- mw.site.namespaces.Template
local nsm = 828 -- mw.site.namespaces.Module
local mwtitle = mw.title.getCurrentTitle()
modes.main_title = mwtitle.text -- Server mw.uri.new
local nsX = mw.title.getCurrentTitle():inNamespaces("10", "11", "828", "829")
local nsX = mwtitle:inNamespaces("10", "11", "828", "829")
local ns = tostring(mw.site.namespaces.id)
if viewers.is_in_sp(ns, "10;11;828;829", ";") then
-- Change QITEM only where title cannot be in wikidata.
id = id or modes.main_title or modes.args_template.title or modes.args_template.QITEM or modes.args_template.label or modes.args_template.itemid
end
return id
end -- function modes.change_itemid(id_in)
 
function modes.args_known_structure(t, args_known) -- modes_args_known_structure_title = Table structure of arguments
-- if true then return "" end -- to DEBUG : S170606aks
local t = t or "\n* <b>args_known_structure :</b> " -- modes_list_all_args_main_title
local tt
local args_known = args_known or modes.args_known or p.args_known or {} -- optional value from p.args_known = { }
if type(args_known) == "table" then
for key, elem in pairs(args_known) do
tt = viewers.tam("typ", elem.typ) .. viewers.tam("keyword", elem.keyword) .. viewers.tam("syn", elem.syn)
tt = tt .. viewers.tam("need", elem.need) .. viewers.tam("prop", elem.prop) .. viewers.tam("format", elem.format)
tt = string.sub(tt, 3, -1)
t = t .. '\n: ' .. tostring(key) .. ' = { ' .. tt .. ' } '
end
end
return t
end -- function modes.args_known_structure(t, args_known)
 
function modes.levenshtein(word1, word2) -- Compute the Levenshtein distance between 2 ASCII words.
-- prevent exceptions
local cout = 0
if (type(word1) ~= "string") or (type(word2) ~= "string") then
return 999, "<br>lev: " .. viewers.ta("word1", word1) .. viewers.ta("word2", word2)
end
local len1 = string.len(word1)
local len2 = string.len(word2)
local lev = 0
local t = "<br>lev: " .. viewers.ta("word1", word1) .. viewers.ta("word2", word2)
if (type(word1) ~= "string") or (type(word2) ~= "string") or (word1 == "") or (word2 == "") then
lev = len1 + len2
return lev, t .. viewers.ta("lev", lev)
end
-- simple case
if (word1 == word2) then
lev = 0
return lev, t .. viewers.ta("lev", lev)
end
local d = {}
for i = 1, len1+2 do -- for i = 1, len1-1+1 do
d[i] = {}
-- d[i][1] = 0 -- d[i][1] = i
for j = 1, len2+2 do
-- d[i][j] = {}
d[i][j] = 0 -- d[1][j] = j
end
end
-- simulate double dimensions tables
for i = 2, len1+1 do -- for i = 1, len1-1+1 do
-- d[i] = {}
d[i][1] = i-1 -- d[i][1] = i
end
for j = 2, len2+1 do
d[1][j] = j-1 -- d[1][j] = j
end
for i = 2, len1+1 do -- for i = 2, len1+1 do
for j = 2, len2+1 do -- for j = 2, len2+1 do
-- we recover the two characters
local c1 = string.byte(word1, i-1)
local c2 = string.byte(word2, j-1)
if (c1 == c2) then
cout = 0
d[i][j] = d[i-1][j-1]
else
cout = 1
d[i][j] = math.min(d[i-1][j], d[i][j-1], d[i-1][j-1]) + 1
end
-- d[i][j] = math.min(d[i-1][j]+1, d[i][j-1]+1, d[i-1][j-1]+cout)
end
end
local lev = d[len1+1][len2+1] -- return d[len1-1][len2] - 1
return lev, t .. viewers.ta("lev", lev)
end -- function modes.levenshtein(word1, word2)
 
function modes.levenshtein_test_1(search, word, max)
-- search = mot cherché dans la liste
-- word = un des mot de la liste
if (type(search) ~= "string") then search = "" end
local diffmaxi = modes.similar_args_diffmaxi( string.len(search) )
local len1, len2, lev, tlev, diff
local t = ""
-- t = t .. "<br>- diff: " .. viewers.ta("mot1", mot1) .. viewers.ta("mot2", mot2) .. viewers.ta("diff", diff)
t = "<br>levenshtein : "
if (not search ) or (not word) then
diff = 99
t = t .. viewers.ta("diff", diff) .. " no word. "
elseif search == word then
diff = 0
t = t .. viewers.ta("diff", diff) .. " , " .. search .. " = " .. word .. " "
else
lev, tlev = modes.levenshtein(search, word)
if (lev <= diffmaxi) then
t = t .. viewers.ta("diffmaxi", diffmaxi) .. " >= " .. viewers.ta("lev", lev) .. " <b>" .. search .. " ==> " .. word .. "</b> "
else
t = t .. viewers.ta("diffmaxi", diffmaxi) .. " >= " .. viewers.ta("lev", lev) .. " " .. search .. " / " .. word .. " "
end
diff = lev
end
return diff, t, search, word
end -- function modes.levenshtein_test_1(search, word, max)
 
function modes.levenshtein_similar_tests(t)
local memo = viewers.save_configs("modes.levenshtein_similar_tests") -- Save global configuration before eventual changes.
local t = t or ("\n* " .. viewers.form9user("modes_max_nearest_argument_msg") )
t = t .. "\n* " .. "Formula to compute the near words limit: Formule de calcul de limite des mots proches : "
local key, argsyn, arglingual, txt
local diffmaxi, tt = modes.similar_args_diffmaxi(10, t .. "diffmaxi = ")
t = t .. "\n* List of diffmaxi / lengths : "
for length = 1, 16 do -- For all lengths
diffmaxi = modes.similar_args_diffmaxi(length)
t = t .. ", " .. tostring(diffmaxi) .. " / " .. tostring(length) .. " "
end
local errors = ""
local n, tt = modes.levenshtein_test_1( "nom", "nom")
t = t .. tostring(tt)
local n, tt = modes.levenshtein_test_1( "nom", "Nom")
t = t .. tostring(tt)
local n, tt = modes.levenshtein_test_1( "top", "pot")
t = t .. tostring(tt)
local n, tt = modes.levenshtein_test_1( "ami", "amis")
t = t .. tostring(tt)
local n, tt = modes.levenshtein_test_1( "nom", "name")
t = t .. tostring(tt)
local n, tt = modes.levenshtein_test_1( "m", "mu")
t = t .. tostring(tt)
local n, tt = modes.levenshtein_test_1( "m", "mur")
t = t .. tostring(tt)
local n, tt = modes.levenshtein_test_1( "mur", "m")
t = t .. tostring(tt)
local n, tt = modes.levenshtein_test_1( "c", "C")
t = t .. tostring(tt)
local n, tt = modes.levenshtein_test_1( "c", "cf")
t = t .. tostring(tt)
local n, tt = modes.levenshtein_test_1( "c", "long")
t = t .. tostring(tt)
local n, tt = modes.levenshtein_test_1( "xxx", "")
t = t .. tostring(tt)
local n, tt = modes.levenshtein_test_1( "", "xyz")
t = t .. tostring(tt)
local n, tt = modes.levenshtein_test_1( "xxx", "xyz")
t = t .. tostring(tt)
local n, tt = modes.levenshtein_test_1( "prénom", "Prenom")
t = t .. tostring(tt)
local n, tt = modes.levenshtein_test_1( "catégorie", "Category")
t = t .. tostring(tt)
local n, tt = modes.levenshtein_test_1( "description", "Description")
t = t .. tostring(tt)
local n, tt = modes.levenshtein_test_1( "anneeDeces", "anneeNaissance")
t = t .. tostring(tt)
local n, tt = modes.levenshtein_test_1( "anoNacimiento", "anneeNaissance")
t = t .. tostring(tt)
local n, tt = modes.levenshtein_test_1( "avant-après", "après-avant")
t = t .. tostring(tt)
if errors ~= "" then t = t .. "\n* <b>levenshtein_test</b> errors = " .. viewers.styles_color_error(errors) end
viewers.restore_configs(memo, "modes.levenshtein_similar_tests") -- Restore global configurations after eventual changes.
return t
end -- function modes.levenshtein_similar_tests( res, c)
 
modes.constants = modes.constants or {}
-- Similar words search : diff on length
-- Cerrar de palabras puscadas: diff en longitud
-- Recherche de mots proches: diff sur longueur
modes.constants.near_word_search_diff_coef = 0.30 -- Access to change these constants from anywhere.
modes.constants.near_word_search_diff_const = 0.82
 
-- Maximum number of different letters between 2 argument names
-- Número máximo de letras diferentes entre 2 nombres de argumento
-- Nombre maximum de lettres différentes entre deux noms d'arguments
function modes.similar_args_diffmaxi(length, t) -- diffmaxi from length of argmt arglingual name
local coef = modes.constants.near_word_search_diff_coef or 0.30
local constant = modes.constants.near_word_search_diff_const or 0.82
local diffmaxi = math.floor( coef * length + constant )
if t then t = t .. tostring(coef) .. " * length + " .. tostring(constant) end
return diffmaxi, t
end -- function modes.similar_args_diffmaxi(length, t)
 
-- For an unknown argument, seeks the name of the closest among the known arguments translated
function modes.similar_args_list(args_known)
local list, arglingual = {}, "xxx"
local args_known = args_known or modes.args_known or p.args_known or {}
if type(args_known) ~= "table" then return "similar_args_list", 1 end
for key, argm in pairs(args_known) do -- List only all known arguments
if not tonumber(key) then -- For named arguments only
key = tostring(key)
arglingual = tostring(langs.content_translations[key])
list[key] = arglingual
end
end
return list
end -- function modes.similar_args_list(args_known)
 
-- Check if the value of an argument is among the possible values.
-- Vérifier si la valeur d'un argument est parmi les valeurs possibles.
-- local ... = modes.multiple_values(test.argm, test.argvalue, test.args_final)
function modes.multiple_values(argname, argvalue, args_final, args_known)
if type(args_final) ~= "table" then args_final = modes.args_final or {} end
local args_known = args_known or modes.args_known or p.args_known or {}
local argvalue = argvalue or args_final[argname]
local arg_values, key_values, keyword, keyval, argval, rank
local argmt = args_known[argname]
if argmt then
arg_values = langs.content_translations[argmt.arg_values] or "" -- example "no;nada;cn;50;us;70;mpf" in local language
key_values = argmt.key_values or "" -- example "no;none;cn;50;us;70;mpf" in referal english
end
if type(arg_values) == "string" and type(key_values) == "string" then
local arg_tab = mw.text.split(arg_values, ';') -- table of argmt
local key_tab = mw.text.split(key_values, ';') -- table of key
-- Default values
keyword = nil
rank = 0 -- rank of local value and key value
keyval = nil -- key value
argval = nil
if argmt and arg_values and argvalue then
for i, key in ipairs(arg_tab) do
if key == argvalue then -- Search argvalue in arg_tab
rank = i
keyval = key_tab[i] -- Return correponding keyval in key_tab
argval = argvalue
keyword = argmt.keyword
end
end
end
end
return keyword, keyval, argval, rank, arg_values
end -- function modes.multiple_values(argname, argvalue, args_final, args_known)
 
function modes.multiple_values_tests(t) -- Test: convert a string to a table of words
local t = t or "\n* Test <b>multiple_values</b> :"
local group_test = { -- events.test_group
{ argm = "region", argvalue = "inde", },
{ argm = "region", argvalue = nil, },
{ argm = "rights", argvalue = "mpf", },
{ argm = "rights", argvalue = "non", },
{ argm = "rights", argvalue = nil, },
{ argm = "sex", argvalue = "femme", },
{ argm = "sex", argvalue = "homme", },
{ argm = "sex", argvalue = "enfant", },
-- rights_values = '70,50,mpf,ONU,none', -- example
-- region = 'region', -- argument with verified multiple values
}
local tab_view = {}
tab_view.headers = viewers.form9user("argm; all values; value; keyword; keyval; argval; rank")
tab_view.test_group = group_test
tab_view.rowGroup = {}
if type(group_test) == "table" then
for i, test in ipairs(group_test) do
local keyword, keyval, argval, rank, arg_values = modes.multiple_values(test.argm, test.argvalue, test.args_final)
table.insert( tab_view.rowGroup, { tostring(test.argm or "-"), tostring(arg_values or "-"), tostring(test.argvalue or "-"), tostring(keyword or "-"), tostring(keyval or "-"), tostring(argval or "-"), tostring(rank or "-") } )
end
else t = t .. "error : multiple_values_tests has no table. " end
t = t .. tableview.new(tab_view) -- Formats a table with lines and columns.
return t
end -- function modes.multiple_values_tests(t)
 
function modes.multiple_selection(opt, selector, to_select)
-- Select items to selector containing selecting items
local t, selected_txt, selector_txt, selector_tab, to_select_txt, to_select_tab, selected_tab = "", ""
local cut = string.sub( opt, 1, 1 ) or ";"
if type(selector) == "table" then selector_tab = selector end
if type(selector) == "string" then selector_tab = mw.text.split(selector, cut, true) end
if type(to_select) == "table" then to_select_tab = clone(to_select) end
if type(to_select) == "string" then to_select_tab = mw.text.split(to_select, cut, true) end
selected_tab = {}
local k, Nsel, N, maxi, pos = 0, 0, 1, 999, nil
local reject_select = false
local equal = true
for i, selector in ipairs(selector_tab) do -- selector authorities only following selectors
if Nsel >= maxi then break end
selector = mw.text.trim(selector)
N = tonumber(selector)
if selector == "+" then -- selector all items
for key, val in pairs(to_select_tab) do
Nsel = Nsel + 1
selected_tab[key] = val
end
elseif selector == "-" then -- minus sign rejects all
reject_select = true
elseif N and N < 1 then -- minus sign rejects all
reject_select = true
elseif N and (string.sub(selector, 1, 1) == "+") then -- selector +N more items
maxi = Nsel + N
elseif N then -- selector N maximum total items
maxi = N
else -- selector ONE item from to_select_tab if it matches selector ( not - or + or +N or N )
for key, val in pairs(to_select_tab) do
local select_t, val_t = selector, val
if not viewers.is_in("U", opt) then select_t = string.lower(select_t) end -- recognize lowercase and uppercase
if not viewers.is_in("t", opt) then select_t = mw.text.trim(select_t) end -- recognize after trim
if not viewers.is_in("U", opt) then val_t = string.lower(val_t) end -- recognize lowercase and uppercase
if not viewers.is_in("t", opt) then val_t = mw.text.trim(val_t) end -- recognize after trim
equal = viewers.is_in("=", opt) -- recognize only equal string
if equal then equal = (selector == val) else equal = viewers.is_in(select_t, val_t) end
-- if viewers.is_in(selector, val) then
if equal then -- recognize if selector is equal or is inside an item from to_select_tab
t = t .. viewers.ta(selector, val)
selected_tab[selector] = val
Nsel = Nsel + 1
to_select_tab[key] = " " -- Delete the selected item to use it only once
selected_txt = selected_txt .. val .. ', '
end
end
end
end
return selected_txt, selected_tab, t
end -- function modes.multiple_selection(opt, selector, to_select)
 
function modes.multiple_selection_tests(t) -- reports examples of multiple selections of honors for some persons.
local memo = viewers.save_configs("modes.multiple_selection_tests") -- Save global configuration before eventual changes.
local t = (t or "") .. "\n* <b>multiple_selection</b> options: " .. viewers.ta("=", "equal only") .. viewers.ta("t", "not trim before and after") .. viewers.ta("U", "not lowercase and uppercase")
local function multiple_selection_test1(t, opt, selector, to_select)
local selected_txt, selected_tab, txt = modes.multiple_selection(opt, selector, to_select)
local t = t .. viewers.table_row() .. viewers.table_dat(opt) .. viewers.table_dat(selector) .. viewers.table_dat(to_select) .. viewers.table_dat( txt .. viewers.ta("selected_txt", selected_txt) )
return t, opt, selector, to_select -- , selected_txt, selected_tab
end
local opt = "; "
t = t .. "\n: selector = <b>nobel,+1,président,3,député,prix</b> signifie : sélectionner le premier, puis 1 de plus parmi les suivants, puis 3 en tout au maximum."
local head = mw.text.split( viewers.form9user("modes_multiple_selection_test_headers") , ';')
t = t .. viewers.table_head() .. viewers.table_col(head[1]) .. viewers.table_col(head[2]) .. viewers.table_col(head[3]) .. viewers.table_col(head[4])
-- Todo ? P39 = fonction = "président de Pologne, député à l'Assemblée, Prix Nehru, Nobel de la paix"
-- modes_multiple_selection_test_select = "2, nobel, president, deputy, price",
t = multiple_selection_test1( t, opt, "2; nobel; président; député; prix", "président de Pologne; député à l'Assemblée; Prix Nehru; Nobel de la paix" )
t = multiple_selection_test1( t, ";U", "2; nobel, président; député; prix", "président de Pologne; député à l'Assemblée; Prix Nehru; Nobel de la paix" )
t = multiple_selection_test1( t, opt, "3; député; prix; nobel; président", "président de Pologne; député à l'Assemblée; Prix Nehru, Nobel de la paix" )
t = multiple_selection_test1( t, ";=", "3; député; prix; nobel; président", "président de Pologne; député; Prix Nehru; Nobel" )
t = multiple_selection_test1( t, ";t", "3; député; prix; nobel; président", "président de Pologne; député; Prix Nehru; Nobel" )
t = multiple_selection_test1( t, ";", "3; prix; nobel;+1; président; député", "président de Pologne; député à l'Assemblée; Prix Nehru; Nobel de la paix" )
t = multiple_selection_test1( t, ";", "3; président; nobel; député; prix", "président de Pologne; député à l'Assemblée; Prix Nehru; Nobel de la paix" )
t = multiple_selection_test1( t, ";t", "3; député; prix; nobel; président", "président de Pologne; député; Prix Nehru; Nobel" )
t = multiple_selection_test1( t, ";U", "2; nobel; président; député; prix", "président de Pologne; député à l'Assemblée; Prix Nehru; Nobel de la paix" )
t = t .. viewers.table_end()
viewers.restore_configs(memo, "modes.multiple_selection_tests") -- Restore global configurations after eventual changes.
return t
end -- function modes.multiple_selection_tests(t)
 
function modes.verify_args_tables(_known, _source)
-- initialize all the values to "" in argmt table
-- if type(_known) ~= "table" then _known = modes.args_known end
-- if type(_source) ~= "table" then _source = modes.args_source end
if type(modes.args_known) ~= "table" then
events.add_err("modes_no_known_arguments_err")
events.add_cat("modes_no_known_arguments_i_cat")
return viewers.styles_color_error(" Internal error : no source or no known arguments ! ")
end
if type(modes.args_source) ~= "table" then
events.add_err("modes_no_source_arguments_err")
events.add_cat("modes_no_source_arguments_cat")
return viewers.styles_color_error(" Internal error : no source or no known arguments ! ")
end
return
end -- function modes.verify_args_tables(_known, _source)
 
function modes.get_args(args_known) -- Update argmt.val and argmt.src in p.args_known{}
local m, val = modes, nil
local args_known = args_known or modes.args_known or p.args_known or {} -- optional value from p.args_known = {...}
local prop, props = datas.get_item(args_known, QITEM) -- Get datas from mw.wikibase for the page.
local arguments_known = mw.clone(args_known)
local counts = { ["template"] = 0, ["import"] = 0, ["source"] = 0, ["datas"] = 0, ["final"] = 0, ["known"] = 0, }
local arguments = {}
local tt = ""
for key, argmt in pairs(arguments_known) do -- For all known parameters
if type(argmt) == "table" then
-- * These origins of arguments are in the increasig priority: <code>known</code>, <code>import</code>, <code>datas</code>, <code>template</code>, <code>interact_final</code>.
if argmt.keyword then
argmt.val = argmt.default ; argmt.src = "known" ;
counts.known = counts.known+1 ; tt = tt .. viewers.ta(argmt.src, counts.known)
end
if modes.args_import[argmt.keyword] then
argmt.val = modes.args_import[argmt.keyword] ; argmt.src = "import" ;
counts[argmt.src] = counts[argmt.src]+1 ; tt = tt .. viewers.ta(argmt.src, counts[argmt.src])
end
if prop[argmt.keyword] then
argmt.val = prop[argmt.keyword] ; argmt.src = "datas" ;
counts[argmt.src] = counts[argmt.src]+1 ; tt = tt .. viewers.ta(argmt.src, counts[argmt.src])
end--[[
if modes.args_template[argmt.keyword] then
argmt.val = modes.args_template[argmt.keyword] ; argmt.src = "template" ;
counts[argmt.src] = counts[argmt.src]+1 ; tt = tt .. viewers.ta(argmt.src, counts[argmt.src])
end--]]
if modes.args_final[argmt.keyword] then
argmt.val = modes.args_final[argmt.keyword] ; argmt.src = "final" ;
counts[argmt.src] = counts[argmt.src]+1 ; tt = tt .. viewers.ta(argmt.src, counts[argmt.src])
end
table.insert(arguments, argmt) -- insert in the arguments their own key
end
end
local labelcontent_memo, label_to_change, has_label = {}, {}, {}
for i, onearg in pairs(arguments) do -- To search the label and labelcontent arguments
if onearg.keyword == "labelcontent" then labelcontent_memo = onearg end
if onearg.keyword == "label" then label_to_change = onearg end
end
if label_to_change and labelcontent_memo then -- To search and change the label argument
label_to_change.val = labelcontent_memo.val
label_to_change.keyword = "label"
label_to_change.prop = "label"
label_to_change.src = "datas"
label_to_change.need = labelcontent_memo.need
end
arguments.label = arguments.label or arguments.labeluser or arguments.labelpage or arguments.labelcontent or arguments.labelbylang -- insure label.val
table.sort(arguments, function (a, b) return ( tostring(a.keyword) < tostring(b.keyword) ) end ) -- alphabetic sort of translated arguments
modes.arguments = arguments
return arguments, counts, tt -- With argmt.val and argmt.src
end -- local arguments = modes.get_args(args_known) -- Update argmt.val and argmt.src in p.args_known{}
 
function modes.get_args_report(t) -- Update modes.get_args()=args_known
-- List of twice-view cases : in CentralManual modes.get_args_report ; not in ModuleCentral test mode ; yes in ModuleCentral "Doc with function from string". Search ▼
local memo = viewers.save_configs("modes.get_args_report") -- Save global configuration before eventual changes.
local t = t or "\n* <b>modes.get_args(args_known)</b>: Update argmt.val and argmt.src in p.args_known{}."
t = t .. '\n* List of twice-view cases : in CentralManual modes.get_args_report ; not in ModuleCentral test mode ; yes in ModuleCentral "Doc with function from string". Search ▼'
local arguments, counts, tt = modes.get_args(p.args_known) -- Update argmt.val and argmt.src in p.args_known{}
local tab_view = { -- Group datas and options for a table view with lines and columns.
test_group = arguments, -- Use default cases.
rowGroup = {},
form_one_case = function(case) -- Convert a case from test_group to rowGroup.
return { case.key, case.val or "-", case.typ, case.need, case.keyword, case.syn, case.prop, case.format, case.src or "-", }
end,
title_memo = "modes_get_args_report_title", -- "modes.get_args() Values of the arguments in p.args_known{}.", -- en
headers = "modes_args_known_report_headers", -- "key; val; type; need; keyword; syn; prop; format; source"
} -- drop_box.new(
t = t .. "<br/>" .. tableview.new(tab_view) -- Formats a table view with lines and columns.
t = t .. viewers.ta("args_known", lua_table.level_count(p.args_known) ) .. viewers.ta("arguments", lua_table.level_count(arguments) )
t = t .. "\n* Counts for all args_known{}."
for count, n in pairs(counts) do -- For all known parameters
t = t .. viewers.ta(tostring(count), n)
end
t = t .. "\n* Track argmt.keyword = n : " .. tt
t = t .. "\n* Final content of arguments{}."
for key, argmt in pairs(arguments) do -- For all known parameters
t = t .. viewers.ta(tostring(key), argmt.kw)
end
viewers.restore_configs(memo, "modes.get_args_report") -- Restore global configurations after eventual changes.
return t
end -- t = t .. modes.get_args_report(t) -- Update modes.get_args()=args_known
 
function modes.mix_args(mix, mode_name, args_template) -- Mix arguments from options_for_modes, args_template S170710mix
local mix = mix or {}
modes.mix = mix
-- Get basic values
modes.frame = mw.getCurrentFrame()
modes.args_template = modes.frame:getParent().args
-- mix.args_template = args_template or mix.args_template or modes.args_template or {}
mix.all_args = {}
local function mix_args(args)
if (type(args) ~= "table") then args = {} end
for key, argmnt in pairs(args) do mix.all_args[key] = argmnt end -- get arguments named or in order.
end
-- actual steps to mix -- begin with least priority
mix_args(modes.args_template) -- already known, or default values args_template have the lowest priority
mix_args(mix.args_template)
mix_args(mix.args_import)
mix_args(args_template) -- direct args_template have the highest priority
-- end with most priority
mix.args = mix.all_args
return mix
end -- local mix = modes.mix_args(mix, mode_name, args_template)
 
function modes.mix_modes(mix, mode_name, args_template) -- Mix some modes from several origins
mix = mix or {}
mix.args_template = args_template or modes.args_template or mix.args_template
if (type(mix.args_template) ~= "table") then default = "read" end
mix.mode_name = mix.args_template.mode or mix.args_template[1] or mode_name or "read"
modes.args_template = mix.args_template
modes.mode_name = mix.mode_name
return mix
end -- local mix = modes.mix_modes(mix, mode_name, args_template)
 
function modes.mix_options(mix, old_group, new_group) -- Mix 2 groups of options from diverse origins S170710mix
mix = mix or {}
if (type(old_group) ~= "string") then old_group = "" end
if (type(new_group) ~= "string") then new_group = "" end
local old_group_tab = mw.text.split(old_group, " ", true)
local new_group_tab = mw.text.split(new_group, " ", true)
local all_group_tab = mw.clone(old_group_tab) -- do not disturb old_group_tab
for i, option in ipairs(new_group_tab) do table.insert(all_group_tab, option) end -- add new with old options
local no_options_tab, active_options_tab = {}, {}
for i, option in ipairs(all_group_tab) do -- form 2 groups of no_options and active_options
local no_t, opt_t = string.sub( option, 1, 2), (string.sub( option, 3) or "") -- no prefix and option without no
if ( no_t == "no" )
then no_options_tab[option] = opt_t -- form a group of no_options, perhaps to delete an active option
else active_options_tab[option] = option -- form a group of active_options, perhaps to delete
end
end
local keep_group_tab = mw.clone(all_group_tab)
-- Reject no_options to keep active_options
for i, option in pairs(active_options_tab) do
if ( no_options_tab[option] ) then
active_options_tab[option] = nil -- form a group of active_options, perhaps to delete
end
end
mix.active_options = table.concat(active_options_tab, " ")
mix.no_options = table.concat(no_options_tab, " ")
return mix
end -- active_options = modes.mix_options(old_group, new_group) -- S170710mix
 
function modes.init_args_mode_options(mix, mode_name, args_template) -- Imports and mixes args mode and options from template and invoke
-- Guideline: Any combination of options can define a mixture of options to modify options.
-- This function allows any module to modify this process.
-- The default process gives the priority to options from arguments.
-- Each "option" can be removed by the option "nooption". Options starting with "no" are disabled.
-- Init basic values
local mix = mix or {}
modes.mix = mix
mix.mode_name = mode_name or mix.mode_name or modes.mode_name
-- Steps to mix modes values
--
-- Once run mix_args and mix_modes, in case a mode option would change the mode.
mix = modes.mix_args(mix, mode_name, args_template) -- Mix arguments from options_for_modes, args_template
mix = modes.mix_modes(mix, mode_name, args_template) -- Mix some modes from several origins S170710mix
modes.options = modes.options_for_modes[modes.mode_name] -- options from mode
--
-- Once repeat mix_args and mix_modes, in case the mode changes through them.
mix = modes.mix_args(mix, mode_name, args_template) -- Mix arguments from options_for_modes, args_template
mix = modes.mix_modes(mix, mode_name, args_template) -- Mix some modes from several origins S170710mix
modes.options = modes.options_for_modes[modes.mode_name] -- options from mode
mix = modes.mix_options(mix, modes.options, modes.args_template.options ) -- Mix options from template
modes.options = mix.options
--
-- activate init_args_mode_options
modes.list_invoke = mix.list_invoke or modes.list_invoke
modes.list_template = mix.list_template or modes.list_template
modes.args_template = mix.args_template or modes.args_template
modes.mode_template = mix.mode_template or modes.mode_template or modes.args_template.mode
modes.active_options = mix.active_options or modes.active_options
modes.no_options = mix.no_options or modes.no_options or table.concat(no_options_tab, " ")
modes.options_template = mix.options_template or modes.options_template or modes.args_template.options
modes.mode_name = mix.mode_name or modes.mode_name
modes.options_for_modes = mix.options_for_modes or modes.options_for_modes
modes.options = mix.options or modes.options
return mix
end -- modes.args_mixed = function modes.init_args_mode_options(mix, mode_name, args_template)
 
function modes.args_mixer(args_template) -- S170703amo
-- Guideline: Any combination of templates can define a mixture of arguments to modify arguments.
-- This function allows any module to modify this process.
-- The default process gives the priority to templates arguments.
local t = "\n* <b>modes.args_mixer()</b> Import and mix arguments from templates and invoke."
local args_template = args_template or modes.args_template or {}
t = t .. "\n* " .. viewers.ta("\n* args_template", args_template)
if (type(args_template) == "table") then
for arg_key, argment in pairs(args_template) do
args_template[arg_key] = argment -- sought args from templates
args_template.QITEM = args_template.QITEM or args_template.itemid -- temporary debug the test page
t = t .. viewers.ta(arg_key, argment)
if arg_key == "itemid" then t = t .. viewers.ta("QITEM", argment) end -- temporary debug the test page
end
end
args_template.QITEM = args_template.QITEM or args_template.itemid -- temporary debug the test page
viewers.TITL = tracker.initadd({ ["name"] = "TITL", limit = 2, }) -- Initialize a track
TITL.add(TITL, 1, "args_mixer", args_template ) -- TITL.t
-- Activate the sought args
modes.args_mixed = args_template
t = t .. viewers.ta("modes.args_mixed count", lua_table.count_all(modes.args_mixed) )
return modes.args_mixed
end -- local t = modes.args_mixer(args_template)
 
function modes.modes_mixer(args_template) -- S170703amo
local t = ""
args_template = args_template or modes.args_template
t = t .. viewers.ta("modes.args_template[1]", modes.args_template[1]) .. viewers.ta("modes.args_template.mode", modes.args_template.mode)
-- Activate the sought mode
modes.mode_name = modes.args_template.mode or modes.args_template[1]
modes.args_mixed.mode_name = modes.mode_name
t = t .. viewers.ta("sought mode_name", modes.mode_name)
return t, modes.mode_name
end -- local t = modes.modes_mixer(args_template)
 
function modes.options_mixer(args_template) -- S170703amo
-- Guideline: Any combination of options can define a mixture of options to modify options.
-- This function allows any module to modify this process.
-- The default process gives the priority to options from arguments.
-- Each option can be deleted by the nooption option. Then options cannot begin by "no" chars.
--
-- First, import args, then mix modes and options.
local t = "\n* <b>modes.options_mixer()</b> Import and mix options from template."
-- modes.options = " docdata docmin docdef docmax docline docview docafter docnotice docsrc: " -- for documentation
modes.options_template = modes.args_template.options or " catview nobox1 doclist docdata nodocline"
modes.options_all = modes.options_template .. " " .. modes.options_invoke
t = t .. viewers.ta("\n* options_template", modes.options_template )
t = t .. viewers.ta("\n* options_invoke", modes.options_invoke )
modes.options_tab = mw.text.split(modes.options_all, " ", true)
local opt_pretab, opt_tab, noopt_tab, opt_list = {}, {}, {}, " "
for i, option in pairs(modes.options_tab) do -- Build the subgroup table from the groupname string
local no_t, opt_t = string.sub( option, 1, 2), string.sub( option, 3)
if ( no_t == "no" )
then noopt_tab[option] = opt_t -- no_option to delete an active option
else opt_pretab[option] = option end -- active option
end
local lst = "" ; for key, val in pairs(modes.options_tab) do lst = lst .. viewers.ta(key, val ) end
t = t .. viewers.ta("\n* #modes.options_tab", lua_table.count_all( modes.options_tab ) ) .. viewers.ta("options_tab", lst )
local lst = "" ; for key, val in pairs(opt_pretab) do lst = lst .. viewers.ta(key, val ) end
t = t .. viewers.ta("\n* #opt_pretab", lua_table.count_all( opt_pretab ) ) .. viewers.ta("opt_pretab", lst )
local lst = "" ; for key, val in pairs(noopt_tab) do lst = lst .. viewers.ta(key, val ) end
t = t .. viewers.ta("\n* #noopt_tab", lua_table.count_all( noopt_tab ) ) .. viewers.ta("noopt_tab", lst )
opt_tab = mw.clone(opt_pretab) -- unknown arguments to detect are source arguments without known arguments.
for option, opt_t in pairs(noopt_tab) do -- Build the subgroup table from the groupname string
opt_tab[opt_t] = nil -- no_option delete an active option
end -- active options are in opt_tab
local lst = "" ; for key, val in pairs(opt_tab) do lst = lst .. viewers.ta(key, val ) end
t = t .. viewers.ta("\n* #opt_tab = " .. lua_table.count_all( opt_tab ) ) .. viewers.ta("opt_tab whitout no", lst )
-- Activate the sought options
local template_options = " "
for key, val in pairs(noopt_tab) do template_options = template_options .. " " .. val end
modes.template_options = template_options
t = t .. viewers.ta("modes.template_options", modes.template_options)
return t, modes.template_options
end -- local t = modes.options_mixer(args_template)
 
function modes.import_args_mode_options(args_template) -- Import and mix args mode and options from template and invoke -- S170703amo
-- Guideline: Any combination of options can define a mixture of options to modify options.
-- This function allows any module to modify this process.
-- The default process gives the priority to options from arguments.
-- Each option can be deleted by the nooption option. Then options begining by "no" are forbiden.
-- local fenv = getfenv() -- Not activated in fr.wikisource.org by allowEnvFuncs in the engine configuration.
if (type(modes.options_for_modes) ~= "table") then modes.options_for_modes = {} end
if (type(modes.args_template) ~= "table") then modes.args_template = {} end
if (type(args_template) == "table") then args_template = modes.args_template end
-- Import args mode options
local t = "t= * * * "
modes.frame = mw.getCurrentFrame() -- frame or modes.frame or
modes.args_template = modes.frame:getParent().args
args_template = modes.args_template
modes.mode_name = args_template.mode or args_template[1] or "read"
modes.args_mixed = modes.args_mixer(args_template)
modes.modes_mixer(args_template)
modes.options_mixer(args_template)
return modes.args_mixed
end -- local t = modes.import_args_mode_options(args_template)
 
-- For an unknown argument, seeking the name of the nearest argument among the known arguments
function modes.similar_args_search(search, list)
local dist, lengths, tlev = 9, 0
local trouve1, trouve2, trouve3 = nil, nil, nil
local min1, min2, min3 = 99, 99, 99
if (type(search) ~= "string") then search = "" end
local diffmaxi = modes.similar_args_diffmaxi( string.len(search) )
local t = ", " .. tostring(diffmaxi) .. " / " .. tostring(length) .. " "
for key, arglingual in pairs(list) do
-- Search the most similar and same length. Buscar las más similares y la misma longitud. Chercher le plus ressemblant et la même longueur.
dist, tlev = modes.levenshtein(search, arglingual)
if (dist <= min1) then
trouve3 = trouve2
min3 = min2
trouve2 = trouve1
min2 = min1
min1 = dist
trouve1 = tostring(arglingual)
end
end
t = t .. "<br>" .. viewers.ta("cherche", cherche) .. viewers.ta("trouve1", trouve1) .. viewers.ta("min1", min1) .. viewers.ta("trouve2", trouve2) .. viewers.ta("min2", min2) .. " " .. t
if trouve1 and min1 == 0 then t = t .. viewers.styles_color_wikidata(viewers.ta("connu", trouve1)) end
if trouve1 and min1 <= diffmaxi then t = t .. viewers.styles_color_wikidata(viewers.ta("min1 "..min1.."<="..diffmaxi, trouve1)) end
if trouve2 and min2 <= diffmaxi then t = t .. viewers.styles_color_wikidata(viewers.ta("min2 "..min2.."<="..diffmaxi, trouve2)) end
if trouve3 and min3 <= diffmaxi then t = t .. viewers.styles_color_wikidata(viewers.ta("min3 "..min3.."<="..diffmaxi, trouve3)) end
return trouve1, min1, trouve2, min2, t
end -- function modes.similar_args_search(search, list)
 
function modes.import_arguments(args_known, args_source, content_translations, args_wikidata) -- Import all arguments from template, or invoke, or wikidata
local args_known = args_known or modes.args_known or p.args_known or {} -- optional value from p.args_known = { }
modes.args_known = args_known
local args_wikidata = args_wikidata or modes.args_wikidata or p.args_wikidata or {} -- optional value from p.args_known = { -- }
modes.args_wikidata = args_wikidata
local args_import = args_import or modes.args_import or {} -- optional value from p.args_known = { }
modes.args_import = args_import
-- default parameters
if type(args_source) ~= "table" then args_source = modes.args_source end
content_translations = content_translations or langs.content_translations
-- Mix args_source in args_import, with priority for present args_source.
for key, argm in pairs(modes.args_template) do modes.args_import[key] = argm end
local err = nil
local cats = ""
modes.nowyear = tonumber(os.date("%Y") ) -- now_date = os.date("%Y-%m-%d %H:%M:%S")
ARGS.add(viewers.ARGS, 1, "import_arguments", { ["argsknown"] = args_known, ["argssource"] = args_source, ["argswikidata"] = args_wikidata, ["nowyear"] = modes.nowyear, } ) -- ARGS.t
modes.import_arguments_err = ""
modes.import_arguments_track = ""
local err = modes.verify_args_tables(args_known, args_source)
if err then return args_import, err end
---------------------------------------
langs.main_i18n = versions.memo_i18n
local i18n = versions.memo_i18n or versions.main_i18n
local err, er1, t2 = "", "", ""
local key, argval, argid = "kkk", "xxx", ""
local argknw, arglingual, argreceived = nil, "", ""
local argm = {} -- used arguments
local key_N, key_NN = 0, 0
local arg_found, rec_found, already_found = false, false, false
-- initialize all arguments to "not found" before import them from p.args_known = { -- }
for key_known, argm in pairs(args_known) do
if type(argm) == "table" then argm.found = 0 end
end
modes.args_unknown = mw.clone(modes.args_source) -- unknown arguments to detect are source arguments without known arguments.
local key_known_init = nil
local argm_syn = nil
-- Get datas from mw.wikibase for the page and Mix datas in modes.args_import.
datas.prop, datas.props = datas.get_item(modes.args_unknown, QITEM) -- Get datas from mw.wikibase for the page.
-- Try to read all known arguments. Intentar leer todos los argumentos conocidos. Essayer de lire tous les arguments connus.
for key_known, argm in pairs(args_known) do
if type(argm) == "table" then
argm.src = nil
argm.trk = " n"
key_known_init = key_known
-- first initialise each known argument
modes.import_arguments_track = tostring(modes.import_arguments_track) .. " - " .. tostring(key_known)
argm_syn = args_known[argm.keyword]
ARGS.add(viewers.ARGS, 1, "args_known for", { key = key_known, Nargm = lua_table.level_count(argm), syn = argm.syn, } ) -- ARGS.t
if argm.syn == 2 then
-- Name an unnamed argument, positional, by its synonym. Nommer un argument non nommé, numéroté, par son synonyme.
-- Rename a named argument, by its synonym. Renommer un argument nommé, par son synonyme.
-- argm_orig = key_known -- DEBUG
key_known = argm.keyword
-- synonyms are defined with the stamp "syn = 2", then here stamp the basic argument with "syn = 1".
args_known[key_known].syn = 1
argm = args_known[key_known] -- new variable argm
argm.src = nil
argm.trk = "s"
modes.import_arguments_track = tostring(modes.import_arguments_track) .. ">" .. tostring(key_known)
end
-- initialise an argument.
arg_found = false
argval = nil
argm.trk = argm.trk.."="
-- Import a wikidata argument. Importer un argument wikidata
if type(datas.props) == "table" and datas.props[key_known] then
argm["val"] = datas.props[key_known]
argval = datas.props[key_known]
argm.src = "wd"
argm.trk = argm.trk.."w"
if argm_orig then
-- args_known[argm_orig].src = "wd"
-- args_known[argm_orig].trk = (args_known[argm_orig].trk or "").."w"
end
arg_found = true
modes.import_arguments_track = modes.import_arguments_track .. "=<b>" .. tostring(argval) .. "</b> "
end
-- import a source argument. importer un argument source.
arglingual = content_translations[key_known]
modes.import_arguments_track = modes.import_arguments_track .. "/" .. tostring(arglingual)
if arglingual then -- The argument name has a translation in wiki language
if args_source[arglingual] and not modes.args_source[arglingual] then -- the argument come from template else from invoke else from wikidata
-- if argval then -- the argument value exist and come from template else from invoke else from wikidata
argval = args_source[arglingual]
argm.src = "args"
argm.trk = argm.trk.." a"
arg_found = true
local arg_values = content_translations[argm.arg_values]
if argm.keys_values and arg_values then
-- The argument is limited to multiple values with arg_values and keys_values, and the values are defined.
local pos = string.find(arg_values, argval)
if pos then
-- The value of the argument is in the multiple values of the arguments.
-- argm.src = "args"
argm.trk = argm.trk.."m"
-- arg_found = true
if argm_orig then
-- args_known[argm_orig].src = "args"
-- args_known[argm_orig].trk = (args_known[argm_orig].trk or "").."d"
end
else
events.add_err("modes_args_values_err", argm.keyword, argval, arg_values)
-- argval = nil
end
else
-- argm.src = "args"
argm.trk = argm.trk.."c"
-- arg_found = true
if argm_orig then
-- args_known[argm_orig].src = "args"
-- args_known[argm_orig].trk = (args_known[argm_orig].trk or "").."c"
end
end
modes.import_arguments_track = modes.import_arguments_track .. "=<b>" .. tostring(argval) .. "</b> "
end -- not args_source[arglingual] is normal
else -- internal error and category
-- events.add_err("versions_module_miss_i18n_trad_err", key_known)
-- Generate a category to list all modules with missing translation
cats = cats .. events.add_cat( "versions_err_module_miss_i18n_cat" )
end
key_N = tonumber(key_known_init)
if key_N and not args_known[key_N] then
events.add_err("modes_too_unnamed_arguments_err", key_N, argval)
events.add_cat("versions_with_usage_error_cat")
end
-- Record the argument. Guarde el argumento. Enregistrer l'argument.
if arg_found == true then
argm.found = argm.found + 1 -- count redifined arguments
argm.val = argval
args_import[key_known] = argval -- received international arguments table
if modes.args_unknown[arglingual] then
modes.args_unknown[arglingual] = nil -- unknown arguments are source arguments without known arguments.
end
end
end
end
-- modes.import_arguments: after import itself, some surrounding checks.
for key_known, argm in pairs(args_known) do -- For all known arguments
-- Redefined arguments. Argumentos redefinieron. Arguments redéfinis.
-- synonyms are defined with the stamp "syn = 2", then here stamp the basic argument with "syn = 1".
if argm.keyword and args_known[argm.keyword] and args_known[argm.keyword].syn then -- if the argument is a synonym, increase the found level
if argm.found and (argm.found > 2) then
events.add_err("modes_value_re_defined_err", (argm["keyword"] or "**") ) --.. ">2")
cats = cats .. events.add_cat("versions_with_usage_error_cat")
end
else
if argm.found and (argm.found > 1) then
events.add_err("modes_value_re_defined_err", (argm["keyword"] or "**") ) --.. ">1")
cats = cats .. events.add_cat("versions_with_usage_error_cat")
end
end
-- need = 0 not necessary argument
-- need = 1 necessary from argument
-- need = 2 necessary from argument or module interaction
-- Missing Arguments. Argumentos que faltan. Arguments manquants.
if argm.need and (argm.need == 1) and (not argm.val) then
arglingual = content_translations[key_known]
if arglingual then
events.add_err("modes_need_arg_value_err", arglingual)
cats = cats .. events.add_cat("versions_with_usage_error_cat")
end
end
end
-- All arguments sources have they been used?
-- modes.args_unknown -- unknown arguments are source arguments without known arguments.
local args_list = modes.similar_args_list(modes.args_known)
for key_src, val_src in pairs(modes.args_unknown) do -- For all unknown source arguments. function tableview.new(
arglingual = tostring(key_src) -- look for the translated argument
key_N = tonumber(arglingual)
-- No error for unmamed arguments
if not key_N then
events.add_err("modes_unknown_argument_err", arglingual, val_src)
cats = cats .. events.add_cat("versions_with_usage_error_cat")
-- "Error: parameter <b>%1</b> is unknown in this template. Check the name or flag this gap.",
-- Look for a known and similar name argument
local diffmaxi = modes.similar_args_diffmaxi( string.len(arglingual) )
local trouve1, min1, trouve2, min2 = modes.similar_args_search(arglingual, args_list)
if min1 and (min1 <= diffmaxi) then
events.add_err("modes_nearest_argument_err", trouve1)
end
if min2 and (min2 <= diffmaxi) then
events.add_err("modes_nearest_argument_err", trouve2)
end
end
key_N = tonumber(arglingual)
if key_N and not args_known[key_N] then
events.add_err("modes_too_unnamed_arguments_err", key_N, val_src)
events.add_cat("versions_with_usage_error_cat")
end
end -- For all unknown source arguments.
modes.nowyear = tonumber(os.date("%Y") ) -- now_date = os.date("%Y-%m-%d %H:%M:%S")
modes.args_import.nowyear = modes.nowyear
modes.args_import = args_import
return modes.args_import
end -- modes.args_import = modes.import_arguments(args_known, args_source, content_translations, args_wikidata)
 
function modes.args_unknown_report(t) -- Report unknown arguments.
local t = t or "\n* modes.args_unknown_report(t) Report main unknown arguments."
local tab_view = { -- Group datas and options for a table view with lines and columns.
test_group = modes.args_unknown, -- Use default cases.
rowGroup = {},
form_one_case = function(case) -- Convert a case from test_group to rowGroup.
return { case.i, case.where, case.save, }
end,
title_memo = "modes_args_unknown_report_title",
headers = "modes_args_unknown_report_headers",
headers = "i;where;save",
}
t = t .. "<br/>" .. tableview.new(tab_view) -- Formats a table view with lines and columns.
return t
end -- t = t .. modes.args_unknown_report(t) -- Report unknown arguments.
-- res = res .. drop_box.new(selector, "modes_args_unknown_report_title", modes.args_unknown_report)
 
-- - - - ------------------ - - - - ---------------------------------
-- Argts : Generate documentation. Generar documentación. Générer la documentation.
-- - - - ------------------ - - - - ---------------------------------
 
function modes.generDoc(opt, args_final, module_name)
-- List of paramètres for the module documentation
-- Lister des paramètres pour la documentation du module
-- "docview" or ":" ajouter le panneau de documentation
-- "docmin" quelques paramètres de base
-- "docdef" seulement les paramètres définis, ayant une valeur non nulle
-- "docmax" tous les paramètres connus
-- "docnotice" generer les documentations des notices
-- "docline" mettre tous les paramètres sur une seule ligne
-- "docsrc" mettre les paramètres en couleurs selon les sources
-- modes.options = " docdata docmin docdef docmax docline docview docafter docnotice docsrc: " -- for documentation
-- modes.options = " erron noerr nobox1 nocatview " -- without normal result
-- modes.options = " debug tests en es fr " -- for debug or enforce language
-- Option nocatview means "Do not categorize and do not show categories."
local args_known = modes.args_known
local err = modes.verify_args_tables(args_known, modes.args_source)
if err then return err end
if type(module_name) ~= "string" then module_name = modes.module_name end
if type(module_name) ~= "string" then module_name = modes.frame:getTitle() end -- main module, example "Auteur"
if type(module_name) ~= "string" then module_name = "Central" end
local n, t, val = 0, "", ""
if type(args_final) ~= "table" then t = t.."err_args_final="..type(args_final).."<br>" end -- optional arguments
if type(args_final) ~= "table" then args_final = modes.args_final end -- optional arguments
local key, argknw, argval, arglingual = "", "", ""
local lst = true
local lst_doc, lst_1, lst_t = {}, {}, ""
for key, parm in pairs(args_final) do -- for all known arguments
val = ""
n = tonumber(key)
if n then key = tostring(parm["keyword"]) end -- key for unnamed arguments, in numeric sort
argknw = args_known[key]
arglingual = viewers.form9user(arglingual) -- multilingual name of the argmt in the template
if arglingual == "nil" then arglingual = key end -- if argument is translatable
val = parm -- tostring(args_import[key])
if not viewers.is_def(val) then val = "" end
lst = false
opt = opt .. " docdef " -- optional display
if modes.option("docmin", opt) and argknw and (argknw["need"] > 0) then lst = true end
if modes.option("docdef", opt) and (val ~= "") then lst = true end
if modes.option("docmax", opt) then lst = true end
if not args_known[key] then lst = false end
if key and args_known[key] and args_known[key].typ == "sys" then lst = false end
if lst then t = t .. viewers.tam( viewers.form9user(key), parm) end -- list if found and selected
end
t = "\n* " .. module_name .. " " .. t -- .. "}}" -- <br>
return t
end -- function modes.generDoc(opt, args_final, module_name)
 
function modes.sources_of_datas_colors()
local res = ""
if modes.docolor then -- Document the data sources by colors
local datas_sources_of_datas = viewers.form9user("datas_sources_of_datas")
-- datas_sources_of_datas = "Informations from: /Wikidata, /template or module, /other, /warning, /error",
local splitxt = mw.text.split(datas_sources_of_datas, "/", true)
res = res .. splitxt[1] .. " <b> " .. viewers.styles_color_wikidata(splitxt[2]) .. viewers.styles_color_colargs(splitxt[3]) .. viewers.styles_color_normal(splitxt[4]) .. viewers.styles_color_warning(splitxt[5]) .. viewers.styles_color_error(splitxt[6]) .. ".</b> <br>"
end
return res
end -- function modes.sources_of_datas_colors()
 
function modes.module_init(frame) -- Get modes.args_source with modes.args_source
local frame = frame or modes.frame or mw.getCurrentFrame()
modes.frame = frame
modes.nowyear = tonumber(os.date("%Y") ) -- UTC now_date = os.date("%Y-%m-%dT%H:%M:%S")
-- Mix arguments from {{#invoke:}}, then arguments from the prioritary template which replace ones from {{#invoke:}}.
local v2, nn, ni = 0, 0, 0
local args_tab, mode = {}
local templat = frame:getParent().args -- arguments from template
-- Mix invoked modified arguments from prioritary template arguments.
-- Argument 1 from template become the mode in #invoke. Other i arguments must be shifted.
local invoked = frame.args -- arguments from #invoke module
local args_tab = mw.clone(invoked) -- less priority than template
for key, val in pairs(args_tab) do -- invoked arguments can modify #invoke arguments.
local key = mw.text.trim(key)
local val = mw.text.trim(val)
local i = tonumber(key)
if i then
if i == 1 then
mode = val -- mode = template[1]
args_tab.mode = val
else args_tab[i-1] = val end -- transmit other unnamed arguments template[i], but shifted because the mode is in template[1]
else args_tab[key] = val end -- transmit any named template arguments template. Even the mode, which replace template[1], behind.
end
local args_tab = mw.clone(templat) -- template have the priority and can itself #invoke arguments
for key, val in pairs(templat) do -- template arguments can modify #invoke arguments.
local key = mw.text.trim(key)
local val = mw.text.trim(val)
local i = tonumber(key)
if i then
if i == 1 then
mode = val -- mode = template[1]
args_tab.mode = val
else args_tab[i-1] = val end -- transmit other unnamed arguments template[i], but shifted because the mode is in template[1]
else args_tab[key] = val end -- transmit any named template arguments template. Even the mode, which replace template[1], behind.
end
modes.args_source = args_tab -- args from: modes.module_init() -- Get modes.args_source with modes.args_source
-- modes.args_source = modes.argsConfigIinit(modes.args_source) -- Extract and put apart args_source from args_source
-- Default values of main module version.
if versions.main_versions then
versions.main_versions.versionName = versions.main_versions.versionName or "Central0"
versions.main_versions.versionNumber = versions.main_versions.versionNumber or "0.0.0"
versions.main_versions.versionDate = versions.main_versions.versionDate or "2018-06-15"
end
return modes.args_source
end -- modes.args_source = function modes.module_init(frame)
 
function modes.init_options_for_modes(frame, options_for_modes, mode_name)
local res = "\n* modes.init_options_for_modes()"
frame = frame or mw.getCurrentFrame()
modes.frame = frame
modes.options_for_modes = options_for_modes or modes.options_for_modes
modes.mode_name = mode_name or modes.mode_name or "read"
modes.mode_options = modes.options_from_mode(modes.mode_name, modes.options_for_modes)
return res
end -- function modes.init_options_for_modes(frame, options_for_modes, mode_name)
 
function modes.get_arg_mode(mode_name, source_key, lang, args_source) -- Select the actual mode from some sources
local mode_key = "mode"
local args_source = args_source or modes.args_source
if type(args_source) == "table" -- and type(args_source[source_key]) == "string"
then mode_name = mode_name or args_source[source_key] or "read"
else modes.mode_name = mode_name or modes.mode_name or "read" end
return mode_name, source_key, lang, args_source
end -- function modes.get_arg_mode(mode_name, source_key, lang, args_source)
 
function modes.all_categories_list(t) -- List all eventual categories of this wiki
local memo = viewers.save_configs("modes.all_categories_list") -- Save global configuration before eventual changes.
local t = "\n* " .. (t or viewers.form9user("modes_all_categories_list_title") )
for key, txt in pairs(versions.memo_i18n[langs.user_lang]) do
if viewers.is_in("cat_", key) or viewers.is_in("_cat", key) then
txt = viewers.form9user(key, "**", "**", "**", "**", "**", "**")
t = t .. "<br>" .. viewers.ta(key, txt)
end
end
viewers.restore_configs(memo, "modes.all_categories_list") -- Restore global configurations after eventual changes.
return t
end -- function modes.all_categories_list(t)
 
function modes.all_errors_list(t) -- List detectable errors of this module
local t = "\n* " .. (t or viewers.form9user("modes_all_errors_list_title") )
for key, txt in pairs(versions.memo_i18n[langs.user_lang] or modes.modes_args.userlang) do
if viewers.is_in("err_", key) or viewers.is_in("_err", key) then
txt = viewers.form9user(key, "**", "**", "**", "**", "**", "**")
t = t .. "<br>" .. viewers.ta(key, txt)
end
end
return t
end -- function modes.all_errors_list(t)
 
function modes.list_all_args_main(t, args_known) -- List of all accepted arguments
local memo = viewers.save_configs("modes.list_all_args_main") -- Save global configuration before eventual changes.
local t = "\n* " .. (t or viewers.form9user("modes_list_all_args_main_title") )
local args_known = args_known or modes.args_known or p.args_known or {}
if type(args_known) ~= "table" then return (t .. "The known arguments table modes.args_known misses.") end
t = t .. viewers.ta("args N", lua_table.level_count(args_known) )
local descr, description = "", ""
local args = mw.clone(args_known)
local arglst = {}
for key, elem in pairs(args) do
elem.key = tostring(key)
descr = key .. "_descr" -- key for description of an argument
elem.description = langs.user_translations[descr] or "**missing translation**"
elem.user_lang_key = langs.user_translations[elem.key] or "**missing key**"
elem.user_lang_keyword = langs.user_translations[elem.keyword] or "**missing keyword**"
-- elem.base_id = elem.base_id
-- elem.base_base = elem.base_base
-- elem.not_type = elem.not_type
table.insert(arglst, elem)
end -- insert in the arguments their own key
table.sort(arglst, function (a, b) return (a.user_lang_key < b.user_lang_key) end ) -- alphabetic sort of translated arguments
local gr_sys, gr_config, gr_need, gr_other, gr_authority = {}, {}, {}, {}, {}
for i, elem in ipairs(arglst) do -- group arguments in some groups
if elem.need == 1 or elem.need == 2 then table.insert(gr_need, elem)
elseif elem.typ == "sys" then table.insert(gr_sys, elem)
elseif elem.typ == "config" then table.insert(gr_config, elem)
elseif elem.base_base then table.insert(gr_authority, elem)
else table.insert(gr_other, elem) end
end
local needed = viewers.styles_small_caps(viewers.form9user("modes_needed_to_verify"))
local function list_group( group, needed )
needed = needed or ""
local t = ""
for key, elem in pairs(group or {}) do
if elem.syn
then t = t .. "<br>* <b>" .. tostring(elem.user_lang_key) .. "</b> => <b>" .. elem.user_lang_keyword .. "</b> : " .. needed .. " " .. tostring(elem.description) -- .. elem.lev_arg_txt
else t = t .. "<br>* <b>" .. tostring(elem.user_lang_key) .. "</b> : " .. needed .. " " .. tostring(elem.description) end
end
return t
end
t = t .. "<br><br>* <b>" .. viewers.form9user("modes_list_needed_args") .. "</b> " .. list_group( gr_need, needed )
t = t .. "<br><br>* <b>" .. viewers.form9user("modes_list_all_other_args") .. "</b> " .. list_group( gr_other )
t = t .. "<br><br>* <b>" .. viewers.form9user("list_all_authorities") .. "</b> " .. list_group( gr_authority )
t = t .. "<br><br>* <b>" .. viewers.form9user("modes_list_all_config_arguments") .. "</b> " .. list_group( gr_config )
t = t .. "<br><br>* <b>" .. viewers.form9user("modes_list_all_system_arguments") .. "</b> " .. list_group( gr_sys )
viewers.restore_configs(memo, "modes.list_all_args_main") -- Restore global configurations after eventual changes.
return t
end -- function modes.list_all_args_main(t, args_known) -- modes_list_all_args_main_title for main
 
function modes.recursive_normal( recursiveLevel_in, recursive_limit_in, modes_recursiveLevel_err ) -- Normalize recursiveLevel and recursive_limit
-- recursiveLevel, recursive_limit, recursiveLevel_err == modes.recursive_normal(recursiveLevel, recursive_limit) -- typical use
-- default modes.recursive_limit
local recursiveLevel, recursive_limit = recursiveLevel_in, recursive_limit_in
local recursiveLevel_err = recursiveLevel_err or""
if type(modes_recursiveLevel_err) ~= "string" then modes_recursiveLevel_err = "modes_recursiveLevel_err" end
if type(modes.recursive_limit) ~= "number" then modes.recursive_limit = 11111 end
if modes.recursive_limit < 1 then modes.recursive_limit = 11111 end
if type(recursive_limit) ~= "number" then recursive_limit = modes.recursive_limit end
-- If recursive_limit is defined, it can be greater or lesser than modes.recursive_limit
recursive_limit = math.floor(recursive_limit) + 1
if recursive_limit < 1 then recursive_limit = modes.recursive_limit end
-- default recursiveLevel
if type(recursiveLevel) ~= "number" then recursiveLevel = 1 end
recursiveLevel = math.floor( recursiveLevel ) + 1
if recursiveLevel < 1 then recursiveLevel = 1 end
--
if recursiveLevel > recursive_limit then
recursiveLevel_err = viewers.form9user( modes_recursiveLevel_err, recursiveLevel, recursive_limit)
recursiveLevel_err = viewers.styles_color_error( tostring(recursiveLevel_err) )
end
return recursiveLevel, recursive_limit, recursiveLevel_err
end -- function modes.recursive_normal( recursiveLevel_in, recursive_limit_in, modes_recursiveLevel_err )
 
function modes.recursive_normal_tests( t ) -- Test Normalize recursiveLevel and recursive_limit
local memo = viewers.save_configs("modes.recursive_normal_tests") -- Save global configuration before eventual changes.
-- recursiveLevel, recursive_limit, recursiveLevel_err == modes.recursive_normal(recursiveLevel, recursive_limit) -- typical use
local t = t or "\n* modes.recursive_normal_tests: "
local function recursive_normal_test1(recursiveLevel_in, recursive_limit_in, modes_recursiveLevel_err)
local recursiveLevel, recursive_limit, recursiveLevel_err =
modes.recursive_normal( recursiveLevel_in or modes.recursive_limit or 1, recursive_limit_in or modes.recursive_limit or 3 )
local t = "\n* " .. viewers.ta("Level_in", recursiveLevel_in) .. viewers.ta("Limit_in", recursive_limit_in)
t = t .. viewers.ta("recursiveLevel", recursiveLevel) .. viewers.ta("recursive_limit", recursive_limit) .. viewers.ta("recursiveLevel_err", recursiveLevel_err)
return t
end
t = t .. recursive_normal_test1()
t = t .. recursive_normal_test1(-12, 5)
t = t .. recursive_normal_test1(0, 5)
t = t .. recursive_normal_test1(1, 5)
t = t .. recursive_normal_test1(2.718, 3.1416)
t = t .. recursive_normal_test1(3)
t = t .. recursive_normal_test1(5, 5)
t = t .. recursive_normal_test1(6, 5)
t = t .. recursive_normal_test1(11111, 5, "versions_module_miss_i18n_txt_err")
t = t .. recursive_normal_test1(11112, 5, "versions_module_miss_i18n_count_err")
t = t .. recursive_normal_test1(23456, 5, "modes_recursiveLevel_err")
viewers.restore_configs(memo, "modes.recursive_normal_tests") -- Restore global configurations after eventual changes.
return t
end -- function modes.recursive_normal_tests(recursiveLevel, recursive_limit)
 
function modes.namespaces_page_list(t) -- List namespaces for the actual page.
if type(t) ~= "string" then t = nil end
local t = t or "\n* <b>spaces_page_names_test</b> :"
local mwtitle = mw.title.getCurrentTitle()
t = t .. viewers.ta("mwtitle", mwtitle)
local nsText = mwtitle.nsText
t = t .. viewers.ta("nsText", nsText)
local baseText = mwtitle.baseText -- namespace for the page
t = t .. viewers.ta("baseText", baseText)
local url = tostring(mwtitle:canonicalUrl( ))
t = t .. viewers.ta("url", url)
t = t .. "\n* Module namespace: "
local ns = mw.site.namespaces
if ns and ns[828] then
t = t .. viewers.ta("id828", ns[828].id)
t = t .. viewers.ta("canonicalName828", ns[828].canonicalName)
t = t .. viewers.ta("name828", ns[828].name)
t = t .. viewers.ta("displayName828", ns[828].displayName)
end
t = t .. "\n* All namespaces (from 0 to 2000): "
local ns = ""
for ins = 0, 2000 do
if mw.site.namespaces[ins] then
ns = mw.site.namespaces[ins].canonicalName
t = t .. viewers.ta(ns, ins)
end
end
t = t .. "\n* mw.title.getCurrentTitle(): "
local getCurrentTitle = mw.title.getCurrentTitle()
for key, val in pairs(getCurrentTitle) do -- Synthesis and descriptions of all status
t = t .. viewers.ta( viewers.value(key), viewers.value(val) )
end
return t
end -- function modes.namespaces_page_list()
 
function modes.init_modes_translate_events(frame, Central_version, mode_name, args_known, options_for_modes, QITEM)
-- After versions.init(), initialize modes and their options, known arguments, translations, and default item.
local res = ""
modes.frame = frame
langs.Central_version = Central_version -- To adapt the version of Module:Centralizer in any translated text.
modes.args_known = args_known or modes.args_known
modes.module_init(frame) -- Get modes.args_source with modes.args_source
modes.mode_name = mode_name or modes.mode_name or "read"
modes.init_options_for_modes(frame, options_for_modes, mode_name) -- Needed to init categories and errors
local mode_name, source_key, try_lang = modes.get_arg_mode(mode_name, source_key, try_lang, args_source)
langs.init_content_page_user_lang(modes.args_source.contentlang, modes.args_source.pagelang, modes.args_source.userlang, "modes.init")
local recursiveLevel, recursive_limit, recursiveLevel_err = modes.recursive_normal(recursiveLevel, modes.recursive_limit)
return res
end -- function modes.init_modes_translate_events(frame, Central_version, mode_name, args_known, options_for_modes, QITEM)
 
-- cut_libraries
 
-- - - - ------------------ - - - - ------------------ - - - - -----------------------------
-- - - - ------------------ - - - - ------------------ - - - - -----------------------------
-- The Library:tests_groups initialises, runs and formats groups of tests for MediaWiki and users.
-- It supports modules coders and users to:
-- * Increase the stability of central modules.
-- * Formats some views for users
-- - - - ------------------ - - - - ------------------ - - - - -----------------------------
-- - - - ------------------ - - - - ------------------ - - - - -----------------------------
 
tests_groups = {}
mw.tests_groups = tests_groups -- From 20170729
-- Translations for tests_groups library
tests_groups.i18n = {}
tests_groups.i18n.en = {
tests_groups_recursive_tests_title = "tests_groups.recursive_tests(t) Tests cases for users and MediaWiki",
tests_groups_getTestProvider_title = "viewers.simple_list_test() Tests: Implement getTestProvider in central modules",
tests_groups_getTestProvider_tests_title = "viewers.simple_list_test() Tests: Implement getTestProvider in central modules",
tests_groups_subdiffs_abnormal_error = "Internal error: abnormal subDiffs process",
tests_groups_subdiffs_boolean_error = "subDiffs boolean error",
tests_groups_subdiffs_function_error = "subDiffs function error",
tests_groups_subdiffs_nil_error = "subDiffs nil error",
tests_groups_subdiffs_number_error = "subDiffs number error",
tests_groups_subdiffs_string_error = "subDiffs string error",
tests_groups_subdiffs_table_error = "subDiffs table error",
tests_groups_subdiffs_tables_error = "subDiffs tables error",
tests_groups_subdiffs_type_error = "subDiffs type error",
tests_groups_subdiffs_types_error = "subDiffs types error",
tests_groups_recursiveLevel_error = "subDiffs recursion level exceeded error",
tests_groups_search_Diffs_tests_title = "testsCases.search_Diffs_tests() Search detailed differences in testsCases",
tests_groups_search_Diffs_tests_headers = "Expected value; Actual value; Test indentifier; Results + Errors : expected-actual-details",
tests_groups_tests_groups_report_title = "testsCases.tests_groups_report() MediaWiki recursive testsCases",
tests_groups_group_Diffs_tests_title = "testsCases.group_Diffs_tests() Tests: Report detailed differences, where, recursively",
tests_groups_group_Diffs_test_headers = "Expected value; Actual value; Test indentifier; Results + Errors : expected-actual-details",
} -- tests_groups.i18n.en
tests_groups.i18n.es = {
tests_groups_recursive_tests_title = "tests_groups.recursive_tests(t) Prueba casos para usuarios y MediaWiki",
tests_groups_getTestProvider_tests_title = "viewers.simple_list_test() Pruebas: Implementar getTestProvider en módulos centrales",
tests_groups_subdiffs_abnormal_error = "Error interno: subDiffs proceso anormal",
tests_groups_subdiffs_boolean_error = "subDiffs booleano error",
tests_groups_subdiffs_function_error = "subDiffs función error",
tests_groups_subdiffs_nil_error = "subDiffs nulo error",
tests_groups_subdiffs_number_error = "subDiffs numero error",
tests_groups_subdiffs_string_error = "subDiffs texto error",
tests_groups_subdiffs_table_error = "subDiffs tabla error",
tests_groups_subdiffs_tables_error = "subDiffs tablas error",
tests_groups_subdiffs_type_error = "subDiffs typo error",
tests_groups_subdiffs_types_error = "subDiffs typos error",
tests_groups_recursiveLevel_error = "subDiffs nivel de recursividad superó error",
tests_groups_search_Diffs_tests_title = "testsCases.search_Diffs_tests() Buscar diferencias detalladas en testsCases",
tests_groups_search_Diffs_tests_headers = "Valor prevista; Valor activa; Identificador del prueba; Resultados + Errores : prevista-activa-detalles",
tests_groups_tests_groups_report_title = "testsCases.tests_groups_report() MediaWiki testsCases recursivos",
tests_groups_group_Diffs_tests_title = "testsCases.group_Diffs_tests() Pruebas: Reporte detallado de las diferencias, ¿dónde? recursivamente",
tests_groups_group_Diffs_test_headers = "Valor prevista; Valor activa; Identificador del prueba; Resultados + Errores : prevista-activa-detalles",
} -- tests_groups.i18n.es
tests_groups.i18n.fr = {
tests_groups_recursive_tests_title = "tests_groups.recursive_tests(t) Tests cases for users and MediaWiki",
tests_groups_getTestProvider_tests_title = "viewers.simple_list_test() Tests: Implement getTestProvider in central modules",
tests_groups_subdiffs_abnormal_error = "Erreur interne : processus subDiffs anormal",
tests_groups_subdiffs_boolean_error = "subDiffs erreur de booléen",
tests_groups_subdiffs_function_error = "subDiffs erreur de fonction",
tests_groups_subdiffs_nil_error = "subDiffs erreur de nul",
tests_groups_subdiffs_number_error = "subDiffs erreur de nombre",
tests_groups_subdiffs_string_error = "subDiffs erreur de texte",
tests_groups_subdiffs_table_error = "subDiffs erreur de table",
tests_groups_subdiffs_tables_error = "subDiffs erreur de tables",
tests_groups_subdiffs_type_error = "subDiffs erreur de type",
tests_groups_subdiffs_types_error = "subDiffs erreur de types",
tests_groups_recursiveLevel_error = "subDiffs erreur de niveau de récursivité dépassé",
tests_groups_search_Diffs_tests_title = "testsCases.search_Diffs_tests() Chercher les différences détaillées dans les testsCases",
tests_groups_search_Diffs_tests_headers = "Valeur attendue; Valeur active; Identifiant du test; Résultats + Erreurs : attendue-active-détails",
tests_groups_tests_groups_report_title = "testsCases.tests_groups_report() MediaWiki testsCases recursifs",
tests_groups_group_Diffs_tests_title = "testsCases.group_Diffs_tests() Tests: Rapport detaillé des différences, où, recursivement",
tests_groups_group_Diffs_test_headers = "Valeur attendue; Valeur active; Identifiant du test; Résultats + Erreurs : attendue-active-détails",
} -- tests_groups.i18n.fr
tests_groups.i18n.vi = {
tests_groups_recursive_tests_title = "tests_groups.recursive_tests(t) Tests cases for users and MediaWiki",
tests_groups_getTestProvider_tests_title = "viewers.simple_list_test() Tests: Implement getTestProvider in central modules",
tests_groups_subdiffs_abnormal_error = "Erreur interne : processus subDiffs anormal",
tests_groups_subdiffs_boolean_error = "subDiffs erreur de booléen",
tests_groups_subdiffs_function_error = "subDiffs erreur de fonction",
tests_groups_subdiffs_nil_error = "subDiffs erreur de nul",
tests_groups_subdiffs_number_error = "subDiffs erreur de nombre",
tests_groups_subdiffs_string_error = "subDiffs erreur de texte",
tests_groups_subdiffs_table_error = "subDiffs erreur de table",
tests_groups_subdiffs_tables_error = "subDiffs erreur de tables",
tests_groups_subdiffs_type_error = "subDiffs erreur de type",
tests_groups_subdiffs_types_error = "subDiffs erreur de types",
tests_groups_recursiveLevel_error = "subDiffs erreur de niveau de récursivité dépassé",
tests_groups_search_Diffs_tests_title = "testsCases.search_Diffs_tests() Chercher les différences détaillées dans les testsCases",
tests_groups_search_Diffs_tests_headers = "Valeur attendue; Valeur active; Identifiant du test; Résultats + Erreurs : attendue-active-détails",
tests_groups_tests_groups_report_title = "testsCases.tests_groups_report() MediaWiki testsCases recursifs",
tests_groups_group_Diffs_tests_title = "testsCases.group_Diffs_tests() Tests: Rapport detaillé des différences, où, recursivement",
tests_groups_group_Diffs_test_headers = "Valeur attendue; Valeur active; Identifiant du test; Résultats + Erreurs : attendue-active-détails",
} -- tests_groups.i18n.vi
 
tests_groups.default_test_group = { -- events.test_group
{ ["errorsKey"] = 2, ["modulename"] = "mathroman", ["funcname"] = "mathroman.roman2int", ["args"] = { "MCXI" }, ["expect"] = { 1111 } }, -- case
{ ["name.roman2intTests.1"] = "mathroman", ["modulename"] = "mathroman", ["groupname"] = "mathroman.roman2intTests", }, -- group
{ ["name"] = "tests_groups.autotests.1", ["modulename"] = "tests_groups", ["groupname"] = "tests_groups.autotests_group", }, -- group
} -- tests_groups.default_test_group
 
mathroman.roman2intNMC = { -- Tests cases for tests_groups.resultdiffs("mathroman.testsRecur", "mathroman.roman2intNMC", case, opt, 1) only
-- each test_case defines a name, a function, an input, an output. See also viewers.strTestCase. 6 cases
{ ["args"] = { "-X" }, ["expect"] = { 10, "mathroman_char_X_in_N_err" }, -- change one key [" ] ,"
["errorsKey"] = 2, ["modulenameNMC"] = "mathroman", ["funcname"] = "mathroman.roman2int", },
{ ["args"] = { "0" }, ["expect"] = { 0, "mathroman_NMC" }, -- change one string value, and change a value in the args table
["errorsKey"] = 2, ["modulename"] = "mathroman", ["funcname"] = "mathroman.roman2intNMC", },
{ ["args"] = { "XIA" }, ["expect"] = { 11, "character A in 3" }, -- missing key/val in level 1 and sub table
["errorsKey"] = 2, ["funcname"] = "mathroman.roman2int", },
{ ["args"] = { "MCXI" }, ["expect"] = { 1111 }, -- missing case
["errorsKey"] = 2, ["modulename"] = "mathroman", ["funcname"] = "mathroman.roman2int",},
}
 
mathroman.roman2intTests = { -- Autotest cases to validate the mathroman library at MediaWiki level.
-- each test_case defines a name, a function, an input, an output. See also viewers.strTestCase. 6 cases
{ ["errorsKey"] = 2, ["args"] = { "IV" }, ["expect"] = { 4 }, ["funcname"] = "mathroman.roman2int", ["modulename"] = "mathroman", },
{ ["errorsKey"] = 2, ["args"] = { "MCXI" }, ["expect"] = { 1111 }, ["funcname"] = "mathroman.roman2int", ["modulename"] = "mathroman", }, -- case
}
 
mathroman.testsRecur = { -- Autotest cases to validate the mathroman library at MediaWiki level.
{ ["name"] = "mathroman", ["modulename"] = "mathroman", ["groupname"] = "mathroman.roman2intTests", }, -- group
{ ["errorsKey"] = 2, ["modulename"] = "mathroman", ["funcname"] = "mathroman.int2roman", ["args"] = { "31" }, ["expect"] = { "XXX1" } },
{ ["name"] = "mathroman", ["modulename"] = "mathroman", ["groupname"] = "mathroman.main_tests_groups", }, -- group
}
 
local func_example = { ["funcname"] = "mathroman.roman2int", ["args"] = { "MCXI" }, ["expect"] = { 1111 }, ["errorsKey"] = 2, }
local group_example = { ["name"] = "mathroman.roman2int.5", ["modulename"] = "mathroman", ["groupname"] = "mathroman.testsRecur", }
tests_groups.main_tests_groups = { -- Autotest cases to validate the mathroman library at MediaWiki level.
{ ["errorsKey"] = 2, ["modulename"] = "mathroman", ["funcname"] = "mathroman.roman2int", ["args"] = { "VIA", }, ["expect"] = { 6, "character A in 3" }, },
{ ["name"] = "mathroman", ["modulename"] = "mathroman", ["groupname"] = "mathroman.testsRecur", },
{ ["errorsKey"] = 2, ["modulename"] = "mathroman", ["funcname"] = "mathroman.int2roman", ["args"] = { "19" }, ["expect"] = { "XII" } },
{ ["name"] = "tests_groups", ["modulename"] = "tests_groups", ["groupname"] = "tests_groups.autotests_group", },
}
 
tests_groups.autotests_group = { -- events.test_group
{ ["errorsKey"] = 2, ["modulename"] = "tests_groups", ["funcname"] = "tests_groups.autotests", -- 1
["args"] = { "1111", ["guide"] = "t1: small result = expect", },
["expect"] = { "MCXI" },
["result"] = { "MCXI" },
},
{ ["errorsKey"] = 2, ["modulename"] = "tests_groups", ["funcname"] = "tests_groups.autotests", -- 2
["args"] = { "abc2", 222, ["guide"] = "t2: = -s; 2 = -s", },
["expect"] = { "xyz2", "xyz2-e", }, -- 2 = -e
["result"] = { "xyz2", "xyz2-s", },
},
{ ["errorsKey"] = 2, ["modulename"] = "tests_groups", ["funcname"] = "tests_groups.autotests", -- 3
["args"] = { "abc3", 333, ["guide"] = "t3: ident levels > no error", },
["expect"] = { "xyz3", ["subgrp3"] = { ["one3"] = 33, ["endgrp33"] = "good", }, },
["result"] = { "xyz3", ["subgrp3"] = { ["one3"] = 33, ["endgrp33"] = "good", }, },
},
{ ["errorsKey"] = 2, ["modulename"] = "tests_groups", ["funcname"] = "tests_groups.autotests", -- 4
["args"] = { "abc4", 444, ["guide"] = "t4: val: good ~= BAD in val of level 2", },
["expect"] = { "xyz4", ["subgrp"] = { ["one"] = 44, ["endgrp"] = "good4", }, },
["result"] = { "xyz4", ["subgrp"] = { ["one"] = 44, ["badgrp"] = "BAD4", }, },
},
} -- tests_groups.autotests_group = {}
 
function tests_groups.autotests(case, opt) -- Formats tests cases to run for MediaWiki and users.
if (type(case.result) ~= "table") and (type(case.expect) == "table") then
case.result = case.result or case.expect or {} -- default
end
return case
end
 
tests_groups.main_groupname = "mathroman.testsGroups" -- Autotest cases to validate the mathroman library at MediaWiki level.
tests_groups.main_groupname = "tests_groups.main_tests_groups" -- Main group of tests cases for auto-test tests_groups itself.
 
function tests_groups.Organisation(case) -- See mw:Extension:Scribunto/Lua reference manual#Test cases
if nil then -- Do not disturb other process, in case of bad use.
local case = case or {}
local ClassNameTests = { ["count"] = nmaxi, ["name"] = caseid, ["count"] = nmaxi, } -- ClassNameTests.lua as if it were the page "Module:ClassNameTests"
case.count = case.nmaxi -- count: Integer, number of tests
case.name = case.name -- string identifier of the test case
case.provide = tests_groups.provide_func( n ) -- Function that returns three values: n, the test name, a string
case.run = tests_groups.provide_run( n ) -- run( n ): Function that runs test n and returns one string.
case.result_string = case.run( n ) -- run( n ): Function that runs test n and returns one string.
local n, the_test_name, a_string = case.provide(n, case)
local tests_groups = require 'Module:TestFramework' -- local tests_groups = require 'Module:TestFramework'
tests_groups.getTestProvider( { "Tests go here" } ) -- return tests_groups.getTestProvider( { -- Tests go here } )
case = {
["name"] = "name of the test",
["func"] = "function to execute",
["args"] = "Optional table of arguments to pass to the function",
["expect"] = "Results to expect",
["type"] = 'Optional "type" of the test, default is "Normal"',
["types"] = "Included types are",
["Normal"] = "expect is a table of return values, or a string if the test should raise an erro",
["Iterator"] = "expect is a table of tables of return values",
["ToString"] = 'Like "Normal", except each return value is passed through tostring()',
} -- Each test is itself a table, with the following properties:
end
return nil
end -- function tests_groups.Organisation(case)
 
tests_groups.allpublics = { ["readers"] = "readers", ["helpers"] = "helpers", ["coders"] = "coders", } -- Available status of errors
tests_groups.alldescriptions = {} -- Descriptions of errors
 
function tests_groups.errors_init(allstatus) -- Checks and standardizes errors objects. Formats a table view of errors definitions.
local memo = viewers.save_configs("tests_groups.errors_init") -- Saves global configuration before eventual changes.
if ( type(tests_groups.allstatus) ~= "table" ) then tests_groups.allstatus = {} end
if ( type(allstatus) ~= "table" ) then allstatus = tests_groups.allstatus end
tests_groups.allpublics = {}
tests_groups.alldescriptions = {}
local allpublics, alldescriptions = tests_groups.allpublics, tests_groups.alldescriptions
for key, an_error in pairs(allstatus) do -- Synthesis and descriptions of all status
-- tests_groups.allstatus[an_error.name] = an_error.status
tests_groups.allpublics["public"] = an_error.public
tests_groups.alldescriptions[an_error.name] = an_error.descript
end
-- tests_groups.alldescriptions[key] = an_error.descript -- Descriptions of errors
-- tests_groups.allstatus = errors -- direct update from init()
local t = "\n* tests_groups.errors_init(errors) -- Check and standardize errors objects"
local tab_view = { -- Group datas and options for a table view with lines and columns.
tests_title = "tests_groups.errors_init(errors) -- Check and standardize errors objects", -- "mathroman.int2roman() Test digital numbers to roman numbers"
test_group = tests_groups.allstatus,
headers = "Error name; Status; Public; Description", -- "Digital number; Roman value; Correct; Error(s)"
rowGroup = {},
}
tab_view.t = (tab_view.t or "") .. viewers.ta("int2roman_tests: ", "start")
tab_view.t = tab_view.t .. viewers.ta("#test_group: ", lua_table.level_count(tab_view.test_group) )
function tab_view.form_one_case(an_error) -- Convert a case from test_group to rowGroup.
return { an_error.name, an_error.status, an_error.public, an_error.descript, }
end
t = t .. tableview.new(tab_view) -- Formats a table view with lines and columns.
viewers.restore_configs(memo, "tests_groups.errors_init") -- Restore global configurations after eventual changes.
return t, errors
end -- local t, errors = tests_groups.errors_init(tests_groups.allstatus)
 
function tests_groups.ClassNameTests(case) -- expecting it to return an object with the following properties: count, name, case.provide.
case.count = case.nmaxi or 1 -- count: Integer, number of tests
case.n = case.n or 1 -- count: Integer, number of tests
case.name = (case.funcname or "case.funcname") .. "." .. case.n -- string identifier of the test case
case.provide = tests_groups.provide_func(case.n, case) -- Function that returns three values: n, the test name, a string
return case
end -- local case = tests_groups.ClassNameTests(case)
 
function tests_groups.getTestProvider(mw_tests, nmaxi) -- Formats tests cases to run for MediaWiki and users.
local memo = viewers.save_configs("tests_groups.getTestProvider") -- Save global configuration before eventual changes. See T176362
-- function tests_groups.getTestProvider(), .init(), .gettestsgroups(), .getcases(), .resultdiffs(), .form(), .recursive_tests(), viewers.form9en(),
-- This will load the file _getTestProvider.lua as if it were the page "Module:_getTestProvider",
-- expecting it to return an object with the following properties:
-- count: Integer, number of tests
-- provide( n ): Function that returns three values: n, the name of test n, and a string that is the expected output for test n.
-- run( n ): Function that runs test n and returns one string.
-- Guideline:
-- Before to run tests cases mw.tests_groups.getTestProvider() must first
-- * Get all tests cases, in a composite and recursive exploration of available modules and libraries.
-- * And build, from that exploration, a single level table of all tests cases.
-- * And return this table to MediaWiki to really run these tests cases.
-- To run these tasks the main module replace this function by its own.
-- That happens each time a Lua-coder try or record a change of a module.
-- Tests cases:
-- tests_groups.getTestProvider(mw_tests, 0) return the table of tests cases, for MediaWiki only, which check the coherence of all returned tests cases.
-- Any other uses are available for the calling module or library.
-- Structures of tests:
-- return tests_groups.getTestProvider( { Tests go here } )
-- getTestModules(): returns a group of controls
-- getTestProvider return one control: count = number of tests; provide(n) returns n, name of n, expected string; run( n ) returns one string.
-- One test case contains: name, func, args, expect, type
-- One type is: Normal = {table}, Iterator like pairs(), ToString = tostring()
mw_tests = mw_tests or {}
local nn = nmaxi or 0
if (type(CNT) ~= "table") or (type(CNT.add) ~= "function") then CNT = tracker.initadd({ ["name"] = "NMC", ["limit"] = 2 }) end -- Initialize a track
local t = "\n* tests_groups.getTestProvider() -- Run testcases for MediaWiki and users."
local last_case = {}
local mw_cases = {}
local nmaxi = lua_table.level_count(mw_tests)
for k, case in pairs(mw_tests) do -- For all cases to run
local func_example = { ["funcname"] = "mathroman.roman2int", ["args"] = { "MCXI" }, ["expect"] = { 1111 }, ["errorsKey"] = 2, }
local group_example = { ["name"] = "mathroman.roman2int.5", ["modulename"] = "mathroman", ["groupname"] = "mathroman.testsRecur", }
local test_example =
{ ["errorsKey"] = 2, ["modulename"] = "tests_groups", ["funcname"] = "tests_groups.autotests", -- 2
["args"] = { "abc2", 123, ["guide"] = "2 = -s; 2 = -s", },
["expect"] = { "xyz2", "xyz2-e", }, -- 2 = -e
["simul"] = { "xyz2", "xyz2-s", }, } -- 2 = -s
if ( type(case) == "table" ) and ( type(case.funcname) == "string" ) and ( type(case.args) == "table" ) then
-- count: Integer, number of tests
-- provide( n ): Function that returns three values: n, the name of test n, and a string that is the expected output for test n.
-- run( n ): Function that runs test n and returns one string.
-- Normal: expect{} is a table of returned values, or a string if the test should raise an error. func is simply called.
-- Each test is defined in a table, with the following properties:
-- Active params of the case:
case.name = case.name -- The name of the test. a string
case.func = lua_table.from_subnames_table(case.funcname) -- The function to execute.
case.args = case.args -- Optional table of arguments to pass to the function.
case.expect = case.expect -- Results to expect.
case.type = case.type or "Normal" -- Optional "type" of the test, default is "Normal".
-- Default id of the case:
case.nmaxi = nmaxi -- count integer is the number of cases
case.n = k -- or nn or case.n -- number of cases
case.OK = case.OK or "OK" -- Optional "type" of the test, default is "Normal".
case.provide = tests_groups.provide_func(case.n, case) -- returns n, its test name, and "OK" or "error string".
-- This will load the file getTestProvider.lua as if it were the page "Module:getTestProvider", expecting it to return an object with the following properties:
local n, name, ok = case.provide(case.n, case.name, case.OK) -- returns n, its test name, and "OK" or "error string".
CNT.add(CNT, 1, "CNTest:provide", { ["n"] = n, ["name"] = name, ["ok"] = ok, } )
case.run = tests_groups.run_func(n, case.func) -- runs the test n. Returns n and one string: "OK" or "error string".
case = tests_groups.ClassNameTests(case) -- expecting it to return an object with the following properties: count, name, case.provide.
case.NameTest = { case.count, case.name , case.provide} -- return object { count, name, provide(n) }
CNT.add(CNT, 1, "case.NameTest", { ["k"] = k, ["name"] = tostring(case.NameTest.name), ["case.NameTest.count"] = case.NameTest.count,
["#NameTest"] = lua_table.level_count(case.NameTest), ["provide"] = tostring(case.NameTest.provide), } )
table.insert(mw_cases, case)
last_case = case
else -- error: mw_tests must be fine
t = t .. CNT.add(CNT, 1, "CNTest:NO RUN", { ["k"] = k, ["funcname"] = tostring(case.funcname), } )
end
end
if last_case and ( lua_table.level_count(mw_tests) ~= lua_table.level_count(mw_cases) ) then
last_case.expect = "Cases count error: ".. lua_table.level_count(mw_tests) .. " = #mw_tests ~= #mw_cases = ".. lua_table.level_count(mw_cases)
end -- Check the count of cases
-- t = t .. CNT.t
viewers.restore_configs(memo, "tests_groups.getTestProvider") -- Restore global configurations after eventual changes.
return mw_cases, t
end -- local mw_cases, t = tests_groups.getTestProvider(mw_tests, n)
 
function tests_groups.normalcase(case, expect_tab_name, result_tab_name, diff) -- Normalize case options.
local case = case
local allstatus = tests_groups.allstatus
if (type(case) ~= "table") then case = {} end -- Initialize a track
if (type(CNT) ~= "table") or (type(CNT.add) ~= "function") then CNT = tracker.initadd({ ["name"] = "CNT", ["limit"] = 2 }) end -- Initialize a track
-- tests_groups.status_memo = "OK,code,differ,equal,excess,miss,tabcount,taberr,types" -- tests_groups.allstatus status values
local tt, errors = tests_groups.errors_init(tests_groups.allstatus)
-- local allstatus, allpublics, alldescriptions = tests_groups.allstatus, tests_groups.allpublics, tests_groups.alldescriptions
case.status = case.status or tests_groups.allstatus.OK.status
case.level = case.level or 1
if case.level == 1 then case.expect_base = case.expect or {} end
if case.level == 1 then case.result_base = case.result or {} end
case.levelsup = case.levelsup or 1
if case.level > case.levelsup then case.levelsup = case.level else case.levelsup = 1 end
case.levelLimit = case.levelLimit or 3
case.all_diffs = case.all_diffs or {}
case.diff = diff or case.diff or false
case.expect_tab_name = expect_tab_name or case.expect_tab_name
case.result_tab_name = result_tab_name or case.result_tab_name
case.ref_key = case.ref_key or ""
if type(case.expect_tab_name) ~= "string" then case.expect_tab_name = "mathroman.testsRecur" end -- to debug when begin
if type(case.result_tab_name) ~= "string" then case.result_tab_name = "mathroman.roman2intTests" end -- to debug when begin ; roman2intNMC
--
case.get_expect_tab = function(expect_tab_name) return lua_table.from_subnames_table(case.expect_tab_name, case.expect_base) end -- expect table
case.get_result_tab = function(result_tab_name) return lua_table.from_subnames_table(case.result_tab_name, case.result_base) end -- result table
--
local ref_tab = case.get_expect_tab(case.expect_tab_name) -- expect table. Do not get it in case. To not duplicate it when mw.clone(case)
local alt_tab = case.get_expect_tab(case.result_tab_name) -- result table. Do not get it in case. To not duplicate it when mw.clone(case)
local ref_tab = lua_table.from_subnames_table(case.expect_tab_name, case.expect_base) -- expect table. Do not get in case to avoid duplicate in clone nor loop.
local alt_tab = lua_table.from_subnames_table(case.result_tab_name, case.result_base) -- result table. Do not get in case to avoid duplicate in clone nor loop. mw.clone(case)
-- case.get_result_tab = function(result_tab_name) return lua_table.from_subnames_table(case.expect_base) end -- expect table
case.missing_jobs = " missbranch misslevel missarg diffs " -- example of jobs for missing parts
case.diffs_jobs = " missbranch misslevel missarg newbranch newlevel newarg diffs " -- default jobs for diffs
case.all_jobs = " missbranch misslevel missarg newbranch newlevel newarg diffs altbranchs altlevel altarg " -- "now"
case.jobs = case.jobs or case.all_jobs -- example of jobs for missing parts
case.sub_key = case.sub_key or ""
case.errors = case.errors or ""
case.all_errors = case.all_errors or {}
case.all_diffs = case.all_diffs or {}
case.result = case.result or {}
return case
end -- local case = tests_groups.normalcase(case, expect_tab_name, result_tab_name, diff) -- Normalize case options.
 
tests_groups.defaultform = "status=%1: result=%2 <b>≠</b> expect=%3" -- for: status, result_val, expect_val -- Unicode Character 'NOT EQUAL TO' (U+2260) : ≠
 
function tests_groups.add_error(case, form, status, result_val, expect_val, ...) -- Formats one error, default: "status=%1: result=%2 <b>≠</b> expect=%3"
-- tests_groups.add_error(case, "result_type = %1 <b>≠</b> %2", sub_key, allstatus.taberr, result_type, expect_type) -- Formats errors for helpers
local sub_key, expect, result, errortxt, diff_type
local expect_key, expect_val, expect_type, result_key, result_val, result_type
local result_val = result_val or case.result_val
local expect_val = expect_val or case.expect_val
local status = status or case.status or "code"
local form = form or case.form or tests_groups.defaultform -- for: status, result_val, expect_val
local sub_key = sub_key or case.sub_key or ""
case.transform = viewers.form9en(case.form) -- to test only the tranlations
if (type(case.form) == "string") and (case.transform ~= case.form) then case.form = case.transform end -- if form has translations, use it
--
-- tests_groups.status_memo = "OK,code,differ,equal,excess,miss,tabcount,taberr,types" -- tests_groups.allstatus status values
if (type(form) == "string") and viewers.is_in_sp(form, tests_groups.status_memo, ",") then form = tests_groups.defaultform end
if (type(status) ~= "string") then case.status = tests_groups.allstatus.code.status ; status = case.status end
--
local vals = { ... } -- vals = { status, result_val, expect_val, ... }
case.transform = viewers.form9en(form, status, result_val, expect_val, ...) -- Show one diff between result and expect. Always in english for tests_groups.
table.insert( case.all_errors, case.transform )
local errortxt = sub_key .. case.transform -- Show one diff between alt and ref. Always in english for tests_groups.
return errortxt
end -- local errortxt = tests_groups.add_error(case, form, status, result_val, expect_val, ...) -- Formats one error
 
tests_groups.allstatus = {
["OK"] = { ["name"] = "OK", ["status"] = "OK", ["public"] = "readers", ["descript"] = "Normal default state of error status.", },
["code"] = { ["name"] = "code", ["status"] = "code", ["public"] = "readers", ["descript"] = "Abnormal coding error.", },
["differ"] = { ["name"] = "differ",["status"] = "differ", ["public"] = "helpers", ["descript"] = "The result differs from the expected value.", },
["equal"] = { ["name"] = "equal", ["status"] = "equal", ["public"] = "helpers", ["descript"] = "Equal values when compared.", },
["excess"] = { ["name"] = "excess",["status"] = "excess", ["public"] = "coders", ["descript"] = "The value is not expected in the result.", },
["miss"] = { ["name"] = "miss", ["status"] = "miss", ["public"] = "coders", ["descript"] = "The value miss in the result.", },
["tabcount"]= { ["name"] = "tabcount",["status"] = "tabcount",["public"] = "coders",["descript"] = "Result and expect (sub)tables have different sizes.", },
["taberr"] = { ["name"] = "taberr",["status"] = "taberr", ["public"] = "coders", ["descript"] = "The value miss in the result.", },
["types"] = { ["name"] = "types",["status"] = "types",["public"] = "coders",["descript"] = "Result and expect are of different types.", },
} -- tests_groups errors uses and documentations
tests_groups.status_memo = "OK,code,differ,equal,excess,miss,tabcount,taberr,types" -- tests_groups.allstatus status values
 
function tests_groups.resultdiffs(case) -- Formats errors in case.result{} where it differs from case.expect{}.
local sub_key, expect, result, errortxt, diff_type, level, status, allstatus
local expect_key, expect_val, expect_type, result_key, result_val, result_type
local allstatus = tests_groups.allstatus
case.subexpect = case.subexpect or case.expect or {}
case.subresult = case.subresult or case.result or {}
case.expect_base = case.expect or {} -- Only exactly in expect{} and result{}
case.result_base = case.result or {} -- Only exactly in expect{} and result{}
case.expect_key = case.key or 1 -- variable to check in case.expect
case.result_key = case.key or 1 -- variable to check in case.result
case.expect_val = case.expect[case.expect_key]
case.result_val = case.result[case.result_key]
case.level = case.level or 0
case.levelsup = case.levelsup or 0
if case.level > case.levelsup then case.levelsup = case.level else case.levelsup = 1 end
case.levelmaxi = case.levelmaxi or 3
case.error_n = case.error_n or 0
case.errorsmaxi = case.errorsmaxi or 4
case.sub_key = (case.sub_key or case.name or "") .. "[" .. case.level .. "]"
sub_key = case.sub_key
if case.error_n > case.errorsmaxi then return case end
case.transform = viewers.form9en(case.form)
if (type(case.form) == "string") and case.transform ~= case.form then case.form = case.transform end -- if form translate, use it
--
for key, val in pairs(case.subresult) do
if not case.subexpect[key] then -- Detect a result key absent in expect
tests_groups.add_error(case, "excess", "excess", key, "nil") -- Formats one error, default: "status=%1: result=%2 <b>≠</b> expect=%3"
end
end
if (result_type ~= expect_type) then -- Detect diffs on types.
tests_groups.add_error(case, "types", "types", case.result_val, case.expect_val) -- Formats one error, default: "status=%1: result=%2 <b>≠</b> expect=%3"
elseif (case.result_val ~= case.expect_val) then -- if diff on counts of values
tests_groups.add_error(case, "differ", "differ", result_val, expect_val)
end
-- tests_groups.status_memo = "OK,code,differ,equal,excess,miss,tabcount,taberr,types" -- tests_groups.allstatus status values
if (type(case.subresult) == "table") and (type(case.subexpect) == "table") then -- Loop in sub-tables to a sub level.
local count_subresult, count_subexpect = lua_table.level_count(case.subresult), lua_table.level_count(case.subexpect)
if (count_subresult ~= count_subexpect) then -- if diff level_count
tests_groups.add_error(case, "tabcount", count_subresult, count_subexpect)
end
if (case.subresult ~= case.subexpect) then -- pointers always differ Loop in tables levels to an upper level.
-- tests_groups.add_error(case, "differ", "differ", case.subresult, case.subexpect)
end -- ["guide"] = "t4: val: good ~= BAD in val of level 2"
 
if case.level <= case.levelmaxi then
case.level = case.level + 1
case = tests_groups.resultdiffs(case)
end
end
if ( lua_table.level_count(case.all_errors) == 0 ) then case.errors = allstatus.OK.status -- There is no error.
else -- List error(s)
case.errors = "List error(s): "
for k, errortxt in pairs(case.all_errors) do -- Get all differences in excess (line 6236)
case.errors = case.errors .. tostring(errortxt) .. ", "
end
end
return case
end -- local case = function tests_groups.resultdiffs(case)
 
function tests_groups.run_func(n, case) -- for case.run(n) = tests_groups.run_func(n)
local run = function(n) return tostring(n) end -- Function that runs test n and returns one string.
return run
end
 
function tests_groups.provide_func(n, case) -- for case.provide(n) = tests_groups.provide_func(n)
-- provide( n ): Function that returns three values: n, the name of test n, and a string that is the expected output for test n.
-- case.result = case.func(case.args)
if (type(tests_groups.result_cases) ~= "table") then tests_groups.result_cases = {} end
-- local case = tests_groups.result_cases[n]
local provide = function(n, case)
-- tests_groups.kept_groups = result_cases
-- tests_groups.result_cases = result_cases
if (type(case) ~= "table") then case = tests_groups.result_cases[n] end
if (type(case) ~= "table") then case = { args = { case }, expect = { }, res = { }, } end
local case = tests_groups.normalcase(case, expect_tab_name, result_tab_name, diff) -- Normalize case options.
local ref_tab = case.ref_tab or case.expect -- expect table
local alt_tab = case.alt_tab or case.result -- result table
case.expect = case.ref_tab or case.expect or {} -- expect table
case.result = alt_tab or case.result or {} -- result table
if (type(case.result) == "table") and (type(case.result.jobs) == "string") then
CNT.add(CNT, 1, "provide_func 6793", { ["RES.ERROR"] = "RES.ERROR", ["#case.result"] = lua_table.level_count(case.result), ["jobs"] = case.result.jobs, } )
end
case.n = n
if (type(case.funcname) == "string") then -- Get the function to test
case.func = lua_table.from_subnames_object(case.funcname) -- Get the last sub-object from its sub-names.
if (type(case.func) == "function") then -- Get new diffs
case = tests_groups.resultdiffs(case) -- Compare expected and actual results of one test case.
else
case.err = "Internal error: abnormal function to compute case.result"
case.errors = case.err
case.result = { "missing function", case.errors }
if (type(case.result) == "table") and (type(case.result.jobs) == "string") then
CNT.add(CNT, 1, "subdiffs 6805", { ["RES.ERROR"] = "RES.ERROR", ["#case.result"] = lua_table.level_count(case.result), ["jobs"] = case.result.jobs, } )
end
end
end
if (type(case.errorsKey) ~= "number") then case.errorsKey = 2 end
-- Use new diffs
case.res1 = case.result[1] or "res1pv" -- default result value
case.err2 = case.result[case.errorsKey] or case.errors or case.err
local errorsOK = case.errors or case.err2
if errorsOK == "" then errorsOK = nil end
errorsOK = errorsOK or case.OK
return n, case.name, errorsOK -- Function that returns three values: n, name of test n, and a string as expected output of test n.
end
return provide
end -- function tests_groups.provide_func(n, case)
 
function tests_groups.gettestsgroups(groupname, modulename, kept_groups, recursiveLevel) -- Get groups of tests cases for MW and users.
-- function tests_groups.getTestProvider(), .init(), .gettestsgroups(), .getcases(), .resultdiffs(), .form(), .recursive_tests(), viewers.form9en(),
-- Guideline: to convert a tree of groups, even in case of loops in any leve:
-- Inside each level of the tree of groups, search only sub groups and add only news groups.
local recursiveLevel, recursive_limit, recursiveLevel_err = modes.recursive_normal(recursiveLevel, (tests_groups.gettestsgroups_recursive_limit or 11) )
local level = recursiveLevel
local groupname = groupname
local t = "<br>gettestsgroups: "
if (type(groupname) ~= "string") then groupname = tests_groups.main_groupname end -- initial default main group
if (type(recursiveLevel) ~= "number") then recursiveLevel = 3 end -- initial default main group
local main_groups, search_groups, kept_groups = {}, {}, kept_groups or {}
local ante_name, post_name
local tests_groups = {} -- Get cases in tests_groups
main_groups = lua_table.from_subnames_table(groupname) -- for the main or any new group of groups
local modulename = modulename
if (type(modulename) ~= "string") then modulename = main_groups.modulename end -- initial module to test
local func_example = { ["funcname"] = "mathroman.roman2int", ["args"] = { "MCXI" }, ["expect"] = { 1111 }, ["errorsKey"] = 2, }
local group_example = { ["name"] = "mathroman.roman2int.5", ["modulename"] = "mathroman", ["groupname"] = "mathroman.testsRecur", }
function get_tests_groups(groupname, kept_groups, recursiveLevel)
local groupname = groupname
local modulename = modulename
local recursiveLevel, recursive_limit, recursiveLevel_err = modes.recursive_normal(recursiveLevel, (tests_groups.gettestsgroups_recursive_limit or 11) )
local level = recursiveLevel
if (type(groupname) ~= "string") then groupname = tests_groups.main_groupname end
local main_groups = lua_table.from_subnames_table(groupname) -- for the main or any new group of groups
local search_groups = main_groups or {}
local kept_groups = kept_groups or {}
CNT.add(CNT, 1, "get_tests_groups:begin", { ["groupname"] = groupname, ["#kept_groups"] = lua_table.level_count(kept_groups), } )
for key, group in pairs(search_groups) do -- For all sub groups in one level
if ( type(group) == "table" ) then
local group_example = { ["name"] = "mathroman.roman2int.5", ["groupname"] = "mathroman.testsRecur", ["modulename"] = "mathroman", }
groupname = group.groupname
modulename = group.modulename
if ( type(group) == "table" ) and ( type(groupname) == "string" )
and ( type(kept_groups[groupname]) ~= "table" ) then -- antiLoop: if the case is new in the tree of cases groups.
kept_groups[groupname] = group -- The groupname as key avoid abnormal loops, like table.insert( kept_groups, group )
group["level"] = level
CNT.add(CNT, 1, "get_tests_groups:INSERT", { ["groupname"] = groupname, ["#kept_groups"] = lua_table.level_count(kept_groups), } )
if ( recursiveLevel < recursive_limit ) then
kept_groups = get_tests_groups(groupname, kept_groups, recursiveLevel + 1)
end
end
search_groups = mw.clone(kept_groups)
else -- type(group) ~= "table" to debug : versions.bindable_libraries
CNT.add(CNT, 1, "get_tests_groups:no group", { ["key"] = tostring(key), ["type(group)"] = type(group), ["tostring(group)"] = tostring(group), } )
end
end
CNT.add(CNT, 1, "get_tests_groups:end", { ["recursiveLevel"] = recursiveLevel, ["groupname"] = groupname, ["#kept_groups"] = lua_table.level_count(kept_groups), } )
return kept_groups
end -- function get_tests_groups()
local kept_groups = get_tests_groups(groupname, kept_groups, recursiveLevel)
local func_example = { ["funcname"] = "mathroman.roman2int", ["args"] = { "MCXI" }, ["expect"] = { 1111 }, ["errorsKey"] = 2, }
local group_example = { ["name"] = "mathroman.roman2int.5", ["modulename"] = "mathroman", ["groupname"] = "mathroman.testsRecur", }
local cases_groups, case = {}, {}
for key, keptgroup in pairs(kept_groups) do
case = lua_table.from_subnames_table(keptgroup.groupname or "mathroman.int2roman") -- Get the last sub-table from its sub-names.
table.insert(cases_groups, case) -- Re-form a normal group of groups, from all sub-groups.
end
tests_groups = cases_groups
table.sort(tests_groups, function (a, b) return ( tostring(a.groupname) ) < ( tostring(b.groupname) ) end )
local result_cases = {}
for i, group in pairs(tests_groups) do -- For all known tests_groups
for k, case in pairs(group) do -- For all cases in each group
local func_example = { ["funcname"] = "mathroman.roman2int", ["args"] = { "MCXI" }, ["expect"] = { 1111 }, ["errorsKey"] = 2, }
local group_example = { ["name"] = "mathroman.roman2int.5", ["modulename"] = "mathroman", ["groupname"] = "mathroman.testsRecur", }
if ( type(case.funcname) == "string" ) then -- Select only tests cases using functions
table.insert( result_cases, case )
end
end
end
kept_groups = result_cases
tests_groups.kept_groups = result_cases
return kept_groups, t
end -- local kept_groups = tests_groups.gettestsgroups(groupname, modulename, kept_groups, recursiveLevel)
 
function tests_groups.getcases(kept_groups) -- Get a group of tests cases for MW and users.
-- function tests_groups.getTestProvider(), .init(), .gettestsgroups(), .getcases(), .resultdiffs(), .form(), .recursive_tests(), viewers.form9en(),
-- tests_groups.gettestsgroups_recursive_limit = 11
local t = "tests_groups.getcases(tab_view) Formats the result of tests for MW and users."
if (type(kept_groups) ~= "table") then kept_groups = {} end
local result_cases = {}
local n, more = 0, 0
for k, case in pairs(kept_groups) do -- For all cases in each group -- testsRecur
CNT.add(CNT, 1, "for case in kept_groups", { ["case"] = viewers.rough_view(case), } )
case.func = lua_table.from_subnames_table(case.funcname or "mathroman.int2roman") -- Get the last sub-table from its sub-names.
if ( type(case) == "table" ) then -- Select only tests cases using functions
n = n + 1
case.n = n
case.name = case.funcname .. "." .. n
CNT.add(CNT, 1, "for case", { ["k"] = k, ["funcname"] = case.funcname or "func?", ["modulename"] = case.modulename or "module", ["#args"] = lua_table.level_count(case.args), } )
end
local func_example = { ["funcname"] = "mathroman.roman2int", ["args"] = { "MCXI" }, ["expect"] = { 1111 }, ["errorsKey"] = 2, }
local group_example = { ["name"] = "mathroman.roman2int.5", ["modulename"] = "mathroman", ["groupname"] = "mathroman.testsRecur", }
if ( type(case) == "table" ) and ( type(case.funcname) == "string" ) then -- Select only tests cases using functions
more = more + 1
table.insert( result_cases, case )
CNT.add(CNT, 1, "CASES:INSERT", { ["funcname"] = case.funcname, ["#args"] = lua_table.level_count(case.args), } )
end
end
-- tests_groups.kept_groups = result_cases
tests_groups.result_cases = result_cases
CNT.add(CNT, 1, "getcases all", { ["#kept_groups"] = lua_table.level_count(kept_groups), ["#result_cases"] = lua_table.level_count(result_cases), } )
return result_cases
end -- local result_cases = tests_groups.getcases(kept_groups)
 
function tests_groups.run_one_case(case) -- Run one case for users and MediaWiki tests cases.
-- function tests_groups.getTestProvider(), .init(), .gettestsgroups(), .getcases(), .resultdiffs(), .form(), .recursive_tests(), viewers.form9en(),
local case = tests_groups.normalcase(case) -- Normalize case options.
if type(case.args) ~= "table" then case.args = { case.args } end
if type(case.funcname) == "string" then
case.run = lua_table.from_subnames_object(case.funcname, base_table) -- Get the last sub-object from its sub-names.
end -- function lua_table.from_subnames_table(
if type(case.run) == "function" then -- 555 666 777
case.result = { case.run( case.args ) } -- Run the test case and record its results. see case.run =
case = tests_groups.resultdiffs(case) -- Formats errors in case.result{} where it differs from case.expect{}.
case.errors = case.errors
CNT.add(CNT, 1, "run_one_case after resultdiffs 6889", { ["case.key"] = case.key, ["case.error_n"] = case.error_n, ["errors"] = case.errors, } )
else
case.result = { [1] = "no case.run function", [2] = "no case.run function", } -- Run the test case and record its results. case.run =
CNT.add(CNT, 1, "run_one_case no function 6891", { ["case.result[1]"] = case.result[1], ["case.result[2]"] = case.result[2], } )
end
if (type(case.result) ~= "table") then -- Get diffs
case.result = case.result or {}
case.err = viewers.ta("case.result", case.result)
case.all_diffs = case.all_diffs or {}
table.insert( case.all_diffs, { ["sub_key"] = sub_key, ["status"] = status, ["err"] = case.err, } )
end
case.res1 = case.result[1] or "res1roc" -- DEBUG : mathroman.int2roman() can fail without blocking page.
case.err2 = case.result[case.errorsKey] or "err2" -- DEBUG : mathroman.int2roman() can fail without blocking page.e2
-- Use new diffs
case.res1 = case.result[1] or "res1" -- DEBUG : mathroman.int2roman() can fail without blocking page.
case.err2 = case.result[case.errorsKey] or "err2" -- DEBUG : mathroman.int2roman() can fail without blocking page.e2
return case -- for function tab_view.form_one_case(case)
end -- case = tests_groups.run_one_case(case)
 
-- cut_libraries
 
-- - - - ------------------ - - - - ------------------ - - - - -----------------------------
-- - - - ------------------ - - - - ------------------ - - - - -----------------------------
-- The Object:tracker implements parametrable track objects to debug the Lua code.
-- - - - ------------------ - - - - ------------------ - - - - -----------------------------
-- - - - ------------------ - - - - ------------------ - - - - -----------------------------
 
-- activity = {} -- already declared by Scribunto, in _G space, then in package.loaded["begin"].
-- tracker = {} -- already declared by Scribunto, see central_library.new() -- Record a library in package.loaded
tracker.obj = { -- Options from: default, init and use steps. To mix in obj.*
["level"] = 1, -- level of detail of each track line
["name"] = "TRACK", -- name of the track
["where"] = "IN TRACK", -- name of the track
["limit"] = 2, -- Limit of track more or less details
["form"] = "\n* %1 in=<b>%2</b>", -- begin or each track line
["more"] = ", arg%1=<b>%2</b>", -- add to the previous text
["t"] = "", -- resulting text with all track lines
["groupname"] = "*.+!;-/", -- to display all grouped events with a same name
["add"] = function() return "" end, -- for tracker.initadd(opt)
["trk"] = function() return "" end, -- for tracker.initrack(opt)
}
 
function tracker.new(opt) -- Initializes a track list.
-- The groupid option can select which track select and add in the groupname group.
if (type(opt) ~= "table") then opt = {} end
opt.level = opt.level or 1 -- level of detail of each track line
opt.name = opt.name or "TRACK" -- name of the track
opt.limit = opt.limit or 1 -- limit of detailed lines
opt.form = opt.form or "\n* %1 in=<b>%2</b>" -- begin or each track line
opt.more = opt.more or ", arg%1=<b>%2</b>" -- add to the previous text
opt.t = opt.t or "" -- resulting text with all track lines
opt.trackon = 1 -- track on or not (= 0) for one track object.
opt.groupid = opt.groupid -- to select tracks in a group
opt.groupname = opt.groupname -- to display all grouped events with a same name
return opt
end -- function tracker.new(opt)
 
function tracker.add(opt, level, IN, ... ) -- Adds, or not, a new track line to the track list.
local t = "" -- function tracker:add(self, ...) -- table.func = function ( self, var-list ) block end
if (type(opt) ~= "table") then return t end
if opt.trackon == 0 then return t end
if viewers.is_in_sp(opt.groupid, IN) then
opt.grouptrack = opt.groupname or opt.groupid
end
if opt.grouptrack then t = t .. "<b>" .. opt.grouptrack .. ":</b> " end
if (type(level) == "number") and (level > opt.limit) then return t end
local vals, vals_t = { ... }, ""
local vals_t = "\n* <b>" .. opt.name .. "</b>: " .. viewers.ta("in", IN)
if (type(vals[1]) == "table") then vals = vals[1] end
for k, var in pairs( vals ) do
if var ~= nil then vals_t = vals_t .. viewers.ta(k, tostring(var) ) end
end
if where == opt.name then -- List the tracker options
opt.values = viewers.ta("name", opt.name) -- .. viewers.ta("level", opt.level)
.. viewers.ta("limit", opt.limit) -- .. viewers.ta("form", opt.form) .. viewers.ta("more", opt.more)
.. viewers.ta("opt_N", lua_table.count_all(opt) ) .. viewers.ta("trackon", opt.trackon) -- .. viewers.ta("t", opt.t)
return opt.t .. vals_t .. opt.values .. "<br>"
end
opt.t = opt.t .. vals_t -- add this track to the list of track lines
t = t .. "<br>"
return t -- report local track line
end -- tracker.ARGS.t
 
function tracker.initadd_old(opt) -- Initialize a track
local obj = mw.clone(tracker.obj)
if (type(opt) ~= "table") then opt = {} end
for key, val in pairs(opt) do
if (type(key) == "string") and (val ~= nil) then obj[key] = val end
end
obj = tracker.new(obj)
opt.add = tracker.add
_G[obj.name] = obj
return obj
end -- function tracker.initadd(opt)
 
function tracker.initadd(opt) -- Initialize a track
if (type(opt) ~= "table") then opt = {} end
if (type(opt) == "table") and (type(opt.add) == "function") and (opt.name == _G[opt.name]) then
-- _G[opt.name] = opt -- Reuse already initialized tracker for its continuity.
-- return opt
end
opt = tracker.new(opt)
opt.add = tracker.add
_G[opt.name] = opt
return opt
end -- ARGS = tracker.initadd({ ["name"] = "ARGS", limit = 2, }) -- Initialize a track
 
-- See: "Function as a method in a table" in Lua_reference_manual#Function_declaration_statements
function tracker.initrack(opt) -- Initialize one new tracker and its track lines.
if (type(opt) ~= "table") then opt = { ["name"] = "DEFAULTRACK", ["limit"] = 2 } end
if (type(opt.name) ~= "string") then opt.name = "DEFAULTRACK" end
if (type(opt.limit) ~= "number") then opt.limit = 2 end
local optrk = mw.clone(opt) -- New initial tracker object
function optrk:trk(self, limit, name, vals) -- see S171015trk
return tracker.add(self, limit, name, vals) or "\n* optrk:trk. "
end
_G[optrk.name] = optrk
return optrk
end -- ARGS = tracker.initrack({ ["name"] = "ARGS", limit = 2, }) -- Initialize a track
 
-- cut_libraries
 
-- - - - ------------------ - - - - ------------------ - - - - -----------------------------
-- - - - ------------------ - - - - ------------------ - - - - -----------------------------
-- The Library:versions installs other libraries, supports versions, then binds modules, libraries and i18n translations.
-- This library supports modules to:
-- * Collect and bind modules and sub-modules depending from their p.version{}
-- * Collect and bind translations from modules or libraries itself, and their /I18N sub-modules
-- * Formats parametrable strings_c
-- * Add a language needs only to add its own i18n subtable, like i18n.en = {}
-- * Manage alternate versions of sub-modules sought in main, like Module:Sub, Module:Sub.2.1, Module:SubPlus.
-- A central module and its translations can inpedendently change. Its p.version{} identifications change also.
-- For this goal a module contains at least one i18n tranlations table. Its /I18N sub-modules contains translations in several languages.
-- Central Libraries, like modules, contain their own p.version{} identifications and i18n translations in Module:Library/library_name/I18N.
-- - - - ------------------ - - - - ------------------ - - - - -----------------------------
-- - - - ------------------ - - - - ------------------ - - - - -----------------------------
 
-- versions = {} -- The Library:versions installs other libraries, bind modules and libraries, bind i18n translations, manage versions.
-- versions = {} -- The Library:versions must stay in _G global space, to not change in init phase.
-- versions = {} -- already declared by Scribunto, see central_library.new() -- Record a library in package.loaded
-- Translations for versioning library
 
-- These Module:Centralizer/I18N translations for versions library update and complete Module:Centralizer translations.
versions.i18n = {}
versions.i18n.br = {
-- Principaux textes, erreurs et catégories des outils
versions_module_with_error_err = "Module avec erreur",
versions_with_internal_error = "Module avec erreur interne",
versions_with_internal_error_cat = "Module avec erreur interne",
versions_with_usage_error = "Module avec erreur d'utilisation",
versions_with_usage_error_cat = "Module avec erreur d'utilisation",
versions_err_module_miss_i18n_i_cat = "Module manquant de traduction i18n",
versions_module_miss_i18n_mini_err = "Erreur interne : La table i18n n'a que <b>%1</b> traductions.",
versions_running_times_title = "versions.running_times() Temps d'exécution et références pour les Lua-codeurs.",
versions_luatables_counts = "<b>%1</b> variables, <b>%3</b> sous-tables, <b>%2</b> fonctions",
versions_table_dont_exists = "La table <b>%1</b> n'existe pas.",
versions_table_listlimit_levelmaxi = "Limite de niveau recursive_limit = <b>%1</b> ",
versions_table_listlimit_max_n = "Limite de longueur max_n = <b>%1</b> ",
versions_antiCrash_tests_title = "versions.anti_crash() Test: en cas d'erreur en cours d'exécution, ne pas écraser la page.",
versions_antiCrash_reference_label = "Références",
versions_antiLoop_function_err = "versions.antiLoop() Erreur dans la <b>%3</b> <b>%1()</b>, boucle n = <b>%2</b>, args = ",
versions_with_usage_error_cat = "Module avec erreur d'utilisation",
versions_module_with_error_err = "Module avec erreur",
versions_with_internal_error_cat = "Module avec erreur interne",
 
-- Gestion des versions
versions_versions_no_select_altern_err = "Erreur de versions : pas de sélection dans l'alternative <b>%1</b> du module <b>%2</b>.",
versions_versions_too_select_altern_err = "Erreur de versions : <b>%1</b> sélections dans l'alternative <b>%2</b> du module <b>%3</b>.",
versions_versions_select_not_used_err = "Erreur de versions : le sélecteur <b>%1</b> n'est pas dans les alternatives <b>%2</b> du module <b>%3</b>.",
versions_versions_missing_module_err = "Erreur de versions : module absent pour la version <b>%1</b> du module <b>%2</b>.",
versions_main_module_missing_err = "Le module principal est introuvable.",
versions_select_unknown_module_err = "Internal error: Le Module:<b>%1</b> manquant est remplacé par le module normal Module:<b>%2</b>.",
versions_I18N_module_no_base_err = "Le module de traductions <b>%1</b> n'a pas de version de base.",
versions_no_versions_module_err = "Le module <b>%1</b> n'est pas dans le système des versions.",
versions_all_versions_tests = "Versions avertissements : <b>%1</b>, normaux : <b>%2</b>, liste : <b>%3</b>.",
versions_all_versions_check = "Versions: manquantes: <b>%1</b>, inconnues: <b>%2</b>, normales: <b>%3</b>, en excès: <b>%4</b>, toutes selectionées : <b>%5</b>.",
versions_missing_versions_err = "Le module <b>%1</b> manque dans le module principal <b>%2</b>.",
versions_replaced_versions_err = "Le module <b>%1</b> remplace le sous-module absent dans le module principal <b>%2</b>.",
versions_unknownversions_err = "Le module <b>%1</b> est inconnu dans le module principal <b>%2</b>.",
versions_module_miss_i18n_txt_err = "Erreur interne : Le texte <b>%1</b> manque de traduction en langue <b>%2</b>, et/ou d'autres.",
versions_module_miss_i18n_count_err = "Erreur interne : Il y a <b>%1</b> manques parmi <b>%2</b> traductions.",
versions_module_miss_i18n_none_err = "OK, aucune traduction manquante.",
versions_module_miss_i18n_trad_err = "Erreur interne : manque de traduction pour l'argument <b>i18n.%1.%2</b>.",
 
-- Titres des tests
versions_all_G_and_loaded_list_title = "versions.all_G_and_loaded_list() Objects dans l'espace global _G",
versions_central_changes_headers = "clé; valeur; compte; niveau",
versions_support_desk_title = "Informations de soutien: en version <b>%1</b>",
versions_versions_management_report = "versions.versions_management_report() Rapport de gestion des versions",
-- versions_bind_modules_tests_title = "versions.bind_modules_test() Test de la gestion des versions des modules",
versions_verif_bind_modules_report = "Liaison des modules et contrôle des versions",
versions_bind_modules_test_headers = "Versions demandées; Versions utilisées; Versions connues; ACTUEL : Erreurs dans le module actif; SIMULATION : Erreurs dans le module actif",
versions_tasks_changes_report = "versions.tasks_changes_report() Documentations, tâches et modifications",
versions_sort_central_modules_title = "versions.sort_central_modules_report() Liste triée des modules et bibliothèques centraux.",
versions_sort_central_modules_headers = "Titre; Version; Date; Traductions / Langues",
versions_sort_central_modules_counts = "ceci: + <b>%2</b>/<b>%3</b> T/L, ",
versions_versions_management_title = "versions.versions_management_test() Tests du support de versions.",
versions_versions_management_headers = "sought; versions; process; comments",
versions_add_deprecated_err = "Fonction obsolète <b>%1(...)</b>. Remplacez-la par <b>%2(...)</b> dans le module <b>%3</b>.",
versions_deprecated_function_tests = "versions.deprecated_function() Test: Fonction obsolète. Remplacez-la dans le module.",
} -- versions.i18n.br
versions.i18n.de = {
-- Principaux textes, erreurs et catégories des outils
versions_module_with_error_err = "Modul mit Fehler",
versions_with_internal_error = "Modul mit internem Fehler",
versions_with_internal_error_cat = "Modul mit internem Fehler",
versions_with_usage_error = "Modul mit Bedienungsfehler",
versions_with_usage_error_cat = "Modul mit Bedienungsfehler",
versions_err_module_miss_i18n_i_cat = "Modul fehlende Übersetzung i18n",
versions_module_miss_i18n_mini_err = "Erreur interne : La table i18n n'a que <b>%1</b> traductions.",
versions_running_times_title = "versions.running_times() Temps d'exécution et références pour les Lua-codeurs.",
versions_luatables_counts = "<b>%1</b> variables, <b>%3</b> sous-tables, <b>%2</b> fonctions",
versions_table_dont_exists = "La table <b>%1</b> n'existe pas.",
versions_table_listlimit_levelmaxi = "Limite de niveau recursive_limit = <b>%1</b> ",
versions_table_listlimit_max_n = "Limite de longueur max_n = <b>%1</b> ",
versions_antiCrash_tests_title = "versions.anti_crash() Test: en cas d'erreur en cours d'exécution, ne pas écraser la page.",
versions_antiCrash_reference_label = "Références",
versions_antiLoop_function_err = "versions.antiLoop() Erreur dans la <b>%3</b> <b>%1()</b>, boucle n = <b>%2</b>, args = ",
versions_with_usage_error_cat = "Module avec erreur d'utilisation",
versions_module_with_error_err = "Module avec erreur",
versions_with_internal_error_cat = "Module avec erreur interne",
 
-- Gestion des versions
versions_versions_no_select_altern_err = "Erreur de versions : pas de sélection dans l'alternative <b>%1</b> du module <b>%2</b>.",
versions_versions_too_select_altern_err = "Erreur de versions : <b>%1</b> sélections dans l'alternative <b>%2</b> du module <b>%3</b>.",
versions_versions_select_not_used_err = "Erreur de versions : le sélecteur <b>%1</b> n'est pas dans les alternatives <b>%2</b> du module <b>%3</b>.",
versions_versions_missing_module_err = "Erreur de versions : module absent pour la version <b>%1</b> du module <b>%2</b>.",
versions_main_module_missing_err = "Le module principal est introuvable.",
versions_select_unknown_module_err = "Internal error: Le Module:<b>%1</b> manquant est remplacé par le module normal Module:<b>%2</b>.",
versions_I18N_module_no_base_err = "Le module de traductions <b>%1</b> n'a pas de version de base.",
versions_no_versions_module_err = "Le module <b>%1</b> n'est pas dans le système des versions.",
versions_all_versions_tests = "Versions avertissements : <b>%1</b>, normaux : <b>%2</b>, liste : <b>%3</b>.",
versions_all_versions_check = "Versions: manquantes: <b>%1</b>, inconnues: <b>%2</b>, normales: <b>%3</b>, en excès: <b>%4</b>, toutes selectionées : <b>%5</b>.",
versions_missing_versions_err = "Le module <b>%1</b> manque dans le module principal <b>%2</b>.",
versions_replaced_versions_err = "Le module <b>%1</b> remplace le sous-module absent dans le module principal <b>%2</b>.",
versions_unknownversions_err = "Le module <b>%1</b> est inconnu dans le module principal <b>%2</b>.",
versions_module_miss_i18n_txt_err = "Erreur interne : Le texte <b>%1</b> manque de traduction en langue <b>%2</b>, et/ou d'autres.",
versions_module_miss_i18n_count_err = "Erreur interne : Il y a <b>%1</b> manques parmi <b>%2</b> traductions.",
versions_module_miss_i18n_none_err = "OK, aucune traduction manquante.",
versions_module_miss_i18n_trad_err = "Erreur interne : manque de traduction pour l'argument <b>i18n.%1.%2</b>.",
 
-- Titres des tests
versions_all_G_and_loaded_list_title = "versions.all_G_and_loaded_list() Objects dans l'espace global _G",
versions_central_changes_headers = "clé; valeur; compte; niveau",
versions_support_desk_title = "Informations de soutien: en version <b>%1</b>",
versions_versions_management_report = "versions.versions_management_report() Rapport de gestion des versions",
-- versions_bind_modules_tests_title = "versions.bind_modules_test() Test de la gestion des versions des modules",
versions_verif_bind_modules_report = "Liaison des modules et contrôle des versions",
versions_bind_modules_test_headers = "Versions demandées; Versions utilisées; Versions connues; ACTUEL : Erreurs dans le module actif; SIMULATION : Erreurs dans le module actif",
versions_tasks_changes_report = "versions.tasks_changes_report() Documentations, tâches et modifications",
versions_sort_central_modules_title = "versions.sort_central_modules_report() Liste triée des modules et bibliothèques centraux.",
versions_sort_central_modules_headers = "Titre; Version; Date; Traductions / Langues",
versions_sort_central_modules_counts = "ceci: + <b>%2</b>/<b>%3</b> T/L, ",
versions_versions_management_title = "versions.versions_management_test() Tests du support de versions.",
versions_versions_management_headers = "sought; versions; process; comments",
versions_add_deprecated_err = "Fonction obsolète <b>%1(...)</b>. Remplacez-la par <b>%2(...)</b> dans le module <b>%3</b>.",
versions_deprecated_function_tests = "versions.deprecated_function() Test: Fonction obsolète. Remplacez-la dans le module.",
} -- versions.i18n.de
versions.i18n.en = {
-- Main string, errors and categories of tools
versions_module_with_error_err = "Module with error",
versions_with_internal_error = "Module with internal error",
versions_with_internal_error_cat = "Module with internal error",
versions_with_usage_error = "Module with usage error",
versions_with_usage_error_cat = "Module with usage error",
versions_running_times_title = "versions.running_times() Running times and references for Lua coders.",
versions_luatables_counts = "<b>%1</b> variables, <b>%3</b> sub-tables, <b>%2</b> functions",
versions_table_dont_exists = "The table <b>%1</b> does not exist.",
versions_table_listlimit_levelmaxi = "Level limit recursive_limit = <b>%1</b> ",
versions_table_listlimit_max_n = "Length limit max_n = <b>%1</b> ",
versions_antiCrash_tests_title = "versions.anti_crash() Test: in case of running error, do not crash the page.",
versions_antiCrash_reference_label = "References",
versions_antiLoop_function_err = "versions.antiLoop() error in the <b>%3</b> <b>%1()</b>, loop n = <b>%2</b>, args = ",
-- Versions management
versions_versions_no_select_altern_err = "Versions error: no selection in the alternative <b>%1</b> of the module <b>%2</b>.",
versions_versions_too_select_altern_err = "Versions error: <b>%1</b> selections in the alternative <b>%2</b> of the module <b>%3</b>.",
versions_versions_select_not_used_err = "Versions error: <b>%1</b> selector is not in alternative <b>%2</b> of the module <b>%3</b>.",
versions_versions_missing_module_err = "Versions error: missing module for the version <b>%1</b> of the module <b>%2</b>.",
versions_main_module_missing_err = "The main module is not found.",
versions_select_unknown_module_err = "Internal error: The missing Module:<b>%1</b> is replaced by the normal Module:<b>%2</b>.",
versions_I18N_module_no_base_err = "The <b>%1</b> translations module has no basic version.",
versions_no_versions_module_err = "The module <b>%1</b> is not in the system of versions.",
versions_all_versions_tests = "Versions warning: <b>%1</b>, normal: <b>%2</b>, listall: <b>%3</b>.",
versions_all_versions_check = "Versions: missings: <b>%1</b>, unknowns: <b>%2</b>, normals: <b>%3</b>, excess: <b>%4</b>, all selected: <b>%5</b>.",
versions_missing_versions_err = "The module <b>%1</b> misses in the main module <b>%2</b>.",
versions_replaced_versions_err = "The module <b>%1</b> replaces the missing sub-module in the main module <b>%2</b>.",
versions_unknownversions_err = "The module <b>%1</b> is unknown in the main module <b>%2</b>.",
versions_module_miss_i18n_txt_err = "Internal Error: The text <b>%1</b> lack of translation in <b>%2</b> language, and/or others.",
versions_module_miss_i18n_count_err = "Internal Error: There are <b>%1</b> missings in <b>%2</b> translations.",
versions_module_miss_i18n_none_err = "OK, none missing translations.",
versions_module_miss_i18n_trad_err = "Internal Error: Module missing i18n translation for the argument <b>i18n.%1.%2</b>.",
versions_err_module_miss_i18n_cat = "Module missing i18n translation",
versions_err_module_miss_i18n_cat = "Module with internal error",
versions_module_miss_i18n_mini_err = "Error: I18n table has only <b>1%</b> translations.",
 
-- Titles of tests
versions_all_G_and_loaded_list_title = "versions.all_G_and_loaded_list() Objects in _G global space",
versions_central_changes_headers = "key; val; count; level",
versions_support_desk_title = "Support information: in version <b>%1</b>",
versions_versions_management_report = "versions.versions_management_report() Versions management report",
-- versions_bind_modules_tests_title = "versions.bind_modules_test() Test for management of modules versions",
versions_verif_bind_modules_report = "Binding of modules and versions control",
versions_bind_modules_test_headers = "Sought versions; Used versions; Known versions; ACTUAL: Errors in the active module; SIMULATION: Errors in the active module",
versions_tasks_changes_report = "versions.tasks_changes_report() Documentations, tasks and changes",
versions_sort_central_modules_title = "versions.sort_central_modules_report() Sorted list of central modules and libraries.",
versions_sort_central_modules_headers = "Title; Version; Date; Translations / Languages",
versions_sort_central_modules_counts = "this: + <b>%2</b>/<b>%3</b> T/L, ",
versions_versions_management_title = "versions.versions_management_test() Tests of versions management.",
versions_versions_management_headers = "sought; versions; process; comments",
versions_add_deprecated_err = "Deprecated function <b>%1(...)</b>. Replace it by <b>%2(...)</b> in the module <b>%3</b>.",
versions_deprecated_function_tests = "versions.deprecated_function() Test: Deprecated function. Replace it in the module.",
} -- versions.i18n.en
versions.i18n.es = {
-- Textos principales, errores y categorías de instrumentos
versions_module_with_error_err = "Módulo con error",
versions_with_internal_error = "Módulo con error interno",
versions_with_internal_error_cat = "Módulo con error interno",
versions_with_usage_error = "Módulo con error del uso",
versions_with_usage_error_cat = "Módulo con error del uso",
versions_err_module_miss_i18n_i_cat = "Módulo traducción i18n que falta",
versions_running_times_title = "versions.running_times() Tiempos de ejecución y referencias para los codificadores Lua.",
versions_luatables_counts = "<b>%1</b> variables, <b>%3</b> subtablas, <b>%2</b> funciones",
versions_table_dont_exists = "La tabla <b>%1</b> no existe.",
versions_table_listlimit_levelmaxi = "Límite de nivel recursive_limit = <b>%1</b>",
versions_table_listlimit_max_n = "Límite de longitud max_n = <b>%1</b>",
versions_antiCrash_tests_title = "versions.anti_crash() Prueba: en caso de error de ejecución, no sobrescribir la página.",
versions_antiCrash_reference_label = "Referencias",
versions_antiLoop_function_err = "versions.antiLoop() Error en el <b>%3</b> <b>%1()</b>, bucle n = <b>%2</b>, args = ",
versions_with_usage_error_cat = "Módulo con error del uso",
versions_module_with_error_err = "Módulo con error",
versions_with_internal_error_cat = "Módulo con interno error",
 
-- Gestión de versiones
versions_versions_no_select_altern_err = "Error de versiones: no hay selección en alternativa <b>%1</b> del módulo <b>%2</b>.",
versions_versions_too_select_altern_err = "Error de versiones: <b>%1</b> selecciones en la alternativa <b>%2</b> del módulo <b>%3</b>.",
versions_versions_select_not_used_err = "Error de versiones: selector <b>%1</b> no es en alternativas <b>%2</b> del módulo <b>%3</b>.",
versions_versions_missing_module_err = "Error de versiones: módulo ausente para la versión <b>%1</b> del módulo <b>%2</b>.",
versions_main_module_missing_err = "El módulo principal no es encontrado.",
versions_select_unknown_module_err = "Internal error: El Módulo:<b>%1</b> faltante se reemplaza por lo normal Module:<b>%2</b>.",
versions_I18N_module_no_base_err = "El módulo de traducciones <b>%1</b> no tiene ninguna versión básica.",
versions_no_versions_module_err = "El <b>%1</b> módulo no está en el sistema de versiones.",
versions_all_versions_tests = "Versiones aviso: <b>%1</b>, normal: <b>%2</b>, lista: <b>%3</b>.",
versions_all_versions_check = "Versiones: falta: <b>%1</b>, incógnitas: <b>%2</b>, normales: <b>%3</b>, en exceso: <b>%4</b>, selecciona todo: <b>%5</b>.",
versions_missing_versions_err = "El módulo <b>%1</b> no disponible en el módulo principal <b>%2</b>.",
versions_replaced_versions_err = "El módulo <b>%1</b> reemplaza el sub-módulo ausente en el módulo principal <b>%2</b>.",
versions_unknownversions_err = "El módulo <b>%1</b> es desconocido en el módulo principal <b>%2</b>.",
versions_module_miss_i18n_txt_err = "Error Interno: El texto <b>%1</b> falta de traducción en <b>%2</b> lengua, y / o otras.",
versions_module_miss_i18n_count_err = "Error interno: Hay <b>%1</b> que falta en <b>%2</b> traducciones.",
versions_module_miss_i18n_none_err = "OK, ninguno traducciones que faltan.",
versions_module_miss_i18n_trad_err = "Error interno: translation faltan en Módulo i18n para el argumento <b>i18n.%1.%2</b>.",
versions_module_miss_i18n_mini_err = "Error: la tabla i18n tiene solamente <b>1%</b> traducciones.",
 
-- Titres des pruebas
versions_all_G_and_loaded_list_title = "versions.all_G_and_loaded_list() Objects en el espacio global _G",
versions_central_changes_headers = "llave; valor; contar; nivel",
versions_support_desk_title = "Información de soporte: en versión <b>%1</b>",
versions_versions_management_report = "versions.versions_management_report() Informe de gestión de versiones",
-- versions_bind_modules_tests_title = "versions.bind_modules_test() Test for management of modules versions",
versions_verif_bind_modules_report = "Binding of modules and versions control",
versions_bind_modules_test_headers = "Sought versions; Used versions; Known versions; ACTUAL: Errors in the active module; SIMULATION: Errors in the active module",
versions_tasks_changes_report = "versions.tasks_changes_report() Documentación, parches y modificaciones",
versions_sort_central_modules_title = "versions.sort_central_modules_report() Lista ordenada de módulos y bibliotecas centrales.",
versions_sort_central_modules_headers = "Título; Versión; Fecha; Traducciones / Idiomas",
versions_sort_central_modules_counts = "esta + <b>%2</b>/<b>%3</b> T/I, ",
versions_versions_management_title = "versions.versions_management_test() Pruebas de gestión de versiones.",
versions_versions_management_headers = "sought; versions; process; comments",
versions_add_deprecated_err = "Función obsoleta <b>%1(...)</b>. Sustitúyala por <b>%2(...)</b> en el módulo <b>%3</b>.",
versions_deprecated_function_tests = "versions.deprecated_function() Prueba: Función obsoleta. Sustitúyala en el módulo.",
} -- versions.i18n.es
versions.i18n.fr = {
-- Principaux textes, erreurs et catégories des outils
versions_module_with_error_err = "Module avec erreur",
versions_with_internal_error = "Module avec erreur interne",
versions_with_internal_error_cat = "Module avec erreur interne",
versions_with_usage_error = "Module avec erreur d'utilisation",
versions_with_usage_error_cat = "Module avec erreur d'utilisation",
versions_err_module_miss_i18n_i_cat = "Module manquant de traduction i18n",
versions_module_miss_i18n_mini_err = "Erreur interne : La table i18n n'a que <b>%1</b> traductions.",
versions_running_times_title = "versions.running_times() Temps d'exécution et références pour les Lua-codeurs.",
versions_luatables_counts = "<b>%1</b> variables, <b>%3</b> sous-tables, <b>%2</b> fonctions",
versions_table_dont_exists = "La table <b>%1</b> n'existe pas.",
versions_table_listlimit_levelmaxi = "Limite de niveau recursive_limit = <b>%1</b> ",
versions_table_listlimit_max_n = "Limite de longueur max_n = <b>%1</b> ",
versions_antiCrash_tests_title = "versions.anti_crash() Test: en cas d'erreur en cours d'exécution, ne pas écraser la page.",
versions_antiCrash_reference_label = "Références",
versions_antiLoop_function_err = "versions.antiLoop() Erreur dans la <b>%3</b> <b>%1()</b>, boucle n = <b>%2</b>, args = ",
versions_with_usage_error_cat = "Module avec erreur d'utilisation",
versions_module_with_error_err = "Module avec erreur",
versions_with_internal_error_cat = "Module avec erreur interne",
 
-- Gestion des versions
versions_versions_no_select_altern_err = "Erreur de versions : pas de sélection dans l'alternative <b>%1</b> du module <b>%2</b>.",
versions_versions_too_select_altern_err = "Erreur de versions : <b>%1</b> sélections dans l'alternative <b>%2</b> du module <b>%3</b>.",
versions_versions_select_not_used_err = "Erreur de versions : le sélecteur <b>%1</b> n'est pas dans les alternatives <b>%2</b> du module <b>%3</b>.",
versions_versions_missing_module_err = "Erreur de versions : module absent pour la version <b>%1</b> du module <b>%2</b>.",
versions_main_module_missing_err = "Le module principal est introuvable.",
versions_select_unknown_module_err = "Internal error: Le Module:<b>%1</b> manquant est remplacé par le module normal Module:<b>%2</b>.",
versions_I18N_module_no_base_err = "Le module de traductions <b>%1</b> n'a pas de version de base.",
versions_no_versions_module_err = "Le module <b>%1</b> n'est pas dans le système des versions.",
versions_all_versions_tests = "Versions avertissements : <b>%1</b>, normaux : <b>%2</b>, liste : <b>%3</b>.",
versions_all_versions_check = "Versions: manquantes: <b>%1</b>, inconnues: <b>%2</b>, normales: <b>%3</b>, en excès: <b>%4</b>, toutes selectionées : <b>%5</b>.",
versions_missing_versions_err = "Le module <b>%1</b> manque dans le module principal <b>%2</b>.",
versions_replaced_versions_err = "Le module <b>%1</b> remplace le sous-module absent dans le module principal <b>%2</b>.",
versions_unknownversions_err = "Le module <b>%1</b> est inconnu dans le module principal <b>%2</b>.",
versions_module_miss_i18n_txt_err = "Erreur interne : Le texte <b>%1</b> manque de traduction en langue <b>%2</b>, et/ou d'autres.",
versions_module_miss_i18n_count_err = "Erreur interne : Il y a <b>%1</b> manques parmi <b>%2</b> traductions.",
versions_module_miss_i18n_none_err = "OK, aucune traduction manquante.",
versions_module_miss_i18n_trad_err = "Erreur interne : manque de traduction pour l'argument <b>i18n.%1.%2</b>.",
 
-- Titres des tests
versions_all_G_and_loaded_list_title = "versions.all_G_and_loaded_list() Objects dans l'espace global _G",
versions_central_changes_headers = "clé; valeur; compte; niveau",
versions_support_desk_title = "Informations de soutien: en version <b>%1</b>",
versions_versions_management_report = "versions.versions_management_report() Rapport de gestion des versions",
-- versions_bind_modules_tests_title = "versions.bind_modules_test() Test de la gestion des versions des modules",
versions_verif_bind_modules_report = "Liaison des modules et contrôle des versions",
versions_bind_modules_test_headers = "Versions demandées; Versions utilisées; Versions connues; ACTUEL : Erreurs dans le module actif; SIMULATION : Erreurs dans le module actif",
versions_tasks_changes_report = "versions.tasks_changes_report() Documentations, tâches et modifications",
versions_sort_central_modules_title = "versions.sort_central_modules_report() Liste triée des modules et bibliothèques centraux.",
versions_sort_central_modules_headers = "Titre; Version; Date; Traductions / Langues",
versions_sort_central_modules_counts = "ceci: + <b>%2</b>/<b>%3</b> T/L, ",
versions_versions_management_title = "versions.versions_management_test() Tests du support de versions.",
versions_versions_management_headers = "sought; versions; process; comments",
versions_add_deprecated_err = "Fonction obsolète <b>%1(...)</b>. Remplacez-la par <b>%2(...)</b> dans le module <b>%3</b>.",
versions_deprecated_function_tests = "versions.deprecated_function() Test: Fonction obsolète. Remplacez-la dans le module.",
} -- versions.i18n.fr
versions.i18n.hu = {
-- Fő szövegek, hibák és szerszámkategóriák
versions_module_with_error_err = "A modul hibás",
versions_with_internal_error = "Modul belső hibával",
versions_with_internal_error_cat = "Modul belső hibával",
versions_with_usage_error = "Modul hibás használat esetén",
versions_with_usage_error_cat = "Modul hibás használat esetén",
versions_err_module_miss_i18n_i_cat = "Az i18n hiányzó modul hiányzik",
versions_module_miss_i18n_mini_err = "Belső hiba: Az i18n táblázat csak <b>%1</b> fordításokat tartalmaz.",
versions_running_times_title = "versions.running_times() Végrehajtási idők és hivatkozások a Lua-kódolók számára.",
versions_luatables_counts = "<b>%1</b> változók, <b>%2</b> allables, <b>%3</b> függvények",
versions_table_dont_exists = "A <b>%1</b> táblázat nem létezik.",
versions_table_listlimit_levelmaxi = "Szintkorlát recursive_limit = <b>%1</b> ",
versions_table_listlimit_max_n = "Hossza határ max_n = <b>%1</b> ",
versions_antiCrash_tests_title = "versions.anti_crash() Teszt: futás közben hiba esetén ne írja felül az oldalt.",
versions_antiCrash_reference_label = "referenciák",
versions_antiLoop_function_err = "versions.antiLoop() Hiba a <b>%1</b> <b>%2</b> hurokban n = <b>%3</b>, args = ",
versions_with_usage_error_cat = "Modul hibás használat esetén",
versions_module_with_error_err = "A modul hibás",
versions_with_internal_error_cat = "Modul belső hibával",
 
-- Gestion des versions
versions_versions_no_select_altern_err = "Változatok hiba: nincs lehetőség a modul <b>%1</b> alternatívájára <b>%2</b>.",
versions_versions_too_select_altern_err = "Változatok hiba: <b>%1</b> választása a modul <b>%2</b> alternatívájaként <b>%3</b>.",
versions_versions_select_not_used_err = "Változatok hiba: a <b>%1</b> választó nem szerepel az alternatívákban <b>%2</b> a modul <b>%3</b>.",
versions_versions_missing_module_err = "Változatok hiba: hiányzó modul a verzióhoz <b>%1</b> a modul <b>%2</b>.",
versions_main_module_missing_err = "A főmodul nem található.",
versions_select_unknown_module_err = "Belső hiba: Modul: <b>%1</b> hiányzik a normál modul helyett. Modul:<b>%2</b>.",
versions_I18N_module_no_base_err = "A fordítási modul <b>%1</b> nem rendelkezik alapváltozattal.",
versions_no_versions_module_err = "A <b>%1</b> modul nincs a verziórendszerben.",
versions_all_versions_tests = "Figyelmeztető verziók: <b>%1</b>, normál: <b>%2</b>, lista: <b>%3</b>.",
versions_all_versions_check = "Változatok: hiányzik: <b>%1</b>, ismeretlen: <b>%2</b>, normál: <b>%3</b>, feleslegben: <b>%4</b>, minden kiválasztott: <b>%5</b>.",
versions_missing_versions_err = "A modul <b>%1</b> manque dans le module principal <b>%2</b>.",
versions_replaced_versions_err = "A modul <b>%1</b> helyettesíti a hiányzó al-modulot a főmodulban <b>%2</b>.",
versions_unknownversions_err = "A modul <b>%1</b> a fő modulban ismeretlen <b>%2</b>.",
versions_module_miss_i18n_txt_err = "Belső hiba: A <b>%1</b> szöveg hiányzik a <b>%2</b> fordításban és / vagy más nyelven.",
versions_module_miss_i18n_count_err = "Belső hiba: <b>%1</b> hiányosságok vannak a <b>%2</b> fordítások között.",
versions_module_miss_i18n_none_err = "OK, nincs hiányzó fordítás.",
versions_module_miss_i18n_trad_err = "Belső hiba: az érvelés fordításának hiánya <b>i18n.%1.%2</b>.",
 
-- Titres des tests
versions_all_G_and_loaded_list_title = "versions.all_G_and_loaded_list() Tárgyak a globális térben _G",
versions_central_changes_headers = "kulcs; érték; figyelembe; szint",
versions_support_desk_title = "Támogatási információ: verzió <b>%1</b>",
versions_versions_management_report = "versions.versions_management_report() Jelentés menedzsment az verziók",
-- versions_bind_modules_tests_title = "versions.bind_modules_test() Modul teszt a menedzsment az verziók",
versions_verif_bind_modules_report = "Modulkötés és verziókezelés",
versions_bind_modules_test_headers = "Kért változatok; Használt verziók; Ismert változatok; CURRENT: Hibák az aktív modulban; SZIMULÁCIÓ: Az aktív modul hibái",
versions_tasks_changes_report = "versions.tasks_changes_report() Dokumentációk, feladatok és módosítások",
versions_sort_central_modules_title = "versions.sort_central_modules_report() A modulok és a központi könyvtárak rendezett listája.",
versions_sort_central_modules_headers = "Cím; változata; dátum; Fordítások / Nyelvek",
versions_sort_central_modules_counts = "ezt: + <b>%2</b>/<b>%3</b> T/L, ",
versions_versions_management_title = "versions.versions_management_test() Teszt a menedzsment az verziók.",
versions_versions_management_headers = "keresett; változatban; folyamat; Hozzászólások",
versions_add_deprecated_err = "Elavult funkció <b>%1(...)</b>. Helyezze vissza <b>%2(...)</b> a modulba <b>%3</b>.",
versions_deprecated_function_tests = "versions.deprecated_function() Teszt: elavult funkció. Helyezze vissza a modulba.",
} -- versions.i18n.hu
versions.i18n.vi = {
-- Các văn bản, lỗi và danh mục chính của công cụ
versions_module_with_error_err = "Mô-đun có lỗi",
versions_with_internal_error = "Mô-đun có lỗi nội bộ",
versions_with_internal_error_cat = "Mô-đun có lỗi nội bộ",
versions_with_usage_error = "Mô-đun có lỗi sử dụng",
versions_with_usage_error_cat = "Mô-đun có lỗi sử dụng",
versions_err_module_miss_i18n_i_cat = "Mô-đun thiếu bản dịch i18n",
versions_module_miss_i18n_mini_err = "Lỗi nội bộ: Bảng i18n chỉ có <b>%1</b> dịch.",
versions_running_times_title = "versions.running_times() Thời gian thực hiện và tài liệu tham khảo cho Lua-coders.",
versions_luatables_counts = "<b>%1</b> biến, <b>%3</b> Subtables, <b>%2</b> chức năng",
versions_table_dont_exists = "Bảng <b>%1</b> không tồn tại.",
versions_table_listlimit_levelmaxi = "Giới hạn mức recursive_limit = <b>%1</b> ",
versions_table_listlimit_max_n = "Giới hạn độ dài max_n = <b>%1</b> ",
versions_antiCrash_tests_title = "versions.anti_crash() Kiểm tra: trong trường hợp lỗi khi chạy, không ghi đè lên trang.",
versions_antiCrash_reference_label = "Khảo",
versions_antiLoop_function_err = "versions.antiLoop() Lỗi trong vòng lặp <b>%3</b> <b>%1()</b>, lặp n = <b>%2</b>, args = ",
versions_with_usage_error_cat = "Mô-đun có lỗi sử dụng",
versions_module_with_error_err = "Mô-đun có lỗi",
versions_with_internal_error_cat = "Mô-đun có lỗi nội bộ",
-- Quản lý phiên bản
versions_versions_no_select_altern_err = "Lỗi phiên bản: không có lựa chọn nào thay thế <b>%1</b> của mô-đun <b>%2</b>.",
versions_versions_too_select_altern_err = "Lỗi phiên bản: <b>%1</b> lựa chọn thay thế <b>%2</b> của mô-đun <b>%3</b>.",
versions_versions_select_not_used_err = "Lỗi phiên bản: bộ chọn <b>%1</b> không có trong lựa chọn thay thế <b>%2</b> của mô-đun <b>%3</b>.",
versions_versions_missing_module_err = "Lỗi phiên bản: mô-đun không khả dụng cho phiên bản <b>%1</b> của mô-đun <b>%2</b>.",
versions_main_module_missing_err = "Không tìm thấy mô-đun chính.",
versions_select_unknown_module_err = "Lỗi nội bộ: Mô-đun:<b>%1</b> mất tích được thay thế bởi bình thường Mô-đun:<b>%2</b>.",
versions_I18N_module_no_base_err = "Mô-đun dịch <b>%1</b> không có phiên bản cơ bản.",
versions_no_versions_module_err = "Mô-đun <b>%1</b> không nằm trong hệ thống phiên bản.",
versions_all_versions_tests = "Các phiên bản cảnh báo: <b>%1</b>, bình thường: <b>%2</b>, danh sách: <b>%3</b>.",
versions_all_versions_check = "Phiên bản: thiếu: <b>%1</b>, ẩn số: <b>%2</b>, bình thường: <b>%3</b>, vượt quá: <b>%4</b>, tất cả đã chọn: <b>%5</b>.",
versions_missing_versions_err = "Mô-đun <b>%1</b> bị thiếu trong mô-đun chính <b>%2</b>.",
versions_replaced_versions_err = "Mô-đun <b>%1</b> thay thế mô-đun phụ bị thiếu trong mô-đun chính <b>%2</b>.",
versions_unknownversions_err = "Mô-đun <b>%1</b> không được biết trong mô-đun chính <b>%2</b>.",
versions_module_miss_i18n_txt_err = "Lỗi nội bộ: Văn bản <b>%1</b> thiếu bản dịch ngôn ngữ <b>%2</b>, và / hoặc những người khác.",
versions_module_miss_i18n_count_err = "Lỗi nội bộ: Có khoảng cách <b>%1</b> trong số <b>%2</b> bản dịch.",
versions_module_miss_i18n_none_err = "OK, không có bản dịch bị thiếu.",
versions_module_miss_i18n_trad_err = "Lỗi nội bộ: thiếu bản dịch cho đối số <b>i18n.%1.%2</b>.",
-- Tiêu đề kiểm tra
versions_all_G_and_loaded_list_title = "versions.all_G_and_loaded_list() Các đối tượng trong không gian toàn cầu _G",
versions_central_changes_headers = "chính; giá trị; tài khoản; trình độ",
versions_support_desk_title = "Thông tin hỗ trợ: Phiên bản <b>%1</b>",
versions_versions_management_report = "versions.versions_management_report() Báo cáo quản lý phát hành",
-- versions_bind_modules_tests_title = "versions.bind_modules_test() Kiểm tra quản lý phiên bản mô-đun",
versions_verif_bind_modules_report = "Kiểm soát phiên bản và ràng buộc mô-đun",
versions_bind_modules_test_headers = "Các phiên bản được yêu cầu; Các phiên bản được sử dụng; Các phiên bản đã biết; CURRENT: Lỗi trong mô-đun đang hoạt động; Mô phỏng: Lỗi trong mô-đun đang hoạt động",
versions_tasks_changes_report = "versions.tasks_changes_report() Tài liệu, nhiệm vụ và sửa đổi",
versions_sort_central_modules_title = "versions.sort_central_modules_report() Sắp xếp danh sách các mô-đun và thư viện trung tâm.",
versions_sort_central_modules_headers = "Tiêu đề; phiên bản; ngày; Bản dịch / Ngôn ngữ",
versions_sort_central_modules_counts = "điều này: + <b>%2</b>/<b>%3</b> T/L, ",
versions_versions_management_title = "versions.versions_management_test() Kiểm tra hỗ trợ phiên bản.",
versions_versions_management_headers = "tìm kiếm; phiên bản; quá trình; bình luận",
versions_add_deprecated_err = "Hàm không được chấp nhận <b>%1(...)</b>. Thay thế bằng <b>%2(...)</b> trong mô-đun <b>%3</b>.",
versions_deprecated_function_tests = "versions.deprecated_function() Test: Chức năng lỗi thời. Thay thế nó trong mô-đun.",
} -- versions.i18n.vi
 
versions.ModuleNS = mw.site.namespaces.Module.name .. ":"
 
function versions.bind_all_i18n() -- Bind all i18n translations from all sub-modules in reverse order.
-- Translate all translations in the exact reverse order, using the memorised binding order.
-- Then upper modules happens later and can adapt translations.
local t = "\n* versions.bind_all_i18n() "
for i = lua_table.level_count(versions.central_libraries_sort), 1, -1 do -- in reverse order
sub_module_name = versions.central_libraries_sort[i]
local get = versions.bind_main_and_sub_modules_get[sub_module_name] -- Use the get descriptor of the sub_module.
-- Add i18n translations from the sub-module itself:
if (type(get.title) == "string") and (type(get.i18n) == "table") then
versions.add_one_i18n("", get.title, get.i18n) -- Add i18n translations with previews one's.
t = t .. "\n*" .. viewers.ta("title", get.title)
t = t .. viewers.ta("#i18n", lua_table.level_count(get.i18n) )
end
-- Add i18n translations from an eventual /I18N sub-module:
if (type(get.subI18N) == "string") then
local get, module = versions.get_one_module_or_library(get.subI18N)
if (type(get.title) == "string") and (type(get.i18n) == "table") then
versions.add_one_i18n("", get.title, get.i18n) -- Add i18n translations with previews one's.
t = t .. "\n*" .. viewers.ta("title", get.title)
t = t .. viewers.ta("#i18n", lua_table.level_count(get.i18n) )
end
end
end
return t
end -- t = versions.bind_all_i18n() -- Bind all sub-modules of the main module.
 
function versions.bind_the_main_module() -- Bind the main module, all sub-modules and all their i18n.
-- The main module call this function to load needed sub-modules and translations.
local res = "\n* versions.bind_the_main_module() "
local frame = mw.getCurrentFrame()
local title = frame:getTitle() -- main module, example "Auteur"
local get, main_module = versions.get_one_module_or_library(title) -- Get the main module.
-- Table to collect loaded sub-modules names in binding order and i18n translations in reverse order.
versions.mainversion = title
versions.central_libraries_sort = versions.central_libraries_sort or {}
table.insert(versions.central_libraries_sort, title) -- Record first the main module name.
versions.bind_main_and_sub_modules_get = versions.bind_main_and_sub_modules_get or {}
versions.bind_main_and_sub_modules_get[title] = get -- Record the get descriptor of the main module.
--
-- After get the main module, get the versions for their management.
-- The main module can use or not the versions management.
versions.main_module = main_module
if type(main_module) == "table" and type(main_module.version) == "table" then -- For main modules using versions management
versions.main_versions = main_module.version
end
local main_versions = versions.main_versions -- nil if the main module do not uses the versions management.
--
if not versions.main_module then -- The main module is not found.
res = res .. viewers.styles_color_error( viewers.form9user("versions_main_module_missing_err") )
end
langs.main_i18n = langs.main_i18n or versions.main_i18n or {}
versions.main_i18n = langs.main_i18n
return res
end -- function versions.bind_the_main_module() -- Bind the main module, all sub-modules and all their i18n.
 
function versions.bind_all_sub_modules_test() -- Test : Bind all sub-modules of the main module.
versions.bind_all_sub_modules_track = "TEST"
local memo = viewers.save_configs("versions.bind_all_sub_modules_test") -- Save global configuration before eventual changes.
local sub_modules = versions.sub_modules
local iftest = true
local t = "\n* versions.bind_all_sub_modules() TEST Bind all sub-modules of the main module."
t = t .. "\n* bind_all_sub_modules_test <b>sub_modules.sub_tries</b> :" .. viewers.rough_view(sub_modules.sub_tries)
local tab_view = { -- Group datas and options for a table view with lines and columns.
test_group = sub_modules.sub_tries,
title_memo = "versions.bind_all_sub_modules() Bind all sub-modules of the main module",
headers = " insub; sub; sought; known; errors ",
headers_class = "wikitable alternative center sortable",
-- track_on = true,
}
--
tab_view.test_group = sub_modules.sub_tries
tab_view.headers = " insub; sub; sought; sub_modules.sub_tries known; errors "
function tab_view.form_one_case(case, all_cases) -- Convert a case from test_group to rowGroup.
return { case.insub, case.sub, case.sought, case.known, case.errors or "", }
end
local tt, sub_tries = versions.bind_all_sub_modules(sub_modules, iftest) -- Bind all sub-modules of the main module.
--
t = t .. "\n* bind_all_sub_modules_test <b>sub_modules.sub_tries</b> :" .. viewers.rough_view(sub_modules.sub_tries)
tab_view.test_group = sub_modules.sub_tries
tab_view.headers = " insub; sub; sought; sub_modules.sub_tries known; errors "
t = t .. tableview.new(tab_view) -- Formats a table view with lines and columns.
--
t = t .. "\n* bind_all_sub_modules_test <b>sub_modules.sub_used</b> :" .. viewers.rough_view(sub_modules.sub_used)
tab_view.test_group = sub_modules.sub_used
tab_view.headers = " insub; sub; sought; sub_modules.sub_used known; errors "
t = t .. tableview.new(tab_view) -- Formats a table view with lines and columns.
--
viewers.restore_configs(memo, "versions.bind_all_sub_modules_test") -- Restore global configurations after eventual changes.
return t
end -- t = versions.bind_all_sub_modules_test()
 
versions.bind_all_sub_modules_track = "SOURCE"
versions.sub_modules = {}
versions.sub_modules.sub_tries = { -- TEST: Bind all sub-modules of the main module.
-- Normal cases: all known = "Box1, Box3 * Group;Group2;Group4 * Item;Item5;Item7"
Main = { versionName = "Main", sought = "Box1;Group2;Item5", known = "Box1;Box3 * Group;Group2;Group4 * Item5;Item7", },
Box1 = { versionName = "Box1", sought = "Group2;Item5", known = "Group;Group2;Group4 * Item5;Item7", },
Box3 = { versionName = "Box3", sought = "Group2;Item", known = "Group2;Group4 * Item;Item5", },
Group2 = { versionName = "Group2", sought = "Item", known = "Item;Item5,Item7", },
Group4 = { versionName = "Group4", sought = "Item5", known = "Item;Item5,Item7", },
-- Errors cases:
Box1_ms = { versionName = "Box1", sought = "Group2", known = "Group;Group2;Group4 * Item5;Item7", }, -- missing sought
Box3_es = { versionName = "Box3", sought = "Group2;ItemERR", known = "Group2;Group4 * Item;Item5", }, -- erroneous sought
Group2_mk = { versionName = "Group2", sought = "Item", known = "Item5,Item7", }, -- missing known
Group4_ek = { versionName = "Group4", sought = "Item5", known = "Item;ItemERR,Item7", }, -- erroneous known
Box3_ks = { versionName = "Box3", sought = "Group2;ItemERR", known = "Group2;Group4 * Item;Item5", }, -- known repairs erroneous sought
}
 
-- versions.bind_the_main_module() -- Bind the main module, all sub-modules and all their i18n.
function versions.bind_all_sub_modules(sub_modules, iftest) -- Bind all sub-modules of the main module.
local t = "\n* versions.bind_all_sub_modules() Bind all sub-modules of the main module."
t = t .. "\n* versions.bind_all_sub_modules_track : " .. versions.bind_all_sub_modules_track
-- Method: Record in a stack the sought sub-modules for the main_module.
-- For each try of sub-module, add it in stack. That extend the stack along the procces.
-- For each error, when found, add it the errors stack. At the end prioritize them and display only the most significant.
-- To report that display sought known and used sub-modules like in the stack, in colors to show typical errors.
-- To test these process, try normal and erroneous cases.
-- These process are like a small expert system.
-- The main module call this function to load needed sub-modules and translations.
-- Later run versions.bind_reverse_i18n_translations() -- Bind all i18n translations in reverse order, from modules and their /I18N sub-modules
local sub_modules = sub_modules
local iftest = iftest or false
local actual_init, sub_modules_stack
local main_module, main_versions, ModuleNS
local sub_tries, i_tries, sub_used, i_used
local sought, known = "", ""
-- Select and activate the right scenario, actual or for test.
if iftest then -- TEST: Bind all sub-modules of the main module.
versions.bind_all_sub_modules_track = "TEST"
sub_modules.ModuleNS = "Module:"
if (type(sub_modules) ~= "table") and (type(versions.sub_modules) == "table") then sub_modules = versions.sub_modules end
sub_modules = mw.clone(sub_modules)
sub_tries = sub_modules.sub_tries or {}
sub_modules.sub_used = {}
i_tries = sub_modules.i_tries or {}
sub_modules.i_used = {}
main_versions = sub_tries.Main -- from main test, with versions.versionName = "Main" as example
else -- ACTUAL: Bind all sub-modules of the main module.
versions.bind_all_sub_modules_track = "ACTUAL"
main_module = versions.main_module
main_versions = versions.main_versions
sub_modules = {}
sub_modules.ModuleNS = mw.site.namespaces.Module.name .. ":"
sub_modules.sub_tries = {}
sub_modules.sub_used = {}
sub_modules.i_tries = {}
sub_modules.i_used = {}
sub_tries = sub_modules.sub_tries or {}
sub_tries.Main = main_module.version -- from main actual, with versions.versionName = "Central-s-fr" as example
if (type(main_module.version) ~= "table") then -- Start the version management binding for the main module.
-- ACTUAL: Bind all sub-modules of the main module.
main_versions = sub_tries.Main
end
if (type(main_module.version) == "table") then -- Start the version management binding for the main module.
-- ACTUAL: Bind all sub-modules of the main module.
sub_tries.Main = main_module.version -- with versions.versionName = "Central-s-fr" as example
end
end
-- Get initial sought and known sub_modules
local function viewers_sub_to_i_sub(sub) -- Formats a sequence table from a keyed table.
local tosub = {}
for key, elem in pairs(sub) do
elem[insub] = key
table.insert(tosub, elem)
end
return tosub
end
t = t .. "\n* bind_sub_modules() start: "
local sought_t = string.gsub(sought or "", " ", ";") -- ";" .. .. ";"
local sought_tab = mw.text.split(sought_t, ";", true)
local sought_maxn = table.maxn(sought_tab)
local known_tab = mw.text.split(main_versions.known or known or "", "*", true)
local known_maxn = table.maxn(known_tab) -- local known_maxn = #known_tab
local used = ";"
t = t .. "\n* list versioning sought.bind_sub_modules : "
.. viewers.ta("main_versions.versionName", main_versions.versionName)
.. viewers.ta("main_versions.sought", main_versions.sought) .. viewers.ta("sought_maxn", sought_maxn)
.. "<br>" .. viewers.ta("main_versions.known", main_versions.known) .. viewers.ta("known_maxn", known_maxn)
local sub_tries = {} -- Duplicate sub_tries to not disturb original sub_modules.sub_tries
for key, elem in pairs(sub_modules.sub_tries) do -- alternatives = known_tab[i]
local try = mw.clone(elem) -- Duplicate sub_tries to not disturb original sub_modules.sub_tries
sub_tries[key] = try
end
local normal, altern, alternatives, kind, altern_tab
local elem, module, normal, alias, name_I18N, version
for i, try in pairs(sub_tries) do -- alternatives = known_tab[i]
local sought_t = string.gsub(try.sought or "", " ", ";") -- ";" .. .. ";"
local known_tab = mw.text.split(try.known or "", "*", true)
local known_maxn = table.maxn(known_tab) -- local known_maxn = #known_tab
try.errors = ""
alternatives = try.known
alternatives = ";" .. mw.text.trim(alternatives) .. ";" -- normalize versions between ";"
local altern_tab = mw.text.split(alternatives, "*", true) -- see _Example
for i, alternate in ipairs(altern_tab) do
local sought_tab = mw.text.split(sought_t, ";", true)
local sought_maxn = table.maxn(sought_tab)
normal = "" ; version = ""
for v, altern in ipairs(sought_tab) do
altern = tostring(altern)
altern = mw.text.trim(altern)
if v == 1 then -- Permit to select normal version in case of none others match.
normal = altern
kind = "normal"
end
-- Try others alternate versions
local try = { insub = normal, versionName = altern, ["sought"] = sought, ["known"] = known, }
try.errors = ""
local insert_try = false
if v == 1 and string.find(";" .. sought .. ";", ";" .. altern .. ";", 1, true) then
-- sub_modules.sub_used = {} -- Bind all sub-modules used in the main module.
end
if v > 1 then -- and viewers.is_in_sp(altern, sought, ";")
version = altern
kind = "version"
end
if not viewers.is_in_sp(altern, sought, ";") then
try.errors = try.errors .. "; altern_is_not_in_sought"
end
if viewers.is_in_sp("WantedError", known, ";") then
-- { insub = "Box2", versionName = "Group4", sought = "Item4;Item", known = "Item2;WantedError;Item3", }, -- Example of test case
try.errors = (try.errors or "") .. "altern_is_WantedError"
try.known = "Item2;Item3" -- PREVENT A RECURSIVE LOOP IN STACK
end
if try.versionName == "Box3" then
try.versionName = "Box345" -- PREVENT A RECURSIVE LOOP IN STACK
try.errors = try.errors .. "; altern_is_Box3"
end
if try.insub == "Group2" then
try.errors = try.errors .. "; altern_is_WantedError"
end
if viewers.is_in_sp(altern, known, ";") then -- Try another sub_module
local new_try = nil
if iftest then -- In test of versions management
if (type(sub_tries[altern]) == "table") then new_try = sub_tries[altern] end
else -- In normal run of versions management
-- Get a module or a library, then form and record a descriptor of it.
local get, module = versions.get_one_module_or_library( sub_modules.ModuleNS .. altern )
if (type(get.module) == "table") and (type(get.moduleName) == "string") then -- Verify main module and versions management ability.
new_try = { insub = altern, versionName = get.moduleName, ["sought"] = get.module.version.sought, ["known"] = get.module.version.known, errors = "" }
insert_try = true
end
end
if new_try and lua_table.level_count(sub_tries) < 111 then -- Limit the number of sub_modules to 111
sub_modules.sub_tries[altern] = new_try
sub_modules.i_tries = viewers_sub_to_i_sub(sub_modules.sub_tries) -- Formats a sequence table from a keyed table.
sub_modules.sub_used[altern] = new_try
sub_modules.i_used = viewers_sub_to_i_sub(sub_modules.sub_tries) -- Formats a sequence table from a keyed table.
sought = sought .. ";" .. new_try.sought -- this sub_modules extend sought for inner sub_modules
known = known .. " * " .. new_try.known -- this sub_modules extend known for inner sub_modules
else
try.errors = try.errors .. "; Limit the number of sub_modules to 111"
end
end
end
end
end -- for i = known_maxn, 1, -1 do -- alternatives = known_tab[i]
--
local tab_view = { -- Group datas and options for a table view with lines and columns.
test_group = sub_modules.sub_tries,
title_memo = "versions.bind_all_sub_modules() Bind all sub-modules of the main module",
headers = " insub; sub; sought; known; errors ",
headers_class = "wikitable alternative center sortable",
-- track_on = true,
}
tab_view.test_group = sub_modules.i_tries
tab_view.headers = " insub; sub; sought; sub_modules.i_tries known; errors "
--
tab_view.test_group = sub_modules.i_used
tab_view.headers = " insub; sub; sought; sub_modules.i_used known; errors "
--
if iftest then versions.bind_all_sub_modules_test_report = t -- TEST: Bind all sub-modules of the main module.
else versions.bind_all_sub_modules_actual_report = t end -- TEST: Bind all sub-modules of the main module