KoD 1.6.2

- Migliorata funzione cerca trailer\n- Episodio successivo: è ora disponibile la modalità playlist (puoi usare il tasto riproduci successivo di kodi)\n- aggiunto www.accuradio.com\n- migliorie varie\n
This commit is contained in:
mac12m99
2021-04-07 20:16:21 +02:00
parent 8441b1e28a
commit b2bd3e61d1
30 changed files with 457 additions and 391 deletions
+5
View File
@@ -343,6 +343,11 @@ class SearchWindow(xbmcgui.WindowXML):
and self.item.infoLabels['year']:
logger.debug('retring adding year on channel ' + channel)
dummy, valid, dummy = search(self.item.text + " " + str(self.item.infoLabels['year']))
# some channels may use original title
if self.item.mode != 'all' and not valid and self.item.infoLabels.get('originaltitle'):
logger.debug('retring with original title on channel ' + channel)
dummy, valid, dummy = search(self.item.infoLabels.get('originaltitle'))
except:
pass
+4
View File
@@ -749,6 +749,10 @@ def from_context(item):
else:
return
if config.get_setting('new_search'):
from specials import globalsearch
return globalsearch.Search(item)
if 'list_type' not in item:
if 'wanted' in item:
item.title = item.wanted
+93 -51
View File
@@ -836,9 +836,15 @@ def report_menu(item):
action = 'call_browser'
url = item.url
itemlist.append(Item(channel=item.channel, action=action,
title="**- LOG: [COLOR gold]%s[/COLOR] -**" % item.url, url=url,
title="LOG: [COLOR gold]%s[/COLOR]" % item.url, url=url,
thumbnail=thumb_next, unify=False, folder=False))
if item.one_use:
itemlist.append(Item(channel=item.channel, action="",
title=config.get_localized_string(60305),
thumbnail=thumb_next, folder=False))
itemlist.append(Item(channel=item.channel, action="",
title=config.get_localized_string(60308),
thumbnail=thumb_next, folder=False))
itemlist.append(Item(channel=item.channel, action="call_browser",
title="su Github (raccomandato)", url='https://github.com/kodiondemand/addon/issues',
thumbnail=thumb_next,
@@ -847,14 +853,6 @@ def report_menu(item):
url='https://t.me/kodiondemand', title="Su telegram",
thumbnail=thumb_next, unify=False, folder=False))
if item.one_use:
itemlist.append(Item(channel=item.channel, action="",
title="[COLOR orange]NO ACCEDA al INFORME: se BORRARÁ[/COLOR]",
thumbnail=thumb_next, folder=False))
itemlist.append(Item(channel=item.channel, action="",
title="[COLOR orange]ya que es de un solo uso[/COLOR]",
thumbnail=thumb_next, folder=False))
return itemlist
@@ -917,33 +915,34 @@ def report_send(item, description='', fatal=False):
# directly on the forum. If it is a size problem, you are asked to reset Kodi and redo the fault, to
# that the LOG is smaller.
pastebin_list = {
'hastebin': ('1', 'https://hastebin.com/', 'documents', 'random', '', '',
'data', 'json', 'key', '', '0.29', '10', True, 'raw/', '', ''),
'dpaste': ('1', 'http://dpaste.com/', 'api/v2/', 'random', 'content=',
'&syntax=text&title=%s&poster=alfa&expiry_days=7',
'headers', '', '', 'location', '0.23', '15', True, '', '.txt', ''),
'ghostbin': ('1', 'https://ghostbin.com/', 'paste/new', 'random', 'lang=text&text=',
'&expire=2d&password=&title=%s',
'data', 'regex', '<title>(.*?)\s*-\s*Ghostbin<\/title>', '',
'0.49', '15', False, 'paste/', '', ''),
'write.as': ('1', 'https://write.as/', 'api/posts', 'random', 'body=', '&title=%s',
'data', 'json', 'data', 'id', '0.018', '15', True, '', '', ''),
'oneclickpaste': ('1', 'http://oneclickpaste.com/', 'index.php', 'random', 'paste_data=',
'&title=%s&format=text&paste_expire_date=1W&visibility=0&pass=&submit=Submit',
'data', 'regex', '<a class="btn btn-primary" href="[^"]+\/(\d+\/)">\s*View\s*Paste\s*<\/a>',
'', '0.060', '5', True, '', '', ''),
'bpaste': ('1', 'https://bpaste.net/', '', 'random', 'code=', '&lexer=text&expiry=1week',
'data', 'regex', 'View\s*<a\s*href="[^*]+/(.*?)">raw<\/a>', '',
'0.79', '15', True, 'raw/', '', ''),
'dumpz': ('0', 'http://dumpz.org/', 'api/dump', 'random', 'code=', '&lexer=text&comment=%s&password=',
'headers', '', '', 'location', '0.99', '15', False, '', '', ''),
'file.io': ('1', 'https://file.io/', '', 'random', '', 'expires=1w',
'requests', 'json', 'key', '', '99.0', '30', False, '', '.log', ''),
'uploadfiles': ('1', 'https://up.uploadfiles.io/upload', '', 'random', '', '',
'requests', 'json', 'url', '', '99.0', '30', False, None, '', '')
}
'hastebin': ('1', 'https://hastebin.com/', 'documents', 'random', '', '',
'data', 'json', 'key', '', '0.29', '10', True, 'raw/', '', ''),
'dpaste': ('1', 'http://dpaste.com/', 'api/v2/', 'random', 'content=',
'&syntax=text&title=%s&poster=alfa&expiry_days=7',
'headers', '', '', 'location', '0.23', '15', True, '', '.txt', ''),
'ghostbin': ('1', 'https://ghostbin.com/', 'paste/new', 'random', 'lang=text&text=',
'&expire=2d&password=&title=%s',
'data', 'regex', '<title>(.*?)\s*-\s*Ghostbin<\/title>', '',
'0.49', '15', False, 'paste/', '', ''),
'write.as': ('1', 'https://write.as/', 'api/posts', 'random', 'body=', '&title=%s',
'data', 'json', 'data', 'id', '0.018', '15', True, '', '', ''),
'oneclickpaste': ('1', 'http://oneclickpaste.com/', 'index.php', 'random', 'paste_data=',
'&title=%s&format=text&paste_expire_date=1W&visibility=0&pass=&submit=Submit',
'data', 'regex', '<a class="btn btn-primary" href="[^"]+\/(\d+\/)">\s*View\s*Paste\s*<\/a>',
'', '0.060', '5', True, '', '', ''),
'bpaste': ('1', 'https://bpaste.net/', '', 'random', 'code=', '&lexer=text&expiry=1week',
'data', 'regex', 'View\s*<a\s*href="[^*]+/(.*?)">raw<\/a>', '',
'0.79', '15', True, 'raw/', '', ''),
'dumpz': ('0', 'http://dumpz.org/', 'api/dump', 'random', 'code=', '&lexer=text&comment=%s&password=',
'headers', '', '', 'location', '0.99', '15', False, '', '', ''),
'file.io': ('1', 'https://file.io/', '', 'random', '', 'expires=1w',
'requests', 'json', 'key', '', '99.0', '30', False, '', '', ''),
'uploadfiles': ('0', 'https://up.ufile.io/v1/upload', '', 'random', '', '',
'curl', 'json', 'url', '', '99.0', '30', False, None, '', {'Referer': 'https://ufile.io/'}),
'anonfiles': ('1', 'https://api.anonfiles.com/upload', 'upload', 'random', '', '',
'requests', 'json', 'data', 'file,url,short', '99.0', '30', False, None, '', '')
}
pastebin_list_last = ['hastebin', 'ghostbin', 'file.io'] # We leave these services the last
pastebin_one_use = ['file.io'] # Single-use servers and deletes
pastebin_dir = []
@@ -994,7 +993,7 @@ def report_send(item, description='', fatal=False):
random.shuffle(pastebin_dir)
pastebin_dir.extend(pastebin_list_last) # We leave these services the last
#pastebin_dir = ['uploadfiles'] # For testing a service
# pastebin_dir = ['file.io'] # For testing a service
#log_data = 'TEST FOR SERVICE TESTS'
# The list of "pastebin" servers is scrolled to locate an active one, with capacity and availability
@@ -1018,7 +1017,7 @@ def report_send(item, description='', fatal=False):
paste_file_size = float(pastebin_list[paste_name][10]) # Server capacity in MB
if paste_file_size > 0: # If it is 0, the capacity is unlimited
if log_size > paste_file_size: # Capacity and size verification
msg = 'Log file too large. Restart Kodi and retry'
msg = config.get_localized_string(60334)
continue
paste_timeout = int(pastebin_list[paste_name][11]) # Timeout for the server
paste_random_headers = pastebin_list[paste_name][12] # Do you use RAMDOM headers to mislead the serv?
@@ -1029,15 +1028,12 @@ def report_send(item, description='', fatal=False):
paste_headers.update(jsontools.load((pastebin_list[paste_name][15])))
if paste_name in pastebin_one_use:
pastebin_one_use_msg = 'DO NOT ACCESS THE REPORT: it will be DELETED'
item.one_use = True
else:
pastebin_one_use_msg = ''
try:
# POST is created with server options "pastebin"
# This is the "requests" format
if paste_type == 'requests':
if paste_type in ['requests', 'curl']:
paste_file = {'file': (paste_title+'.log', log_data)}
if paste_post1:
paste_file.update(paste_post1)
@@ -1079,8 +1075,50 @@ def report_send(item, description='', fatal=False):
data = httptools.downloadpage(paste_host, params=paste_params, file=log_data,
file_name=paste_title+'.log', timeout=paste_timeout,
random_headers=paste_random_headers, headers=paste_headers)
elif paste_type == 'curl':
paste_sufix = '/create_session'
data_post = {'file_size': len(log_data)}
logger.error(data_post)
data = httptools.downloadpage(paste_host+paste_sufix, params=paste_params,
ignore_response_code=True, post=data_post, timeout=paste_timeout, alfa_s=True,
random_headers=paste_random_headers, headers=paste_headers).data
data = jsontools.load(data)
if not data.get("fuid", ""):
logger.error("fuid: %s" % str(data))
raise
fuid = data["fuid"]
paste_sufix = '/chunk'
log_data_chunks = log_data
i = 0
chunk_len = 1024
while len(log_data_chunks) > 0:
i += 1
chunk = log_data_chunks[:chunk_len]
log_data_chunks = log_data_chunks[chunk_len:]
data_post = {'fuid': fuid, 'chunk_index': i}
data = httptools.downloadpage(paste_host+paste_sufix, params=paste_params, file=chunk, alfa_s=True,
ignore_response_code=True, post=data_post, timeout=paste_timeout, CF_test=False,
random_headers=paste_random_headers, headers=paste_headers).data
if not 'successful' in data:
logger.error("successful: %s" % str(data))
raise
data = {}
paste_sufix = '/finalise'
data_post = {'fuid': fuid, 'total_chunks': i, 'file_name': paste_title+'.log', 'file_type': 'doc'}
resp = httptools.downloadpage(paste_host+paste_sufix, params=paste_params,
ignore_response_code=True, post=data_post, timeout=paste_timeout,
random_headers=paste_random_headers, headers=paste_headers)
if not resp.data:
logger.error("resp.content: %s" % str(resp.data))
raise
data['data'] = resp.data
data = type('HTTPResponse', (), data)
except:
msg = 'Inténtelo más tarde'
msg = 'Try later'
logger.error('Failed to save report. ' + msg)
logger.error(traceback.format_exc())
continue
@@ -1093,16 +1131,20 @@ def report_send(item, description='', fatal=False):
paste_host_return = ''
# Responses to REQUESTS requests
if paste_type == 'requests': # Response of request type "requests"?
if paste_type in ['requests', 'curl']: # Response of request type "requests"?
if paste_resp == 'json': # Answer in JSON format?
if paste_resp_key in data.data:
if not paste_url:
key = jsontools.load(data.data)[paste_resp_key] # with a label
else:
key = jsontools.load(data.data)[paste_resp_key][paste_url] # with two nested tags
item.url = "%s%s%s" % (paste_host_resp+paste_host_return, key,
paste_host_return_tail)
else:
key = jsontools.load(data.data)[paste_resp_key]
if paste_url and key: # hay etiquetas adicionales?
try:
for key_part in paste_url.split(','):
key = key[key_part] # por cada etiqueta adicional
except:
key = ''
if key:
item.url = "%s%s%s" % (paste_host_resp+paste_host_return, key,
paste_host_return_tail)
if not key:
logger.error('ERROR in data return format. data.data=' + str(data.data))
continue
+100 -188
View File
@@ -1,36 +1,40 @@
# -*- coding: utf-8 -*-
# --------------------------------------------------------------------------------
# Search trailers from youtube, filmaffinity, mymovies, vimeo, etc...
# Search trailers from tmdb, youtube and mymovies...
# --------------------------------------------------------------------------------
from __future__ import division
#from builtins import str
# from builtins import str
import sys
import xbmcaddon
from channelselector import get_thumb
PY3 = False
if sys.version_info[0] >= 3: PY3 = True; unicode = str; unichr = chr; long = int
from past.utils import old_div
if PY3:
#from future import standard_library
#standard_library.install_aliases()
import urllib.parse as urllib # It is very slow in PY2. In PY3 it is native
# from future import standard_library
# standard_library.install_aliases()
import urllib.parse as urllib # It is very slow in PY2. In PY3 it is native
import urllib.parse as urlparse
from concurrent import futures
else:
import urllib # We use the native of PY2 which is faster
import urllib # We use the native of PY2 which is faster
import urlparse
from concurrent_py2 import futures
import re
from core import httptools, jsontools, scrapertools, servertools
from core import httptools, scrapertools, servertools
from core.support import match, thumb
from core.item import Item
from platformcode import config, logger
from platformcode import config, logger, launcher
from platformcode import platformtools
info_language = ["it", "en", "es", "fr", "de", "pt"] # from videolibrary.json
info_language = ["de", "en", "es", "fr", "it", "pt"] # from videolibrary.json
def_lang = info_language[config.get_setting("info_language", "videolibrary")]
result = None
@@ -44,10 +48,14 @@ else:
def buscartrailer(item, trailers=[]):
logger.debug()
if item.contentType != "movie":
tipo = "tv"
else:
tipo = "movie"
# List of actions if run from context menu
if item.action == "manual_search" and item.contextual:
itemlist = manual_search(item)
itemlist = manual_search(item, tipo)
item.contentTitle = itemlist[0].contentTitle
elif 'search' in item.action and item.contextual:
itemlist = globals()[item.action](item)
@@ -67,7 +75,8 @@ def buscartrailer(item, trailers=[]):
item.contentTitle = item.contentTitle.strip()
elif keyboard:
contentTitle = re.sub(r'\[\/*(B|I|COLOR)\s*[^\]]*\]', '', item.contentTitle.strip())
item.contentTitle = platformtools.dialog_input(default=contentTitle, heading=config.get_localized_string(70505))
item.contentTitle = platformtools.dialog_input(default=contentTitle,
heading=config.get_localized_string(70505))
if item.contentTitle is None:
item.contentTitle = contentTitle
else:
@@ -87,32 +96,28 @@ def buscartrailer(item, trailers=[]):
title, url, server = servertools.findvideos(url)[0]
title = "Trailer [" + server + "]"
itemlist.append(item.clone(title=title, url=url, server=server, action="play"))
if item.show or item.infoLabels['tvshowtitle'] or item.contentType != "movie":
tipo = "tv"
else:
tipo = "movie"
try:
if not trailers:
itemlist.extend(tmdb_trailers(item, tipo))
else:
for trailer in trailers:
title = trailer['name'] + " [" + trailer['size'] + "p] (" + trailer['language'].replace("en", "ING").replace("it", "ITA") + ") [tmdb/youtube]"
itemlist.append(item.clone(action="play", title=title, url=trailer['url'], server="youtube"))
for trailer in trailers:
title = trailer['name'] + " [" + trailer['size'] + "p] (" + trailer['language'].replace("en",
"ING").replace(
"it", "ITA") + ") [tmdb/youtube]"
itemlist.append(item.clone(action="play", title=title, url=trailer['url'], server="youtube"))
except:
import traceback
logger.error(traceback.format_exc())
if item.contextual: title = "%s"
else: title = "%s"
itemlist.append(item.clone(title=title % config.get_localized_string(70507), action="youtube_search", thumbnail=thumb('search')))
itemlist.append(item.clone(title=title % config.get_localized_string(70508), action="mymovies_search", thumbnail=thumb('search')))
itemlist.append(item.clone(title=title % config.get_localized_string(70024), action="filmaffinity_search", thumbnail=thumb('search')))
multi_search(item, itemlist, tipo)
if not itemlist:
itemlist.append(item.clone(title=config.get_localized_string(70501), title2=item.contentTitle,
action="", thumbnail=get_thumb('nofolder.png'), text_color=""))
from lib.fuzzy_match import algorithims
itemlist.sort(key=lambda r: algorithims.trigram(item.contentTitle + ' trailer', r.title), reverse=True)
if item.contextual:
global window_select, result
select = Select("DialogSelect.xml", config.get_runtime_path(), item=item, itemlist=itemlist, caption=config.get_localized_string(70506) + item.contentTitle)
select = Select("DialogSelect.xml", config.get_runtime_path(), item=item, itemlist=itemlist,
caption=config.get_localized_string(70506) + item.contentTitle)
window_select.append(select)
select.doModal()
@@ -121,16 +126,24 @@ def buscartrailer(item, trailers=[]):
return itemlist
def manual_search(item):
def multi_search(item, itemlist, tipo):
ris = []
with futures.ThreadPoolExecutor() as executor:
ris.append(executor.submit(mymovies_search, item))
ris.append(executor.submit(youtube_search, item))
ris.append(executor.submit(tmdb_trailers, item, tipo))
for r in futures.as_completed(ris):
itemlist.extend(r.result())
def manual_search(item, tipo):
logger.debug()
itemlist = []
texto = platformtools.dialog_input(default=item.contentTitle, heading=config.get_localized_string(30112))
if texto is not None:
if item.extra == "mymovies":
return mymovies_search(item.clone(contentTitle=texto))
elif item.extra == "youtube":
return youtube_search(item.clone(contentTitle=texto, page=""))
elif item.extra == "filmaffinity":
return filmaffinity_search(item.clone(contentTitle=texto, page="", year=""))
multi_search(item.clone(contentTitle=texto), itemlist, tipo)
return itemlist
def tmdb_trailers(item, tipo="movie"):
@@ -145,9 +158,18 @@ def tmdb_trailers(item, tipo="movie"):
tmdb_search = Tmdb(texto_buscado=item.contentTitle, tipo=tipo, year=item.infoLabels['year'])
if tmdb_search:
for result in tmdb_search.get_videos():
title = result['name'] + " [" + result['size'] + "p] (" + result['language'].replace("en", "ING").replace("it", "ITA") + ") [tmdb/youtube]"
itemlist.append(item.clone(action="play", title=title, url=result['url'], server="youtube"))
for vid in tmdb_search.get_videos():
found = False
if vid['type'].lower() == 'trailer':
title = vid['name']
it = item.clone(action="play", title=title, title2="TMDB(youtube) - " + vid['language'].replace("en", "ING").replace("it", "ITA") + " [" + vid['size'] + "p]", url=vid['url'], server="youtube")
itemlist.append(it)
if vid['language'] == def_lang and not found: # play now because lang is correct and TMDB is trusted
found = True
launcher.run(it)
while platformtools.is_playing():
xbmc.sleep(100)
return itemlist
@@ -164,30 +186,25 @@ def youtube_search(item):
else:
title = urllib.quote(title)
title = title.replace("%20", "+")
data = httptools.downloadpage("https://www.youtube.com/results?sp=EgIQAQ%253D%253D&q=" + title).data
patron = r'thumbnails":\[\{"url":"(https://i.ytimg.com/vi[^"]+).*?'
data = httptools.downloadpage("https://www.youtube.com/results?sp=EgIQAQ%253D%253D&search_query=" + title).data
patron = r'thumbnails":\[\{"url":"(https://i.ytimg.com/vi[^"]+).*?'
patron += r'text":"([^"]+).*?'
patron += r'simpleText":"[^"]+.*?simpleText":"([^"]+).*?'
patron += r'url":"([^"]+)'
matches = scrapertools.find_multiple_matches(data, patron)
for scrapedthumbnail, scrapedtitle, scrapedduration, scrapedurl in matches:
scrapedtitle = scrapedtitle if PY3 else scrapedtitle.decode('utf8').encode('utf8') + " (" + scrapedduration + ")"
scrapedtitle = scrapedtitle if PY3 else scrapedtitle.decode('utf8').encode('utf8')
if item.contextual:
scrapedtitle = "%s" % scrapedtitle
url = urlparse.urljoin('https://www.youtube.com/', scrapedurl)
itemlist.append(item.clone(title=scrapedtitle, action="play", server="youtube", url=url, thumbnail=scrapedthumbnail))
next_page = scrapertools.find_single_match(data, '<a href="([^"]+)"[^>]+><span class="yt-uix-button-content">')
if next_page != "":
next_page = urlparse.urljoin("https://www.youtube.com", next_page)
itemlist.append(item.clone(title=config.get_localized_string(30992), action="youtube_search", extra="youtube", page=next_page, thumbnail=thumb('search'), text_color=""))
if not itemlist:
itemlist.append(item.clone(title=config.get_localized_string(70501) % title, action="", thumbnail="", text_color=""))
if keyboard:
if item.contextual:
title = "%s"
else:
title = "%s"
itemlist.append(item.clone(title=title % config.get_localized_string(70510), action="manual_search", thumbnail=thumb('search'), extra="youtube"))
itemlist.append(item.clone(title=scrapedtitle, title2='Youtube - ' + scrapedduration, action="play", server="youtube",
url=url, thumbnail=scrapedthumbnail))
# next_page = scrapertools.find_single_match(data, '<a href="([^"]+)"[^>]+><span class="yt-uix-button-content">')
# if next_page != "":
# next_page = urlparse.urljoin("https://www.youtube.com", next_page)
# itemlist.append(item.clone(title=config.get_localized_string(30992), action="youtube_search", extra="youtube",
# page=next_page, thumbnail=thumb('search'), text_color=""))
return itemlist
@@ -197,146 +214,48 @@ def mymovies_search(item):
title = item.contentTitle
url = 'https://www.mymovies.it/ricerca/ricerca.php?limit=true&q=' + title
js = json.loads(httptools.downloadpage(url).data)['risultati']['film']['elenco']
try:
js = json.loads(httptools.downloadpage(url).data)['risultati']['film']['elenco']
except:
return []
itemlist = []
for it in js:
itemlist.append(item.clone(title=it['titolo'], thumbnail=it['immagine'].replace('\\',''), url=it['url'].replace('\\',''), action ='search_links_mymovies'))
if not itemlist:
itemlist.append(item.clone(title=config.get_localized_string(70501), action="", thumbnail="", text_color=""))
if keyboard:
if item.contextual: title = "%s"
else: title = "%s"
itemlist.append(item.clone(title=title % config.get_localized_string(70511), action="manual_search", thumbnail=thumb('search'), extra="mymovies"))
with futures.ThreadPoolExecutor() as executor:
ris = [executor.submit(search_links_mymovies, item.clone(title=it['titolo'], title2='MYmovies', thumbnail=it['immagine'].replace('\\', ''), url=it['url'].replace('\\', ''))) for it in js]
for r in futures.as_completed(ris):
if r.result():
itemlist.append(r.result())
return itemlist
def search_links_mymovies(item):
global result
logger.debug()
trailer_url = match(item, patron=r'<li class="bottone_playlist"[^>]+><a href="([^"]+)"').match
itemlist = []
data = httptools.downloadpage(item.url).data
trailer_url = match(item, patron=r'<source src="([^"]+)').match
if trailer_url:
itemlist.append(item.clone(title=config.get_localized_string(60221) + ' ' + item.title, url=trailer_url, server='directo', action="play"))
itemlist = servertools.get_servers_itemlist(itemlist)
else:
if keyboard:
if item.contextual:
title = "%s"
else:
title = "%s"
itemlist.append(item.clone(title=title % config.get_localized_string(70513), action="manual_search", thumbnail=thumb('search'), extra="filmaffinity"))
return itemlist
def filmaffinity_search(item):
logger.debug()
if item.filmaffinity:
item.url = item.filmaffinity
return search_links_filmaff(item)
# Check if it is a zero search or comes from the Next option
if item.page != "":
data = httptools.downloadpage(item.page).data
else:
params = urllib.urlencode([('stext', item.contentTitle), ('stype%5B%5D', 'title'), ('country', ''), ('genre', ''), ('fromyear', item.year), ('toyear', item.year)])
url = "http://www.filmaffinity.com/es/advsearch.php?%s" % params
data = httptools.downloadpage(url).data
itemlist = []
patron = '<div class="mc-poster">.*?<img.*?src="([^"]+)".*?' \
'<div class="mc-title"><a href="/es/film(\d+).html"[^>]+>(.*?)<img'
matches = scrapertools.find_multiple_matches(data, patron)
# If there is only one result, search directly for the trailers, but list all the results
if len(matches) == 1:
item.url = "http://www.filmaffinity.com/es/evideos.php?movie_id=%s" % matches[0][1]
item.thumbnail = matches[0][0]
if not item.thumbnail.startswith("http"): item.thumbnail = "http://www.filmaffinity.com" + item.thumbnail
itemlist = search_links_filmaff(item)
elif len(matches) > 1:
for scrapedthumbnail, id, scrapedtitle in matches:
if not scrapedthumbnail.startswith("http"): scrapedthumbnail = "http://www.filmaffinity.com" + scrapedthumbnail
scrapedurl = "http://www.filmaffinity.com/es/evideos.php?movie_id=%s" % id
if PY3: scrapedtitle = unicode(scrapedtitle, encoding="utf-8", errors="ignore")
scrapedtitle = scrapertools.htmlclean(scrapedtitle)
itemlist.append(item.clone(title=scrapedtitle, url=scrapedurl, action="search_links_filmaff", thumbnail=scrapedthumbnail))
next_page = scrapertools.find_single_match(data, '<a href="([^"]+)">&gt;&gt;</a>')
if next_page != "":
next_page = urlparse.urljoin("http://www.filmaffinity.com/es/", next_page)
itemlist.append(item.clone(title=config.get_localized_string(30992), page=next_page, action="filmaffinity_search", thumbnail=thumb('search'), text_color=""))
if not itemlist: itemlist.append(item.clone(title=config.get_localized_string(70501) % item.contentTitle, action="", thumbnail="", text_color=""))
if keyboard:
if item.contextual: title = "%s"
else: title = "%s"
itemlist.append(item.clone(title=title % config.get_localized_string(70513), action="manual_search", thumbnail=thumb('search'), extra="filmaffinity"))
return itemlist
def search_links_filmaff(item):
logger.debug()
itemlist = []
data = httptools.downloadpage(item.url).data
if not '<a class="lnkvvid"' in data:
itemlist.append(item.clone(title=config.get_localized_string(70503), action="", text_color=""))
else:
patron = '<a class="lnkvvid".*?<b>(.*?)</b>.*?iframe.*?src="([^"]+)"'
matches = scrapertools.find_multiple_matches(data, patron)
for scrapedtitle, scrapedurl in matches:
if not scrapedurl.startswith("http:"):
scrapedurl = urlparse.urljoin("http:", scrapedurl)
trailer_url = scrapedurl.replace("-nocookie.com/embed/", ".com/watch?v=")
if "youtube" in trailer_url:
server = "youtube"
code = scrapertools.find_single_match(trailer_url, 'v=([A-z0-9\-_]+)')
thumbnail = "https://img.youtube.com/vi/%s/0.jpg" % code
else:
server = ""
thumbnail = item.thumbnail
if PY3:
scrapedtitle = unicode(scrapedtitle, encoding="utf-8", errors="ignore")
scrapedtitle = scrapertools.htmlclean(scrapedtitle)
scrapedtitle += " [" + server + "]"
if item.contextual:
scrapedtitle = "%s" % scrapedtitle
itemlist.append(item.clone(title=scrapedtitle, url=trailer_url, server=server, action="play", thumbnail=thumbnail))
itemlist = servertools.get_servers_itemlist(itemlist)
if keyboard:
if item.contextual:
title = "%s"
else:
title = "%s"
itemlist.append(item.clone(title=title % config.get_localized_string(70513), action="manual_search", thumbnail="", extra="filmaffinity"))
return itemlist
it = item.clone(url=trailer_url, server='directo', action="play")
if 'tmdb_id' in it.infoLabels:
del it.infoLabels['tmdb_id'] # for not saving watch time
return it
try:
import xbmcgui
import xbmc
class Select(xbmcgui.WindowXMLDialog):
def __init__(self, *args, **kwargs):
self.item = kwargs.get('item')
self.itemlist = kwargs.get('itemlist')
self.caption = kwargs.get('caption')
self.result = None
def onInit(self):
try:
self.control_list = self.getControl(6)
self.getControl(5).setNavigation(self.control_list, self.control_list, self.control_list, self.control_list)
self.getControl(5).setNavigation(self.control_list, self.control_list, self.control_list,
self.control_list)
self.getControl(3).setEnabled(0)
self.getControl(3).setVisible(0)
except:
@@ -347,35 +266,30 @@ try:
except:
pass
self.getControl(1).setLabel("" + self.caption + "")
self.getControl(5).setLabel(config.get_localized_string(60495))
if keyboard:
self.getControl(5).setLabel(config.get_localized_string(70510))
self.items = []
for item in self.itemlist:
item_l = xbmcgui.ListItem(item.title)
item_l = xbmcgui.ListItem(item.title, item.title2)
item_l.setArt({'thumb': item.thumbnail})
item_l.setProperty('item_copy', item.tourl())
self.items.append(item_l)
self.control_list.reset()
self.control_list.addItems(self.items)
self.setFocus(self.control_list)
def onClick(self, id):
global window_select, result
# Cancel button y [X]
if id == 7:
window_select[-1].close()
if id == 5:
self.result = "_no_video"
result = "no_video"
if id == 5 and keyboard:
self.close()
window_select.pop()
if not window_select:
if not self.item.windowed:
del window_select
else:
window_select[-1].doModal()
buscartrailer(self.item.clone(action="manual_search", extra="youtube"))
def onAction(self, action):
global window_select, result
if action == 92 or action == 110:
self.result = "no_video"
result = "no_video"
self.close()
window_select.pop()
@@ -394,10 +308,8 @@ try:
xbmc.sleep(200)
if puede:
result = video_urls[-1][1]
self.result = video_urls[-1][1]
else:
result = None
self.result = None
elif item.action == "play" and not self.item.windowed:
for window in window_select:
window.close()
+2 -1
View File
@@ -417,6 +417,8 @@ def findvideos(item):
all_videolibrary = []
ch_results = []
list_servers = []
with futures.ThreadPoolExecutor() as executor:
for nom_canal, json_path in list(list_canales.items()):
if filtro_canal and filtro_canal != nom_canal.capitalize():
@@ -476,7 +478,6 @@ def findvideos(item):
del item.library_urls[nom_canal]
item_json = Item().fromjson(filetools.read(json_path))
list_servers = []
# support.dbg()
try: from urllib.parse import urlsplit
except ImportError: from urlparse import urlsplit