Module:Composition Division de France
Apparence
La documentation de ce module est générée par le modèle {{Documentation module}}.
Les éditeurs peuvent travailler dans le bac à sable (modifier).
Voir les statistiques d'appel depuis le wikicode sur l'outil wstat et les appels depuis d'autres modules.
local p = {}
local PopulationFrance = require 'Module:Population de France/Données'
local Unite = require 'Module:Unité'
local lang = mw.getContentLanguage()
local charte = 'default'
local configData = {
default = {
titreTableau = ' ',
selectCapitale = '(siège)',
colonnes = { 'intercommunalité' },
couleurEntete = '#f2f2f2',
insee = 'P374'
},
['aire urbaine'] = {
titreTableau = 'de l\'aire urbaine',
selectCapitale = '(ville-centre)',
colonnes = { 'département' },
couleurEntete = '#ece5ca',
},
['aav'] = {
titreTableau = 'de l\'aire d\'attraction',
selectCapitale = '(commune-centre)',
colonnes = { 'département', 'statut_AAV2020' },
couleurEntete = '#ece5ca',
},
['arrondissement'] = {
titreTableau = 'de l\'arrondissement',
selectCapitale = '(chef-lieu)',
couleurEntete = '#e1e1e1',
insee = 'P3423',
},
['canton'] = {
titreTableau = 'du canton',
selectCapitale = '(bureau centralisateur)',
couleurEntete = '#ece5ca',
insee = 'P2506'
},
['département'] = {
titreTableau = 'du département',
selectCapitale = '(préfecture)',
colonnes = { 'code postal', 'arrondissement', 'canton', 'intercommunalité' },
couleurEntete = '#f6f3dd',
insee = 'P2586'
},
['intercommunalité'] = {
titreTableau = 'de l\'intercommunalité',
colonnes = { 'département', 'gentilé' },
couleurEntete = '#ffe2bf',
insee = 'P1616',
},
['localité'] = {
titreTableau = 'de la localité'
},
['circonscription'] = {
titreTableau = 'de la circonscription',
couleurEntete = '#ece5ca'
},
['commune nouvelle'] = {
titreTableau = ' historiques',
colonnes = { 'code postal' },
couleurEntete = '#ddffdd',
},
['métropole'] = {
titreTableau = 'de la métropole',
colonnes = { 'gentilé' },
couleurEntete = '#f6f3dd',
},
['région'] = {
titreTableau = 'de la région',
selectCapitale = '(préfecture)',
colonnes = { 'département'},
couleurEntete = '#bbdefd',
insee = 'P2585',
},
['unité urbaine'] = {
titreTableau= 'de l\'unité urbaine',
selectCapitale = '(ville-centre)',
colonnes = { 'département', 'statut_UU2020' },
couleurEntete = '#ece5ca',
},
['pays'] = {
titreTableau = ' ',
selectCapitale = '(capitale)',
colonnes = { 'région', 'département' },
couleurEntete = '#f2f2f2',
},
}
local function config( param, liste )
if liste and param == 'colonnes' and liste:lower() ~= 'communes' then
return {}
else
return configData[ charte ][ param ] or configData.default[ param ]
end
end
local function abbr( abrev, description )
local wiki = mw.html.create( 'abbr' )
:addClass( 'abbr')
:attr{ title = description }
:wikitext( abrev )
return wiki
end
local function getValue( t, v, ... )
if v and type(t) == 'table' then
return getValue( t[v], ... )
elseif v then
return nil
else
return t
end
end
p.getValue = getValue
local aliasTableCommons = {
['département'] = 'dep',
['région'] = 'region',
['canton'] = 'cv',
['arrondissement'] = 'arr',
['intercommunalité'] = 'epci',
['insee'] = 'code',
['AAV'] = 'AAV2020',
['unité urbaine'] = 'UU2020',
}
local function getCommonsData( name )
name = 'Table/' .. lang:ucfirst( name ) .. '.tab'
return mw.ext.data.get( name, '_' )
end
local function findCommonsColumn( json, name )
name = mw.ustring.lower( name )
name = aliasTableCommons[ name ] or name
for i, v in ipairs( json.schema.fields ) do
if v.name == name then
return i
end
end
end
local function findCommonsData( json, name, value )
local column = findCommonsColumn( json, name )
for i, v in ipairs( json.data ) do
if v[ column ] == value then
return json.data[ i ]
end
end
end
local function findCommonsDataSet( json, name, value, list )
local column = findCommonsColumn( json, name )
list = list or {}
for i, v in ipairs( json.data ) do
if v[ column ] == value then
table.insert( list, json.data[ i ] )
end
end
return list
end
local function getCommonsValue( json, name1, value1, name2 )
local data = findCommonsData( json, name1, value1 )
local column = findCommonsColumn( json, name2 )
return data and data[ column ]
end
--[[ Normalisation qui retire les diacritiques
pour le tri alphabétique ]]--
local tableAccents = {
['à'] = 'a',
['â'] = 'a',
['ç'] = 'c',
['è'] = 'e',
['é'] = 'e',
['ê'] = 'e',
['ë'] = 'e',
['î'] = 'i',
['ï'] = 'i',
['ô'] = 'o',
['ù'] = 'u',
['û'] = 'u',
['ü'] = 'u',
['À'] = 'A',
['Â'] = 'A',
['Ç'] = 'C',
['È'] = 'E',
['É'] = 'E',
['Ê'] = 'E',
['Ë'] = 'E',
['Î'] = 'I',
['Ï'] = 'I',
['Ô'] = 'O',
['Ù'] = 'U',
['Û'] = 'U',
['Ü'] = 'U',
['œ'] = 'oe',
['Œ'] = 'Oe'
}
local function normalise( str )
-- Solution inspirée de http://lua-users.org/wiki/LuaUnicode
-- La regex utilisée est plus spécifique et balaye uniquement les séquences décimales UTF-8
-- des [[diacritiques utilisés en français]] latins
-- voir tableau https://www.utf8-chartable.de/unicode-utf8-table.pl?utf8=dec&unicodeinhtml=dec&htmlent=1
local normalised = str:gsub( '[%z\197][\146-\147]', tableAccents ):gsub( '[%z\195][\128-\191]', tableAccents )
return normalised
end
local function removeColumn(tab, column)
for i, v in ipairs( tab ) do
if tab[ i ] == column then
table.remove(tab, i)
return tab
end
end
end
--------------------------------------
function p.getList( args )
if args.debug then
charte = args.charte
end
if charte == 'default' or not args[ charte ] then
mw.log 'pas de charte'
return
end
local dataDivisions = getCommonsData( charte .. 's' )
local id = mw.wikibase.getEntityIdForTitle( lang:ucfirst( args[ charte ] ) )
if not ( id and dataDivisions ) then
mw.log( "pas d'id ou de table " .. charte .. 's' )
return
end
local inseeProp = mw.wikibase.getBestStatements( id, config( 'insee' ) )
local insee = args.insee or getValue( inseeProp, 1, 'mainsnak', 'datavalue', 'value' )
if (args[ charte ] == "Mayotte") then -- L'article principal de Mayotte n'a pas le même id Wikidata (Q17063) que le département de Mayotte (Q124284929)
insee = '976'
end
args.insee = insee
if not ( insee ) then
mw.log 'pas de code insee'
return
end
-- donnée sur les divisions de la chartes
local dataDivision = findCommonsData( dataDivisions, 'code', insee )
if not dataDivision then
mw.log 'pas de donnée sur cette division'
return
end
-- trouve la liste de divisions
local nomRegion = { '' }
local codeChef
args['liste de'] = ( args['liste de'] or 'communes' ):lower()
local listNomCommonsData = { args['liste de'] }
if args['liste de'] == 'communes' then
codeChef = dataDivision[ findCommonsColumn( dataDivisions, 'capitale' ) ]
-- trouve la région
local regions = getCommonsData 'Régions'
local codeRegion = dataDivision[ findCommonsColumn( dataDivisions, 'région' ) ]
listNomCommonsData = {}
for code in mw.text.gsplit( codeRegion, ', ?' ) do
table.insert(
listNomCommonsData,
'Communes ' .. getCommonsValue( regions, 'code', code, 'name' )
)
end
end
local completeList, list
for _, nomCommonsData in ipairs( listNomCommonsData ) do
completeList = getCommonsData( nomCommonsData )
if not completeList then
mw.log( 'pas de liste de sous-divisions « ' .. nomCommonsData .. ' »' )
return
end
list = findCommonsDataSet( completeList, charte, insee, list )
end
if charte == 'canton'
and args['liste de']:lower() == 'communes'
and dataDivision[ findCommonsColumn( dataDivisions, 'typct' ) ] ~= 1
then
fractions = require 'Module:Données/Fractions cantonales/évolution population'.parCodeCanton[ insee ]
if fractions then
args.fraction = true
for i, v in ipairs( fractions ) do
table.insert( list, findCommonsData( completeList, 'code', v.codeCommune ) )
end
end
end
-- tri et définition des paramètres
local idColumn = findCommonsColumn( completeList, 'qid' )
local codeColumn = findCommonsColumn( completeList, 'code' )
local nccColumn = findCommonsColumn( completeList, 'ncc' )
local listeCommunes = {}
for i, v in ipairs( list ) do
local id = v[ idColumn ]
if v[ codeColumn ] == codeChef then
args['chef-lieu'] = mw.wikibase.getSitelink( id )
else
local commune = { titre = true, cleTri = true }
commune.titre = mw.wikibase.getSitelink( id )
if args['liste de'] == 'communes' then
commune.cleTri = v[ nccColumn ] -- Le NCC n'existe que pour les communes
else
commune.cleTri = normalise( commune.titre ) -- Pour les autres divisions, on utilise la normalisation des diacritiques
end
table.insert( listeCommunes , commune )
end
end
table.sort( listeCommunes, function( a, b ) return a.cleTri < b.cleTri end )
for i, v in ipairs( listeCommunes ) do
args[ 'commune ' .. i ] = v.titre
end
-- début du titre, avec vérification que la liste est complète
local titre
if args['liste de'] == 'communes' then
local nbCom = tonumber( dataDivision[ findCommonsColumn( dataDivisions, 'nbcom' ) ] )
if nbCom and nbCom == #list then
if #list ==1 then
if charte == 'canton'
and tonumber( dataDivision[ findCommonsColumn( dataDivisions, 'typct' ) ] ) >= 4 then
titre = 'Liste de la fraction'
else
titre = 'Liste de la commune'
end
else
titre = 'Liste des ' .. nbCom .. ' communes'
args.exhaustif = true
end
else
titre = 'Liste partielle des communes'
mw.log( 'nombre de commune attendues : ', nbCom )
mw.log( 'nombre de commune dans la liste : ', #list )
end
else
titre = 'Liste des ' .. args['liste de']
end
-- poursuite du titre
local nomDivision = mw.wikibase.getLabel( id )
local test, moduleCarte = pcall( require, 'Module:Carte/données/' .. mw.ustring.lower( nomDivision ) )
if test and moduleCarte.genre then
local genreTab = require 'Module:Drapeau/Domaine'.genre
local genre = genreTab[ moduleCarte.genre:gsub( '[ME]', '' ):gsub( '\'', 'a' ) ] or { du = '' }
if charte == 'région' then -- on ne met pas de genre devant la région pour éviter "de la région de l'Île-de-France"
nomDivision = nomDivision
else
nomDivision = genre.du .. nomDivision
end
else
local String
nomDivision = mw.ustring.gsub(nomDivision, " [(][^()]*[)]$", "") -- retire le contenu des parenthèses dans le titre (homonymie)
-- nomDivision = args[ charte ]:gsub( ' %(' .. charte .. '%)$', '' ) -- ne retire le contenu des parenthèses que s'il contient la charte
end
titre = titre
.. ' '
.. config( 'titreTableau' )
.. ' '
.. nomDivision
.. ' au '
.. require 'Module:Date'.modeleDate{ completeList.description.date, nolinks=true }
args.titre = titre :gsub( '\'intercommunalité Communauté', 'la communauté' )
:gsub( '\'intercommunalité [Mm]étropole', 'la métropole' )
:gsub( '\'arrondissement [Aa]rrondissement', '\'arrondissement')
:gsub( 'canton [Cc]anton', 'canton')
:gsub( 'de La ', 'de la ')
:gsub( 'de L\'', 'de l\'')
:gsub( 'du département [Cc]irconscription', 'de la circonscription')
:gsub( 'du département de la Guadeloupe', 'de la Guadeloupe')
:gsub( 'du département de la Martinique', 'de la Martinique')
:gsub( 'du département de la Guyane', 'de la Guyane')
:gsub( 'du département de [Ll]a Réunion', 'de La Réunion')
return args
end
local function getData( division )
if not division or division == '' then
return nil
end
local data, existe = PopulationFrance.charge_donnees( division )
if existe == true or existe > 2 then
data.page = division
data.population = data.dernier and data[ data.dernier ].pop
if data.superficie == -1 then -- on n'affiche pas la superficie (il y a des communes qui ont une superficie de 1.00, d'où -1)
data.superficie = nil
end
if data.division == "canton" and data.superficie == 1 then -- rétrocompatibilité
data.superficie = nil
end
if data.superficie and data.population then
data.densite = data.population / data.superficie
local prec = 1 - math.floor( math.log10( data.densite ) )
data.precisionDensite = math.min( 2, math.max( 0, prec ) )
end
return data
end
end
function p.tableau( args )
local testCharte = mw.ustring.lower( args.charte or '' )
if configData[ testCharte ] then
charte = testCharte
end
-- liste
if not (args[ 'commune 1' ] or args[ 'commune 2' ]) then
p.getList( args )
end
-- récupération des données
local dataCommunes = {}
local dataDivision = getData( args[ charte ] )
local fractions
local superficieTotale, populationTotale, datePop = 0, 0
if charte == 'canton' then
fractions = require 'Module:Données/Fractions cantonales/évolution population'
end
local chef = getData( args['chef-lieu'] or args['bureau'] )
if chef then
chef.selectCapitale = config( 'selectCapitale' )
chef.canton = fractions and fractions.parCommune[ chef.page ] or chef.canton
table.insert( dataCommunes, chef )
end
for i = 1, 891 do
local nomCommune = args[ 'commune ' .. i ]
if nomCommune and nomCommune ~= '' then
local commune = getData( nomCommune )
if commune then
commune.canton = fractions and fractions.parCommune[ nomCommune ] or commune.canton
table.insert( dataCommunes, commune )
else
table.insert( dataCommunes, nomCommune )
end
end
end
local colonnes = config( 'colonnes', args['liste de'] )
if (args[ charte ] == "Mayotte") then -- Pas d'arrondissement à Mayotte
removeColumn( colonnes, "arrondissement")
end
if (args[ charte ] == "Guyane" or args[ charte ] == "Martinique") then -- Pas de canton en Guyane et en Martinique
removeColumn( colonnes, "canton")
end
-- construction du tableau
local wiki = mw.html.create()
-- entête
wiki:newline()
:wikitext( '{| class="wikitable sortable titre-en-couleur" align="center" style="text-align:center;"' )
:newline()
:wikitext( '|+ ', args.titre or 'Liste des communes ' .. config( 'titreTableau' ) .. ( args.autre or '' ) )
:newline()
:wikitext( '|- style="background:', config( 'couleurEntete' ), ';"' )
:newline()
:wikitext( '! scope="col" | Nom' )
:newline()
:wikitext( '! scope="col" | Code' )
:tag( 'br' ):done()
:node( abbr( 'Insee', 'Institut national de la statistique et des études économiques' ) )
for _, colonne in ipairs( colonnes ) do
local nomColonne = colonne :gsub( '[Ss]tatut_UU2020', 'Statut' )
:gsub( '[Ss]tatut_AAV2020', 'Statut' )
if type( colonne ) == 'table' then
nomColonne = colonne.titre
end
wiki:newline()
:wikitext( '! scope="col" | ', lang:ucfirst( nomColonne ) )
end
wiki:newline()
:wikitext( '! scope="col" | Superficie' )
:tag( 'br' ):done()
:tag( 'small' )
:node( abbr( '(km<sup>2</sup>)', 'kilomètres carrés' ) )
:done()
:newline()
:wikitext( '! scope="col" data-sort-type="number" | Population' )
:tag( 'br' ):done()
:tag( 'small' )
:addClass( 'nowrap' )
:wikitext( '(dernière [[Recensement de la population en France#Décomposition de la population légale depuis 2009|' )
:node( abbr( 'pop. légale', 'population légale' ) )
:wikitext( ']])')
:done()
:newline()
:wikitext( '! scope="col" data-sort-type="number" | Densité' )
:tag( 'br' ):done()
:tag( 'small' )
:addClass( 'nowrap' )
:node( abbr( '(hab./km<sup>2</sup>)', 'habitants par kilomètre carré' ) )
:done()
:newline()
:wikitext( '! scope="col" class="unsortable" | Modifier' )
-- Lignes
local frame = mw.getCurrentFrame()
for i, commune in ipairs( dataCommunes ) do
wiki:newline()
:wikitext( '|-' )
:newline()
:wikitext( '| style="text-align:left;" | ' )
if type( commune ) == 'table' then
local nomModele = 'Données/' .. commune.page .. '/informations générales'
local utilisationModele = false
if commune.selectCapitale then
wiki:wikitext( "'''", commune['nom-wp'], "'''" )
:tag( 'br' ):done()
:tag( 'small' )
:wikitext( commune.selectCapitale )
:done()
else
wiki:wikitext( commune['nom-wp'] )
end
superficieTotale = superficieTotale + (commune.superficie or 0)
populationTotale = populationTotale + (commune.population or 0)
if datePop == nil then
datePop = commune.dernier
elseif datePop ~= commune.dernier then
args.exhaustif = false
end
wiki:newline()
:wikitext( '| ' )
:wikitext( commune.insee )
for _, colonne in ipairs( colonnes ) do
local nomColonne = colonne
if type( colonne ) == 'table' then
nomColonne = colonne.source
end
local dataColonne, test = commune[ nomColonne ]
if not dataColonne then
test, dataColonne = pcall(
frame.expandTemplate,
frame,
{ title = nomModele, args = { nomColonne } }
)
if test then
utilisationModele = true
else
dataColonne = ''
end
elseif type( dataColonne ) == 'table' then
if type( dataColonne[1] ) == 'table' then
local tempDataColonne = {}
for _, v in ipairs( dataColonne ) do
table.insert( tempDataColonne, v['canton-wp'] )
end
dataColonne = tempDataColonne
end
dataColonne = table.concat( dataColonne, '<br>' )
end
wiki:newline()
:wikitext( '| ' )
:wikitext( dataColonne )
end
wiki:newline()
:wikitext( '| ' )
:wikitext( Unite._unite{ commune.superficie, ['décimales'] = 2 } )
:newline()
:wikitext( '| ' )
if commune.population then
local fraction
if charte == 'canton' and type( commune.canton ) == 'table' then
for _, c in ipairs( commune.canton ) do
if c.canton == mw.title.getCurrentTitle().text or c.canton == args.canton then
fraction = c
break
end
end
end
if fraction then
populationTotale = populationTotale - commune.population + fraction.pop
wiki:wikitext( 'Fraction : ', Unite._unite{ fraction.pop }, ' ' )
:tag( 'small' )
:wikitext( '(' ..fractions.dateDonnees .. ')' )
:done()
:tag( 'br' ):done()
:tag( 'small' )
:wikitext( 'Commune : ', Unite._unite{ commune.population }, ' ' )
:tag( 'small' )
:wikitext( '(' ..commune.dernier .. ')' )
:done()
:done()
else
-- l'attribut data-sort-value permet un triage sur une
-- valeur spécifique pour éviter de prendre en compte l'année
wiki:wikitext( 'data-sort-value="', commune.population, '" | ')
:wikitext( Unite._unite{ commune.population }, ' ' )
:tag( 'small' )
:wikitext( '(' ..commune.dernier .. ')' )
:done()
end
end
wiki:newline()
:wikitext( '| ' )
:wikitext( Unite._unite{ commune.densite, ['décimales'] = commune.precisionDensite } )
:newline()
:wikitext( '| ' )
:wikitext( '[[File:Blue pencil.svg|modifier les données|10px|baseline|class=noviewer|link=' .. commune.module .. ']]' )
if utilisationModele then
wiki:wikitext( ' [[File:Green pencil.svg|modifier les données|10px|baseline|class=noviewer|link=Modèle:' .. nomModele .. ']]' )
end
else
args.exhaustif = false
wiki:wikitext( commune )
:newline()
:wikitext( '| ' )
:tag( 'span' )
:css{ color = 'red' }
:wikitext( '????' )
:wikitext( '[[Catégorie:Article avec modèle Composition Division de France erroné]]' )
:done()
:newline()
:wikitext( '|' )
for i = 1, 3 + #colonnes do
wiki:wikitext( ' ||' )
end
end
end
-- ligne pour la division
if not dataDivision and args.exhaustif then
dataDivision = {
insee = args.insee,
['nom-wp'] = args[ charte ],
population = populationTotale,
dernier = datePop,
}
end
if dataDivision then
if not dataDivision.superficie and args.exhaustif and not args.fraction and populationTotale == dataDivision.population then
dataDivision.superficie = superficieTotale
dataDivision.densite = populationTotale / superficieTotale
local prec = 1 - math.floor( math.log10( dataDivision.densite ) )
dataDivision.precisionDensite = math.min( 2, math.max( 0, prec ) )
end
wiki:newline()
:wikitext( '|- style="background:', config( 'couleurEntete' ), ';"' )
:newline()
:wikitext( '! scope="row" | ' )
:wikitext( dataDivision['nom-wp'] )
:newline()
:wikitext( '! ' )
:wikitext( dataDivision.insee )
for _, colonne in ipairs( colonnes ) do
wiki:newline()
:wikitext( '! ' )
end
wiki:newline()
:wikitext( '! ' )
:wikitext( Unite._unite{ dataDivision.superficie, ['décimales'] = 2 } )
:newline()
:wikitext( '! ' )
if dataDivision.population then
wiki:wikitext( Unite._unite{ dataDivision.population }, ' ' )
:tag( 'small' )
:wikitext( '(' ..dataDivision.dernier .. ')' )
:done()
end
wiki:newline()
:wikitext( '! ' )
:wikitext( Unite._unite{ dataDivision.densite, ['décimales'] = dataDivision.precisionDensite } )
:newline()
:wikitext( '! ' )
if dataDivision.module then
wiki:wikitext( '[[File:Blue pencil.svg|modifier les données|10px|baseline|class=noviewer|link=' .. dataDivision.module .. ']]' )
end
end
-- fin du tableau
wiki:newline()
:wikitext( '|}' )
:wikitext( '[[Catégorie:Article avec modèle Composition Division de France]]' )
return tostring( wiki )
end
p["modèle"] = function( frame )
local args = frame.getParent and frame:getParent().args
if args then
return p.tableau( args )
end
return ""
end
return p