Module:File
Scope
File title and file information. If the code here grows beyond a border line, this should be converted to an interface and the processing code should be outsourced.
Usage
Note that an error is thrown, if the title can't be constructed (e.g. a title containing invalid characters is supplied) or meta data isn't available (e.g. due to missing file or extraction error). It is your responsibility to catch them; in Lua through pcall()
; from Wikitext as {{#iferror: {{#invoke:File|function|file=File:P%bar]baz.qqq}} | meaningful message}}
.
From Wikitext
Search (Lua error in Module:LangSwitch at line 135: attempt to concatenate a nil value.+F) for @exports
.
- Examples:
{{#invoke:File|extension|file=File:Test.jpg}}
→jpg
{{#invoke:File|width|file=File:Test.jpg}}
→414
{{#invoke:File|size|file=File:Test.jpg}}
→6782
{{#invoke:File|mime|file=File:Test.jpg}}
→image/jpeg
deprecated{{#invoke:File|mimeType|file=File:Test.jpg}}
→image/jpeg
{{#invoke:File|dateWorkCreated|file=File:Ballot-sprite.png}}
→{{#invoke:File|fileExists|file=File:Ballot-sprite.png}}
→{{#invoke:File|fileExists|file=File:DOESNOTEXIST-0a8de8c83.png}}
→{{#invoke:File|fileExistsRelaxed|file=File:Ba[!#llot-sprite.png}}
→
From Lua
<source lang="Lua"> local file = require( 'Module:File' ) local fileObj = file.File( 'File:Test.svg' ) local withoutExtension = fileObj.woExtension() -- withoutExtension is now 'Test'
local exists = fileObj.metadata().exists if exists then
mw.log( fileObj.metadata().width )
end </source>
-- Module for handling Media files (Origin: Wikimedia Commons) -- Helpers local h, File = {} h.getFile = function(f) return File( f.args[1] or f.args["file"] or f.args["title"] or mw.title.getCurrentTitle().text ) end h.getWikiText = function(title, frame) return '<html>' .. (frame or mw.getCurrentFrame()):expandTemplate{ title = title, args = {}}:gsub('<nowiki>.*?</nowiki>', '') .. '</html>' end File = function(title) local funcs = {} local titleInstance, metadataInstance function getTitle() if titleInstance == nil then titleInstance = mw.title.new( title, 6 ) end return titleInstance end function getMetadata() if metadataInstance == nil then metadataInstance = getTitle().file end return metadataInstance end -- =p.File("Foo.bar.svg").extension() -- @return "svg" funcs.extension = function() local parts = mw.text.split( title, '.', true ) return parts[#parts] end -- =p.File("Foo.bar.svg").woExtension() -- Original author: Bawolff at [[Module:FileName]] -- @return "Foo.bar" funcs.woExtension = function() local parts = mw.text.split( title , '.', true ) local upTo = #parts - 1 if upTo == 0 then upTo = 1 end return table.concat( parts, '.', 1, upTo ) end -- Mapping file extensions to MIME-types (only MIME types accepted for files in Commons) funcs.extensionMap = { -- File types with full support in Commons (See [[Commons:File types]]) DJVU = "image/vnd.djvu", FLAC = "audio/x-flac", GIF = "image/gif", JPEG = "image/jpeg", JPG = "image/jpeg", MID = "audio/midi", OGA = "audio/ogg", OGG = "audio/ogg", OGV = "video/ogg", PDF = "application/pdf", PNG = "image/png", SVG = "image/svg+xml", TIF = "image/tiff", TIFF = "image/tiff", WEBM = "video/webm", WAV = "audio/x-wav", XCF = "image/xcf", -- Other file types with restrictions (not accepted in standard uploads on Commons but in "User:" namespace) -- They could be supported in Wiki pages by embedding their content in an <pre> or <source> elements CSS = "text/css", CSV = "text/csv", JS = "application/javascript", JSON = "application/json", TXT = "text/plain", XML = "application/xml", -- Only generated by MediaWiki on output of some queries, restricted in all uploads GZ = "application/gzip", -- delivered only only for some wiki results ZIP = "application/zip", -- delivered only for some wiki data exports -- Other file types not supported and to convert (a few of them may be in special administration namespaces) DOC = "application/msword", -- please convert to PDF, DJVU, or Wiki F4V = "video/mpeg", -- (deprecated, replaced by MP4) please convert to OGV or WEBM FLV = "video/x-flv", -- (deprecated, replaced by MP4) please convert to OGV or WEBM ICO = "image/vnd.microsoft.icon", -- used in MediaWiki resources for "website icons" MP3 = "audio/mpeg", -- please convert to OGA MP4 = "video/mpeg", -- please convert to OGV or WEBM QT = "video/quicktime", -- (deprecated, replaced by MP4) convert to OGV or WEBM RA = "audio/vnd.rn-realaudio", -- (deprecated, replaced by MP3) convert to OGA SWF = "video/x-flv", -- (deprecated, replaced by MP4) convert to OGV or WEBM WMA = "audio/x-ms-wma", -- please convert to OGA WMV = "video/x-ms-wmv", -- please convert to OGV or WEBM XLS = "application/vnd.ms-excel", -- please convert to PDF, DJVU, or Wiki } -- =p.File("Foo.bar.svg").extension() -- @return "image/svg+xml" funcs.mime = function() local extension = funcs.extension():upper() mw.log( 'mime() is deprecated. Use mimeType.' ) return funcs.extensionMap[extension] or "unknown" end -- =p.File("Foo.bar.tiff").maxthumb() funcs.maxthumb = function() local mime = funcs.mime() if mime == "image/png" then return mw.getCurrentFrame():preprocess( '{{LargePNG/limit}}' ) elseif mime == "image/tiff" or mime == "image/gif" then return mw.getCurrentFrame():preprocess( '{{LargeTIFF/limit}}' ) else return 'unknown @Module:File' end end funcs.dateWorkCreated = function(frame) local page, htmlparser = mw.title.new( title, 6 ).prefixedText, require("Module:HTMLParser") local ok, html = pcall( h.getWikiText, page, frame ) if not ok then return nil end -- add a root node local root = htmlparser.parse(html) local tdElem = root('#fileinfotpl_date') -- We queried an ID so there should be only one result for td in pairs(tdElem) do -- We need the next sibling, which doesn't seem to be directly supported by HTMLParser -- ... so ask him for the parent <tr> and find the <time> element in it local timeElem = td.parent('time') for t in pairs(timeElem) do return t.attributes['datetime'] end end end funcs.metadata = function() return getMetadata() end return funcs end -- @exports local p = {} p.File = File p.extension = function(frame) return h.getFile(frame).extension():lower() end p.extensionUpper = function(frame) return h.getFile(frame).extension():upper() end p.woExtension = function(frame) return h.getFile(frame).woExtension() end p.mime = function(frame) return h.getFile(frame).mime() end p.mimeType = function(frame) return h.getFile(frame).metadata().mimeType end p.maxthumb = function(frame) return h.getFile(frame).maxthumb() end p.dateWorkCreated = function(frame) return h.getFile(frame).dateWorkCreated() or '' end p.fileExists = function(frame) return h.getFile(frame).metadata().exists or '' end -- This one won't throw errors at you p.fileExistsRelaxed = function(frame) local success, metadata = pcall(h.getFile(frame).metadata) if success then return metadata.exists or '' else return '' end end p.width = function(frame) return h.getFile(frame).metadata().width end p.height = function(frame) return h.getFile(frame).metadata().height end p.size = function(frame) return h.getFile(frame).metadata().size end p.pageCount = function(frame) local pages = h.getFile(frame).metadata().pages or {'page'} return #pages end p.runTests = function() local toTest = require('Module:File/tests/all') local result = true for i, t in ipairs(toTest) do local f = File(t.fileName) local stringResult = '' local ret = true local results = { extension = (t.extension == f.extension():lower()), extensionUpper = (t.extensionUpper == f.extension():upper()), woExtension = (t.woExtension == f.woExtension()), mime = (t.mime == f.mime()), maxthumb = (not (tonumber(f.maxthumb()) == nil) == t.maxthumbIsNumber), dateWorkCreated = t.dateWorkCreated == f.dateWorkCreated() } for k, v in pairs(results) do stringResult = stringResult .. k .. ': ' .. (v and 'ok ' or 'failed') .. ' ' ret = ret and v end mw.log(i, ret and 'passed' or 'FAILED', t.typeOfFileName, (not ret) and ('\n >>' .. stringResult .. '\n >> ' .. t.fileName) or '') result = result and ret end return result end return p