Merge branch 'tv' of https://github.com/RuudBurger/CouchPotatoServer into tv_database
This commit is contained in:
commit
72ce919989
17 files changed
+162
-107
No files matched your search
@@ -11,7 +11,7 @@ log = CPLog(__name__)
|
|||||||
|
|
||||||
class Downloader(Provider):
|
class Downloader(Provider):
|
||||||
|
|
||||||
type = []
|
protocol = []
|
||||||
http_time_between_calls = 0
|
http_time_between_calls = 0
|
||||||
|
|
||||||
torrent_sources = [
|
torrent_sources = [
|
||||||
@@ -36,16 +36,16 @@ class Downloader(Provider):
|
|||||||
def __init__(self):
|
def __init__(self):
|
||||||
addEvent('download', self._download)
|
addEvent('download', self._download)
|
||||||
addEvent('download.enabled', self._isEnabled)
|
addEvent('download.enabled', self._isEnabled)
|
||||||
addEvent('download.enabled_types', self.getEnabledDownloadType)
|
addEvent('download.enabled_protocols', self.getEnabledProtocol)
|
||||||
addEvent('download.status', self._getAllDownloadStatus)
|
addEvent('download.status', self._getAllDownloadStatus)
|
||||||
addEvent('download.remove_failed', self._removeFailed)
|
addEvent('download.remove_failed', self._removeFailed)
|
||||||
addEvent('download.pause', self._pause)
|
addEvent('download.pause', self._pause)
|
||||||
addEvent('download.process_complete', self._processComplete)
|
addEvent('download.process_complete', self._processComplete)
|
||||||
|
|
||||||
def getEnabledDownloadType(self):
|
def getEnabledProtocol(self):
|
||||||
for download_type in self.type:
|
for download_protocol in self.protocol:
|
||||||
if self.isEnabled(manual = True, data = {'type': download_type}):
|
if self.isEnabled(manual = True, data = {'protocol': download_protocol}):
|
||||||
return self.type
|
return self.protocol
|
||||||
|
|
||||||
return []
|
return []
|
||||||
|
|
||||||
@@ -91,11 +91,11 @@ class Downloader(Provider):
|
|||||||
def processComplete(self, item, delete_files):
|
def processComplete(self, item, delete_files):
|
||||||
return
|
return
|
||||||
|
|
||||||
def isCorrectType(self, item_type):
|
def isCorrectProtocol(self, item_protocol):
|
||||||
is_correct = item_type in self.type
|
is_correct = item_protocol in self.protocol
|
||||||
|
|
||||||
if not is_correct:
|
if not is_correct:
|
||||||
log.debug("Downloader doesn't support this type")
|
log.debug("Downloader doesn't support this protocol")
|
||||||
|
|
||||||
return is_correct
|
return is_correct
|
||||||
|
|
||||||
@@ -140,7 +140,7 @@ class Downloader(Provider):
|
|||||||
d_manual = self.conf('manual', default = False)
|
d_manual = self.conf('manual', default = False)
|
||||||
return super(Downloader, self).isEnabled() and \
|
return super(Downloader, self).isEnabled() and \
|
||||||
((d_manual and manual) or (d_manual is False)) and \
|
((d_manual and manual) or (d_manual is False)) and \
|
||||||
(not data or self.isCorrectType(data.get('type')))
|
(not data or self.isCorrectProtocol(data.get('protocol')))
|
||||||
|
|
||||||
def _pause(self, item, pause = True):
|
def _pause(self, item, pause = True):
|
||||||
if self.isDisabled(manual = True, data = {}):
|
if self.isDisabled(manual = True, data = {}):
|
||||||
|
|||||||
@@ -10,20 +10,20 @@ log = CPLog(__name__)
|
|||||||
|
|
||||||
class Blackhole(Downloader):
|
class Blackhole(Downloader):
|
||||||
|
|
||||||
type = ['nzb', 'torrent', 'torrent_magnet']
|
protocol = ['nzb', 'torrent', 'torrent_magnet']
|
||||||
|
|
||||||
def download(self, data = {}, movie = {}, filedata = None):
|
def download(self, data = {}, movie = {}, filedata = None):
|
||||||
|
|
||||||
directory = self.conf('directory')
|
directory = self.conf('directory')
|
||||||
if not directory or not os.path.isdir(directory):
|
if not directory or not os.path.isdir(directory):
|
||||||
log.error('No directory set for blackhole %s download.', data.get('type'))
|
log.error('No directory set for blackhole %s download.', data.get('protocol'))
|
||||||
else:
|
else:
|
||||||
try:
|
try:
|
||||||
if not filedata or len(filedata) < 50:
|
if not filedata or len(filedata) < 50:
|
||||||
try:
|
try:
|
||||||
if data.get('type') == 'torrent_magnet':
|
if data.get('protocol') == 'torrent_magnet':
|
||||||
filedata = self.magnetToTorrent(data.get('url'))
|
filedata = self.magnetToTorrent(data.get('url'))
|
||||||
data['type'] = 'torrent'
|
data['protocol'] = 'torrent'
|
||||||
except:
|
except:
|
||||||
log.error('Failed download torrent via magnet url: %s', traceback.format_exc())
|
log.error('Failed download torrent via magnet url: %s', traceback.format_exc())
|
||||||
|
|
||||||
@@ -35,7 +35,7 @@ class Blackhole(Downloader):
|
|||||||
|
|
||||||
try:
|
try:
|
||||||
if not os.path.isfile(fullPath):
|
if not os.path.isfile(fullPath):
|
||||||
log.info('Downloading %s to %s.', (data.get('type'), fullPath))
|
log.info('Downloading %s to %s.', (data.get('protocol'), fullPath))
|
||||||
with open(fullPath, 'wb') as f:
|
with open(fullPath, 'wb') as f:
|
||||||
f.write(filedata)
|
f.write(filedata)
|
||||||
os.chmod(fullPath, Env.getPermission('file'))
|
os.chmod(fullPath, Env.getPermission('file'))
|
||||||
@@ -54,20 +54,20 @@ class Blackhole(Downloader):
|
|||||||
|
|
||||||
return False
|
return False
|
||||||
|
|
||||||
def getEnabledDownloadType(self):
|
def getEnabledProtocol(self):
|
||||||
if self.conf('use_for') == 'both':
|
if self.conf('use_for') == 'both':
|
||||||
return super(Blackhole, self).getEnabledDownloadType()
|
return super(Blackhole, self).getEnabledProtocol()
|
||||||
elif self.conf('use_for') == 'torrent':
|
elif self.conf('use_for') == 'torrent':
|
||||||
return ['torrent', 'torrent_magnet']
|
return ['torrent', 'torrent_magnet']
|
||||||
else:
|
else:
|
||||||
return ['nzb']
|
return ['nzb']
|
||||||
|
|
||||||
def isEnabled(self, manual, data = {}):
|
def isEnabled(self, manual, data = {}):
|
||||||
for_type = ['both']
|
for_protocol = ['both']
|
||||||
if data and 'torrent' in data.get('type'):
|
if data and 'torrent' in data.get('protocol'):
|
||||||
for_type.append('torrent')
|
for_protocol.append('torrent')
|
||||||
elif data:
|
elif data:
|
||||||
for_type.append(data.get('type'))
|
for_protocol.append(data.get('protocol'))
|
||||||
|
|
||||||
return super(Blackhole, self).isEnabled(manual, data) and \
|
return super(Blackhole, self).isEnabled(manual, data) and \
|
||||||
((self.conf('use_for') in for_type))
|
((self.conf('use_for') in for_protocol))
|
||||||
@@ -15,7 +15,7 @@ log = CPLog(__name__)
|
|||||||
|
|
||||||
class NZBGet(Downloader):
|
class NZBGet(Downloader):
|
||||||
|
|
||||||
type = ['nzb']
|
protocol = ['nzb']
|
||||||
|
|
||||||
url = 'http://%(username)s:%(password)s@%(host)s/xmlrpc'
|
url = 'http://%(username)s:%(password)s@%(host)s/xmlrpc'
|
||||||
|
|
||||||
|
|||||||
@@ -19,7 +19,7 @@ log = CPLog(__name__)
|
|||||||
|
|
||||||
class NZBVortex(Downloader):
|
class NZBVortex(Downloader):
|
||||||
|
|
||||||
type = ['nzb']
|
protocol = ['nzb']
|
||||||
api_level = None
|
api_level = None
|
||||||
session_id = None
|
session_id = None
|
||||||
|
|
||||||
|
|||||||
@@ -9,7 +9,7 @@ log = CPLog(__name__)
|
|||||||
|
|
||||||
class Pneumatic(Downloader):
|
class Pneumatic(Downloader):
|
||||||
|
|
||||||
type = ['nzb']
|
protocol = ['nzb']
|
||||||
strm_syntax = 'plugin://plugin.program.pneumatic/?mode=strm&type=add_file&nzb=%s&nzbname=%s'
|
strm_syntax = 'plugin://plugin.program.pneumatic/?mode=strm&type=add_file&nzb=%s&nzbname=%s'
|
||||||
|
|
||||||
def download(self, data = {}, movie = {}, filedata = None):
|
def download(self, data = {}, movie = {}, filedata = None):
|
||||||
@@ -27,7 +27,7 @@ class Pneumatic(Downloader):
|
|||||||
|
|
||||||
try:
|
try:
|
||||||
if not os.path.isfile(fullPath):
|
if not os.path.isfile(fullPath):
|
||||||
log.info('Downloading %s to %s.', (data.get('type'), fullPath))
|
log.info('Downloading %s to %s.', (data.get('protocol'), fullPath))
|
||||||
with open(fullPath, 'wb') as f:
|
with open(fullPath, 'wb') as f:
|
||||||
f.write(filedata)
|
f.write(filedata)
|
||||||
|
|
||||||
|
|||||||
@@ -13,7 +13,7 @@ log = CPLog(__name__)
|
|||||||
|
|
||||||
class Sabnzbd(Downloader):
|
class Sabnzbd(Downloader):
|
||||||
|
|
||||||
type = ['nzb']
|
protocol = ['nzb']
|
||||||
|
|
||||||
def download(self, data = {}, movie = {}, filedata = None):
|
def download(self, data = {}, movie = {}, filedata = None):
|
||||||
|
|
||||||
|
|||||||
@@ -9,13 +9,13 @@ log = CPLog(__name__)
|
|||||||
|
|
||||||
class Synology(Downloader):
|
class Synology(Downloader):
|
||||||
|
|
||||||
type = ['nzb', 'torrent', 'torrent_magnet']
|
protocol = ['nzb', 'torrent', 'torrent_magnet']
|
||||||
log = CPLog(__name__)
|
log = CPLog(__name__)
|
||||||
|
|
||||||
def download(self, data, movie, filedata = None):
|
def download(self, data, movie, filedata = None):
|
||||||
|
|
||||||
response = False
|
response = False
|
||||||
log.error('Sending "%s" (%s) to Synology.', (data['name'], data['type']))
|
log.error('Sending "%s" (%s) to Synology.', (data['name'], data['protocol']))
|
||||||
|
|
||||||
# Load host from config and split out port.
|
# Load host from config and split out port.
|
||||||
host = self.conf('host').split(':')
|
host = self.conf('host').split(':')
|
||||||
@@ -26,38 +26,38 @@ class Synology(Downloader):
|
|||||||
try:
|
try:
|
||||||
# Send request to Synology
|
# Send request to Synology
|
||||||
srpc = SynologyRPC(host[0], host[1], self.conf('username'), self.conf('password'))
|
srpc = SynologyRPC(host[0], host[1], self.conf('username'), self.conf('password'))
|
||||||
if data['type'] == 'torrent_magnet':
|
if data['protocol'] == 'torrent_magnet':
|
||||||
log.info('Adding torrent URL %s', data['url'])
|
log.info('Adding torrent URL %s', data['url'])
|
||||||
response = srpc.create_task(url = data['url'])
|
response = srpc.create_task(url = data['url'])
|
||||||
elif data['type'] in ['nzb', 'torrent']:
|
elif data['protocol'] in ['nzb', 'torrent']:
|
||||||
log.info('Adding %s' % data['type'])
|
log.info('Adding %s' % data['protocol'])
|
||||||
if not filedata:
|
if not filedata:
|
||||||
log.error('No %s data found' % data['type'])
|
log.error('No %s data found' % data['protocol'])
|
||||||
else:
|
else:
|
||||||
filename = data['name'] + '.' + data['type']
|
filename = data['name'] + '.' + data['protocol']
|
||||||
response = srpc.create_task(filename = filename, filedata = filedata)
|
response = srpc.create_task(filename = filename, filedata = filedata)
|
||||||
except Exception, err:
|
except Exception, err:
|
||||||
log.error('Exception while adding torrent: %s', err)
|
log.error('Exception while adding torrent: %s', err)
|
||||||
finally:
|
finally:
|
||||||
return response
|
return response
|
||||||
|
|
||||||
def getEnabledDownloadType(self):
|
def getEnabledProtocol(self):
|
||||||
if self.conf('use_for') == 'both':
|
if self.conf('use_for') == 'both':
|
||||||
return super(Synology, self).getEnabledDownloadType()
|
return super(Synology, self).getEnabledProtocol()
|
||||||
elif self.conf('use_for') == 'torrent':
|
elif self.conf('use_for') == 'torrent':
|
||||||
return ['torrent', 'torrent_magnet']
|
return ['torrent', 'torrent_magnet']
|
||||||
else:
|
else:
|
||||||
return ['nzb']
|
return ['nzb']
|
||||||
|
|
||||||
def isEnabled(self, manual, data = {}):
|
def isEnabled(self, manual, data = {}):
|
||||||
for_type = ['both']
|
for_protocol = ['both']
|
||||||
if data and 'torrent' in data.get('type'):
|
if data and 'torrent' in data.get('protocol'):
|
||||||
for_type.append('torrent')
|
for_protocol.append('torrent')
|
||||||
elif data:
|
elif data:
|
||||||
for_type.append(data.get('type'))
|
for_protocol.append(data.get('protocol'))
|
||||||
|
|
||||||
return super(Synology, self).isEnabled(manual, data) and\
|
return super(Synology, self).isEnabled(manual, data) and\
|
||||||
((self.conf('use_for') in for_type))
|
((self.conf('use_for') in for_protocol))
|
||||||
|
|
||||||
class SynologyRPC(object):
|
class SynologyRPC(object):
|
||||||
|
|
||||||
|
|||||||
@@ -16,7 +16,7 @@ log = CPLog(__name__)
|
|||||||
|
|
||||||
class Transmission(Downloader):
|
class Transmission(Downloader):
|
||||||
|
|
||||||
type = ['torrent', 'torrent_magnet']
|
protocol = ['torrent', 'torrent_magnet']
|
||||||
log = CPLog(__name__)
|
log = CPLog(__name__)
|
||||||
trpc = None
|
trpc = None
|
||||||
|
|
||||||
@@ -34,12 +34,12 @@ class Transmission(Downloader):
|
|||||||
|
|
||||||
def download(self, data, movie, filedata = None):
|
def download(self, data, movie, filedata = None):
|
||||||
|
|
||||||
log.info('Sending "%s" (%s) to Transmission.', (data.get('name'), data.get('type')))
|
log.info('Sending "%s" (%s) to Transmission.', (data.get('name'), data.get('protocol')))
|
||||||
|
|
||||||
if not self.connect():
|
if not self.connect():
|
||||||
return False
|
return False
|
||||||
|
|
||||||
if not filedata and data.get('type') == 'torrent':
|
if not filedata and data.get('protocol') == 'torrent':
|
||||||
log.error('Failed sending torrent, no data')
|
log.error('Failed sending torrent, no data')
|
||||||
return False
|
return False
|
||||||
|
|
||||||
@@ -64,7 +64,7 @@ class Transmission(Downloader):
|
|||||||
torrent_params['seedIdleMode'] = 1
|
torrent_params['seedIdleMode'] = 1
|
||||||
|
|
||||||
# Send request to Transmission
|
# Send request to Transmission
|
||||||
if data.get('type') == 'torrent_magnet':
|
if data.get('protocol') == 'torrent_magnet':
|
||||||
remote_torrent = self.trpc.add_torrent_uri(data.get('url'), arguments = params)
|
remote_torrent = self.trpc.add_torrent_uri(data.get('url'), arguments = params)
|
||||||
torrent_params['trackerAdd'] = self.torrent_trackers
|
torrent_params['trackerAdd'] = self.torrent_trackers
|
||||||
else:
|
else:
|
||||||
|
|||||||
@@ -20,7 +20,7 @@ log = CPLog(__name__)
|
|||||||
|
|
||||||
class uTorrent(Downloader):
|
class uTorrent(Downloader):
|
||||||
|
|
||||||
type = ['torrent', 'torrent_magnet']
|
protocol = ['torrent', 'torrent_magnet']
|
||||||
utorrent_api = None
|
utorrent_api = None
|
||||||
|
|
||||||
def connect(self):
|
def connect(self):
|
||||||
@@ -36,7 +36,7 @@ class uTorrent(Downloader):
|
|||||||
|
|
||||||
def download(self, data, movie, filedata = None):
|
def download(self, data, movie, filedata = None):
|
||||||
|
|
||||||
log.debug('Sending "%s" (%s) to uTorrent.', (data.get('name'), data.get('type')))
|
log.debug('Sending "%s" (%s) to uTorrent.', (data.get('name'), data.get('protocol')))
|
||||||
|
|
||||||
if not self.connect():
|
if not self.connect():
|
||||||
return False
|
return False
|
||||||
@@ -63,11 +63,11 @@ class uTorrent(Downloader):
|
|||||||
if self.conf('label'):
|
if self.conf('label'):
|
||||||
torrent_params['label'] = self.conf('label')
|
torrent_params['label'] = self.conf('label')
|
||||||
|
|
||||||
if not filedata and data.get('type') == 'torrent':
|
if not filedata and data.get('protocol') == 'torrent':
|
||||||
log.error('Failed sending torrent, no data')
|
log.error('Failed sending torrent, no data')
|
||||||
return False
|
return False
|
||||||
|
|
||||||
if data.get('type') == 'torrent_magnet':
|
if data.get('protocol') == 'torrent_magnet':
|
||||||
torrent_hash = re.findall('urn:btih:([\w]{32,40})', data.get('url'))[0].upper()
|
torrent_hash = re.findall('urn:btih:([\w]{32,40})', data.get('url'))[0].upper()
|
||||||
torrent_params['trackers'] = '%0D%0A%0D%0A'.join(self.torrent_trackers)
|
torrent_params['trackers'] = '%0D%0A%0D%0A'.join(self.torrent_trackers)
|
||||||
else:
|
else:
|
||||||
@@ -88,7 +88,7 @@ class uTorrent(Downloader):
|
|||||||
torrent_hash = b16encode(b32decode(torrent_hash))
|
torrent_hash = b16encode(b32decode(torrent_hash))
|
||||||
|
|
||||||
# Send request to uTorrent
|
# Send request to uTorrent
|
||||||
if data.get('type') == 'torrent_magnet':
|
if data.get('protocol') == 'torrent_magnet':
|
||||||
self.utorrent_api.add_torrent_uri(data.get('url'))
|
self.utorrent_api.add_torrent_uri(data.get('url'))
|
||||||
else:
|
else:
|
||||||
self.utorrent_api.add_torrent_file(torrent_filename, filedata)
|
self.utorrent_api.add_torrent_file(torrent_filename, filedata)
|
||||||
|
|||||||
@@ -116,12 +116,7 @@ class Loader(object):
|
|||||||
|
|
||||||
def loadPlugins(self, module, name):
|
def loadPlugins(self, module, name):
|
||||||
try:
|
try:
|
||||||
klass = module.start()
|
module.start()
|
||||||
klass.registerPlugin()
|
|
||||||
|
|
||||||
if klass and getattr(klass, 'auto_register_static'):
|
|
||||||
klass.registerStatic(module.__file__)
|
|
||||||
|
|
||||||
return True
|
return True
|
||||||
except Exception, e:
|
except Exception, e:
|
||||||
log.error('Failed loading plugin "%s": %s', (module.__file__, traceback.format_exc()))
|
log.error('Failed loading plugin "%s": %s', (module.__file__, traceback.format_exc()))
|
||||||
|
|||||||
@@ -19,7 +19,7 @@ log = CPLog(__name__)
|
|||||||
class Searcher(SearcherBase):
|
class Searcher(SearcherBase):
|
||||||
|
|
||||||
def __init__(self):
|
def __init__(self):
|
||||||
addEvent('searcher.get_types', self.getSearchTypes)
|
addEvent('searcher.protocols', self.getSearchProtocols)
|
||||||
addEvent('searcher.contains_other_quality', self.containsOtherQuality)
|
addEvent('searcher.contains_other_quality', self.containsOtherQuality)
|
||||||
addEvent('searcher.correct_year', self.correctYear)
|
addEvent('searcher.correct_year', self.correctYear)
|
||||||
addEvent('searcher.correct_name', self.correctName)
|
addEvent('searcher.correct_name', self.correctName)
|
||||||
@@ -122,29 +122,29 @@ class Searcher(SearcherBase):
|
|||||||
|
|
||||||
return True
|
return True
|
||||||
|
|
||||||
log.info('Tried to download, but none of the "%s" downloaders are enabled or gave an error', (data.get('type', '')))
|
log.info('Tried to download, but none of the "%s" downloaders are enabled or gave an error', (data.get('protocol', '')))
|
||||||
|
|
||||||
return False
|
return False
|
||||||
|
|
||||||
def getSearchTypes(self):
|
def getSearchProtocols(self):
|
||||||
|
|
||||||
download_types = fireEvent('download.enabled_types', merge = True)
|
download_protocols = fireEvent('download.enabled_protocols', merge = True)
|
||||||
provider_types = fireEvent('provider.enabled_types', merge = True)
|
provider_protocols = fireEvent('provider.enabled_protocols', merge = True)
|
||||||
|
|
||||||
if download_types and len(list(set(provider_types) & set(download_types))) == 0:
|
if download_protocols and len(list(set(provider_protocols) & set(download_protocols))) == 0:
|
||||||
log.error('There aren\'t any providers enabled for your downloader (%s). Check your settings.', ','.join(download_types))
|
log.error('There aren\'t any providers enabled for your downloader (%s). Check your settings.', ','.join(download_protocols))
|
||||||
return []
|
return []
|
||||||
|
|
||||||
for useless_provider in list(set(provider_types) - set(download_types)):
|
for useless_provider in list(set(provider_protocols) - set(download_protocols)):
|
||||||
log.debug('Provider for "%s" enabled, but no downloader.', useless_provider)
|
log.debug('Provider for "%s" enabled, but no downloader.', useless_provider)
|
||||||
|
|
||||||
search_types = download_types
|
search_protocols = download_protocols
|
||||||
|
|
||||||
if len(search_types) == 0:
|
if len(search_protocols) == 0:
|
||||||
log.error('There aren\'t any downloaders enabled. Please pick one in settings.')
|
log.error('There aren\'t any downloaders enabled. Please pick one in settings.')
|
||||||
return []
|
return []
|
||||||
|
|
||||||
return search_types
|
return search_protocols
|
||||||
|
|
||||||
def containsOtherQuality(self, nzb, movie_year = None, preferred_quality = {}):
|
def containsOtherQuality(self, nzb, movie_year = None, preferred_quality = {}):
|
||||||
|
|
||||||
|
|||||||
@@ -85,7 +85,7 @@ class MovieSearcher(SearcherBase, MovieTypeBase):
|
|||||||
}
|
}
|
||||||
|
|
||||||
try:
|
try:
|
||||||
search_types = fireEvent('searcher.get_types', single = True)
|
search_protocols = fireEvent('searcher.protocols', single = True)
|
||||||
|
|
||||||
for movie in movies:
|
for movie in movies:
|
||||||
movie_dict = movie.to_dict({
|
movie_dict = movie.to_dict({
|
||||||
@@ -97,7 +97,7 @@ class MovieSearcher(SearcherBase, MovieTypeBase):
|
|||||||
})
|
})
|
||||||
|
|
||||||
try:
|
try:
|
||||||
self.single(movie_dict, search_types)
|
self.single(movie_dict, search_protocols)
|
||||||
except IndexError:
|
except IndexError:
|
||||||
log.error('Forcing library update for %s, if you see this often, please report: %s', (movie_dict['library']['identifier'], traceback.format_exc()))
|
log.error('Forcing library update for %s, if you see this often, please report: %s', (movie_dict['library']['identifier'], traceback.format_exc()))
|
||||||
fireEvent('library.update.movie', movie_dict['library']['identifier'], force = True)
|
fireEvent('library.update.movie', movie_dict['library']['identifier'], force = True)
|
||||||
@@ -115,12 +115,12 @@ class MovieSearcher(SearcherBase, MovieTypeBase):
|
|||||||
|
|
||||||
self.in_progress = False
|
self.in_progress = False
|
||||||
|
|
||||||
def single(self, movie, search_types = None):
|
def single(self, movie, search_protocols = None):
|
||||||
|
|
||||||
# Find out search type
|
# Find out search type
|
||||||
try:
|
try:
|
||||||
if not search_types:
|
if not search_protocols:
|
||||||
search_types = fireEvent('searcher.get_types', single = True)
|
search_protocols = fireEvent('searcher.protocols', single = True)
|
||||||
except SearchSetupError:
|
except SearchSetupError:
|
||||||
return
|
return
|
||||||
|
|
||||||
@@ -168,10 +168,10 @@ class MovieSearcher(SearcherBase, MovieTypeBase):
|
|||||||
quality = fireEvent('quality.single', identifier = quality_type['quality']['identifier'], single = True)
|
quality = fireEvent('quality.single', identifier = quality_type['quality']['identifier'], single = True)
|
||||||
|
|
||||||
results = []
|
results = []
|
||||||
for search_type in search_types:
|
for search_protocol in search_protocols:
|
||||||
type_results = fireEvent('%s.search' % search_type, movie, quality, merge = True)
|
protocol_results = fireEvent('provider.search.%s.movie' % search_protocol, movie, quality, merge = True)
|
||||||
if type_results:
|
if protocol_results:
|
||||||
results += type_results
|
results += protocol_results
|
||||||
|
|
||||||
sorted_results = sorted(results, key = lambda k: k['score'], reverse = True)
|
sorted_results = sorted(results, key = lambda k: k['score'], reverse = True)
|
||||||
if len(sorted_results) == 0:
|
if len(sorted_results) == 0:
|
||||||
|
|||||||
@@ -12,6 +12,7 @@ from urlparse import urlparse
|
|||||||
import cookielib
|
import cookielib
|
||||||
import glob
|
import glob
|
||||||
import gzip
|
import gzip
|
||||||
|
import inspect
|
||||||
import math
|
import math
|
||||||
import os.path
|
import os.path
|
||||||
import re
|
import re
|
||||||
@@ -24,6 +25,8 @@ log = CPLog(__name__)
|
|||||||
|
|
||||||
class Plugin(object):
|
class Plugin(object):
|
||||||
|
|
||||||
|
_class_name = None
|
||||||
|
|
||||||
enabled_option = 'enabled'
|
enabled_option = 'enabled'
|
||||||
auto_register_static = True
|
auto_register_static = True
|
||||||
|
|
||||||
@@ -35,16 +38,29 @@ class Plugin(object):
|
|||||||
http_failed_request = {}
|
http_failed_request = {}
|
||||||
http_failed_disabled = {}
|
http_failed_disabled = {}
|
||||||
|
|
||||||
|
def __new__(typ, *args, **kwargs):
|
||||||
|
new_plugin = super(Plugin, typ).__new__(typ, *args, **kwargs)
|
||||||
|
new_plugin.registerPlugin()
|
||||||
|
|
||||||
|
return new_plugin
|
||||||
|
|
||||||
def registerPlugin(self):
|
def registerPlugin(self):
|
||||||
addEvent('app.do_shutdown', self.doShutdown)
|
addEvent('app.do_shutdown', self.doShutdown)
|
||||||
addEvent('plugin.running', self.isRunning)
|
addEvent('plugin.running', self.isRunning)
|
||||||
self._running = []
|
self._running = []
|
||||||
|
|
||||||
|
if self.auto_register_static:
|
||||||
|
self.registerStatic(inspect.getfile(self.__class__))
|
||||||
|
|
||||||
def conf(self, attr, value = None, default = None, section = None):
|
def conf(self, attr, value = None, default = None, section = None):
|
||||||
return Env.setting(attr, section = section if section else self.getName().lower(), value = value, default = default)
|
class_name = self.getName().lower().split(':')
|
||||||
|
return Env.setting(attr, section = section if section else class_name[0].lower(), value = value, default = default)
|
||||||
|
|
||||||
def getName(self):
|
def getName(self):
|
||||||
return self.__class__.__name__
|
return self._class_name or self.__class__.__name__
|
||||||
|
|
||||||
|
def setName(self, name):
|
||||||
|
self._class_name = name
|
||||||
|
|
||||||
def renderTemplate(self, parent_file, templ, **params):
|
def renderTemplate(self, parent_file, templ, **params):
|
||||||
|
|
||||||
|
|||||||
@@ -13,13 +13,32 @@ import traceback
|
|||||||
import urllib2
|
import urllib2
|
||||||
import xml.etree.ElementTree as XMLTree
|
import xml.etree.ElementTree as XMLTree
|
||||||
|
|
||||||
|
|
||||||
log = CPLog(__name__)
|
log = CPLog(__name__)
|
||||||
|
|
||||||
|
|
||||||
|
class MultiProvider(Plugin):
|
||||||
|
|
||||||
|
def __init__(self):
|
||||||
|
self._classes = []
|
||||||
|
|
||||||
|
for Type in self.getTypes():
|
||||||
|
klass = Type()
|
||||||
|
|
||||||
|
# Overwrite name so logger knows what we're talking about
|
||||||
|
klass.setName('%s:%s' % (self.getName(), klass.getName()))
|
||||||
|
|
||||||
|
self._classes.append(klass)
|
||||||
|
|
||||||
|
def getTypes(self):
|
||||||
|
return []
|
||||||
|
|
||||||
|
def getClasses(self):
|
||||||
|
return self._classes
|
||||||
|
|
||||||
|
|
||||||
class Provider(Plugin):
|
class Provider(Plugin):
|
||||||
|
|
||||||
type = None # movie, nzb, torrent, subtitle, trailer
|
type = None # movie, show, subtitle, trailer, ...
|
||||||
http_time_between_calls = 10 # Default timeout for url requests
|
http_time_between_calls = 10 # Default timeout for url requests
|
||||||
|
|
||||||
last_available_check = {}
|
last_available_check = {}
|
||||||
@@ -79,7 +98,11 @@ class Provider(Plugin):
|
|||||||
|
|
||||||
class YarrProvider(Provider):
|
class YarrProvider(Provider):
|
||||||
|
|
||||||
cat_ids = []
|
protocol = None # nzb, torrent, torrent_magnet
|
||||||
|
type = 'movie'
|
||||||
|
|
||||||
|
cat_ids = {}
|
||||||
|
cat_backup_id = None
|
||||||
|
|
||||||
sizeGb = ['gb', 'gib']
|
sizeGb = ['gb', 'gib']
|
||||||
sizeMb = ['mb', 'mib']
|
sizeMb = ['mb', 'mib']
|
||||||
@@ -89,14 +112,13 @@ class YarrProvider(Provider):
|
|||||||
last_login_check = 0
|
last_login_check = 0
|
||||||
|
|
||||||
def __init__(self):
|
def __init__(self):
|
||||||
addEvent('provider.enabled_types', self.getEnabledProviderType)
|
addEvent('provider.enabled_protocols', self.getEnabledProtocol)
|
||||||
addEvent('provider.belongs_to', self.belongsTo)
|
addEvent('provider.belongs_to', self.belongsTo)
|
||||||
addEvent('yarr.search', self.search)
|
addEvent('provider.search.%s.%s' % (self.protocol, self.type), self.search)
|
||||||
addEvent('%s.search' % self.type, self.search)
|
|
||||||
|
|
||||||
def getEnabledProviderType(self):
|
def getEnabledProtocol(self):
|
||||||
if self.isEnabled():
|
if self.isEnabled():
|
||||||
return self.type
|
return self.protocol
|
||||||
else:
|
else:
|
||||||
return []
|
return []
|
||||||
|
|
||||||
@@ -273,6 +295,7 @@ class ResultList(list):
|
|||||||
|
|
||||||
defaults = {
|
defaults = {
|
||||||
'id': 0,
|
'id': 0,
|
||||||
|
'protocol': self.provider.protocol,
|
||||||
'type': self.provider.type,
|
'type': self.provider.type,
|
||||||
'provider': self.provider.getName(),
|
'provider': self.provider.getName(),
|
||||||
'download': self.provider.loginDownload if self.provider.urls.get('login') else self.provider.download,
|
'download': self.provider.loginDownload if self.provider.urls.get('login') else self.provider.download,
|
||||||
|
|||||||
@@ -3,7 +3,8 @@ import time
|
|||||||
|
|
||||||
|
|
||||||
class NZBProvider(YarrProvider):
|
class NZBProvider(YarrProvider):
|
||||||
type = 'nzb'
|
|
||||||
|
protocol = 'nzb'
|
||||||
|
|
||||||
def calculateAge(self, unix):
|
def calculateAge(self, unix):
|
||||||
return int(time.time() - unix) / 24 / 60 / 60
|
return int(time.time() - unix) / 24 / 60 / 60
|
||||||
@@ -7,7 +7,7 @@ log = CPLog(__name__)
|
|||||||
|
|
||||||
class TorrentProvider(YarrProvider):
|
class TorrentProvider(YarrProvider):
|
||||||
|
|
||||||
type = 'torrent'
|
protocol = 'torrent'
|
||||||
|
|
||||||
def imdbMatch(self, url, imdbId):
|
def imdbMatch(self, url, imdbId):
|
||||||
if getImdb(url) == imdbId:
|
if getImdb(url) == imdbId:
|
||||||
@@ -27,6 +27,6 @@ class TorrentProvider(YarrProvider):
|
|||||||
|
|
||||||
class TorrentMagnetProvider(TorrentProvider):
|
class TorrentMagnetProvider(TorrentProvider):
|
||||||
|
|
||||||
type = 'torrent_magnet'
|
protocol = 'torrent_magnet'
|
||||||
|
|
||||||
download = None
|
download = None
|
||||||
@@ -2,13 +2,21 @@ from bs4 import BeautifulSoup
|
|||||||
from couchpotato.core.helpers.encoding import tryUrlencode, toUnicode
|
from couchpotato.core.helpers.encoding import tryUrlencode, toUnicode
|
||||||
from couchpotato.core.helpers.variable import tryInt
|
from couchpotato.core.helpers.variable import tryInt
|
||||||
from couchpotato.core.logger import CPLog
|
from couchpotato.core.logger import CPLog
|
||||||
|
from couchpotato.core.providers.base import MultiProvider
|
||||||
|
from couchpotato.core.providers.movie.base import MovieProvider
|
||||||
from couchpotato.core.providers.torrent.base import TorrentProvider
|
from couchpotato.core.providers.torrent.base import TorrentProvider
|
||||||
import traceback
|
import traceback
|
||||||
|
|
||||||
log = CPLog(__name__)
|
log = CPLog(__name__)
|
||||||
|
|
||||||
|
|
||||||
class SceneAccess(TorrentProvider):
|
class SceneAccess(MultiProvider):
|
||||||
|
|
||||||
|
def getTypes(self):
|
||||||
|
return [Movie]
|
||||||
|
|
||||||
|
|
||||||
|
class Base(TorrentProvider):
|
||||||
|
|
||||||
urls = {
|
urls = {
|
||||||
'test': 'https://www.sceneaccess.eu/',
|
'test': 'https://www.sceneaccess.eu/',
|
||||||
@@ -19,28 +27,26 @@ class SceneAccess(TorrentProvider):
|
|||||||
'download': 'https://www.sceneaccess.eu/%s',
|
'download': 'https://www.sceneaccess.eu/%s',
|
||||||
}
|
}
|
||||||
|
|
||||||
cat_ids = [
|
|
||||||
([22], ['720p', '1080p']),
|
|
||||||
([7], ['cam', 'ts', 'dvdrip', 'tc', 'r5', 'scr', 'brrip']),
|
|
||||||
([8], ['dvdr']),
|
|
||||||
]
|
|
||||||
|
|
||||||
http_time_between_calls = 1 #seconds
|
http_time_between_calls = 1 #seconds
|
||||||
|
|
||||||
def _search(self, movie, quality, results):
|
def _buildUrl(self, search, quality_identifier):
|
||||||
|
|
||||||
url = self.urls['search'] % (
|
url = self.urls['search'] % (
|
||||||
self.getCatId(quality['identifier'])[0],
|
self.getCatId(quality_identifier)[0],
|
||||||
self.getCatId(quality['identifier'])[0]
|
self.getCatId(quality_identifier)[0]
|
||||||
)
|
)
|
||||||
|
|
||||||
arguments = tryUrlencode({
|
arguments = tryUrlencode({
|
||||||
'search': movie['library']['identifier'],
|
'search': search,
|
||||||
'method': 1,
|
'method': 1,
|
||||||
})
|
})
|
||||||
url = "%s&%s" % (url, arguments)
|
url = "%s&%s" % (url, arguments)
|
||||||
|
|
||||||
|
return url
|
||||||
|
|
||||||
|
def _search(self, media, quality, results):
|
||||||
|
|
||||||
|
url = self.buildUrl(media, quality)
|
||||||
data = self.getHTMLData(url, opener = self.login_opener)
|
data = self.getHTMLData(url, opener = self.login_opener)
|
||||||
|
|
||||||
if data:
|
if data:
|
||||||
@@ -73,13 +79,6 @@ class SceneAccess(TorrentProvider):
|
|||||||
except:
|
except:
|
||||||
log.error('Failed getting results from %s: %s', (self.getName(), traceback.format_exc()))
|
log.error('Failed getting results from %s: %s', (self.getName(), traceback.format_exc()))
|
||||||
|
|
||||||
def getLoginParams(self):
|
|
||||||
return tryUrlencode({
|
|
||||||
'username': self.conf('username'),
|
|
||||||
'password': self.conf('password'),
|
|
||||||
'submit': 'come on in',
|
|
||||||
})
|
|
||||||
|
|
||||||
def getMoreInfo(self, item):
|
def getMoreInfo(self, item):
|
||||||
full_description = self.getCache('sceneaccess.%s' % item['id'], item['detail_url'], cache_timeout = 25920000)
|
full_description = self.getCache('sceneaccess.%s' % item['id'], item['detail_url'], cache_timeout = 25920000)
|
||||||
html = BeautifulSoup(full_description)
|
html = BeautifulSoup(full_description)
|
||||||
@@ -89,7 +88,28 @@ class SceneAccess(TorrentProvider):
|
|||||||
item['description'] = description
|
item['description'] = description
|
||||||
return item
|
return item
|
||||||
|
|
||||||
|
# Login
|
||||||
|
def getLoginParams(self):
|
||||||
|
return tryUrlencode({
|
||||||
|
'username': self.conf('username'),
|
||||||
|
'password': self.conf('password'),
|
||||||
|
'submit': 'come on in',
|
||||||
|
})
|
||||||
|
|
||||||
def loginSuccess(self, output):
|
def loginSuccess(self, output):
|
||||||
return '/inbox' in output.lower()
|
return '/inbox' in output.lower()
|
||||||
|
|
||||||
loginCheckSuccess = loginSuccess
|
loginCheckSuccess = loginSuccess
|
||||||
|
|
||||||
|
|
||||||
|
class Movie(Base, MovieProvider):
|
||||||
|
|
||||||
|
cat_ids = [
|
||||||
|
([22], ['720p', '1080p']),
|
||||||
|
([7], ['cam', 'ts', 'dvdrip', 'tc', 'r5', 'scr', 'brrip']),
|
||||||
|
([8], ['dvdr']),
|
||||||
|
]
|
||||||
|
|
||||||
|
def buildUrl(self, media, quality):
|
||||||
|
return self._buildUrl(media['library']['identifier'], quality['identifier'])
|
||||||
|
|
||||||
Reference in new issue
Block a user