Modul:Dátumszűrés
Megjelenés
A modult a Modul:Dátumszűrés/doc lapon tudod dokumentálni
-- A MODUL FÜGGVÉNYEIT ÉS ADATAIT CSAK require('Modul:Dátumszűrés') MÓDON TUDJUK ELÉRNI.
-- A CitWeb és családja számára készült el.
require('strict')
-- a magyar dátumhoz kell
local honapok = {'jan.', 'feb.', 'márc.', 'ápr.', 'máj.', 'jún.', 'júl.', 'aug.', 'szept.', 'okt.', 'nov.', 'dec.'}
-- ellenőrizzük az egyes hónapok hosszát
local honaphossz = {31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31}
-- pop a nyomkövetés céljait szolgálja
local ou = ''
local function pop(...) -- idézőjeles rész és bővítmények az ou számára
--[[ memóriatúllépést okoz, csak teszteléshez
local list = {...}
for _, var in pairs(list) do
ou = ou .. tostring(var) .. '\n '
mw.log(ou)
end
]]
end
-- a magyar helyesírás szerinti rövidített hónapnevek a honapnevesdate() kimenetének
-- előállításához
-- az ISO 8604 szabvány szerinti dátumban a hónap helyére lépő stringet szolgáltatja
local honapsorszamekezetnelkul = {
['jan'] = '01', -- january, Januar
['feb'] = '02', -- february, Februar, février
['mar'] = '03', -- mars, März, mars
['apr'] = '04', -- april, avril első betű a, második v APRL AVRL
['maj'] = '05', -- may mai mai az első betű m, a harmadik nem r MAY
['jun'] = '06', -- june, juin az első kettő ju de a harmadik i JUN
['jul'] = '07', -- july, juli, juillet viszont itt is i, VEGYÜK KI AZ I-T A NÉVBŐL: JUL
['aug'] = '08', -- august, aout első betű a, második o
['sze'] = '09', -- sept
['okt'] = '10',
['nov'] = '11',
['dec'] = '12'
}
-- a római számmal megadott hónap decimális megfelelője
local decimal = {
['I'] = 1,
['II'] = 2,
['III'] = 3,
['IV'] = 4,
['V'] = 5,
['VI'] = 6,
['VII'] = 7,
['VIII'] = 8,
['IX'] = 9,
['X'] = 10,
['XI'] = 11,
['XII'] = 12
}
local hibavan = false
-- kell a dátum ellenőrzéséhez
-- a numerikus dátumokat kezeli le és ISO 8604 szabvány szerinti dátumot csinál a bemeneti esetleg helytelenül megadott dátumból
--[[
DÁTUMSZŰRŐ:
Kiszűri a bemenetén kapott dátumokból
a) a csupa számból álló ISO 8604 dátumokat
b) a római számmal megadott magyar dátumokat
c) a magyar vagy idegen hónapneveket tartalmazó dátumokat
és ezekből mind helyesen formázott ISO 8604 dátumokat csinál
--]]
local function error(about) -- hibajelzést szolgál
-- Enclose errorMsg with <span>
-- Precondition:
-- about -- string
hibavan = true
local r = about
if type(about) == 'string' then
if #about == 0 then
r = 'Lua-hiba'
end
else
r = tostring(about)
end
return '<span class="error">' .. r .. '</span>, '
end -- error()
local function isRoman(v)
if type(v) ~= 'string' then
-- A római számok stringek
return false
end
if v:find('[^IVXLCDM]') then
return false
end
end
--[[ month_to_hu(m)
segéd-funkció, mely az idegen hónapneveket helyettesíti azékezet nélküli, három karakteres rövidített
magyar hónapnevekre (a rövidítést nem jelzi ponntal)
Ennek alapján beküzdi a kétjegyű hónap-sorszámot az ISO 8604 szabványnak megfelelő alakban
--]]
local function month_to_hu(m)
--[[
Spanyol: enero febrero marzo abril mayo junio julio ago septiembre v. setiembre octubre noviembre diziembre
Portugál: janeiro fevereiro marco abril maio junho julho agosto setembro outubro novembro dezembro
Olasz: gennaio febbraio marzo aprile maggio giugno luglio agosto settembre ottobre novemre dicembre
--]]
local alfa, eb, ub, e2b
if not m then
return
end
m = string.gsub(m, ' ', '') -- cseréljük fel a szóközöket üressel
m = string.gsub(m, 'ä', 'a') -- März, mars problem ôû
m = string.gsub(m, 'û', 'u')
m = string.lower(m) -- minden kisbetűs
alfa = string.match(m, '[a-z%-]+') -- kötőjel problémás
if alfa then -- vannak egyáltalán betűk
pop('1- alfa=', alfa)
m = string.sub(m, 1, 3) --három betünk van
eb = string.sub(m, 1, 1)
if eb == 'm' then
ub = string.sub(m, -1, -1)
if ub == 'i' then m = 'maj'
elseif ub == 'r' then m = 'mar'
elseif ub == 'y' then m = 'maj'
elseif ub == 'g' then m = 'maj' --maggio
end
elseif eb == 'e' then
m = 'jan' --spanyol
elseif eb == 'g' then
e2b = string.sub(m, 1, 2)
if e2b == 'ge' then
m = 'jan'
elseif e2b == 'gi' then
m = 'jun' --- olasz
end
elseif eb == 'j' then
if string.sub(m, 2, 2) == 'a' then
m = 'jan'
elseif string.sub(m, 3, 3) == 'n' then
m = 'jun'
elseif string.sub(m, 3, 3) == 'i' then
m = 'jul'
end
elseif eb == 'a' then
if m:find('^a[pvb]') then
m = 'apr'
elseif m:find('^a[ugo]') then
m = 'aug'
end
elseif eb == 'f' then m = 'feb'
elseif eb == 'l' then m = 'jul' --olasz
elseif eb == 's' then m = 'sze'
elseif eb == 'o' then m = 'okt'
elseif eb == 'n' then m = 'nov'
elseif eb == 'd' then m = 'dec'
else
return false
end
else
return false
end
return m
end
local function szokoev(ev)
if ev == nil then
return false
end
local e = tonumber(ev)
if e then -- is numeric?
if e % 400 == 0 then return true end
if e % 100 == 0 then return false end
if e % 4 == 0 then return true end
end
return false
end
--[[ en_to_hu(de)
Angol vagy amerikai angol dátumokból, illetve német, francia, olasz, spanyol
és portugál dátumokból csinál ISO 8604 szabvány szerinti dátumot. Esetleg
bővíthető ez a lista, ha nem vezet kollízióra az idegen neveket értelmező
en_to_hu funkcióban. Hibás dátum esetén false értékkel tér vissza.
--]]
local function en_to_hu(de)
pop('en_to_hu indul')
--Az angol dátumokat jó lenne felismernie: "Dec. 10, 2013". string.lower(s)
local ev, ho, nap, maradek
if type(de) ~= 'string' then
return false
end
de = string.gsub(de, ' ', '') -- cseréljük fel a szóközöket üressel
de = string.gsub(de, '[%.%-]', '/')-- cseréljük fel a pontot és kötőjelet perjellel dec/10/2013
--éôûäde = string.gsub(de, 'é', 'e')--éôûäF
de = string.lower(de) -- minden kisbetűs
ev = string.match(de, '%d%d%d%d?')-- keress a dátumban az évet 2013
if ev then
maradek = string.gsub(de, ev, '')
else
return false
end
if maradek then
pop('en maradek?', maradek)
-- számmal indul mert little endian
maradek = string.gsub(maradek, '/', '') -- már nincsenek perjelek dec10, vagy pl dec
local i, j
i, j = string.match(maradek, '()%d%d?()')
pop('nap indexei a maradékban=', i, j)
if j then
nap = string.sub(maradek, i, j-1)
end
pop('nap ?= ', nap)
if nap then
ho = string.gsub(maradek, nap, '')
else
ho = maradek
end -- azaz dec10 esetén marad dec, dec esetén pedig ő a hónap
end
de = ev
ho = honapsorszamekezetnelkul[month_to_hu(ho)]
if ho then
de = de .. '-' .. ho
end
if nap then
de = de .. '-' .. nap
end -- összeraktuk a dátumot
pop('USA&en átalakult?', de)
local honum = tonumber(ho)
pop('honum', honum)
if honum == nil or 1 > honum or honum > 12 then
return false -- hónap sorszáma hibás
end
pop('nap=', nap)
pop('nap típusa: ', type(nap))
if nap then
local napnum = tonumber(nap)
pop('napnum', napnum)
if napnum ~= nil and 1 <= napnum and napnum <= 31 then
pop('napnum jó?g', napnum)
if szokoev(ev) then
honaphossz[2] = 29
else
honaphossz[2] = 28
end
if honaphossz[honum] < napnum then
return false
end -- nap sorszáma hibás
else
return false
end -- nap sorszáma hibás
end
return de
end
local function ekezet_le(s)
s = string.gsub(s, 'á', 'a')
s = string.gsub(s, 'é', 'e')
s = string.gsub(s, 'í', 'i')
s = string.gsub(s, 'ó', 'o')
s = string.gsub(s, 'ő', 'ö')
s = string.gsub(s, 'ú', 'u')
s = string.gsub(s, 'ű', 'ö')
s = string.gsub(s, 'ä', 'a')
s = string.gsub(s, 'ô', 'o')
s = string.gsub(s, 'û', 'u')
return s
end
local function numdate(de)
local ev, ho, nap, i, j, maradek
local de, perek = string.gsub(de, '%-', '/')
pop('numdate de perekkel = ', de, tostring(perek))
if perek == 2 then
i, j = string.find(de, '/')
pop('numdate_2peres, benne hol a perjel = ', i, j)
ev = string.sub(de, 1, j-1)
maradek = string.sub(de, j+1, -1)
pop('numdate_2peres: év, maradek = ' .. ev .. ', ' .. maradek)
i, j = string.find(maradek, '/')
pop('numdate_2peres i,j a hóhoz és naphoz = ', i, j)
ho = string.sub(maradek, 1, j-1)
nap = string.sub(maradek, j+1, -1)
pop('2peres év, maradekban ho, nap = ', ho, nap)
elseif perek == 1 then -- van év és hó
i, j = string.find(de, '/')
pop('numdate_1peres, benne hol a perjel = ', i, j)
ev = string.sub(de, 1, j-1)
ho = string.sub(de, j+1, -1)
pop('numdate_1peres: év, hó = ', ev, ho)
else
ev = de
end
if #ev < 3 then
return false
end
pop('év hossza=', tostring(#ev))
if ho then
local honum = tonumber(ho)
pop('ho számmal=', tostring(honum))
if honum then
if 1 > honum or honum > 12 then
-- hónap sorszáma hibás
return false
end
if nap then
local napnum = tonumber(nap)
pop('nap számmal=', tostring(napnum))
if not (napnum and 1 <= napnum and napnum <= 31) then
return false
end
if szokoev(ev) then
honaphossz[2] = 29
else
honaphossz[2] = 28
end
if honaphossz[honum] < napnum then
pop('túl a hónaphatáron a nap')
return false -- nap sorszáma hibás
else
pop('ellenőrzött év, hó, nap', ev, ho, nap)
end
end
end
end
de = ev
if ho and ho ~= '' then
de = de .. '-' .. ho
end
if nap then
de = de .. '-' .. nap
end
pop('numdate átadja:', de)
return de
end
local function hudate(de)
pop('hudate indul')
local i, j, ev, ho, nap, maradek
pop(de)
ev = string.match(de, '^%d%d%d%d?') -- ééé v. éééé levágva ev-be
pop('ev=', ev)
local hostring = string.match(de, '%a+')
if hostring then
ho = string.sub(hostring, 1, 3)
end
pop('ho=', ho)
if ho then
i, j = string.find(de, ho)
maradek = string.gsub(string.sub(de, j+1, -1), '%p', '')
nap = string.match(maradek, '%d%d?')
pop('nap=', nap)
end
if isRoman(ho) then
ho = decimal[ho]
if ho then
-- A római számból decimálist csinál a tábla, ebből ismét string kell,
-- hogy az if utasítás végén mindenképpen string hónapunk legyen
ho = tostring(ho)
else
return false
end
pop('ho rómaiból = ', ho)
else
ho = honapsorszamekezetnelkul[ho]
end
if ho then
local honum = tonumber(ho)
pop('honum=', tostring(honum))
if honum then
if 1 > honum or honum > 12 then
-- A hónap sorszáma hibás
return false
end
if nap then
local napnum = tonumber(nap)
pop('napnum=', tostring(napnum))
if not (napnum and 1 <= napnum and napnum <= 31) then
return false
end
if szokoev(ev) then
honaphossz[2] = 29
else
honaphossz[2] = 28
end
if honaphossz[honum] < napnum then
pop('fals nap')
return false -- nap sorszáma hibás
else
pop('másodszor', ev, ho, nap)
end
end
end
end
if ho~= nil and #ho < 2 then
ho = '0' .. ho
end
de = ev
if ho then
de = de .. '-' .. ho
end
if nap then
de = de .. '-' .. nap
end
return de
end
--[[ datumszuro(de)
megszűri a numerikus éééé-hh-nn, illetve a Dec. 10, 2001, 10 january 2001, 2001. december 10 formákat,
leellenőrzi a dátumot (hónaphossz, létező hónap sorszám)
és valamennyiből az ISO 8604 szabvány szerinti dátumot csinál
--]]
local function datumszuro(de)
local log, cserelt
if not de then
return ou, false
else
de, cserelt = string.gsub(de, '%.', '-')
if cserelt == 2 then
de = string.gsub(de, '%-*$', '')
end -- ha a végén van kötőjel, lecsipjük
end
pop('datumszurodatuma paramétere= ', de)
de = ekezet_le(de)
pop('ékezetek nélküli dátum=', de)
de = string.gsub(de, '%s', '')
local i, j = string.match(de, '()%d%d%d%d?()')
if not j then
return ou, false -- mert nincs év a dátumban
else
-- ha j == 5, akkor a dátum elején áll az év, magyar a dátum vagy ISO
pop(i, j, string.sub(de, i, j-1))
end
if not de or type(de)~= 'string' then
return ou, false
end
local d2 = string.gsub(de, '[%p%-]', '') -- punctuation, kötjel is üres lesz
pop('d2 van benne kötjel?', d2)
d2 = tonumber(d2)
pop('d2 mint szám', d2)
if d2 then
--[[ a dátum számjegyes
adB1) keresünk %d%d%d%d? mintával négy- vagy háromjegyű decimálist a dátumban
ha van, megnézzük, hogy hol van ő a dátreturn 1, false endumban,
ha elől akkor tényleg magyar a dátum (átadjuk a kezelőjének: ennek nagy része már megvan az datumoutput-ban)
különben ad B2) höz
--]]
log = numdate(de)
if log == false then
-- hibás a dátum
return ou, false
end
else
-- betűk is vannak d2-ben
local i, j = string.match(de, '()%d%d%d%d?()')
if j == 5 then
log = hudate(de)-- mert magyar a dátum
pop('hudate utáni dátum= ', log)-- meghívjuk a magyar dátum lekezelését log vagy false, vagy a magyar dátum
else
log = en_to_hu(de)
pop('en_to_hu utáni dátum= ', log)
end
end
if log == false then
-- hibás a dátum
return ou, false
end
pop('dátum a dátumszűrés végén = ', log)
return ou, log -- azaz a dátum
end
local function honapnevesdate(isodate)
local ev, ho, nap, i, j, maradek, de
if not isodate then
return
end
isodate = string.gsub(isodate, '%s+', '')
i, j = string.find(isodate, '-')
if i then
ev, maradek = string.match(isodate, '(%d+)%s*%-%s*([%d%p%-]+)') --, ho, nap --%-%s*(%d+)%s*%s*(%d+)%s"
pop('isodate ev,maradek=', ev, maradek)
i, j = string.find(maradek, '-')
if i then
ho, nap = string.match(maradek, '(%d+)%s*%-%s*([%d%p%-]+)')
pop('isodate ho, nap = ', tostring(ho), nap)
else
ho = maradek
end
ho = honapok[tonumber(ho)]
else
ev = isodate
end
de = ev
if ho then
de = de .. '. ' .. ho
end
if nap then
de = de .. ' ' .. tonumber(nap) .. '.'
end
return de
end
-- csak a dátumszűrés és a honapnevesdate publikus a modulból
local q = {
datumszuro = datumszuro,
honapnevesdate = honapnevesdate
}
return q