Модуль:Languages: различия между версиями

Материал из in.wiki
Перейти к навигации Перейти к поиску
м (отмена правки 63574012 участника Saint Johann (обс) хмм нет)
 
(не показано 67 промежуточных версий 18 участников)
Строка 1: Строка 1:
--[[ Модуль для работы с языками ISO 639
+
-- Модуль для работы с языками ISO 639
  Наверное его надо целиком переписать, это только proof of concept
 
]]
 
  
 
-- загрузка модуля данных с таблицей языков
 
-- загрузка модуля данных с таблицей языков
local languages = mw.loadData("Module:Languages/data")
+
local languages = mw.loadData('Module:Languages/data')
 
local p = {}
 
local p = {}
 +
 +
-- Проверяет, пустой ли дан параметр
 +
local function isEmpty(s)
 +
return s == nil or s == ''
 +
end
  
 
-- вспомогательная функция, удаляет пробелы
 
-- вспомогательная функция, удаляет пробелы
Строка 28: Строка 31:
 
end
 
end
  
function p.getRefHtml( wikidataItemId )
+
function p.getRefHtml( code )
 +
local l = languages[code];
 +
if l == nil then
 +
mw.log( 'Language description for code ' .. code .. ' not found' )
 +
        return ""
 +
    else
 +
        return '<span class="ref-info" title="' .. l[ 2 ] .. '" style="cursor:help">(' .. l[ 1 ] .. ')</span>'
 +
    end
 +
end
 +
 
 +
function p.getWikidataRefHtmlFrame( frame )
 +
return p.getWikidataRefHtml( trimstr( frame.args[1] ) )
 +
end
 +
 
 +
function p.getWikidataRefHtml( wikidataItemId )
 
local codeByItemId = mw.loadData( "Module:Wikidata/Language-codes" )
 
local codeByItemId = mw.loadData( "Module:Wikidata/Language-codes" )
 
local code = codeByItemId[ wikidataItemId ];
 
local code = codeByItemId[ wikidataItemId ];
Строка 34: Строка 51:
 
mw.log( 'Language code not found for ' .. wikidataItemId )
 
mw.log( 'Language code not found for ' .. wikidataItemId )
 
return ""
 
return ""
else
+
end
    local l = languages[code];
+
return p.getRefHtml( code )
if l == nil then
+
end
mw.log( 'Language description for code ' .. code .. ' not found' )
+
 
        return ""
+
-- принимает zh, возвращает аббревиатуру
    else
+
function p.abbr(frame)
        return '<span class="ref-info" title="' .. l[ 2 ] .. '" style="font-size:85%; cursor:help; color:#888;">(' .. l[ 1 ] .. ')</span>'
+
local code = trimstr( frame.args[1] )
    end
+
if not isEmpty(code) then
 +
return (languages[code] and languages[code][1] or '')
 +
end
 +
end
 +
 
 +
-- принимает zh|我|tt|мин, возвращает название статьи из Module:Languages/data
 +
function p.name(frame)
 +
local code = trimstr( frame.args[1] )
 +
if code ~= nil and code ~= '' then
 +
return (languages[code] and languages[code][2] or '')
 
end
 
end
 
end
 
end
Строка 51: Строка 77:
  
 
     for n, v in frame:argumentPairs() do
 
     for n, v in frame:argumentPairs() do
      local trimmed = trimstr(v)
+
local trimmed = trimstr(v)
      if curr_lang == nil then
+
if curr_lang == nil then
          if trimmed ~= '' then
+
if trimmed ~= '' then
              -- если язык пропущен, оставим прошлый
+
-- если язык пропущен, оставим прошлый
              curr_lang = trimstr(v)
+
curr_lang = trimstr(v)
          end
+
end
      else
+
else
          if trimmed ~= '' then
+
if trimmed ~= '' then
              local link, lang_code = get_lang_data(curr_lang)
+
local link, lang_code = get_lang_data(curr_lang)
              local list_item
+
local list_item
              if lang_code ~= '' then
+
if lang_code ~= '' then
                  list_item = link .. "&nbsp;<span lang='" .. lang_code .. "'>" .. trimmed .. "</span>"
+
list_item = link .. "&nbsp;<span dir='auto' lang='" .. lang_code .. "'>" .. trimmed .. "</span>"
              else
+
else
                  list_item = link .. " <span class='unknown-foreign-lang'>" .. trimmed .. "</span>"
+
list_item = link .. " <span class='unknown-foreign-lang'>" .. trimmed .. "</span>".."[[Category:Проект:Статьи с нераспознанным языком]]"
              end
+
end
         
+
              if result == nil then
+
if result == nil then
                  result = list_item
+
result = list_item
              else
+
else
                  result = result .. ", " .. list_item
+
result = result .. ", " .. list_item
              end
+
end
          else
+
else
              -- Пустой текст — значит, текущий язык совпадает с следующим
+
-- Пустой текст — значит, текущий язык совпадает с следующим
              local link, lang_code = get_lang_data(curr_lang)
+
local link, lang_code = get_lang_data(curr_lang)
              if result == nil then
+
if result == nil then
                  result = link
+
result = link
              else
+
else
                  result = result .. ", " .. link
+
result = result .. ", " .. link
              end
+
end
          end
+
end
         
+
          curr_lang = nil
+
curr_lang = nil
 
       end
 
       end
 
     end
 
     end
Строка 97: Строка 123:
 
     return result
 
     return result
 
end
 
end
   
+
 
 +
-- принимает zh|tt, возвращает ref-zh, ref-tt
 +
function p.list_ref(frame)
 +
local result = ''
 +
local v = frame.args['в'] or nil
 +
local ref = nil
 +
 
 +
if v then
 +
ref = '&nbsp;<span class="ref-info" style="cursor:help;" title="на %2%">&#091;%1%&#093;</span>'
 +
else
 +
ref = '&nbsp;<span class="ref-info" style="cursor:help;" title="на %2%">(%1%)</span>'
 +
end
 +
 
 +
for x, lg in pairs( frame.args ) do
 +
local code = mw.ustring.lower(trimstr(lg))
 +
if code ~= '' and code ~= 'в' then
 +
local l = languages[code]
 +
if l and l ~= nil then
 +
result = result .. mw.ustring.gsub(mw.ustring.gsub(ref, '%%2%%', p._transform_lang(code)), '%%1%%', l[1])
 +
else
 +
if mw.title.new('ref-' .. code, 10).exists == false then
 +
code = 'und'
 +
end
 +
result = result .. frame:expandTemplate{ title = 'ref-' .. code } .. '[[Category:Проект:Статьи с нераспознанным языком (ref)]]'
 +
end
 +
end
 +
end
 +
 
 +
return result
 +
end
 +
 
 +
-- Выводит название языка в предложном падеже
 +
function p._transform_lang(code)
 +
if isEmpty(languages[code]) then return '&lt;неизвестный код ' .. code .. '&gt;' end
 +
    if languages[code][3] then return languages[code][3] end
 +
    local ln = mw.ustring.lower(
 +
        languages[code] and languages[code][2]
 +
        or mw.language.fetchLanguageName(code,'ru')
 +
    ):gsub('%s+язык%s+', ' '):gsub('%s*%(?язык%)?%s*',  '')
 +
    if not ln then return 'языке с ISO-кодом '..code..' (?)' end
 +
    if ln:match('.*лингва$') then return ln:gsub('а$','е') end
 +
    if mw.ustring.match(ln,'[сц]кий$') or ln:match('ный$') or mw.ustring.match(ln,'[сц]кий%s%b()$') or ln:match('ный%s%b()$')
 +
    then
 +
        ln = mw.ustring.gsub(
 +
            mw.ustring.gsub(ln, 'н([ыи])й(%A)', function(y,s) return (y=='ы' and 'ном' or 'нем')..s end)
 +
                :gsub('ный$', 'ном'),
 +
            '([сц]к)ий(%A)', '%1ом%2'
 +
        ):gsub('ский$', 'ском'):gsub('цкий$', 'цком');
 +
        if ln:match('%)$') and not (ln:match('ом%)$') or ln:match('нем%)$')) -- «языке» перед уточнением, если оно не склоняется
 +
        then
 +
            local r,s=ln:gsub('(%s)(%b())$','%1языке%1%2');
 +
            if s==1 then return r end
 +
        end
 +
        return ln..' языке'
 +
    else
 +
        return 'языке '..ln
 +
    end
 +
end
 +
 
 +
function p.transform_lang(frame)
 +
return p._transform_lang(trimstr(frame.args[1]))
 +
end
 +
 
 
return p
 
return p

Текущая версия от 22:13, 12 апреля 2025

Для документации этого модуля может быть создана страница Модуль:Languages/doc

-- Модуль для работы с языками ISO 639

-- загрузка модуля данных с таблицей языков
local languages = mw.loadData('Module:Languages/data')
local p = {}

-- Проверяет, пустой ли дан параметр
local function isEmpty(s)
	return s == nil or s == ''
end

-- вспомогательная функция, удаляет пробелы
local function trimstr(s)
  return (s:gsub("^%s*(.-)%s*$", "%1"))
end

-- получает код языка, возвращает ссылку и нормализованный код языка (или пустые строки)
local function get_lang_data(code)
    local l = languages[code];
    if l ~= nil then
        return "[[" .. l[2] .. "|" .. l[1] .. "]]", code
    elseif code ~= "" then
        return code, ""
    else
        return "", ""
    end
end

function p.getRefHtmlFrame( frame )
	return p.getRefHtml( trimstr( frame.args[1] ) )
end

function p.getRefHtml( code )
	local l = languages[code];
	if l == nil then
		mw.log( 'Language description for code ' .. code .. ' not found' )
        return ""
    else
        return '<span class="ref-info" title="' .. l[ 2 ] .. '" style="cursor:help">(' .. l[ 1 ] .. ')</span>'
    end
end

function p.getWikidataRefHtmlFrame( frame )
	return p.getWikidataRefHtml( trimstr( frame.args[1] ) )
end

function p.getWikidataRefHtml( wikidataItemId )
	local codeByItemId = mw.loadData( "Module:Wikidata/Language-codes" )
	local code = codeByItemId[ wikidataItemId ];
	if code == nil then
		mw.log( 'Language code not found for ' .. wikidataItemId )
		return ""
	end
	return p.getRefHtml( code )
end

-- принимает zh, возвращает аббревиатуру
function p.abbr(frame)
	local code = trimstr( frame.args[1] )
	if not isEmpty(code) then
		return (languages[code] and languages[code][1] or '')
	end
end

-- принимает zh|我|tt|мин, возвращает название статьи из Module:Languages/data
function p.name(frame)
	local code = trimstr( frame.args[1] )
	if code ~= nil and code ~= '' then
		return (languages[code] and languages[code][2] or '')
	end
end

-- принимает zh|我|tt|мин, возвращает список через запятую
function p.list(frame)
    local curr_lang = nil
    local result = nil

    for n, v in frame:argumentPairs() do
		local trimmed = trimstr(v)
		if curr_lang == nil then
		if trimmed ~= '' then
			-- если язык пропущен, оставим прошлый
			curr_lang = trimstr(v)
		end
		else
		if trimmed ~= '' then
			local link, lang_code = get_lang_data(curr_lang)
			local list_item
			if lang_code ~= '' then
				list_item = link .. "&nbsp;<span dir='auto' lang='" .. lang_code .. "'>" .. trimmed .. "</span>"
			else
				list_item = link .. " <span class='unknown-foreign-lang'>" .. trimmed .. "</span>".."[[Category:Проект:Статьи с нераспознанным языком]]"
			end
			
			if result == nil then
				result = list_item
			else
				result = result .. ", " .. list_item
			end
		else
		-- Пустой текст — значит, текущий язык совпадает с следующим
		local link, lang_code = get_lang_data(curr_lang)
		if result == nil then
			result = link
		else
			result = result .. ", " .. link
		end
		end
		
		curr_lang = nil
      end
    end
    
    -- просто #invoke:Languages|list|yue должно возвращать всё же ссылку без текста
    if curr_lang ~= nil then
        local link, lang_code = get_lang_data(curr_lang)
        if result ~= nil then
            result = result .. ", " .. link
        else
            result = link
        end
    end
    return result
end

-- принимает zh|tt, возвращает ref-zh, ref-tt
function p.list_ref(frame)
	local result = ''
	local v = frame.args['в'] or nil
	local ref = nil

	if v then
		ref = '&nbsp;<span class="ref-info" style="cursor:help;" title="на %2%">&#091;%1%&#093;</span>'
	else
		ref = '&nbsp;<span class="ref-info" style="cursor:help;" title="на %2%">(%1%)</span>'
	end

	for x, lg in pairs( frame.args ) do
		local code = mw.ustring.lower(trimstr(lg))
		if code ~= '' and code ~= 'в' then
			local l = languages[code]
			if l and l ~= nil then
				result = result .. mw.ustring.gsub(mw.ustring.gsub(ref, '%%2%%', p._transform_lang(code)), '%%1%%', l[1])
			else
				if mw.title.new('ref-' .. code, 10).exists == false then
					code = 'und'
				end
				result = result .. frame:expandTemplate{ title = 'ref-' .. code } .. '[[Category:Проект:Статьи с нераспознанным языком (ref)]]'
			end
		end
	end

	return result
end

-- Выводит название языка в предложном падеже
function p._transform_lang(code)
	if isEmpty(languages[code]) then return '&lt;неизвестный код ' .. code .. '&gt;' end
    if languages[code][3] then return languages[code][3] end
    local ln = mw.ustring.lower(
        languages[code] and languages[code][2]
        or mw.language.fetchLanguageName(code,'ru')
     ):gsub('%s+язык%s+',  ' '):gsub('%s*%(?язык%)?%s*',  '')
    if not ln then return 'языке с ISO-кодом '..code..' (?)' end
    if ln:match('.*лингва$') then return ln:gsub('а$','е') end
    if mw.ustring.match(ln,'[сц]кий$') or ln:match('ный$') or mw.ustring.match(ln,'[сц]кий%s%b()$') or ln:match('ный%s%b()$')
    then
        ln = mw.ustring.gsub(
            mw.ustring.gsub(ln, 'н([ыи])й(%A)', function(y,s) return (y=='ы' and 'ном' or 'нем')..s end)
                :gsub('ный$', 'ном'),
            '([сц]к)ий(%A)', '%1ом%2'
        ):gsub('ский$', 'ском'):gsub('цкий$', 'цком');
        if ln:match('%)$') and not (ln:match('ом%)$') or ln:match('нем%)$')) -- «языке» перед уточнением, если оно не склоняется
        then 
            local r,s=ln:gsub('(%s)(%b())$','%1языке%1%2');
            if s==1 then return r end
        end
        return ln..' языке'
    else
        return 'языке '..ln
    end
end

function p.transform_lang(frame)
	return p._transform_lang(trimstr(frame.args[1]))
end

return p