Module:File
Documentation for this module may be created at Module:File/doc
-- Module for handling Media files (Origin: Wikimedia Commons) -- Helpers local h = {} h.expandPage = function(fullPageName, args) -- This expansion may fail, use it with pcall and inspect error status return mw.getCurrentFrame():expandTemplate{title = ':' .. fullPageName, args} end h.expandPageNoFail = function(fullPageName, args) local ok, wikiText = pcall(h.expandPage, fullPageName, args) if ok then return wikiText end return '' end -- Limits in megapixels are currently stored in Commons templates, they could be in this module. -- There may be more limits for other supported mime types (djvu, flac, ogv, pdf, svg, webm, xcf). h.maxthumbMap = { -- ['image/gif'] = h.expandPageNoFail('Template:LargeTIFF/limit', {}), -- current value is '50' but higher now ['image/png' ] = h.expandPageNoFail('Template:LargePNG/limit', {}), -- current value is '2500' ['image/tiff'] = h.expandPageNoFail('Template:LargeTIFF/limit', {}), -- current value is '50' but higher now } h.maxthumbMap['image/gif' ] = h.maxthumbMap['image/tiff'] -- current value is '50' but higher now h.extensionMap = { -- File types with full support in Commons (See [[c:Commons:File types]]). DJVU = 'image/vnd.djvu', FLAC = 'audio/x-flac', GIF = 'image/gif', JPEG = 'image/jpeg', JPG = 'image/jpeg', MID = 'audio/midi', MP3 = 'audio/mpeg', 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' MP4 = 'video/mp4', -- please convert to OGV or WEBM QT = 'video/quicktime', -- (deprecated, replaced by MP4) please convert to OGV or WEBM RA = 'audio/vnd.rn-realaudio', -- (deprecated, replaced by MP3) please convert to OGA SWF = 'video/x-flv', -- (deprecated, replaced by MP4) please 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 } h.parse = require("Module:HTMLParser").parse local 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 getFullName() return getTitle().prefixedText 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() -- @return "Foo.bar" -- Original author: Bawolff at [[Module:FileName]] 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 function getMetadata() if metadataInstance == nil then metadataInstance = getTitle().file end return metadataInstance end funcs.metadata = function() return getMetadata() end -- Mapping file extensions to MIME-types (only MIME types accepted for files in Commons). -- Works even if file still does not exist. -- =p.File('Foo.bar.svg').extension() -- @return 'image/svg+xml' funcs.mime = function() local ok, metadata = pcall(funcs.metadata()) if ok and metadata.exists then -- Note: does not work if file does not exist, where metadata == {'exists': false} only return metadata.mimeType end -- mw.log('mime() is deprecated. Use metadata().mimeType.') return h.extensionMap[funcs.extension():upper()] or 'unknown' end -- =p.File('Foo.bar.tiff').maxthumb() funcs.maxthumb = function() return h.maxthumbMap[funcs.mime()] or 'unknown @Module:File' end funcs.dateWorkCreated = function() -- Parse the expanded wiki text into an html root node and select a child node by specific ID. local root = h.parse('<html>' .. h.expandPageNoFail(getFullName(), {}) :gsub('<nowiki>.*?</nowiki>', '') .. '</html>') local tdElem = root('#fileinfotpl_date') for td in pairs(tdElem) do -- We queried an ID so there should be only one result in this loop. -- We need the next sibling, which doesn't seem to be directly supported by HTMLParser. -- ... so ask him for the parent <tr> node and find the first <time> element in it. local timeElem = td.parent('time') for t in pairs(timeElem) do return t.attributes['datetime'] end end end return funcs end h.getFile = function(frame) return File(frame.args[1] or frame.args["file"] or frame.args["title"] or mw.title.getCurrentTitle().text) 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.csExtension = function(frame) return h.getFile(frame).extension() end p.woExtension = function(frame) return h.getFile(frame).woExtension() end p.mime = function(frame) return h.getFile(frame).mime() 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 ok, metadata = pcall(h.getFile(frame).metadata) if ok then return metadata.exists or '' else return '' end 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(frame) or '' end p.width = function(frame) return h.getFile(frame).metadata().width end p.height = function(frame) return h.getFile(frame).metadata().height end p.dimensions = function(frame) local d = h.getFile(frame).metadata() return d.width .. ' × ' .. d.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 {1} return #pages end -- Module autotest 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()), extensionLower = (t.extensionLower == 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\t>>\t' .. t.fileName .. '\n\t>>\t' .. stringResult) or '') result = result and ret end return result end -- p.h = h -- if needed for running some tests return p