Module:Arcaea Data:修订间差异

来自Arcaea中文维基
无编辑摘要
(忽略song.deleted)
 
(未显示4个用户的24个中间版本)
第4行: 第4行:
    -- 将曲包ID转换为曲包名称。
    -- 将曲包ID转换为曲包名称。
    -- 传入Songlist中定义的曲包ID,返回Packlist中的曲包名称。如果Template:Transition.json中存在转换,则使用转换后的名称。
    -- 传入Songlist中定义的曲包ID,返回Packlist中的曲包名称。如果Template:Transition.json中存在转换,则使用转换后的名称。
   if type(id) ~= "string"
   then
     mw.log("id值类型不符,类型为"..type(id))
     return "undefined"
   end


    -- 检查曲包ID→曲包名称转换表是否存在转换规则。
    -- 检查曲包ID→曲包名称转换表是否存在转换规则。
第13行: 第18行:
    if packlist == nil then
    if packlist == nil then
      packlist = mw.text.jsonDecode(mw.getCurrentFrame():expandTemplate{ title = 'Packlist.json' })
      packlist = mw.text.jsonDecode(mw.getCurrentFrame():expandTemplate{ title = 'Packlist.json' })
   end
   for i, k in ipairs(packlist['packs']) do
     if k['id'] == id then return k['name_localized']['en'] end
    end
    end


    for i, k in ipairs(packlist['packs']) do
   if packlistNS == nil then
     packlistNS = mw.text.jsonDecode(mw.getCurrentFrame():expandTemplate{ title = 'Packlist NS' })
   end
    for i, k in ipairs(packlistNS['packs']) do
      if k['id'] == id then return k['name_localized']['en'] end
      if k['id'] == id then return k['name_localized']['en'] end
    end
    end
   mw.log("未找到曲包名称,id为"..id)
   return id
end
end


第39行: 第53行:
end
end


function jsonAssayForSingleSong(json, index, typed)
function extractInfoFromSingleSongData(info, key)
    --  传入JSON文件,索引 和索引值类型(索引是ID还是曲名)。分析JSON文件以获得曲目信息,返回的是一个 查找 单一曲目中信息的函数。仅获取单一曲目的信息。table中的索引名请查看下方switch表。
    --  如果info无 即无法在songlist中 查找 索引值,则 返回nil
 
    if info == nil then 
   -- Songlist是以数字为 索引值, 因此遍历Songlist,直到发现需要找的曲目,将信息存入info变量中。
      mw.log( ' 无法在Songlist中发现目标,索引值为:'.. (index or 'nil') )
   local s, info = "", {}
      return nil
   -- 如果模式是ID 遍历songlist直至发现id值为索引值为止,并获取内容。曲名同理
    if typed == "id" then
      for i, k in ipairs(json['songs']) do
       if k['id'] == index then list[index] = k end
     end
   else
     for i, k in ipairs(json['songs']) do
       if k['title_localized']['en'] == index then info = k end
      end
    end
    end


    -- 此处返回一个函数用于查询内容。
    local difficulties={}
 
   return function(key)


     -- 如果info无值即无法在songlist中查找到索引值,则返回nil。
   if info["difficulties"] then
    
      for _, difficulty in ipairs(info["difficulties"]) do
     if info == nil
        difficulties[difficulty["ratingClass"]] = difficulty
      then
       mw.log( '无法在Songlist中发现目标,索引值为:'..index )
        return nil
      end
      end
   end


     -- 此处定义一个switch table以达到switch函数的效用。如果需要查找的参数在switch中不存在,返回nil。
   -- 此处定义一个switch table以达到switch函数的效用。如果需要查找的参数在switch中不存在,返回nil。
     local switch = {
   local switch = {
       ["id"] = function() return info["id"] end,
     ["id"] = function() return info["id"] end,
       ["title"] = function() return info['title_localized']['en'] end,
     ["title"] = function() 
       ["artist"] = function() return info["artist"] end,
     if info['title_localized'] then
       ["bpm"] = function() return info["bpm"] end,
     return info['title_localized']['en']
       ["set"] = function() return info["set"] end,
     end
       ["side"] = function() return info["side"] end,
     end,
       ["date"] = function() return info["date"] end,
     ["artist"] = function() return info["artist"] end,
       ["version"] = function() return info["version"] end,
     ["bpm"] = function() return info["bpm"] end,
        ["bg"] = function()
     ["set"] = function() return info["set"] end,
     ["category"] = function() return info["category"] end,
     ["side"] = function() return info["side"] end,
     ["date"] = function() return info["date"] end,
     ["version"] = function() return info["version"] end,
     ["bg"] = function()
        if info["bg"] ~= "" then
         return info["bg"]
       else
         if info["side"] == 0 then
           return 'base_light'
         else
           if info['side'] ==1 then
             return 'base_conflict'
           else
             return 'undefined'
           end
         end
       end
     end,
     ["pstChartDesigner"] = function()
       if info["difficulties"] then
         return difficulties[0]['chartDesigner']
       end
     end,
     ["pstJacketDesigner"] = function()
       if info["difficulties"] then
         return difficulties[0]['jacketDesigner']
       end
     end,
     ["pstRating"] = function()
       if difficulties[0]['ratingPlus'] then
         return difficulties[0]['rating'] .. '+'
       else
         return difficulties[0]['rating']
       end
     end,
     ["prsChartDesigner"] = function()
       if info["difficulties"] then
         return difficulties[1]['chartDesigner']
       end
     end,
     ["prsJacketDesigner"] = function()
       if info["difficulties"] then
         return difficulties[1]['jacketDesigner']
       end
     end,
     ["prsRating"] = function()
       if difficulties[1]['ratingPlus'] then
         return difficulties[1]['rating'] .. '+'
       else
         return difficulties[1]['rating']
       end
     end,
     ["ftrChartDesigner"] = function()
       if info["difficulties"] then
         return difficulties[2]['chartDesigner']
       end
     end,
     ["ftrJacketDesigner"] = function()
       if info["difficulties"] then
         return difficulties[2]['jacketDesigner']
       end
     end,
     ["ftrRating"] = function()
       if info["difficulties"] then
         if difficulties[2]['ratingPlus'] then
           return difficulties[2]['rating'] .. '+'
         else
           return difficulties[2]['rating']
         end
       end
     end,
     ["bydChartDesigner"] = function()
       if info["difficulties"] and difficulties[3] then
         return difficulties[3]['chartDesigner']
       end
     end,
     ["bydJacketDesigner"] = function()
       if info["difficulties"] and difficulties[3] then
         return difficulties[3]['jacketDesigner']
       end
     end,
     ["bydRating"] = function()
       if info["difficulties"] and difficulties[3] then
         if difficulties[3]['ratingPlus'] then
           return difficulties[3]['rating'] .. '+'
         else
           return difficulties[3]['rating']
         end
       end
     end,
     ["etrChartDesigner"] = function()
       if info["difficulties"] and difficulties[4] then
         return difficulties[4]['chartDesigner']
       end
     end,
     ["etrJacketDesigner"] = function()
       if info["difficulties"] and difficulties[4] then
         return difficulties[4]['jacketDesigner']
       end
     end,
     ["etrRating"] = function()
       if info["difficulties"] and difficulties[4] then
         if difficulties[4]['ratingPlus'] then
           return difficulties[4]['rating'] .. '+'
         else
           return difficulties[4]['rating']
         end
       end
     end,
     ["pstChange"] = function()
       if info["difficulties"] and difficulties[0] then
         return difficulties[0]['has_controller_alt_chart']
       end
     end,
     ["prsChange"] = function()
       if info["difficulties"] and difficulties[1] then
         return difficulties[1]['has_controller_alt_chart']
       end
     end,
     ["ftrChange"] = function()
       if info["difficulties"] and difficulties[2] then
         return difficulties[2]['has_controller_alt_chart']
       end
     end,
     ["bydChange"] = function()
       if info["difficulties"] and difficulties[3] then
         return difficulties[3]['has_controller_alt_chart']
       end
     end,
     ["etrChange"] = function()
       if info["difficulties"] and difficulties[4] then
         return difficulties[4]['has_controller_alt_chart']
       end
     end,
     ["bydAudioChange"] = function()
       if info["difficulties"] and difficulties[3] then
         return difficulties[3]['audioOverride']
       end
     end,
     ["bydBPM"] = function()
       if info["difficulties"] and difficulties[3] then
         return difficulties[3]['bpm']
       end
     end,
     ["bydArtist"] = function()
       if info["difficulties"] and difficulties[3] then
         return difficulties[3]['artist']
       end
     end,
     ["bydSongName"] = function()
       if info["difficulties"] and difficulties[3] and difficulties[3].title_localized then
         return difficulties[3].title_localized.en
       end
     end,
     ["bydDate"] = function()
       if info["difficulties"] and difficulties[3] then
         return difficulties[3].date
       end
     end,
     ["bydVersion"] = function()
       if info["difficulties"] and difficulties[3] then
         return difficulties[3].version
       end
     end,
     ["etrDate"] = function()
       if info["difficulties"] and difficulties[4] then
         return difficulties[4].date
       end
     end,
     ["etrVersion"] = function()
       if info["difficulties"] and difficulties[4] then
         return difficulties[4].version
       end
     end,
     ["pstBg"] = function()
       if info["difficulties"] and difficulties[0] and difficulties[0]['bg'] then
         return difficulties[0]['bg']
       else
          if info["bg"] ~= "" then
          if info["bg"] ~= "" then
            return info["bg"]
            return info["bg"]
第91行: 第271行:
            end
            end
          end
          end
        end,
        end
       ["pstChartDesigner"] = function()
     end,
         return info["difficulties"][1]['chartDesigner']
     ["prsBg"] = function()
       end,
       if info["difficulties"] and difficulties[1] and difficulties[1]['bg'] then
       ["pstJacketDesigner"] = function()
          return difficulties[1]['bg']
         return info["difficulties"][1]['jacketDesigner']
        else
       end,
          if info["bg"] ~= "" then
       ["pstRating"] = function()
            return info["bg"]
         return info["difficulties"][1]['rating']
       end,
       ["prsChartDesigner"] = function()
          return info["difficulties"][2]['chartDesigner']
        end,
       ["prsJacketDesigner"] = function()
          return info["difficulties"][2]['jacketDesigner']
       end,
       ["prsRating"] = function()
         return info["difficulties"][2]['rating']
       end,
       ["ftrChartDesigner"] = function()
         return info["difficulties"][3]['chartDesigner']
       end,
       ["ftrJacketDesigner"] = function()
         return info["difficulties"][3]['jacketDesigner']
       end,
       ["ftrRating"] = function()
         if info["difficulties"][3]['ratingPlus'] then
            return info["difficulties"][3]['rating'] .. '+'
          else
          else
            return info["difficulties"][3]['rating']
            if info["side"] == 0 then
             return 'base_light'
           else
             if info['side'] ==1 then
               return 'base_conflict'
             else
               return 'undefined'
             end
           end
          end
          end
        end,
        end
       ["bydChartDesigner"] = function()
     end,
         if info["difficulties"][4] then
     ["ftrBg"] = function()
            return info["difficulties"][4]['chartDesigner']
       if info["difficulties"] and difficulties[2] and difficulties[2]['bg'] then
         return difficulties[2]['bg']
       else
         if info["bg"] ~= "" then
            return info["bg"]
         else
           if info["side"] == 0 then
             return 'base_light'
           else
             if info['side'] ==1 then
               return 'base_conflict'
             else
               return 'undefined'
             end
           end
          end
          end
        end,
        end
       ["bydJacketDesigner"] = function()
     end,
         if info["difficulties"][4] then
     ["bydBg"] = function()
            return info["difficulties"][4]['jacketDesigner']
       if info["difficulties"] and difficulties[3] and difficulties[3]['bg'] then
         return difficulties[3]['bg']
       else
         if info["bg"] ~= "" then
            return info["bg"]
         else
           if info["side"] == 0 then
             return 'base_light'
           else
             if info['side'] ==1 then
               return 'base_conflict'
             else
               return 'undefined'
             end
           end
          end
          end
        end,
        end
       ["bydRating"] = function()
     end,
         if info["difficulties"][4] then
     ["etrBg"] = function()
           return info["difficulties"][4]['rating']
       if info["difficulties"] and difficulties[4] and difficulties[4]['bg'] then
          end
          return difficulties[4]['bg']
       end,
        else
       ["pstChange"] = function()
         if info["bg"] ~= "" then
         if info["difficulties"][1] then
            return info["bg"]
           return info["difficulties"][1]['has_controller_alt_chart']
          else
         end
           if info["side"] == 0 then
        end,
             return 'base_light'
       ["prsChange"] = function()
           else
         if info["difficulties"][2] then
             if info['side'] ==1 then
            return info["difficulties"][2]['has_controller_alt_chart']
               return 'base_conflict'
          end
             else
       end,
               return 'undefined'
       ["ftrChange"] = function()
             end
         if info["difficulties"][3] then
           end
           return info["difficulties"][3]['has_controller_alt_chart']
         end
       end,
       ["bydAudioChange"] = function()
         if info["difficulties"][4] then
           return info["difficulties"][4]['audioOverride']
         end
       end,
       ["bydBg"] = function()
         if info["difficulties"][4] then
           return info["difficulties"][4]['bg']
         end
       end,
       ["bydBPM"] = function()
         if info["difficulties"][4] then
           return info["difficulties"][4]['bpm']
         end
       end,
       ["bydArtist"] = function()
         if info["difficulties"][4] then
           return info["difficulties"][4]['artist']
          end
          end
        end
        end
      }
      end
   }
 
   if switch[key] == nil
   then
     mw.log( '未定义的索引类型,请检查是否拼写错误。' )
     return nil
   end
 
   return switch[key]()
end
 
function jsonAssayForSingleSong(json, index, indexTyped)
   -- 传入JSON文件,索引值和索引值类型(索引是ID还是曲名)。分析JSON文件以获得曲目信息,返回的是一个查找单一曲目中信息的函数。仅获取单一曲目的信息。table中的索引名请查看下方switch表。


     if switch[key] == nil
   -- Songlist是以数字为索引值,因此遍历Songlist,直到发现需要找的曲目,将信息存入info变量中。
      then
   local s, info = "", {}
       mw.log( ' 未定义的索引类型,请检查是否拼写错误。' )
   -- 如果模式是ID则遍历songlist直至发现id值为索引值为止,并获取内容。曲名同理。
        return nil
   if indexTyped == "id" then
      for i, k in ipairs(json['songs']) do
        if not k.deleted and k['id'] == index then info = k break end
      end
      end
   else
     for i, k in ipairs(json['songs']) do
       if not k.deleted and string.lower(k['title_localized']['en']) == string.lower(index) then info = k break end
     end
   end


      return switch[key]()
   -- 此处返回一个函数用于查询内容。
 
   return function(key)
      return extractInfoFromSingleSongData(info, key)
    end
    end
end
end
第191行: 第389行:
    then
    then
      if indexTyped == "id"  then
      if indexTyped == "id"  then
        return jsonAssayForSingleSong(mw.text.jsonDecode(mw.getCurrentFrame():expandTemplate{ title = 'Songlist.json' } ), id, 'id')
        return jsonAssayForSingleSong(mw.text.jsonDecode(mw.getCurrentFrame():expandTemplate{ title = 'Songlist.json' } ), index, 'id')
      else
      else
        return jsonAssayForSingleSong(mw.text.jsonDecode(mw.getCurrentFrame():expandTemplate{ title = 'Songlist.json' } ), name, 'name')
        return jsonAssayForSingleSong(mw.text.jsonDecode(mw.getCurrentFrame():expandTemplate{ title = 'Songlist.json' } ), index, 'name')
      end
      end
    else
    else
      if indexTyped == "id"  then
      if indexTyped == "id"  then
        return jsonAssayForSingleSong(mw.text.jsonDecode(mw.getCurrentFrame():expandTemplate{ title = 'Songlist NS.json' } ), id, 'id')
        return jsonAssayForSingleSong(mw.text.jsonDecode(mw.getCurrentFrame():expandTemplate{ title = 'Songlist NS.json' } ), index, 'id')
      else
      else
        return jsonAssayForSingleSong(mw.text.jsonDecode(mw.getCurrentFrame():expandTemplate{ title = 'Songlist NS.json' } ), name, 'name')
        return jsonAssayForSingleSong(mw.text.jsonDecode(mw.getCurrentFrame():expandTemplate{ title = 'Songlist NS.json' } ), index, 'name')
      end
      end
    end
    end
第209行: 第407行:


    local s, info = "", {}
    local s, info = "", {}
    if typed == "id" then
    if indexTyped == "id" then
      for i, k in ipairs(json['songs']) do
      for i, k in ipairs(json['songs']) do
        info[k['id']] = k
        info[k['id']] = k
第222行: 第420行:


    return function(index, key)
    return function(index, key)
 
      return extractInfoFromSingleSongData(info[index], key)
      -- 如果info无值即无法在songlist中查找到索引值,则返回nil。
    
     if info[index] == nil
     then
       mw.log( '无法在Songlist中发现目标,索引值为:'..index )
       return nil
     end
 
     -- 此处定义一个switch table以达到switch函数的效用。如果需要查找的参数在switch中不存在,返回nil。
     local switch = {
       ["id"] = function() return info[index]["id"] end,
       ["title"] = function() return info[index]['title_localized']['en'] end,
       ["artist"] = function() return info[index]["artist"] end,
       ["bpm"] = function() return info[index]["bpm"] end,
       ["set"] = function() return info[index]["set"] end,
       ["side"] = function() return info[index]["side"] end,
       ["date"] = function() return info[index]["date"] end,
       ["version"] = function() return info[index]["version"] end,
       ["bg"] = function()
         if info[index]["bg"] ~= "" then
           return info[index]["bg"]
         else
           if info[index]["side"] == 0 then
             return 'base_light'
           else
             if info[index]['side'] ==1 then
               return 'base_conflict'
             else
               return 'undefined'
             end
           end
         end
       end,
       ["pstChartDesigner"] = function()
         return info[index]["difficulties"][1]['chartDesigner']
       end,
       ["pstJacketDesigner"] = function()
         return info[index]["difficulties"][1]['jacketDesigner']
       end,
       ["pstRating"] = function()
         return info[index]["difficulties"][1]['rating']
       end,
       ["prsChartDesigner"] = function()
         return info[index]["difficulties"][2]['chartDesigner']
       end,
       ["prsJacketDesigner"] = function()
         return info[index]["difficulties"][2]['jacketDesigner']
       end,
       ["prsRating"] = function()
         return info[index]["difficulties"][2]['rating']
       end,
       ["ftrChartDesigner"] = function()
         return info[index]["difficulties"][3]['chartDesigner']
       end,
       ["ftrJacketDesigner"] = function()
         return info[index]["difficulties"][3]['jacketDesigner']
       end,
       ["ftrRating"] = function()
         if info[index]["difficulties"][3]['ratingPlus'] then
           return info[index]["difficulties"][3]['rating'] .. '+'
         else
           return info[index]["difficulties"][3]['rating']
         end
       end,
       ["bydChartDesigner"] = function()
         if info[index]["difficulties"][4] then
           return info[index]["difficulties"][4]['chartDesigner']
         end
       end,
       ["bydJacketDesigner"] = function()
         if info[index]["difficulties"][4] then
           return info[index]["difficulties"][4]['jacketDesigner']
         end
       end,
       ["bydRating"] = function()
         if info[index]["difficulties"][4] then
           return info[index]["difficulties"][4]['rating']
         end
       end,
       ["pstChange"] = function()
         if info[index]["difficulties"][1] then
           return info[index]["difficulties"][1]['has_controller_alt_chart']
         end
       end,
       ["prsChange"] = function()
         if info[index]["difficulties"][2] then
           return info[index]["difficulties"][2]['has_controller_alt_chart']
         end
       end,
       ["ftrChange"] = function()
         if info[index]["difficulties"][3] then
           return info[index]["difficulties"][3]['has_controller_alt_chart']
         end
       end,
       ["bydAudioChange"] = function()
         if info[index]["difficulties"][4] then
           return info[index]["difficulties"][4]['audioOverride']
         end
       end,
       ["bydBg"] = function()
         if info[index]["difficulties"][4] then
           return info[index]["difficulties"][4]['bg']
         end
       end,
       ["bydBPM"] = function()
         if info[index]["difficulties"][4] then
           return info[index]["difficulties"][4]['bpm']
         end
       end,
       ["bydArtist"] = function()
         if info[index]["difficulties"][4] then
           return info[index]["difficulties"][4]['artist']
         end
       end
     }
 
     if switch[key] == nil
     then
       mw.log( '未定义的索引类型,请检查是否拼写错误。' )
       return nil
     end
 
     return switch[key]()
    end
    end


第380行: 第455行:
p.Song_Query = makeInvokeFunc('_Song_Query')
p.Song_Query = makeInvokeFunc('_Song_Query')


function p._Song_Query(songIndexType, songIndex, attributeName, platform)
function p._Song_Query(args)
    -- 面向wikitext直接查询
    -- 面向wikitext直接查询
    return p.singleSongInformation(songIndex, songIndexType, platform)(attributeName)
    -- return p.singleSongInformation(songIndex, songIndexType, platform)(attributeName)
   return p.singleSongInformation(args[1], args[2], args[4])(args[3])
end
end


p.Pack_Query = makeInvokeFunc('_Pack_Query')
p.Pack_Query = makeInvokeFunc('_Pack_Query')


function p._Pack_Query(id)
function p._Pack_Query(args)
    -- 面向wikitext直接查询
    -- 面向wikitext直接查询
    return p.packName(id)
    return p.packName(args[1])
end
end


return p
return p

2024年10月4日 (五) 23:29的最新版本

本模块可查询Arcaea数据文件中存在的信息,为元模块,为其他模块提供支持。也提供接口对模块外直接查询。

通过模板:Songlist.json模板:Songlist NS.json模板:Packlist.json模板:Unlocks.json进行分析以提供数据。

面向模块函数

singleSongInformation

获取一个曲目所有信息,返回值是一个函数。可以通过该函数进行查询。

使用方法

local data = require("Module:Arcaea Data")
local query = data.singleSongInformation("该曲目的索引值", "索引值的类型,id或name", "查找内容的平台,mobile或ns")
mw.log(query("需要查询的属性的名称"))

示例

local data = require("Module:Arcaea Data")
local query = data.singleSongInformation("ifi", "id", "mobile")
-- 此时query是一个函数,传入需要查询的属性名称返回该属性的值。
mw.log(query("pstChartDesigner"))
-- 输出"夜浪"

allSongInformation

获取任何曲目的任何信息,返回值是一个函数。可以通过该函数进行查询。
和前者比效率略低一点点,查询更不方便(如果只需要查询一个曲目的话)。

使用方法

local data = require("Module:Arcaea Data")
local query = data.singleSongInformation("索引值的类型,id或name", "查找内容的平台,mobile或ns")
mw.log(query("该曲目的索引值", "需要查询的属性的名称"))

示例

local data = require("Module:Arcaea Data")
local query = data.allSongInformation("id", "mobile")
-- 此时query是一个函数,传入需要查询的属性名称返回该属性的值。
mw.log(query("ifi", "pstChartDesigner"))
-- 输出"夜浪"

packName

获传入曲包ID,获得Packlist中的曲包名称,返回值是一个字符串。
Template:Transition.json中存在转换,则使用转换后的名称,否则直接传出Packlist中的曲包名称。

使用方法

local data = require("Module:Arcaea Data")
local query = data.packName
mw.log(query("曲包ID"))

示例

local data = require("Module:Arcaea Data")
local query = data.packName
mw.log(query("vs"))
-- 输出"Black Fate"

unlockText

正在编写中。

直接查询函数

已将函数封为模板:Arcaea Data,可使用封包的模板来查询数据。

Song_Query

用法

{{Arcaea Data|type=Song_Query|索引名称|索引名称类型|属性名称|平台}}

示例

{{Arcaea Data|type=Song_Query|ifi|id|title|mobile}}

Pack_Query

用法

{{Arcaea Data|type=Pack_Query|曲包ID}}

示例

{{Arcaea Data|type=Pack_Query|vs}}

属性名列表

  • id
  • title
  • artist
  • bpm
  • set
  • side
  • date
  • version
  • bg
  • pstChartDesigner
  • pstJacketDesigner
  • pstRating
  • prsChartDesigner
  • prsJacketDesigner
  • prsRating
  • ftrChartDesigner
  • ftrJacketDesigner
  • ftrRating
  • bydChartDesigner
  • bydJacketDesigner
  • bydRating
  • etrChartDesigner
  • etrJacketDesigner
  • etrRating
  • pstChange
  • prsChange
  • ftrChange
  • bydChange
  • etrChange
  • bydAudioChange
  • bydBPM
  • bydArtist
  • 新背景参数:如果没有单独指定使用bg
  • pstBg
  • prsBg
  • ftrBg
  • bydBg
  • etrBg

local p = {}

function p.packName(id)
    -- 将曲包ID转换为曲包名称。
    -- 传入Songlist中定义的曲包ID,返回Packlist中的曲包名称。如果Template:Transition.json中存在转换,则使用转换后的名称。
    if type(id) ~= "string"
    then
        mw.log("id值类型不符,类型为"..type(id))
        return "undefined"
    end

    -- 检查曲包ID→曲包名称转换表是否存在转换规则。
    local covList = mw.text.jsonDecode(mw.getCurrentFrame():expandTemplate{ title = 'Transition.json' })["packName"]
    if covList[id] then return covList[id] end

    -- 判断变量是否已有值,为多次调用预备。
    -- 变量为全局变量
    if packlist == nil then
        packlist = mw.text.jsonDecode(mw.getCurrentFrame():expandTemplate{ title = 'Packlist.json' })
    end
    for i, k in ipairs(packlist['packs']) do
        if k['id'] == id then return k['name_localized']['en'] end
    end

    if packlistNS == nil then
        packlistNS = mw.text.jsonDecode(mw.getCurrentFrame():expandTemplate{ title = 'Packlist NS' })
    end
    for i, k in ipairs(packlistNS['packs']) do
        if k['id'] == id then return k['name_localized']['en'] end
    end

    mw.log("未找到曲包名称,id为"..id)
    return id
end

function p.unlockText(songId)
    -- 还未编写好的函数。目的:传入Songid,检索unlock,返回一个解锁要求文本的字符串。

    -- 变量为全局变量
    if unlock == nil
    then
        unlock = mw.text.jsonDecode(mw.getCurrentFrame():expandTemplate{ title = 'Packlist.json' })
    end
    
    local result = {}
    for i, k in ipairs(json) do
        if k['songId'] == songId then
            result[tonumber(k['ratingClass'] + 1)] = k['conditions']
            -- coding...
        end
    end
    return result
end

function extractInfoFromSingleSongData(info, key)
    -- 如果info无值即无法在songlist中查找到索引值,则返回nil。
    if info == nil then 
        mw.log( '无法在Songlist中发现目标,索引值为:'.. (index or 'nil') )
        return nil 
    end

    local difficulties={}

    if info["difficulties"] then
        for _, difficulty in ipairs(info["difficulties"]) do
            difficulties[difficulty["ratingClass"]] = difficulty
        end
    end

    -- 此处定义一个switch table以达到switch函数的效用。如果需要查找的参数在switch中不存在,返回nil。
    local switch = {
        ["id"] = function() return info["id"] end,
        ["title"] = function() 
        	if info['title_localized'] then
        		return info['title_localized']['en']
        	end
        end,
        ["artist"] = function() return info["artist"] end,
        ["bpm"] = function() return info["bpm"] end,
        ["set"] = function() return info["set"] end,
        ["category"] = function() return info["category"] end,
        ["side"] = function() return info["side"] end,
        ["date"] = function() return info["date"] end,
        ["version"] = function() return info["version"] end,
        ["bg"] = function()
            if info["bg"] ~= "" then
                return info["bg"]
            else
                if info["side"] == 0 then
                    return 'base_light'
                else
                    if info['side'] ==1 then
                        return 'base_conflict'
                    else
                        return 'undefined'
                    end
                end
            end
        end,
        ["pstChartDesigner"] = function()
            if info["difficulties"] then
                return difficulties[0]['chartDesigner']
            end
        end,
        ["pstJacketDesigner"] = function()
            if info["difficulties"] then
                return difficulties[0]['jacketDesigner']
            end
        end,
        ["pstRating"] = function()
            if difficulties[0]['ratingPlus'] then
                return difficulties[0]['rating'] .. '+'
            else
                return difficulties[0]['rating']
            end
        end,
        ["prsChartDesigner"] = function()
            if info["difficulties"] then
                return difficulties[1]['chartDesigner']
            end
        end,
        ["prsJacketDesigner"] = function()
            if info["difficulties"] then
                return difficulties[1]['jacketDesigner']
            end
        end,
        ["prsRating"] = function()
            if difficulties[1]['ratingPlus'] then
                return difficulties[1]['rating'] .. '+'
            else
                return difficulties[1]['rating']
            end
        end,
        ["ftrChartDesigner"] = function()
            if info["difficulties"] then
                return difficulties[2]['chartDesigner']
            end
        end,
        ["ftrJacketDesigner"] = function()
            if info["difficulties"] then
                return difficulties[2]['jacketDesigner']
            end
        end,
        ["ftrRating"] = function()
            if info["difficulties"] then
                if difficulties[2]['ratingPlus'] then
                    return difficulties[2]['rating'] .. '+'
                else
                    return difficulties[2]['rating']
                end
            end
        end,
        ["bydChartDesigner"] = function()
            if info["difficulties"] and difficulties[3] then
                return difficulties[3]['chartDesigner']
            end
        end,
        ["bydJacketDesigner"] = function()
            if info["difficulties"] and difficulties[3] then
                return difficulties[3]['jacketDesigner']
            end
        end,
        ["bydRating"] = function()
            if info["difficulties"] and difficulties[3] then
                if difficulties[3]['ratingPlus'] then
                    return difficulties[3]['rating'] .. '+'
                else
                    return difficulties[3]['rating']
                end
            end
        end,
        ["etrChartDesigner"] = function()
            if info["difficulties"] and difficulties[4] then
                return difficulties[4]['chartDesigner']
            end
        end,
        ["etrJacketDesigner"] = function()
            if info["difficulties"] and difficulties[4] then
                return difficulties[4]['jacketDesigner']
            end
        end,
        ["etrRating"] = function()
            if info["difficulties"] and difficulties[4] then
                if difficulties[4]['ratingPlus'] then
                    return difficulties[4]['rating'] .. '+'
                else
                    return difficulties[4]['rating']
                end
            end
        end,
        ["pstChange"] = function()
            if info["difficulties"] and difficulties[0] then
                return difficulties[0]['has_controller_alt_chart']
            end
        end,
        ["prsChange"] = function()
            if info["difficulties"] and difficulties[1] then
                return difficulties[1]['has_controller_alt_chart']
            end
        end,
        ["ftrChange"] = function()
            if info["difficulties"] and difficulties[2] then
                return difficulties[2]['has_controller_alt_chart']
            end
        end,
        ["bydChange"] = function()
            if info["difficulties"] and difficulties[3] then
                return difficulties[3]['has_controller_alt_chart']
            end
        end,
        ["etrChange"] = function()
            if info["difficulties"] and difficulties[4] then
                return difficulties[4]['has_controller_alt_chart']
            end
        end,
        ["bydAudioChange"] = function()
            if info["difficulties"] and difficulties[3] then
                return difficulties[3]['audioOverride']
            end
        end,
        ["bydBPM"] = function()
            if info["difficulties"] and difficulties[3] then
                return difficulties[3]['bpm']
            end
        end,
        ["bydArtist"] = function()
            if info["difficulties"] and difficulties[3] then
                return difficulties[3]['artist']
            end
        end,
        ["bydSongName"] = function()
            if info["difficulties"] and difficulties[3] and difficulties[3].title_localized then
                return difficulties[3].title_localized.en
            end
        end,
        ["bydDate"] = function()
            if info["difficulties"] and difficulties[3] then
                return difficulties[3].date
            end
        end,
        ["bydVersion"] = function()
            if info["difficulties"] and difficulties[3] then
                return difficulties[3].version
            end
        end,
        ["etrDate"] = function()
            if info["difficulties"] and difficulties[4] then
                return difficulties[4].date
            end
        end,
        ["etrVersion"] = function()
            if info["difficulties"] and difficulties[4] then
                return difficulties[4].version
            end
        end,
        ["pstBg"] = function()
            if info["difficulties"] and difficulties[0] and difficulties[0]['bg'] then
                return difficulties[0]['bg']
            else
                if info["bg"] ~= "" then
                    return info["bg"]
                else
                    if info["side"] == 0 then
                        return 'base_light'
                    else
                        if info['side'] ==1 then
                            return 'base_conflict'
                        else
                            return 'undefined'
                        end
                    end
                end
            end
        end,
        ["prsBg"] = function()
            if info["difficulties"] and difficulties[1] and difficulties[1]['bg'] then
                return difficulties[1]['bg']
            else
                if info["bg"] ~= "" then
                    return info["bg"]
                else
                    if info["side"] == 0 then
                        return 'base_light'
                    else
                        if info['side'] ==1 then
                            return 'base_conflict'
                        else
                            return 'undefined'
                        end
                    end
                end
            end
        end,
        ["ftrBg"] = function()
            if info["difficulties"] and difficulties[2] and difficulties[2]['bg'] then
                return difficulties[2]['bg']
            else
                if info["bg"] ~= "" then
                    return info["bg"]
                else
                    if info["side"] == 0 then
                        return 'base_light'
                    else
                        if info['side'] ==1 then
                            return 'base_conflict'
                        else
                            return 'undefined'
                        end
                    end
                end
            end
        end,
        ["bydBg"] = function()
            if info["difficulties"] and difficulties[3] and difficulties[3]['bg'] then
                return difficulties[3]['bg']
            else
                if info["bg"] ~= "" then
                    return info["bg"]
                else
                    if info["side"] == 0 then
                        return 'base_light'
                    else
                        if info['side'] ==1 then
                            return 'base_conflict'
                        else
                            return 'undefined'
                        end
                    end
                end
            end
        end,
        ["etrBg"] = function()
            if info["difficulties"] and difficulties[4] and difficulties[4]['bg'] then
                return difficulties[4]['bg']
            else
                if info["bg"] ~= "" then
                    return info["bg"]
                else
                    if info["side"] == 0 then
                        return 'base_light'
                    else
                        if info['side'] ==1 then
                            return 'base_conflict'
                        else
                            return 'undefined'
                        end
                    end
                end
            end
        end
    }

    if switch[key] == nil 
    then 
        mw.log( '未定义的索引类型,请检查是否拼写错误。' )
        return nil 
    end

    return switch[key]()
end

function jsonAssayForSingleSong(json, index, indexTyped)
    -- 传入JSON文件,索引值和索引值类型(索引是ID还是曲名)。分析JSON文件以获得曲目信息,返回的是一个查找单一曲目中信息的函数。仅获取单一曲目的信息。table中的索引名请查看下方switch表。

    -- Songlist是以数字为索引值,因此遍历Songlist,直到发现需要找的曲目,将信息存入info变量中。
    local s, info = "", {}
    -- 如果模式是ID则遍历songlist直至发现id值为索引值为止,并获取内容。曲名同理。
    if indexTyped == "id" then
        for i, k in ipairs(json['songs']) do
            if not k.deleted and k['id'] == index then info = k break end
        end
    else
        for i, k in ipairs(json['songs']) do
            if not k.deleted and string.lower(k['title_localized']['en']) == string.lower(index) then info = k break end
        end
    end

    -- 此处返回一个函数用于查询内容。

    return function(key)
        return extractInfoFromSingleSongData(info, key)
    end
end

function p.singleSongInformation(index, indexTyped, platform)
    -- 传入曲名或ID,获得一个查阅信息的函数。直接在下一个模块使用。
    -- index:曲目的索引字符串,和typed一致  indexTyped:id或name,查找曲目的索引值类型  platform:mobile或ns
    if platform == "mobile"
    then
        if indexTyped == "id"  then
            return jsonAssayForSingleSong(mw.text.jsonDecode(mw.getCurrentFrame():expandTemplate{ title = 'Songlist.json' } ), index, 'id')
        else
            return jsonAssayForSingleSong(mw.text.jsonDecode(mw.getCurrentFrame():expandTemplate{ title = 'Songlist.json' } ), index, 'name')
        end
    else
        if indexTyped == "id"  then
            return jsonAssayForSingleSong(mw.text.jsonDecode(mw.getCurrentFrame():expandTemplate{ title = 'Songlist NS.json' } ), index, 'id')
        else
            return jsonAssayForSingleSong(mw.text.jsonDecode(mw.getCurrentFrame():expandTemplate{ title = 'Songlist NS.json' } ), index, 'name')
        end
    end
end

function jsonAssayForAllSong(json, indexTyped)
    -- 传入JSON文件,获得一个通过索引值查找指定曲目指定信息的函数。与jsonAssayForSingleSong不同,本函数可以同时查找多个函数。
    -- 索引值由下一步函数使用来指定,但是索引类型必须刚开始就指定。(id或name)

    local s, info = "", {}
    if indexTyped == "id" then
        for i, k in ipairs(json['songs']) do
            info[k['id']] = k
        end
    else
        for i, k in ipairs(json['songs']) do
            info[k['title_localized']['en']] = k
        end
    end

    -- 此处返回一个函数用于查询内容。

    return function(index, key)
        return extractInfoFromSingleSongData(info[index], key)
    end

end

function p.allSongInformation(indexTyped, platform)
    -- 获得一个查阅信息的函数,可查阅任何曲目。直接在下一个模块使用。
    -- indexTyped:id或name,查找曲目的索引值类型  platform:mobile或ns
    if platform == "mobile"
    then
        if indexTyped == "id"  then
            return jsonAssayForAllSong(mw.text.jsonDecode(mw.getCurrentFrame():expandTemplate{ title = 'Songlist.json' } ), 'id')
        else
            return jsonAssayForAllSong(mw.text.jsonDecode(mw.getCurrentFrame():expandTemplate{ title = 'Songlist.json' } ), 'name')
        end
    else
        if indexTyped == "id"  then
            return jsonAssayForAllSong(mw.text.jsonDecode(mw.getCurrentFrame():expandTemplate{ title = 'Songlist NS.json' } ), 'id')
        else
            return jsonAssayForAllSong(mw.text.jsonDecode(mw.getCurrentFrame():expandTemplate{ title = 'Songlist NS.json' } ), 'name')
        end
    end
end

local getArgs = require('Module:Arguments').getArgs

function makeInvokeFunc(funcName)
    return function(frame)
        local args = getArgs(frame)
        return p[funcName](args)
    end
end

p.Song_Query = makeInvokeFunc('_Song_Query')

function p._Song_Query(args)
    -- 面向wikitext直接查询
    -- return p.singleSongInformation(songIndex, songIndexType, platform)(attributeName)
    return p.singleSongInformation(args[1], args[2], args[4])(args[3])
end

p.Pack_Query = makeInvokeFunc('_Pack_Query')

function p._Pack_Query(args)
    -- 面向wikitext直接查询
    return p.packName(args[1])
end

return p