--- a/share/lua/playlist/youtube.lua 2011-08-06 11:30:49.000000000 +0200 +++ b/share/lua/playlist/youtube.lua 2012-02-02 16:05:32.000000000 +0100 @@ -1,7 +1,7 @@ --[[ $Id$ - Copyright © 2007-2009 the VideoLAN team + Copyright © 2007-2011 the VideoLAN team This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by @@ -24,13 +24,27 @@ return res end -function get_arturl( path, video_id ) - if string.match( vlc.path, "iurl=" ) then - return vlc.strings( get_url_param( vlc.path, "iurl" ) ) +function get_arturl() + local iurl = get_url_param( vlc.path, "iurl" ) + if iurl then + return iurl end - if not arturl then - return "http://img.youtube.com/vi/"..video_id.."/default.jpg" + local video_id = get_url_param( vlc.path, "v" ) + if not video_id then + return nil + end + return "http://img.youtube.com/vi/"..video_id.."/default.jpg" +end + +function get_prefres() + local prefres = -1 + if vlc.var and vlc.var.inherit then + prefres = vlc.var.inherit(nil, "preferred-resolution") + if prefres == nil then + prefres = -1 + end end + return prefres end -- Probe function. @@ -47,18 +61,17 @@ return false end end - return ( string.match( vlc.path, "watch%?v=" ) -- the html page - or string.match( vlc.path, "watch_fullscreen%?video_id=" ) -- the fullscreen page - or string.match( vlc.path, "p.swf" ) -- the (old?) player url - or string.match( vlc.path, "jp.swf" ) -- the (new?) player url (as of 24/08/2007) - or string.match( vlc.path, "player2.swf" ) ) -- another player url + return ( string.match( vlc.path, "/watch%?" ) -- the html page + or string.match( vlc.path, "/v/" ) -- video in swf player + or string.match( vlc.path, "/player2.swf" ) ) -- another player url end -- Parse function. function parse() - if string.match( vlc.path, "watch%?v=" ) + if string.match( vlc.path, "/watch%?" ) then -- This is the HTML page's URL - -- fmt is the format of the video: 18 is HQ (mp4) + -- fmt is the format of the video + -- (cf. http://en.wikipedia.org/wiki/YouTube#Quality_and_codecs) fmt = get_url_param( vlc.path, "fmt" ) while true do -- Try to find the video's title @@ -71,27 +84,42 @@ end if string.match( line, "= 0 then + fmt_list = string.match( line, "\"fmt_list\": \"(.-)\"" ) + if fmt_list then + for itag,height in string.gmatch( fmt_list, "(%d+)\\/%d+x(%d+)\\/[^,]+" ) do + -- Apparently formats are listed in quality + -- order, so we take the first one that works, + -- or fallback to the lowest quality + fmt = itag + if tonumber(height) <= prefres then + break + end + end + end + end end - _,_,t = string.find( line, "\"t\": \"(.-)\"" ) - -- vlc.msg.err( t ) - -- video_id = string.gsub( line, ".*&video_id:'([^']*)'.*", "%1" ) - fmt_url_map = string.match( line, "\"url_encoded_fmt_stream_map\": \"(.-)\"" ) - if fmt_url_map then + + url_map = string.match( line, "\"url_encoded_fmt_stream_map\": \"(.-)\"" ) + if url_map then -- FIXME: do this properly - fmt_url_map = string.gsub( fmt_url_map, "\\u0026", "&" ) - for url,itag in string.gmatch( fmt_url_map, "url=([^&,]+).-&itag=(%d+)" ) do + url_map = string.gsub( url_map, "\\u0026", "&" ) + for url,itag in string.gmatch( url_map, "url=([^&,]+)[^,]*&itag=(%d+)" ) do -- Apparently formats are listed in quality order, -- so we can afford to simply take the first one if not fmt or tonumber( itag ) == tonumber( fmt ) then @@ -101,75 +129,37 @@ end end end - -- Also available on non-HTML5 pages: var swfHTML = (isIE) ? " or + -- tag; but we don't need it now end end - if not video_id then - video_id = get_url_param( vlc.path, "v" ) + if not path then + vlc.msg.err( "Couldn't extract youtube video URL, please check for updates to this script" ) + return { } end - arturl = get_arturl( vlc.path, video_id ) - if not fmt then - -- Prefer WebM formats if this is an &html5=True URL - html5 = get_url_param( vlc.path, "html5" ) - if html5 == "True" and webm_path then - path = webm_path - end + if not arturl then + arturl = get_arturl() end - if not path then - if not base_yt_url then - base_yt_url = "http://youtube.com/" - end - if fmt then - format = "&fmt=" .. fmt - else - format = "" - end - - if t then - path = base_yt_url .. "get_video?video_id="..video_id.."&t="..t..format - else - -- This shouldn't happen ... but keep it as a backup. - path = "http://www.youtube.com/v/"..video_id - end - end return { { path = path; name = name; description = description; artist = artist; arturl = arturl } } else -- This is the flash player's URL - if string.match( vlc.path, "title=" ) then - name = vlc.strings.decode_uri(get_url_param( vlc.path, "title" )) - end video_id = get_url_param( vlc.path, "video_id" ) - arturl = get_arturl( vlc.path, video_id ) + if not video_id then + _,_,video_id = string.find( vlc.path, "/v/([^?]*)" ) + end + if not video_id then + vlc.msg.err( "Couldn't extract youtube video URL" ) + return { } + end fmt = get_url_param( vlc.path, "fmt" ) if fmt then format = "&fmt=" .. fmt else format = "" end - if not string.match( vlc.path, "t=" ) then - -- This sucks, we're missing "t" which is now mandatory. Let's - -- try using another url - return { { path = "http://www.youtube.com/v/"..video_id; name = name; arturl = arturl } } - end - return { { path = "http://www.youtube.com/get_video.php?video_id="..video_id.."&t="..get_url_param( vlc.path, "t" )..format; name = name; arturl = arturl } } + return { { path = "http://www.youtube.com/watch?v="..video_id..format } } end end