#
# This file is part of stov, written by Helmut Pozimski 2012-2014.
#
# stov is free software: you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation, version 2 of the License.
#
# stov is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with stov. If not, see .
# -*- coding: utf8 -*-
from __future__ import unicode_literals
import sys
import ssl
if sys.version_info >= (3,):
import urllib.request as urllib2
else:
import urllib2
from xml.dom.minidom import parseString
from lib_stov import stov_exceptions
class Parser(object):
def __init__(self, api_result):
self.__api_data = api_result
def parse(self):
"""Take the youtube API data and extract the important entries"""
dom = parseString(self.__api_data)
channel = YtChannel()
i = 0
for title in dom.getElementsByTagName('title'):
xmlTag = title.toxml()
if i == 0:
channel.title = xmlTag.replace('
', '')
channel.title = channel.title.replace('', '')
channel.title = channel.title.replace('&', '&')
channel.title = channel.title.replace('"', '"')
else:
video_title = xmlTag.replace('', '')
video_title = video_title.replace('', '')
video_title = video_title.replace('&', '&')
video_title = video_title.replace('"', '"')
try:
xmlTag = dom.getElementsByTagName('media:\
description')[i-1].toxml()
video_description = xmlTag.replace('',
'')
video_description = video_description.replace('', '')
except IndexError:
video_description = ""
video_id = dom.getElementsByTagName('yt:videoid')[i-1].toxml()
video_id = video_id.replace('', '').replace(
'', '')
channel.videos.append(YtVideo(video_title, video_description,
video_id))
i = i + 1
return channel
class YtChannel(object):
def __init__(self):
self.title = ""
self.videos = []
class YtVideo(object):
def __init__(self, title, description, ytid):
self.title = title
self.description = description
self.ytid = ytid
class Connector(object):
"""Handles all connections to the youtube API and invokes the parsing
functions.
"""
def __init__(self, type, name, search, conf):
"""Populates the object will all necessary variables."""
self._type = type
self._name = name
self._search = search
self._conf = conf
self._APIURL = self._ConstructAPIURL()
def ParseAPIData(self):
"""Retrieves the youtube API data and parses them so they can be used
by the object
"""
try:
ConnectAPI = urllib2.urlopen(self._APIURL, timeout=30)
APIResponse = ConnectAPI.read()
ConnectAPI.close()
except urllib2.HTTPError:
raise stov_exceptions.NoDataFromYoutubeAPIException()
except ssl.SSLError:
raise stov_exceptions.YoutubeAPITimeoutException(self._name)
else:
parser = Parser(APIResponse)
parsed_response = parser.parse()
return parsed_response
def _ConstructAPIURL(self):
"""Constructs the API URL which is used to retrieve API data"""
if self._type == "channel":
APIURL = "https://gdata.youtube.com/feeds/api/users/" \
+ urllib2.quote(self._name) + "/uploads/" \
"?v=2&max-results=%s" \
% self._conf.values["maxvideos"]
if self._search != "":
APIURL = APIURL + "&q=" + "%22" \
+ urllib2.quote(self._search) + "%22"
elif self._type == "search":
APIURL = "http://gdata.youtube.com/feeds/api/videos?q=" \
+ urllib2.quote(self._search) + "&v=2" \
+ "&max-results=%s" \
% self._conf.values["maxvideos"]
elif self._type == "playlist":
APIURL = "https://gdata.youtube.com/feeds/api/playlists/" \
+ "%20" + urllib2.quote(self._name) + "%20?v=2" \
+ "&max-results=%s" \
% self._conf.values["maxvideos"]
return APIURL