From 48d690f6178b1e289146d488a7e0c6bca270dd63 Mon Sep 17 00:00:00 2001 From: Toni Gundogdu Date: Mon, 30 May 2011 14:06:03 +0300 Subject: [PATCH] dailymotion.lua: Rewrite for quvi_query_formats --- share/lua/website/dailymotion.lua | 162 ++++++++++++++++++++++---------------- 1 file changed, 92 insertions(+), 70 deletions(-) diff --git a/share/lua/website/dailymotion.lua b/share/lua/website/dailymotion.lua index 1a959a7..97bced2 100644 --- a/share/lua/website/dailymotion.lua +++ b/share/lua/website/dailymotion.lua @@ -20,68 +20,85 @@ -- 02110-1301 USA -- +-- "http://dai.ly/cityofscars", +-- "http://www.dailymotion.com/video/xdpig1_city-of-scars_shortfilms", + +local Dailymotion = {} -- Utility functions unique to this script. + -- Identify the script. function ident(self) package.path = self.script_dir .. '/?.lua' local C = require 'quvi/const' local r = {} r.domain = "dailymotion." - -- - -- 'best' is determined by parsing the available formats, picking - -- the one with the highest height quality. 'default' to the lowest - -- quality. - -- - r.formats = "default|best|h264_480p" + r.formats = "default|best" r.categories = C.proto_http local U = require 'quvi/util' --- "http://dai.ly/cityofscars", --- "http://www.dailymotion.com/video/xdpig1_city-of-scars_shortfilms", - r.handles = - U.handles(self.page_url, {r.domain, "dai.ly"}, {"/video/","/%w+$"}) + r.handles = U.handles(self.page_url, {r.domain, "dai.ly"}, + {"/video/","/%w+$","/family_filter"}) return r end --- Parse video URL. -function parse(self) - self.host_id = "dailymotion" - self.page_url = normalize(self.page_url) +-- Query available formats. +function query_formats(self) + local U = require 'quvi/util' + local page = Dailymotion.fetch_page(self, U) + local formats = Dailymotion.iter_formats(page, U) - local U = require 'quvi/util' - - local _,_,s = self.page_url:find('/family_filter%?urlback=(.+)') - if s then -- Set family_filter arbitrary cookie below. - self.page_url = 'http://dailymotion.com' .. U.unescape(s) + local t = {} + for _,v in pairs(formats) do + table.insert(t, Dailymotion.to_s(v)) end - local opts = {arbitrary_cookie = 'family_filter=off'} - local page = quvi.fetch(self.page_url, opts) + table.sort(t) + self.formats = table.concat(t, "|") + + return self +end + +-- Parse media URL. +function parse(self) + self.host_id = "dailymotion" + + local U = require 'quvi/util' + local page = Dailymotion.fetch_page(self, U) local _,_,s = page:find('title="(.-)"') - self.title = s or error("no match: video title") + self.title = s or error("no match: media title") local _,_,s = page:find("video/(.-)_") - self.id = s or error("no match: video id") + self.id = s or error("no match: media id") local _,_,s = page:find('"og:image" content="(.-)"') self.thumbnail_url = s or '' - local found = iter_media(page, U) - local r_fmt = self.requested_format + local formats = Dailymotion.iter_formats(page, U) + self.url = {U.choose_format(self, formats, + Dailymotion.choose_best, + Dailymotion.choose_default, + Dailymotion.to_s).url + or error("no match: media url")} - local url = (r_fmt == 'default' or not found[r_fmt]) - and choose_default(found).url - or found[r_fmt].url + return self +end - url = (r_fmt == 'best') - and choose_best(found).url - or url +-- +-- Utility functions +-- - self.url = {url or error('no match: media url')} +function Dailymotion.fetch_page(self, U) + self.page_url = Dailymotion.normalize(self.page_url) - return self + local _,_,s = self.page_url:find('/family_filter%?urlback=(.+)') + if s then + self.page_url = 'http://dailymotion.com' .. U.unescape(s) + end + + local opts = {arbitrary_cookie = 'family_filter=off'} + return quvi.fetch(self.page_url, opts) end -function normalize(page_url) -- embedded URL to "regular". +function Dailymotion.normalize(page_url) -- "Normalize" embedded URLs if page_url:find("/swf/") then page_url = page_url:gsub("/video/", "/") page_url = page_url:gsub("/swf/", "/video/") @@ -89,7 +106,7 @@ function normalize(page_url) -- embedded URL to "regular". return page_url end -function iter_media(page, U) +function Dailymotion.iter_formats(page, U) local _,_,seq = page:find('"sequence",%s+"(.-)"') if not seq then local e = "no match: sequence" @@ -100,64 +117,69 @@ function iter_media(page, U) end seq = U.unescape(seq) - local _,_,msg = seq:find('"message":"(.-)"') + local _,_,msg = seq:find('"message":"(.-)[<"]') if msg then msg = msg:gsub('+',' ') - error(msg) + error(msg:gsub('\\','')) end local _,_,vpp = seq:find('"videoPluginParameters":{(.-)}') if not vpp then - local _,_,s = page:find('"video", "(.-)"') - if not s then - error("no match: video plugin params") - else - -- some videos (that require setting family_filter cookie) - -- may list only one link which is not found under - -- "videoPluginParameters". See also: - -- http://sourceforge.net/apps/trac/clive/ticket/4 - return {s} - end + -- See also + error("no match: video plugin params") end local t = {} - for id,url in vpp:gfind('(%w+)URL":"(.-)"') do + for url in vpp:gfind('%w+URL":"(.-)"') do url = url:gsub("\\/", "/") - local _,_,c,w,h = url:find('(%w+)%-(%d+)x(%d+)') - if not c or not w or not h then - error('no match: container, width, height') + local _,_,c,w,h,cn = url:find('(%w+)%-(%d+)x(%d+).-%.(%w+)') + if not c then + error('no match: codec, width, height, container') end - c = string.lower(c) --- print(c,w,h) - local id = c .. '_' .. h .. 'p' - t[id] = {width=tonumber(w), height=tonumber(h), url=url} +-- print(c,w,h,cn) + table.insert(t, {width=tonumber(w), height=tonumber(h), + container=cn, codec=string.lower(c), + url=url}) end + return t end -function choose_default(t) - -- Go with the lowest resolution. - local r = {width=0xffff, height=0xffff, url=nil} - for k,v in pairs(t) do - if v.height < r.height then - r.width = v.width - r.height = v.height - r.url = v.url +function Dailymotion.copy(a,b) + a.container = b.container + a.codec = b.codec + a.width = b.width + a.height = b.height + a.url = b.url +end + +function Dailymotion.choose_default(formats) -- Lowest quality available + local r = {width=0xffff, height=0xffff, + url=nil, container=nil, codec=nil} + local U = require 'quvi/util' + for _,v in pairs(formats) do + if U.is_lower_quality(v,r) then + Dailymotion.copy(r,v) end end +-- for k,v in pairs(r) do print(k,v) end return r end -function choose_best(t) - local r = {width=0, height=0, url=nil} - for k,v in pairs(t) do - if v.height > r.height then - r.width = v.width - r.height = v.height - r.url = v.url +function Dailymotion.choose_best(formats) -- Highest quality available + local r = {width=0, height=0, url=nil, container=nil, codec=nil} + local U = require 'quvi/util' + for _,v in pairs(formats) do + if U.is_higher_quality(v,r) then + Dailymotion.copy(r,v) end end +-- for k,v in pairs(r) do print(k,v) end return r end +function Dailymotion.to_s(t) + return string.format("%s_%sp", t.container, t.height) +end + -- vim: set ts=4 sw=4 tw=72 expandtab: -- 2.11.4.GIT