1.0.0+kodimov.9: get a new guide into Kodi right after start or update
Kodi keeps its own copy of the programme guide and fetches it again only when IPTV Simple reloads its files, on its refresh timer; restarting IPTV Simple is not enough. After the first refresh following a Kodi start or add-on update, if the guide changed and nothing is playing, restart IPTV Simple with a 1-minute timer, wait for the reload, then restart it with the hourly timer again. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
This commit is contained in:
1 parent
5df60a1fb8
commit
e16dd66f63
5 files changed
+50
-16
No files matched your search
@@ -1,7 +1,7 @@
|
|||||||
<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
|
<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
|
||||||
<addon id="plugin.video.kodimovplus"
|
<addon id="plugin.video.kodimovplus"
|
||||||
name="KodiMov+"
|
name="KodiMov+"
|
||||||
version="1.0.0+kodimov.8"
|
version="1.0.0+kodimov.9"
|
||||||
provider-name="Paco8, xocko">
|
provider-name="Paco8, xocko">
|
||||||
<requires>
|
<requires>
|
||||||
<!--- <import addon="xbmc.python" version="2.25.0"/> -->
|
<!--- <import addon="xbmc.python" version="2.25.0"/> -->
|
||||||
@@ -21,7 +21,8 @@
|
|||||||
<summary lang="es_ES">Movistar+ para Kodi, con inicio de sesión automático desde la red de Movistar</summary>
|
<summary lang="es_ES">Movistar+ para Kodi, con inicio de sesión automático desde la red de Movistar</summary>
|
||||||
<description lang="en_GB">Fork of Paco8's Movistar+ add-on (plugin.video.movistarplus). Logs in by itself from the Movistar home network, keeps the channel list and numbers up to date, hides the channels that need stronger DRM than Kodi has, adds free Galician channels (TVG2, TeleVigo) and writes a programme guide for every channel. Requires a Movistar+ subscription.</description>
|
<description lang="en_GB">Fork of Paco8's Movistar+ add-on (plugin.video.movistarplus). Logs in by itself from the Movistar home network, keeps the channel list and numbers up to date, hides the channels that need stronger DRM than Kodi has, adds free Galician channels (TVG2, TeleVigo) and writes a programme guide for every channel. Requires a Movistar+ subscription.</description>
|
||||||
<description lang="es_ES">Fork del addon Movistar+ de Paco8 (plugin.video.movistarplus). Inicia sesión solo desde la red de Movistar, mantiene la lista y los números de los canales al día, oculta los canales que necesitan una protección que Kodi no tiene añade canales gallegos gratuitos (TVG2, TeleVigo) y genera la guía de programación de todos los canales. Se necesita estar abonado a Movistar+.</description>
|
<description lang="es_ES">Fork del addon Movistar+ de Paco8 (plugin.video.movistarplus). Inicia sesión solo desde la red de Movistar, mantiene la lista y los números de los canales al día, oculta los canales que necesitan una protección que Kodi no tiene añade canales gallegos gratuitos (TVG2, TeleVigo) y genera la guía de programación de todos los canales. Se necesita estar abonado a Movistar+.</description>
|
||||||
<news>1.0.0+kodimov.8: the programme guide refresh no longer fails at random inside Kodi, and a failed refresh is tried again half an hour later instead of 6 hours later.
|
<news>1.0.0+kodimov.9: after Kodi starts or the add-on updates, a new programme guide shows up in Kodi within a couple of minutes instead of at the next hourly reload (only while nothing is playing).
|
||||||
|
1.0.0+kodimov.8: the programme guide refresh no longer fails at random inside Kodi, and a failed refresh is tried again half an hour later instead of 6 hours later.
|
||||||
1.0.0+kodimov.7: the programme guide has the synopsis, picture, genre, year and age rating of each programme. IPTV Simple now reloads the guide every hour instead of once a day, so a new guide shows up in Kodi by itself (existing TV guide setups are switched over once).
|
1.0.0+kodimov.7: the programme guide has the synopsis, picture, genre, year and age rating of each programme. IPTV Simple now reloads the guide every hour instead of once a day, so a new guide shows up in Kodi by itself (existing TV guide setups are switched over once).
|
||||||
1.0.0+kodimov.6: the programme guide refreshes on its own again on boxes first set up with kodimov.1, where the automatic guide export had stayed off (the guide ran out after 2 days).
|
1.0.0+kodimov.6: the programme guide refreshes on its own again on boxes first set up with kodimov.1, where the automatic guide export had stayed off (the guide ran out after 2 days).
|
||||||
1.0.0+kodimov.5: TV guide setup writes the programme guide before creating the IPTV Simple settings, so the guide isn't empty on a new box.
|
1.0.0+kodimov.5: TV guide setup writes the programme guide before creating the IPTV Simple settings, so the guide isn't empty on a new box.
|
||||||
|
|||||||
@@ -212,11 +212,12 @@ def write_if_changed(filename, content):
|
|||||||
return True
|
return True
|
||||||
|
|
||||||
|
|
||||||
def use_hourly_iptv_refresh(pvr_dir, addon_id):
|
def set_iptv_refresh(pvr_dir, addon_id, minutes=60):
|
||||||
"""TV guide setups before kodimov.7 made IPTV Simple reload the channel list
|
"""Makes the IPTV Simple instances that read this add-on's files reload the
|
||||||
and programme guide only once a day, at 4:00, so a new epg.xml didn't reach
|
channel list and programme guide every few minutes. Each reload also makes
|
||||||
Kodi for up to a day. Switch them to a reload every hour, which also makes
|
Kodi fetch the guide again. TV guide setups before kodimov.7 reloaded only
|
||||||
Kodi fetch the guide again. Returns True if IPTV Simple must be restarted."""
|
once a day, at 4:00. Returns True if a file changed (IPTV Simple must be
|
||||||
|
restarted to use it)."""
|
||||||
import glob
|
import glob
|
||||||
import re
|
import re
|
||||||
changed = False
|
changed = False
|
||||||
@@ -225,15 +226,38 @@ def use_hourly_iptv_refresh(pvr_dir, addon_id):
|
|||||||
content = f.read()
|
content = f.read()
|
||||||
if 'plugin.video.{}/channels.m3u8'.format(addon_id) not in content: continue
|
if 'plugin.video.{}/channels.m3u8'.format(addon_id) not in content: continue
|
||||||
new = content
|
new = content
|
||||||
for setting, value in (('m3uRefreshMode', '1'), ('m3uRefreshIntervalMins', '60')):
|
for setting, value in (('m3uRefreshMode', '1'), ('m3uRefreshIntervalMins', str(minutes))):
|
||||||
new = re.sub(r'<setting id="{}"[^>]*?(/>|>[^<]*</setting>)'.format(setting),
|
new = re.sub(r'<setting id="{}"[^>]*?(/>|>[^<]*</setting>)'.format(setting),
|
||||||
'<setting id="{}">{}</setting>'.format(setting, value), new)
|
'<setting id="{}">{}</setting>'.format(setting, value), new)
|
||||||
if write_if_changed(filename, new):
|
if new != content:
|
||||||
LOG('use_hourly_iptv_refresh: updated {}'.format(filename))
|
write_if_changed(filename, new)
|
||||||
|
LOG('set_iptv_refresh: {} minutes in {}'.format(minutes, filename))
|
||||||
changed = True
|
changed = True
|
||||||
return changed
|
return changed
|
||||||
|
|
||||||
|
|
||||||
|
def reload_iptv_guide(pvr_dir, addon_id):
|
||||||
|
"""Gets a new programme guide into Kodi now instead of at the next hourly
|
||||||
|
reload. Restarting IPTV Simple isn't enough: Kodi keeps its own copy of the
|
||||||
|
guide and fetches it again only when IPTV Simple reloads, which happens on
|
||||||
|
its timer. So restart it with a 1-minute timer, wait for that reload, then
|
||||||
|
restart it with the hourly timer. Restarting stops live TV, so this does
|
||||||
|
nothing if something is playing."""
|
||||||
|
import xbmc
|
||||||
|
monitor, player = xbmc.Monitor(), xbmc.Player()
|
||||||
|
if player.isPlaying(): return
|
||||||
|
if not set_iptv_refresh(pvr_dir, addon_id, 1): return
|
||||||
|
try:
|
||||||
|
restart_iptv_simple()
|
||||||
|
monitor.waitForAbort(90)
|
||||||
|
finally:
|
||||||
|
set_iptv_refresh(pvr_dir, addon_id, 60)
|
||||||
|
while player.isPlaying(): # until then it keeps reloading every minute
|
||||||
|
if monitor.waitForAbort(10): return
|
||||||
|
if not monitor.abortRequested():
|
||||||
|
restart_iptv_simple()
|
||||||
|
|
||||||
|
|
||||||
def restart_iptv_simple():
|
def restart_iptv_simple():
|
||||||
"""Restarts IPTV Simple so it loads its instance settings again."""
|
"""Restarts IPTV Simple so it loads its instance settings again."""
|
||||||
import xbmc
|
import xbmc
|
||||||
|
|||||||
@@ -1566,7 +1566,7 @@ class Movistar(object):
|
|||||||
if self.add_extra_channels:
|
if self.add_extra_channels:
|
||||||
res.extend(kodimov.extra_channels_xmltv(self.net.session))
|
res.extend(kodimov.extra_channels_xmltv(self.net.session))
|
||||||
res.append('</tv>\n')
|
res.append('</tv>\n')
|
||||||
kodimov.write_if_changed(filename, ''.join(res))
|
return kodimov.write_if_changed(filename, ''.join(res))
|
||||||
|
|
||||||
def save_credentials(self, username, password):
|
def save_credentials(self, username, password):
|
||||||
from .b64 import encode_base64
|
from .b64 import encode_base64
|
||||||
|
|||||||
+10
-3
@@ -787,7 +787,7 @@ def export_channels_now():
|
|||||||
if m.export_channels_to_m3u8(channels_filename, addon.getSettingBool('only_subscribed')):
|
if m.export_channels_to_m3u8(channels_filename, addon.getSettingBool('only_subscribed')):
|
||||||
LOG('export_channels_now: channel list changed')
|
LOG('export_channels_now: channel list changed')
|
||||||
|
|
||||||
def export_epg_now(quiet=False):
|
def export_epg_now(quiet=False, reload_guide=False):
|
||||||
# quiet: background refresh from the service, no pop-ups while watching TV
|
# quiet: background refresh from the service, no pop-ups while watching TV
|
||||||
def notify(message):
|
def notify(message):
|
||||||
if not quiet: show_notification(message, xbmcgui.NOTIFICATION_INFO)
|
if not quiet: show_notification(message, xbmcgui.NOTIFICATION_INFO)
|
||||||
@@ -804,7 +804,14 @@ def export_epg_now(quiet=False):
|
|||||||
|
|
||||||
if True: #not addon.getSettingBool('use_external_epg'):
|
if True: #not addon.getSettingBool('use_external_epg'):
|
||||||
notify(addon.getLocalizedString(30311))
|
notify(addon.getLocalizedString(30311))
|
||||||
m.export_epg_to_xml(epg_filename, addon.getSettingInt('export_days'), report_progress, only_subscribed)
|
changed = m.export_epg_to_xml(epg_filename, addon.getSettingInt('export_days'), report_progress, only_subscribed)
|
||||||
|
if changed and reload_guide:
|
||||||
|
from . import kodimov
|
||||||
|
try:
|
||||||
|
pvr_dir = translatePath(xbmcaddon.Addon('pvr.iptvsimple').getAddonInfo('profile'))
|
||||||
|
except RuntimeError: # IPTV Simple not installed or disabled
|
||||||
|
pvr_dir = None
|
||||||
|
if pvr_dir: kodimov.reload_iptv_guide(pvr_dir, 'kodimovplus')
|
||||||
|
|
||||||
notify(addon.getLocalizedString(30313))
|
notify(addon.getLocalizedString(30313))
|
||||||
|
|
||||||
@@ -900,7 +907,7 @@ def router(paramstring):
|
|||||||
elif params['action'] == 'create_iptv_settings':
|
elif params['action'] == 'create_iptv_settings':
|
||||||
create_iptv_settings()
|
create_iptv_settings()
|
||||||
elif params['action'] == 'export_epg_now':
|
elif params['action'] == 'export_epg_now':
|
||||||
export_epg_now(quiet=params.get('quiet') == '1')
|
export_epg_now(quiet=params.get('quiet') == '1', reload_guide=params.get('reload_guide') == '1')
|
||||||
elif params['action'] == 'to_wishlist':
|
elif params['action'] == 'to_wishlist':
|
||||||
to_wishlist(params)
|
to_wishlist(params)
|
||||||
elif 'iptv' in params['action']:
|
elif 'iptv' in params['action']:
|
||||||
|
|||||||
+4
-2
@@ -33,7 +33,7 @@ if __name__ == '__main__':
|
|||||||
max_age = 0 # always refresh once after Kodi starts
|
max_age = 0 # always refresh once after Kodi starts
|
||||||
try:
|
try:
|
||||||
pvr_dir = translatePath(xbmcaddon.Addon('pvr.iptvsimple').getAddonInfo('profile'))
|
pvr_dir = translatePath(xbmcaddon.Addon('pvr.iptvsimple').getAddonInfo('profile'))
|
||||||
restart_iptv = kodimov.use_hourly_iptv_refresh(pvr_dir, 'kodimovplus')
|
restart_iptv = kodimov.set_iptv_refresh(pvr_dir, 'kodimovplus')
|
||||||
except RuntimeError: # IPTV Simple not installed or disabled
|
except RuntimeError: # IPTV Simple not installed or disabled
|
||||||
restart_iptv = False
|
restart_iptv = False
|
||||||
player = xbmc.Player()
|
player = xbmc.Player()
|
||||||
@@ -47,9 +47,11 @@ if __name__ == '__main__':
|
|||||||
if time.time() >= next_check:
|
if time.time() >= next_check:
|
||||||
next_check = time.time() + 30 * 60
|
next_check = time.time() + 30 * 60
|
||||||
age_limit, max_age = max_age, 6 * 3600 - 120
|
age_limit, max_age = max_age, 6 * 3600 - 120
|
||||||
|
# After Kodi starts (or this add-on updates) also get the new guide into Kodi now
|
||||||
|
reload_guide = '&reload_guide=1' if age_limit == 0 else ''
|
||||||
if addon.getSettingBool('auto_export_epg'): # channels + programme guide
|
if addon.getSettingBool('auto_export_epg'): # channels + programme guide
|
||||||
if file_age(os.path.join(profile_dir, 'epg.xml')) > age_limit:
|
if file_age(os.path.join(profile_dir, 'epg.xml')) > age_limit:
|
||||||
xbmc.executebuiltin('RunPlugin(plugin://plugin.video.kodimovplus/?action=export_epg_now&quiet=1)')
|
xbmc.executebuiltin('RunPlugin(plugin://plugin.video.kodimovplus/?action=export_epg_now&quiet=1' + reload_guide + ')')
|
||||||
elif addon.getSettingBool('export_channels'):
|
elif addon.getSettingBool('export_channels'):
|
||||||
if file_age(os.path.join(profile_dir, 'channels.m3u8')) > age_limit:
|
if file_age(os.path.join(profile_dir, 'channels.m3u8')) > age_limit:
|
||||||
xbmc.executebuiltin('RunPlugin(plugin://plugin.video.kodimovplus/?action=export_channels_now)')
|
xbmc.executebuiltin('RunPlugin(plugin://plugin.video.kodimovplus/?action=export_channels_now)')
|
||||||
|
|||||||
Reference in new issue
Block a user