模块:Dictionary/Vocabulary.lua:修订间差异
来自「荏苒之境」
无编辑摘要 |
无编辑摘要 |
||
(未显示同一用户的44个中间版本) | |||
第1行: | 第1行: | ||
local csv = require("Module:Csv.lua") | local csv = require("Module:Csv.lua") | ||
local dict_utils = require("Module:Dictionary/Utils.lua") | |||
local dict_views = require("Module:Dictionary/Views.lua") | |||
local html = mw.html | local html = mw.html | ||
local cargo = mw.ext.cargo | local cargo = mw.ext.cargo | ||
local DICT_TABLE = dict_views.TABLE | local DICT_TABLE = dict_views.TABLE | ||
local | local DICT_HEADER_PRIORITY = dict_utils.HEADER_PRIORITY | ||
local | local vocabulary = {} | ||
local | local function format_conflict(i, prev_row, row) | ||
prev_row[i] = (prev_row[i] or "").."<br/><i style=\"color: grey\">"..(row[i] or "").."</i>" | |||
end | |||
local function query_existing_rows(language, rows) | |||
local t = { "Language=\"", language, "\" AND Priority<>", tostring(DICT_HEADER_PRIORITY), " AND Spelling in (" } | |||
for i = 1, #rows do | |||
t[#t+1] = "'" | |||
t[#t+1] = rows[i][1] | |||
t[#t+1] = "'," | |||
end | |||
t[#t] = "')" | |||
local query = cargo.query(DICT_TABLE, "Spelling,Definition,Extra,Priority,_pageName", { | |||
where = table.concat(t) | |||
}) | |||
local found = {} | |||
for i = 1, #query do | |||
local raw = query[i] | |||
raw.Priority = tonumber(raw.Priority) | |||
found[raw.Spelling] = raw | |||
end | |||
return found | |||
end | |||
local function check_conflicting(prev_row, row, extra_count, on_conflict) | |||
local compare_count = extra_count and extra_count + 2 or math.max(#row, #prev_row) | |||
local conflict = false | |||
if on_conflict == nil then | |||
for i = 1, compare_count do | |||
local prev = prev_row[i] | |||
local curr = row[i] | |||
if prev ~= curr then | |||
return true | |||
end | |||
end | |||
else | |||
for i = 1, compare_count do | |||
local prev = prev_row[i] | |||
local curr = row[i] | |||
if prev ~= curr then | |||
on_conflict(i, prev_row, row) | |||
conflict = true | |||
end | |||
end | |||
end | |||
return conflict | |||
end | |||
local function store_row(language, priority, row, extra_count) | |||
local extra = {} | |||
for i = 1, extra_count or #row-2 do | |||
extra[i] = row[i+2] | |||
end | |||
cargo.store(DICT_TABLE, { | |||
Language = language, | |||
Spelling = row[1], | |||
Definition = row[2], | |||
Extra = csv.format_row(extra), | |||
Priority = priority | |||
}) | |||
end | |||
vocabulary.show = function(frame) | |||
local args = frame.args | local args = frame.args | ||
local page_name = frame.args.page_name | |||
local language = args.language | local language = args.language | ||
local format = args.format | local format = args.format | ||
local priority = args.priority | local priority = tonumber(args.priority) or 1 | ||
local content = args.content | local content = args.content | ||
local header | |||
local rows | local rows | ||
if format == "csv" then | if format == "csv" then | ||
rows = csv.parse( | rows = csv.parse(content, true) | ||
header = rows.header | |||
else | else | ||
mw.addWarning("无效的词典格式:"..tostring(format)) | mw.addWarning("无效的词典格式:"..tostring(format)) | ||
return | return | ||
end | end | ||
local extra_count = #header - 2 | |||
local prev_header_raw = cargo.query(DICT_TABLE, "Spelling,Definition,Extra,_pageName", { | |||
where = "Language=\""..language.."\" AND Priority="..tostring(DICT_HEADER_PRIORITY) | |||
})[1] | |||
if prev_header_raw ~= nil and page_name ~= prev_header_raw._pageName then | |||
local prev_header = dict_utils.expand_row(prev_header_raw, extra_count) | |||
local is_conflicting = check_conflicting(prev_header, header, extra_count, format_conflict) | |||
if is_conflicting then | |||
return html.create("pre") | |||
:css("color", "red") | |||
:tag("p"):wikitext("检测到该词汇表的标题行(灰色文本)与之前储存的标题行文本冲突,请修复:"):done() | |||
:node(dict_views.vocabulary(prev_header, {})) | |||
end | |||
else | |||
store_row(language, DICT_HEADER_PRIORITY, header, extra_count) | |||
end | |||
local existing_rows = query_existing_rows(language, rows) | |||
local conflicting_rows = {} | |||
for i = 1, #rows do | for i = 1, #rows do | ||
local row = rows[i] | local row = rows[i] | ||
local prev_row_raw = existing_rows[row[1]] | |||
local | local prev_row = prev_row_raw and dict_utils.expand_row(prev_row_raw, extra_count) | ||
local | local ignore_store = false | ||
if prev_row_raw ~= nil then | |||
local prev_p = prev_row_raw.Priority | |||
if prev_p < priority then | |||
if | ignore_store = not check_conflicting(prev_row, row, extra_count) | ||
local | elseif prev_p > priority then | ||
if | |||
ignore_store = true | ignore_store = true | ||
else | else | ||
ignore_store = check_conflicting(prev_row, row, extra_count, format_conflict) | |||
if ignore_store then | |||
table.insert(conflicting_rows, prev_row) | |||
end | |||
end | end | ||
end | end | ||
if not ignore_store then | if not ignore_store then | ||
store_row(language, priority, row, extra_count) | |||
end | end | ||
end | end | ||
第69行: | 第143行: | ||
:css("color", "red") | :css("color", "red") | ||
:tag("p") | :tag("p") | ||
:wikitext(" | :wikitext("检测到旧词汇与新词汇(灰色文本)内容冲突的情况,且二者具有相同优先级,请统一词汇信息:") | ||
:done() | :done() | ||
:node(dict_views.vocabulary(conflicting_rows)) | :node(dict_views.vocabulary(header, conflicting_rows)) | ||
end | end | ||
if frame.args.show_view == "true" then | if frame.args.show_view == "true" then | ||
view:node(dict_views.vocabulary(rows)) | view:node(dict_views.vocabulary(header, rows)) | ||
end | end | ||
return view | return view | ||
end | end | ||
return | return vocabulary |
2025年8月5日 (二) 01:36的最新版本
此模块的文档可以在模块:Dictionary/Vocabulary.lua/doc创建
local csv = require("Module:Csv.lua")
local dict_utils = require("Module:Dictionary/Utils.lua")
local dict_views = require("Module:Dictionary/Views.lua")
local html = mw.html
local cargo = mw.ext.cargo
local DICT_TABLE = dict_views.TABLE
local DICT_HEADER_PRIORITY = dict_utils.HEADER_PRIORITY
local vocabulary = {}
local function format_conflict(i, prev_row, row)
prev_row[i] = (prev_row[i] or "").."<br/><i style=\"color: grey\">"..(row[i] or "").."</i>"
end
local function query_existing_rows(language, rows)
local t = { "Language=\"", language, "\" AND Priority<>", tostring(DICT_HEADER_PRIORITY), " AND Spelling in (" }
for i = 1, #rows do
t[#t+1] = "'"
t[#t+1] = rows[i][1]
t[#t+1] = "',"
end
t[#t] = "')"
local query = cargo.query(DICT_TABLE, "Spelling,Definition,Extra,Priority,_pageName", {
where = table.concat(t)
})
local found = {}
for i = 1, #query do
local raw = query[i]
raw.Priority = tonumber(raw.Priority)
found[raw.Spelling] = raw
end
return found
end
local function check_conflicting(prev_row, row, extra_count, on_conflict)
local compare_count = extra_count and extra_count + 2 or math.max(#row, #prev_row)
local conflict = false
if on_conflict == nil then
for i = 1, compare_count do
local prev = prev_row[i]
local curr = row[i]
if prev ~= curr then
return true
end
end
else
for i = 1, compare_count do
local prev = prev_row[i]
local curr = row[i]
if prev ~= curr then
on_conflict(i, prev_row, row)
conflict = true
end
end
end
return conflict
end
local function store_row(language, priority, row, extra_count)
local extra = {}
for i = 1, extra_count or #row-2 do
extra[i] = row[i+2]
end
cargo.store(DICT_TABLE, {
Language = language,
Spelling = row[1],
Definition = row[2],
Extra = csv.format_row(extra),
Priority = priority
})
end
vocabulary.show = function(frame)
local args = frame.args
local page_name = frame.args.page_name
local language = args.language
local format = args.format
local priority = tonumber(args.priority) or 1
local content = args.content
local header
local rows
if format == "csv" then
rows = csv.parse(content, true)
header = rows.header
else
mw.addWarning("无效的词典格式:"..tostring(format))
return
end
local extra_count = #header - 2
local prev_header_raw = cargo.query(DICT_TABLE, "Spelling,Definition,Extra,_pageName", {
where = "Language=\""..language.."\" AND Priority="..tostring(DICT_HEADER_PRIORITY)
})[1]
if prev_header_raw ~= nil and page_name ~= prev_header_raw._pageName then
local prev_header = dict_utils.expand_row(prev_header_raw, extra_count)
local is_conflicting = check_conflicting(prev_header, header, extra_count, format_conflict)
if is_conflicting then
return html.create("pre")
:css("color", "red")
:tag("p"):wikitext("检测到该词汇表的标题行(灰色文本)与之前储存的标题行文本冲突,请修复:"):done()
:node(dict_views.vocabulary(prev_header, {}))
end
else
store_row(language, DICT_HEADER_PRIORITY, header, extra_count)
end
local existing_rows = query_existing_rows(language, rows)
local conflicting_rows = {}
for i = 1, #rows do
local row = rows[i]
local prev_row_raw = existing_rows[row[1]]
local prev_row = prev_row_raw and dict_utils.expand_row(prev_row_raw, extra_count)
local ignore_store = false
if prev_row_raw ~= nil then
local prev_p = prev_row_raw.Priority
if prev_p < priority then
ignore_store = not check_conflicting(prev_row, row, extra_count)
elseif prev_p > priority then
ignore_store = true
else
ignore_store = check_conflicting(prev_row, row, extra_count, format_conflict)
if ignore_store then
table.insert(conflicting_rows, prev_row)
end
end
end
if not ignore_store then
store_row(language, priority, row, extra_count)
end
end
local view = html.create("div")
if #conflicting_rows ~= 0 then
view:tag("pre")
:css("color", "red")
:tag("p")
:wikitext("检测到旧词汇与新词汇(灰色文本)内容冲突的情况,且二者具有相同优先级,请统一词汇信息:")
:done()
:node(dict_views.vocabulary(header, conflicting_rows))
end
if frame.args.show_view == "true" then
view:node(dict_views.vocabulary(header, rows))
end
return view
end
return vocabulary