Module:PJBSClass/main:修订间差异
无编辑摘要 |
|||
第265行: | 第265行: | ||
if not mw.title.equals(subject_page or "", mw.title.getCurrentTitle()) then |
if not mw.title.equals(subject_page or "", mw.title.getCurrentTitle()) then |
||
--頭尾限400字,以節省效能 |
--頭尾限400字,以節省效能 |
||
local check_body = (body_len > 400) and (mw.ustring.sub(body, 1, 200)..mw.ustring.sub(body, -200, -1)) or body |
local check_body = (body_len > 400) and (mw.ustring.sub(body, 1, 200)..mw.ustring.sub(body, -200, -1)) or body |
||
local check_body = remove_wikiproject_flag(check_body) --避免模板循環 |
local check_body = remove_wikiproject_flag(check_body) --避免模板循環 |
||
if mw.ustring.match(mw.getCurrentFrame():preprocess(check_body.."{{reflist}}") |
if mw.ustring.match(mw.getCurrentFrame():preprocess(check_body.."{{reflist}}") |
2024年1月8日 (一) 08:12的版本
本模組的功能:
- 透過調用Module:PJBSClass/page間接調用Module:PJBSClass
- 讀取{{PJBS}}中的評級值
- 自動透過命名空間盼判斷評級值
- 進階自動評級
- 透過解析頁面內容判斷頁面是否為軟重定向
- 透過解析頁面內容判斷頁面是否為消歧義
- 判斷專題橫幅是繼承{{PJBS}}中的評級值還是自定評級值並加入維護分類
- 輔助{{PJBS}}中的一些與專題評級值相關的功能
用法
本模組主要用於讀取頁面中定義於{{PJBS}}或專題橫幅中的評級值,或自動根據命名空間或維基代碼判斷評級。
判斷種類 | 判斷依據 | 對應的評級 |
---|---|---|
典范条目 | 典范条目模板(如{{Featured article}})
Module:Class第226行Lua错误:attempt to call field 'getPageType' (a nil value) | |
优良条目 | 优良条目模板(如{{Good article}})
Module:Class第226行Lua错误:attempt to call field 'getPageType' (a nil value) | |
特色列表 | 特色列表模板(如{{Featured list}})
Module:Class第226行Lua错误:attempt to call field 'getPageType' (a nil value) | |
特色图片 | 特色图片模板(如{{Featured picture}})
Module:Class第226行Lua错误:attempt to call field 'getPageType' (a nil value) | |
重定向 | 頁面物件的isRedirect 欄位。
Module:Class第226行Lua错误:attempt to call field 'getPageType' (a nil value) | |
軟重定向 | 軟重定向模板(如{{軟重定向}})
Module:Class第226行Lua错误:attempt to call field 'getPageType' (a nil value) | |
沙盒 | 沙盒模板(如{{Sandbox}})
Module:Class第226行Lua错误:attempt to call field 'getPageType' (a nil value) | |
消歧義 | 消歧義模板(如{{消歧義}}) 以及相關魔術字(如 __DISAMBIG__ )
Module:Class第226行Lua错误:attempt to call field 'getPageType' (a nil value) | |
列表 | 名稱以「列表」結尾的頁面
Module:Class第226行Lua错误:attempt to call field 'getPageType' (a nil value) | |
同類索引 | 同類索引模板(如{{同類索引}})
Module:Class第226行Lua错误:attempt to call field 'getPageType' (a nil value) | |
小作品 | 條目的位元組數是否小於2000 (2000~3000間的過渡數值不自動評) Module:Class第226行Lua错误:attempt to call field 'getPageType' (a nil value) |
命名空間 | 前綴 | 對應的評級 |
---|---|---|
模板 | Template:Module:Class第226行Lua错误:attempt to call field 'getPageType' (a nil value) | |
模組 | Module:Module:Class第226行Lua错误:attempt to call field 'getPageType' (a nil value) | |
分類 | Category:Module:Class第226行Lua错误:attempt to call field 'getPageType' (a nil value) | |
文件 | File:Module:Class第226行Lua错误:attempt to call field 'getPageType' (a nil value) | |
草稿 | Draft:Module:Class第226行Lua错误:attempt to call field 'getPageType' (a nil value) | |
主題 | Portal:Module:Class第226行Lua错误:attempt to call field 'getPageType' (a nil value) | |
專題 | PJ:Module:Class第226行Lua错误:attempt to call field 'getPageType' (a nil value) | |
用戶 | User:Module:Class第226行Lua错误:attempt to call field 'getPageType' (a nil value) | |
說明 | Help:Module:Class第226行Lua错误:attempt to call field 'getPageType' (a nil value) | |
MediaWiki | MediaWiki:Module:Class第226行Lua错误:attempt to call field 'getPageType' (a nil value) | |
字幕 | TimedText:Module:Class第226行Lua错误:attempt to call field 'getPageType' (a nil value) | |
媒體 | Media:Module:Class第226行Lua错误:attempt to call field 'getPageType' (a nil value) | |
特殊 | Special:Module:Class第226行Lua错误:attempt to call field 'getPageType' (a nil value) |
模組中的主要函數
- getClass
-
- 模組調用:
p.getClass(class_name)
- 模板調用:
{{#invoke:PJBSClass/main|getClass| class_name | auto=yes/no | inheritance=yes/no | demo=yes/no }}
- 模組調用:
- 間接調用Module:PJBSClass#getClassByPage。
- 取得所在頁面的評級,可以輸入一個評級值(class_name)作為覆蓋與否的判斷依據。auto為是否要以自動判斷的評級為優先;inheritance為是否要以繼承值為優先;demo為是否為模板演示。
- getClassAuto
-
- 模組調用:
p.getClassAuto(page_name, class_default, demo)
- 模板調用:
{{#invoke:PJBSClass/main|getClassAuto| class_name | class=class_default | demo=yes/no }}
- 模組調用:
- 間接調用Module:PJBSClass#getAutoClass,並額外加入了從維基代碼判斷評級的功能,見維基代碼可判斷的評級值。
- 自動判斷名為「page_name」頁面的評級,若「page_name」未輸入則判斷所在頁面的評級。若無法判斷則回傳「class_default」。
- class_json
-
- 模組調用:
p.class_json()
- 模板調用:
{{#invoke:PJBSClass/main|class_json}}
- 模組調用:
- 提供Module:PJBSClass#{{Module:PJBSClass/page}}轉換Lua到JSON的函數。此函數沒有參數,僅回傳所在條目
mw.loadData("Module:PJBSClass/page")
的JSON結果。模板調用應使用{{Module:PJBSClass/page|json=yes}}
。
- getPageType
- 判斷該級別的分類頁面種類。
模組中的元函數
- _getClass
-
- 模組調用:
p._getClass(class_name, auto, inheritance, demo)
- 模板調用:
{{#invoke:PJBSClass/main|_getClass| class_name | auto=yes/no | inheritance=yes/no | demo=yes/no }}
- 模組調用:
- 同#getClass。
- _getProjects
-
- 模組調用:
p._getProjects(html)
- 模板調用:(無法使用)
- 模組調用:
- 解析「html」中的評級模板,列出當中的所有專題名稱。
專題橫幅內部函數
- subjectPageTitle
-
- 模組調用:
p.subjectPageTitle(page_name)
- 模板調用:
{{#invoke:PJBSClass/main|subjectPageTitle| page_name }}
- 模組調用:
- 無論名為「page_name」頁面是否是討論頁都會回傳其所對應之主要頁面的名稱。如果「page_name」不是討論頁,則回傳原頁面名稱。如果「page_name」未輸入則輸出所在頁面(無論是否是討論頁)所對應之主要頁面的名稱。如果所在頁面不是討論頁,則回傳所在頁面名稱。
- listProjects
-
- 模組調用:
p.listProjects(html, code, comma, max_num)
- 模板調用:
{{#invoke:PJBSClass/main|listProjects| html | code=code | comma=comma | tail=tail | max_num=max_num }}
- 模組調用:
- 列舉「html」中所有專題橫幅的專題,主要由{{PJBS}}調用。「code」為輸出的格式,
$1
代表專題名稱、$2
代表分隔符號。「comma」為分隔符號。「tail」為自動加在尾端的文字,預設為專題
。「max_num」為最大列舉數量。
- checkClassInput
- 檢查是否評級繼承與否
- wrongClass
- 檢查是否誤將橫幅與評級輸入在一起
- hasCustomClassName
- 檢查專題橫幅有無自訂評級級別
- customClassName
- 處理專題橫幅的自訂評級級別
- processNotice
- 將輸入到{{PJBS}}的專題橫幅處理成符合{{PJBS}}的樣式,並移除專題橫幅內自帶的提示模板,{{PJBS}}會使用#getNotice將之統一加入。同時解析內容添加適當的維護分類。
- getNotice
- 解析輸入到{{PJBS}}的專題橫幅有無橫幅內自帶的提示模板,移除重複的提示模板後,加以顯示。
判斷頁面屬性函數
- is_softredirect
- 判斷頁面是否為軟重定向。
- is_disambiguation
- 判斷頁面是否為消歧義頁。
- is_sandbox
- 判斷頁面是否為沙盒。
可供其他模組調用的私有函數
- _re_softredirect_template
- 匹配軟重定向模板的正則函數。
- _re_disambiguation_title
- 匹配消歧義標題的正則函數。
- _re_disambiguation_template
- 匹配消歧義模板的正則函數。
- _re_sandbox_template
- 匹配沙盒模板的正則函數。
- _remove_wikiproject_flag
- 用於避免消歧義判斷模板循環的跳脫函數,會破壞輸入的內容、移除魔術字,僅保留模板,以供展看測試有無消歧義魔術字。
除錯用函數
- _checker
- 檢查函數是否會出錯的函數。如無出錯,將頁面加入分類:可以正常讀取評級的條目;如出錯,將頁面加入分類:無法正常讀取評級的條目。
- check_disambig_process
- 列出#is_disambiguation的中間過程,以便除錯。
local p = {}
local yesno = require('Module:Yesno')
local cat_auto_class = "自動評級的頁面"
local cat_use_user_defined_class = "使用自訂專題評級的條目"
local cat_auto_disambig_class = '自動評級的消歧義級頁面'
local class_normalize = require("Module:Class/convert")._main
local TrackingCategory = require('Module:TrackingCategory')
local function isEmptyString(str) return mw.text.trim(tostring(str or '')) == '' end
--取得欲評級頁面的標題
function p.subjectPageTitle(input_data)
local page_name = input_data
local is_lua = true
if type((input_data or {}).args) ~= type(nil) then --input_data is a frame
page_name = input_data.args['1'] or input_data.args[1]
is_lua = false
end
local page = (type(page_name) ~= type(nil)) and ({pcall(mw.title.new, page_name)})[2] or mw.title.getCurrentTitle()
local subject_page = (page or {}).subjectPageTitle
if is_lua then return subject_page end
return subject_page.fullText
end
--讀取所在頁面的評級 函數本體
function p._getClass(input_data, _auto_first, _inheritance_first, _demo)
local class_name = input_data
local auto_first = _auto_first
local inheritance_first = _inheritance_first
local demo = _demo
if type((input_data or {}).args) ~= type(nil) then --input_data is a frame
class_name = input_data.args['1'] or input_data.args[1]
auto_first = yesno(input_data.args.auto)
inheritance_first = yesno(input_data.args.inheritance)
demo = yesno(input_data.args.demo)
end
--使用一頁只讀取一次的函數,讀取目前頁面中WPBS的評級
local WPBS_data = mw.loadData("Module:PJBSClass/page")
local WPBS_class = WPBS_data.class or '' --讀取到的目前頁面中WPBS的評級
if auto_first or --如果 "自動評級" 優先,或
(inheritance_first and (isEmptyString(WPBS_class) or WPBS_data.is_auto)) then --"繼承優先" 且{{WPBS}}有值
--嘗試進行自動判斷評級作業
local success, auto_class = pcall(p.getClassAuto, nil, (class_name == 'no_input' or class_name == '¬') and '' or class_name, demo)
if success then --自動判斷評級作業成功
class_name = (not isEmptyString(auto_class)) and auto_class or class_name
end
end
if class_name ~= nil and --如果並非 "未輸入" 級
(mw.ustring.lower(class_name or '') ~= 'no_input') and
(mw.ustring.lower(class_name or '') ~= '¬')
then
--WPBS的級空白就返回輸入的評級
if mw.text.trim(WPBS_class) == '' then return class_name end
--找不到WPBS模板也返回輸入的評級
if not WPBS_data.has_WPBS then return class_name end
--評級繼承與否判斷作業
return p.checkClassInput(WPBS_class, class_name)
end
return WPBS_class
end
--讀取所在頁面的評級 供呼叫的函數
function p.getClass(input_data)
local success, result = pcall(p._getClass, input_data)
if not success then return "" end
return result
end
--匹配軟重定向模板的正則函數
local function re_softredirect_template(input_text)
local text = input_text or ""
local match_list = {--各種軟重定向模板及其重定向匹配表
--注意:這裡必須全部使用小寫字母
--{"軟重定向模板正則", 是否允許前方有其他字, 是否後方不能有其他字}
{"[軟软]重新?[導导定]向",true},
{"soft[%s_%-]*redirect",true},
{"sr",false, true},
{"wikispecies[%s_%-]*redirect",false},
{"wiki[vs]o[yu][ar][gc]e[%s_%-]*redirect",false},
{"wiki[bq][ou]o[kt][se]?[%s_%-]*redirect",false},
{"commons[%s_%-]*redirect",false},
--如有新種軟重定向模板及其重定向被建立請加入於此
}--致管理員:如有新種軟重定向模板及其重定向被建立,請優先受理軟重定向模板及其重定向匹配項目的編輯請求
local black_list = { --不是軟重定向模板的模板名稱匹配表
"soft[%s-_]*redirect[%s-_]*protection",
}--致管理員:如有新各種軟重定向模板及其重定向被建立,請優先受理軟重定向模板及其重定向匹配項目的編輯請求
local lotext = mw.ustring.lower(text..'\n') --以小寫進行匹配
for i = 1,#match_list do --對每一個軟重定向模板及其重定向進行匹配
local j, k = mw.ustring.find(lotext, "%{%{"..
(match_list[i][2] and "[^%}]*" or "%s*")..match_list[i][1]..
(match_list[i][3] and "[%}%|]*" or "[^%}%|]*")
)
if j ~= nil then --匹配到了軟重定向模板或其重定向
local result = mw.ustring.sub(text, j, k)
result = mw.ustring.match(result, "%{%{%s*([^%}%|]+)$") --讀取匹配到的名稱
if result then
local is_redirect = true
for i1 = 1,#black_list do --檢查是否在黑名單中
if mw.ustring.match(mw.ustring.lower(result), black_list[i1]) then
is_redirect = false --如果不是
break
end
end
if is_redirect then --是軟重定向模板,回傳模板名稱
return mw.text.trim(result)
end
end
end
end
return nil
end
p._re_softredirect_template = re_softredirect_template
--偵測軟重定向
function p.is_softredirect(input_data)
local page_name = input_data
if type((input_data or {}).args) ~= type(nil) then --input_data is a frame
page_name = input_data.args['1'] or input_data.args[1]
end
local page = (type(page_name) ~= type(nil)) and ({pcall(mw.title.new, page_name)})[2] or mw.title.getCurrentTitle()
local talk_page = (page or {}).talkPageTitle
local subject_page = (page or {}).subjectPageTitle
if not subject_page:inNamespaces( --排除沒有軟重定向的命名空間
mw.title.new("File:Ex").namespace,
mw.title.new("MediaWiki:Ex").namespace,
mw.title.new("TimedText:Ex").namespace,
mw.title.new("Media:Ex").namespace,
mw.title.new("Special:Ex").namespace,2600,2300,2302)
then
if subject_page.isRedirect then return false end --"硬" 重定向不是 "軟" 重定向
local body = ""
if subject_page.getContent then body = subject_page:getContent() or "" end
local body_len = mw.ustring.len(body)
if body_len > 10000 or body_len <= 0 then return false end --依據常識,沒有那麼大的軟重定向頁
if re_softredirect_template(body) then --尋找軟重定向的模板
return true
end
end
return false
end
--匹配消歧義標題的正則函數
local function re_disambiguation_title(input_text)
local text = input_text or ""
local match_list = {
--注意:這裡必須全部使用小寫字母
"%([消分]歧[義义頁页]?%)",
"%([消分]歧[義义][頁页]?%)",
"%(disambiguous%)",
"%disambiguation%)",
"%(disambi?g?%)",
}
local lotext = mw.ustring.lower(text)
for i = 1,#match_list do
local j, k = mw.ustring.find(lotext, "%s+"..match_list[i])
if j ~= nil then
local result = mw.ustring.sub(text, j, k)
result = mw.ustring.match(result, "%(([^%)]+)%)$")
return result
end
end
return nil
end
p._re_disambiguation_title = re_disambiguation_title
--匹配消歧義模板的正則函數
local function re_disambiguation_template(input_text)
local text = input_text or ""
local match_list = {--各種消歧義模板及其重定向匹配表
--注意:這裡必須全部使用小寫字母
--{"消歧義模板正則", 是否允許前方有其他字}
{"[^要][消分]歧[義义頁页]?",true},
{"[^要][消分]歧[義义][頁页]?",true},
{"[消分]歧[義义頁页]?",false},
{"[消分]歧[義义][頁页]?",false},
{"dab",false},
{"disambiguous",true},
{"disambiguation",true},
{"disambi?g?",true},
{"aimai",false},
{"disambiguation%s*page",true},
--如有新消歧義模板及其重定向被建立請加入於此
}--致管理員:如有新消歧義模板及其重定向被建立,請優先受理新消歧義模板及其重定向匹配項目的編輯請求
local black_list = { --不是消歧義模板的模板名稱匹配表
"disambiguation[%s-_]*need", "disambiguous[%s-_]*need",
"r to disambig", "disamb[%s-_]*link",
"disambig[%s-_]*list", "disambig[%s-_]*nav",
"title[%s-_]*without[%s-_]*disambig"
--如有新的非消歧義模板但會被匹配到的請加入於此
}--致管理員:如有新非消歧義模板被建立,請優先受理其編輯請求
local lotext = mw.ustring.lower(text..'\n') --以小寫進行匹配
for i = 1,#match_list do --對每一個消歧義模板及其重定向進行匹配
local j, k = mw.ustring.find(lotext, "%{%{"..
(match_list[i][2] and "[^%}]*" or "%s*")..match_list[i][1].."[^%}%|]*")
if j ~= nil then --匹配到了消歧義模板或其重定向
local result = mw.ustring.sub(text, j, k)
result = mw.ustring.match(result, "%{%{%s*([^%}%|]+)$") --讀取匹配到的名稱
if result then
local is_correct = true
for i1 = 1,#black_list do --檢查是否在黑名單中
if mw.ustring.match(mw.ustring.lower(result), black_list[i1]) then
is_correct = false --如果不是
break
end
end
if is_correct then --是消歧義模板,回傳模板名稱
return mw.text.trim(result)
end
end
end
end
return nil
end
p._re_disambiguation_template = re_disambiguation_template
local function remove_wikiproject_flag(input_text)
local text = input_text or ""
local match_list = {
"[Ww][Ii][Kk][Ii]%s*[Pp][Rr][Oo][Jj][Ee][Cc][Tt]",
"[Ww][Pp][Jj]", "[Ww][Pp][Bb][Ss]","[Pp][Jj][Bb][Ss]",
"[維维]基[专專][题題]", "[专專][题題]", --取消專題橫幅
"[<>%[%]]","#%s*[Tt][Aa][Gg]%s*:",--取消參考文獻
"%{%{%s*[Tt][Aa]%s*[%}%|]",":[Tt][Aa][^0-9a-zA-Z]",
"[Nn][Oo][Tt][Ee]%s*[TtAa][TtAa]", --取消{{NoteTA}}
"DEFAULTSORT","DISPLAYTITLE", "NOEXTERNALLANGLINKS", "TOC__",
"SECTION__", "TALK__", "LINK__", "GALLERY__", "CAT__",
"INDEX__", "REDIRECT__" --取消影響頁面內容的魔術字
}
for _, match_pattern in ipairs(match_list) do
text = mw.ustring.gsub(text,match_pattern, "-")
end
return text
end
p._remove_wikiproject_flag = remove_wikiproject_flag
--偵測消歧義頁
function p.is_disambiguation(input_data)
local page_name = input_data
if type((input_data or {}).args) ~= type(nil) then --input_data is a frame
page_name = input_data.args['1'] or input_data.args[1]
end
local page = (type(page_name) ~= type(nil)) and ({pcall(mw.title.new, page_name)})[2] or mw.title.getCurrentTitle()
local talk_page = (page or {}).talkPageTitle
local subject_page = (page or {}).subjectPageTitle
if not subject_page:inNamespaces( --排除沒有消歧義的命名空間
mw.title.new("File:Ex").namespace,
mw.title.new("Module:Ex").namespace,
mw.title.new("Template:Ex").namespace,
mw.title.new("MediaWiki:Ex").namespace,
mw.title.new("TimedText:Ex").namespace,
mw.title.new("Media:Ex").namespace,
mw.title.new("Special:Ex").namespace,2600,2300,2302)
then
if subject_page.isRedirect then return false end --重定向不是消歧義
if re_disambiguation_title(subject_page.fullText or "") then --檢查是否有消歧義標題
return true
end
local body = ""
if subject_page.getContent then body = subject_page:getContent() or "" end
local body_len = mw.ustring.len(body)
if body_len > 10000 or body_len <= 0 then return false end --依據常識,沒有那麼大的消歧義頁
if re_disambiguation_template(body) then --尋找消歧義的模板
return true
end
if not mw.title.equals(subject_page or "", mw.title.getCurrentTitle()) then
--頭尾限400字,以節省效能
local check_body = (body_len > 400) and (mw.ustring.sub(body, 1, 200).."{{tl|tl}} }}{{ {{tl|tl}}"..mw.ustring.sub(body, -200, -1)) or body
local check_body = remove_wikiproject_flag(check_body) --避免模板循環
if mw.ustring.match(mw.getCurrentFrame():preprocess(check_body.."{{reflist}}")
, "__DISAMBIG__") then --匹配展開的模板有無消歧義的魔術字
return true
end
end
end
return false
end
--匹配沙盒模板的正則函數
local function re_sandbox_template(input_text)
local text = input_text or ""
local match_list = {--各種沙盒模板及其重定向匹配表
--注意:這裡必須全部使用小寫字母
--{"沙盒模板正則", 是否允許前方有其他字}
{"[請请]注意",false},
{"沙盒",true},
{"請勿編輯此行",false},
{"sandbox",true},
--如有新沙盒模板及其重定向被建立請加入於此
}--致管理員:如有新沙盒模板及其重定向被建立,請優先受理新沙盒模板及其重定向匹配項目的編輯請求
local black_list = { --不是沙盒模板的模板名稱匹配表
"/沙盒","#invoke:沙盒","/sandbox",
--如有新的非沙盒模板但會被匹配到的請加入於此
}--致管理員:如有新非沙盒模板被建立,請優先受理其編輯請求
local lotext = mw.ustring.lower(text..'\n') --以小寫進行匹配
for i = 1,#match_list do --對每一個沙盒模板及其重定向進行匹配
local j, k = mw.ustring.find(lotext, "%{%{"..
(match_list[i][2] and "[^%}]*" or "%s*")..match_list[i][1].."[^%}%|]*")
if j ~= nil then --匹配到了沙盒模板或其重定向
local result = mw.ustring.sub(text, j, k)
result = mw.ustring.match(result, "%{%{%s*([^%}%|]+)$") --讀取匹配到的名稱
if result then
local is_correct = true
for i1 = 1,#black_list do --檢查是否在黑名單中
if mw.ustring.match(mw.ustring.lower(result), black_list[i1]) then
is_correct = false --如果不是
break
end
end
if is_correct then --是沙盒模板,回傳模板名稱
return mw.text.trim(result)
end
end
end
end
return nil
end
p._re_sandbox_template = re_sandbox_template
function p.is_sandbox(input_data)
local page_name = input_data
if type((input_data or {}).args) ~= type(nil) then --input_data is a frame
page_name = input_data.args['1'] or input_data.args[1]
end
local current_title = mw.title.getCurrentTitle()
--取得頁面標題物件
local page = (type(page_name) ~= type(nil)) and ({pcall(mw.title.new, page_name)})[2] or current_title
local current_page = page.subjectPageTitle or current_title.subjectPageTitle
if current_page:inNamespace(mw.title.new(":EX").namespace) then return false end
local check_title = mw.ustring.lower(tostring(current_page.fullText))
if current_page.isRedirect then return false end
if mw.ustring.match(check_title, "sandbox") or mw.ustring.match(check_title, "沙盒") then
return true
end
local body = ""
if current_page.getContent then body = current_page:getContent() or "" end
body = mw.ustring.sub(body, 1, 400) --檢查頭部
if re_sandbox_template(body) then --尋找沙盒的模板
return true
end
return false
end
--自動偵測重定向、消歧義和命名空間 (模板、模組、分類、檔案、草稿、主題、專題) 產生評級
function p.getClassAuto(input_data, class_input, demo)
local page_name = input_data
local page_name_inputed = false
local class_default = class_input or ''
local demo_flag = yesno(demo or "no")
if type((input_data or {}).args) ~= type(nil) then --input_data is a frame
page_name = input_data.args['1'] or input_data.args[1]
class_default = input_data.args.class or input_data.args.CLASS or ''
demo_flag = yesno(input_data.args.demo or "no")
end
if not isEmptyString(page_name) then page_name_inputed = true end
if demo_flag then return class_default end
local current_title = mw.title.getCurrentTitle()
--取得頁面標題物件
local page = (type(page_name) ~= type(nil)) and ({pcall(mw.title.new, page_name)})[2] or current_title
local current_page = page.subjectPageTitle or current_title.subjectPageTitle
--success=執行成功與失敗, result=執行結果
local success, result = false, ''
if isEmptyString(class_default)then --沒有預輸入評級
local page_is_disambiguation = false
local page_is_softredirect = false
local page_is_sandbox = false
if page_name_inputed then --目前正在讀取其他頁面
page_is_disambiguation = p.is_disambiguation(page_name)
page_is_softredirect = p.is_softredirect(page_name)
page_is_sandbox = p.is_sandbox(page_name)
else --如果是讀取本頁,用讀取一次的方案 : mw.loadData("Module:PJBSClass/page")
local PJBSClassData = mw.loadData("Module:PJBSClass/page")
page_is_disambiguation = PJBSClassData.is_disambiguation
page_is_softredirect = PJBSClassData.is_softredirect
page_is_sandbox = PJBSClassData.is_sandbox
end
if page_is_softredirect then --如果偵測到是軟重定向
return '重定向'
end
if page_is_disambiguation then --如果偵測到是消歧義
local CurrentFrame = mw.getCurrentFrame()
TrackingCategory.append(CurrentFrame, cat_auto_class, 'disambig')
TrackingCategory.append(CurrentFrame, cat_auto_disambig_class)
return '消歧义'
end
if page_is_sandbox then --如果偵測到是軟重定向
return '沙盒'
end
end
local class_default_lower = mw.ustring.lower(class_default)
if current_page.isRedirect or current_page:inNamespaces(
mw.title.new("Template:Ex").namespace,
mw.title.new("Module:Ex").namespace,
mw.title.new("Category:Ex").namespace,
mw.title.new("File:Ex").namespace,
mw.title.new("Draft:Ex").namespace,
mw.title.new("Portal:Ex").namespace,
mw.title.new("PJ:Ex").namespace,
mw.title.new("User:Ex").namespace,
mw.title.new("Help:Ex").namespace,
mw.title.new("MediaWiki:Ex").namespace,
mw.title.new("TimedText:Ex").namespace,
mw.title.new("Media:Ex").namespace,
mw.title.new("Special:Ex").namespace,2600,2300,2302)
then
if current_page:inNamespace(mw.title.new("File:Ex").namespace) and
(class_default_lower == "fm" or class_default_lower == "fi" or
mw.ustring.match(class_default_lower, "特[圖图]") or
mw.ustring.match(class_default_lower, "特色[圖图媒][片體体]") )
then
return class_default
end
success, result = pcall(require("Module:PJBSClass").getAutoClass, input_data)
if success and not isEmptyString(result) then --如果成功讀取,並有讀到評級
TrackingCategory.append(mw.getCurrentFrame(),cat_auto_class)
end
end
--讀取不成功,回傳預輸入評級
if not success then return class_default end
return result
end
--偵錯用 : 只要[[Cat:無法正常讀取評級的條目]]是空的,代表本模組沒問題。
function p._checker(input_data)
local success, result = pcall(p.getClass, input_data)
if not mw.loadData("Module:PJBSClass/page").has_WPBS then return '' end
if not success then return "[[Cat:無法正常讀取評級的條目]]" end
local result_show = (not isEmptyString(result)) and result or ' '
if not isEmptyString(result)then
return "[[Cat:可以正常讀取評級的條目|".. result_show .."]]"
end
return ''
end
--列舉WPBS中的專題
function p.listProjects(frame, _code, _comma, _max_num)
local project_list = p._getProjects(frame)
local code = _code or '$1$2'
local comma = _comma or '、'
local max_num = tonumber("inf")
local tail = "專題"
local default_text = ''
if type(frame.args) == type({"table"}) then
code = frame.args.code or code
comma = frame.args.comma or comma
tail = frame.args.tail or tail
max_num = tonumber(frame.args.max_num or frame.args["max num"]) or max_num
default_text = frame.args.default or default_text
elseif type(frame) == type({"table"}) then
code = frame.code or frame[2] or code
comma = frame.comma or frame[3] or comma
max_num = tonumber(frame.max_num or frame["max num"] or frame[4]) or max_num
tail = frame.tail or tail
default_text = frame.default or default_text
end
if #project_list <= 0 then return default_text end
local result = ''
for i=1,#project_list do
if i > max_num then break end
result = result .. mw.ustring.gsub(code, "%$([%+%-]?%d+)", function(_id)
local id = tonumber(_id)
if id == 1 then
return project_list[i]
elseif id == 2 then
if #project_list == 1 or max_num == 1 then return '' end
return ((i==#project_list or i == max_num) and '' or ((i + 1 == max_num or i + 1 == #project_list) and "和" or comma))
end
return "$".._id
end)
end
if max_num > 1 then
result = result .. "等"
end
result = result .. tail
return result
end
--取得WPBS中的所有已輸入的專題
function p._getProjects(frame)
local text = frame
if type(frame.args) == type({"table"}) then
text = frame.args[1] or ''
elseif type(frame) == type({"table"}) then
text = frame[1] or ''
end
local project_list = {}
local _,j,i,length = 1,1,1,mw.ustring.len(text)
while i <= length do
--類似於$.(".wpb-project")以抓取專題元數據 (metadata)
_,j = mw.ustring.find(text, "class%s*=%s*\"wpb%-project\"", i)
if j then
local k = mw.ustring.find(text, "<%s*/%s*span%s*>", j)
local pj_text = mw.ustring.sub(text, j+1, k or -1)
--獲取專題名稱
project_list[#project_list + 1] = mw.ustring.match(pj_text, "^>%s*(.*)%s*<$")
i = k or length
else break end
end
return project_list
end
--評級繼承與否判斷作業
function p.checkClassInput(_class_input, _class_given)
local class_input = _class_input
local class_given = _class_given or _class_input
local frame = mw.getCurrentFrame()
if type(_class_input.args) == type({"table"}) then
class_input = _class_input.args[1] or ''
class_given = _class_input.args[2] or _class_input.args[1] or ''
frame = _class_input
elseif type(_class_input) == type({"table"}) then
class_input = _class_input[1] or ''
class_given = _class_input[2] or _class_input[1] or ''
end
class_input = mw.text.trim(class_input)
class_given = mw.text.trim(class_given)
if class_input == '' then return class_given end --無輸入為繼承
--轉換為標準評級字串
local norm_class_input = class_normalize({class_input})
local norm_class_given = class_normalize({class_given})
if class_input~='' and class_given~='' then
--如果不繼承評級
if norm_class_input ~= norm_class_given then
--添加維護分類
TrackingCategory.append(frame, cat_use_user_defined_class)
end
end
return class_given
end
function p.class_json()
return mw.text.jsonEncode(mw.loadData("Module:PJBSClass/page"))
end
function p.processNotice(input_data)
local wikitext = input_data or ""
if type((input_data or {}).args) ~= type(nil) then --input_data is a frame
wikitext = input_data.args['1'] or input_data.args[1] or ""
end
wikitext = mw.ustring.gsub(wikitext,'(class="[^"]-messagebox[^"]-)"', "%1 wpb-outside\"")
local re_mbox = '<table[^>]-class="[^"]-[aico]mbox[^"]-"'
local re_wpb_outside = '<table[^>]-class="[^"]-wpb%-outside[^"]-"'
local wikitext_len = mw.ustring.len(wikitext)
local mbox_head, mbox_head_end = mw.ustring.find(wikitext,re_mbox)
if type(mbox_head) ~= type(0) then mbox_head, mbox_head_end = mw.ustring.find(wikitext,re_wpb_outside) end
local mbox_end = nil
while type(mbox_head) == type(0) do
local _, mbox_end = mw.ustring.find(wikitext,'<%s*/%s*table%s*>', mbox_head_end)
if type(mbox_end) == type(0) then
wikitext = mw.ustring.sub(wikitext, 1, mbox_head-1) .. ((mbox_end + 1 >= wikitext_len) and "" or mw.ustring.sub(wikitext, mbox_end + 1, -1))
wikitext_len = mw.ustring.len(wikitext)
end
mbox_head, mbox_head_end = mw.ustring.find(wikitext,re_mbox)
if type(mbox_head) ~= type(0) then mbox_head, mbox_head_end = mw.ustring.find(wikitext,re_wpb_outside) end
end
--追蹤套娃式的基礎條目橫幅
if mw.ustring.match(wikitext, "基础条目") then
wikitext = wikitext .. "[[Cat:錯誤放置基礎條目橫幅的頁面]]"
end
return wikitext
end
function p.getNotice(input_data)
local wikitext = input_data or ""
if type((input_data or {}).args) ~= type(nil) then --input_data is a frame
wikitext = input_data.args['1'] or input_data.args[1] or ""
end
local body = ''
wikitext = mw.ustring.gsub(wikitext,'(class="[^"]-messagebox[^"]-)"', "%1 wpb-outside\"")
local wikitext_len = mw.ustring.len(wikitext)
local re_mbox = '<table[^>]-class="[^"]-[aico]mbox[^"]-"'
local re_wpb_outside = '<table[^>]-class="[^"]-wpb%-outside[^"]-"'
local mbox_list = {}
local mbox_head, mbox_head_end = mw.ustring.find(wikitext,re_mbox)
local mbox_head_o, mbox_head_end_o = mw.ustring.find(wikitext,re_wpb_outside)
if (mbox_head_o or wikitext_len) < (mbox_head or wikitext_len) then
mbox_head, mbox_head_end = mbox_head_o, mbox_head_end_o
end
if type(mbox_head) ~= type(0) then mbox_head, mbox_head_end = mw.ustring.find(wikitext,re_wpb_outside) end
local mbox_end = nil
while type(mbox_head) == type(0) and (mbox_head or wikitext_len) < wikitext_len - 1 do
local _, mbox_end = mw.ustring.find(wikitext,'<%s*/%s*table%s*>', mbox_head_end)
if type(mbox_end) == type(0) then
local mbox_content = mw.ustring.sub(wikitext, mbox_head, mbox_end)
local checker = mw.ustring.lower(mw.ustring.gsub(mbox_content, "[%s_-]", ""))
local has_same = false
for i=1,#mbox_list do
if mbox_list[i][2] == checker then
has_same = true
break
end
end
if not has_same then
mbox_list[#mbox_list + 1] = {mbox_content, checker}
end
end
mbox_head, mbox_head_end = mw.ustring.find(wikitext,re_mbox, mbox_end or (wikitext_len - 1))
mbox_head_o, mbox_head_end_o = mw.ustring.find(wikitext,re_wpb_outside, mbox_end or (wikitext_len - 1))
if (mbox_head_o or wikitext_len) < (mbox_head or wikitext_len) then
mbox_head, mbox_head_end = mbox_head_o, mbox_head_end_o
end
end
for i=1,#mbox_list do
body = body..mbox_list[i][1]
end
return body
end
return p