Merge pull request #695 from croneter/beta-version

Bump stable
This commit is contained in:
croneter 2019-02-03 21:04:52 +01:00 committed by GitHub
commit 85f73126ff
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
29 changed files with 316 additions and 158 deletions

View file

@ -1,5 +1,5 @@
[![stable version](https://img.shields.io/badge/stable_version-2.6.3-blue.svg?maxAge=60&style=flat) ](https://github.com/croneter/binary_repo/raw/master/stable/repository.plexkodiconnect/repository.plexkodiconnect-1.0.2.zip)
[![beta version](https://img.shields.io/badge/beta_version-2.6.3-red.svg?maxAge=60&style=flat) ](https://github.com/croneter/binary_repo/raw/master/beta/repository.plexkodiconnectbeta/repository.plexkodiconnectbeta-1.0.2.zip)
[![stable version](https://img.shields.io/badge/stable_version-2.6.4-blue.svg?maxAge=60&style=flat) ](https://github.com/croneter/binary_repo/raw/master/stable/repository.plexkodiconnect/repository.plexkodiconnect-1.0.2.zip)
[![beta version](https://img.shields.io/badge/beta_version-2.6.4-red.svg?maxAge=60&style=flat) ](https://github.com/croneter/binary_repo/raw/master/beta/repository.plexkodiconnectbeta/repository.plexkodiconnectbeta-1.0.2.zip)
[![Installation](https://img.shields.io/badge/wiki-installation-brightgreen.svg?maxAge=60&style=flat)](https://github.com/croneter/PlexKodiConnect/wiki/Installation)
[![FAQ](https://img.shields.io/badge/wiki-FAQ-brightgreen.svg?maxAge=60&style=flat)](https://github.com/croneter/PlexKodiConnect/wiki/faq)

View file

@ -1,5 +1,5 @@
<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
<addon id="plugin.video.plexkodiconnect" name="PlexKodiConnect" version="2.6.3" provider-name="croneter">
<addon id="plugin.video.plexkodiconnect" name="PlexKodiConnect" version="2.6.4" provider-name="croneter">
<requires>
<import addon="xbmc.python" version="2.1.0"/>
<import addon="script.module.requests" version="2.9.1" />
@ -77,7 +77,16 @@
<summary lang="uk_UA">Нативна інтеграція Plex в Kodi</summary>
<description lang="uk_UA">Підключає Kodi до серверу Plex. Цей плагін передбачає, що ви керуєте всіма своїми відео за допомогою Plex (і ніяк не Kodi). Ви можете втратити дані, які вже зберігаються у відео та музичних БД Kodi (оскільки цей плагін безпосередньо їх змінює). Використовуйте на свій страх і ризик!</description>
<disclaimer lang="uk_UA">Використовуйте на свій ризик</disclaimer>
<news>version 2.6.3:
<news>version 2.6.4:
- Fix music items getting deleted on startup
- Never ignore SSL certificate errors for Kodi >= 18 - just like Kodi
- Fix playback not starting at the beginning
- Improve dialog to manually enter PMS IP and port
- Show logged in Plex home user in the settings and allow changing it
- Update German strings
- Implement Codacy suggestions
version 2.6.3:
- Fix PKC crashing on Xbox
version 2.6.2:

View file

@ -1,3 +1,12 @@
version 2.6.4:
- Fix music items getting deleted on startup
- Never ignore SSL certificate errors for Kodi >= 18 - just like Kodi
- Fix playback not starting at the beginning
- Improve dialog to manually enter PMS IP and port
- Show logged in Plex home user in the settings and allow changing it
- Update German strings
- Implement Codacy suggestions
version 2.6.3:
- Fix PKC crashing on Xbox

View file

@ -493,6 +493,13 @@ msgctxt "#30502"
msgid "Sync Plex artwork from the PMS (recommended)"
msgstr "Plex Bilder vom Plex Medienserver synchronisieren (empfohlen)"
# Message shown if SSL HTTPS certificate fails
msgctxt "#30503"
msgid "SSL certificate failed to validate. Please check {0} for solutions."
msgstr ""
"SSL-Zertifikat konnte nicht validiert werden. Bitte besuche {0} für "
"Lösungsvorschläge."
# PKC Settings, category name
msgctxt "#30506"
msgid "Sync Options"
@ -1193,6 +1200,16 @@ msgctxt "#39082"
msgid "Direct Paths"
msgstr "Direct Paths"
# Dialog for manually entering PMS
msgctxt "#39083"
msgid "Enter PMS IP or URL"
msgstr "PMS IP oder URL eingeben"
# Dialog for manually entering PMS
msgctxt "#39084"
msgid "Enter PMS port"
msgstr "PMS Port eingeben"
msgctxt "#39200"
msgid "Log-out Plex Home User "
msgstr "Plex Home Benutzer abmelden: "
@ -1254,11 +1271,11 @@ msgstr "Plex Media Server IP oder URL eingeben. Zum Beispiel:"
msgctxt "#39217"
msgid ""
"Does your Plex Media Server support SSL connections? (https instead of "
"http)?"
"Use HTTPS (SSL) connections? With Kodi 18 or later, HTTPS will likely not "
"work!"
msgstr ""
"Unterstützt der Plex Media Server sichere SSL Verbindungen (https anstelle "
"von http)?"
"HTTPS (SSL) Verbindungen nutzen? Dies funktioniert u.U. nicht mit Kodi 18 "
"oder späteren Versionen!"
msgctxt "#39218"
msgid "Error contacting PMS"
@ -1308,11 +1325,10 @@ msgctxt "#39227"
msgid "Logged in to plex.tv"
msgstr "Eingeloggt bei plex.tv"
# Message in the PKC settings to display the plex.tv username. Leave the colon
# :
# Message in the PKC settings to display the plex.tv username
msgctxt "#39228"
msgid "Plex user:"
msgstr "Plex Benutzer:"
msgid "Plex admin user"
msgstr "Plex Admin Benutzer"
# Error message if user could not log in; the actual user name will be
# appended at the end of the string
@ -1320,6 +1336,16 @@ msgctxt "#39229"
msgid "Login failed with plex.tv for user"
msgstr "Login für plex.tv fehlgeschlagen für Benutzer"
# Message in the PKC settings to display the plex.tv username
msgctxt "#39230"
msgid "Logged in Plex home user"
msgstr "Eingeloggter Plex Home Benutzer"
# Message in the PKC settings to change the logged in Plex home user
msgctxt "#39231"
msgid "Change logged in Plex home user"
msgstr "Eingeloggten Plex Home Benutzer wechseln"
msgctxt "#39250"
msgid ""
"Running the image cache process can take some time. It will happen in the "

View file

@ -464,6 +464,11 @@ msgctxt "#30502"
msgid "Sync Plex artwork from the PMS (recommended)"
msgstr ""
# Message shown if SSL HTTPS certificate fails
msgctxt "#30503"
msgid "SSL certificate failed to validate. Please check {0} for solutions."
msgstr ""
# PKC Settings, category name
msgctxt "#30506"
msgid "Sync Options"
@ -1081,6 +1086,16 @@ msgctxt "#39082"
msgid "Direct Paths"
msgstr ""
# Dialog for manually entering PMS
msgctxt "#39083"
msgid "Enter PMS IP or URL"
msgstr ""
# Dialog for manually entering PMS
msgctxt "#39084"
msgid "Enter PMS port"
msgstr ""
msgctxt "#39200"
msgid "Log-out Plex Home User "
msgstr ""
@ -1133,7 +1148,7 @@ msgid "Enter your Plex Media Server's IP or URL, Examples are:"
msgstr ""
msgctxt "#39217"
msgid "Does your Plex Media Server support SSL connections? (https instead of http)?"
msgid "Use HTTPS (SSL) connections? With Kodi 18 or later, HTTPS will likely not work!"
msgstr ""
msgctxt "#39218"
@ -1179,9 +1194,9 @@ msgctxt "#39227"
msgid "Logged in to plex.tv"
msgstr ""
# Message in the PKC settings to display the plex.tv username. Leave the colon :
# Message in the PKC settings to display the plex.tv username
msgctxt "#39228"
msgid "Plex user:"
msgid "Plex admin user"
msgstr ""
# Error message if user could not log in; the actual user name will be appended at the end of the string
@ -1189,6 +1204,16 @@ msgctxt "#39229"
msgid "Login failed with plex.tv for user"
msgstr ""
# Message in the PKC settings to display the plex.tv username
msgctxt "#39230"
msgid "Logged in Plex home user"
msgstr ""
# Message in the PKC settings to change the logged in Plex home user
msgctxt "#39231"
msgid "Change logged in Plex home user"
msgstr ""
msgctxt "#39250"
msgid "Running the image cache process can take some time. It will happen in the background. Are you sure you want continue?"
msgstr ""

View file

@ -3,7 +3,7 @@
from __future__ import absolute_import, division, unicode_literals
from logging import getLogger
from .. import utils, json_rpc as js
from .. import utils, json_rpc as js, variables as v
LOG = getLogger('PLEX.connection')
@ -38,7 +38,9 @@ class Connection(object):
def load(self):
LOG.debug('Loading connection settings')
# Shall we verify SSL certificates? "None" will leave SSL enabled
self.verify_ssl_cert = None if utils.settings('sslverify') == 'true' \
# Ignore this setting for Kodi >= 18 as Kodi 18 is much stricter
# with checking SSL certs
self.verify_ssl_cert = None if v.KODIVERSION >= 18 or utils.settings('sslverify') == 'true' \
else False
# Do we have an ssl certificate for PKC we need to use?
self.ssl_cert_path = utils.settings('sslcert') \
@ -61,7 +63,7 @@ class Connection(object):
self.server_name, self.machine_identifier, self.server)
def load_entrypoint(self):
self.verify_ssl_cert = None if utils.settings('sslverify') == 'true' \
self.verify_ssl_cert = None if v.KODIVERSION >= 18 or utils.settings('sslverify') == 'true' \
else False
self.ssl_cert_path = utils.settings('sslcert') \
if utils.settings('sslcert') != 'None' else None

View file

@ -62,7 +62,7 @@ class ImageCachingThread(backgroundthread.KillableThread):
LOG.info("---===### Starting ImageCachingThread ###===---")
try:
self._run()
except:
except Exception:
utils.ERROR()
finally:
LOG.info("---===### Stopped ImageCachingThread ###===---")

View file

@ -131,12 +131,12 @@ class Tasks(list):
class Task(object):
def __init__(self, priority=None):
self._priority = priority
self.priority = priority
self._canceled = False
self.finished = False
def __cmp__(self, other):
return self._priority - other._priority
return self.priority - other.priority
def start(self):
BGThreader.addTask(self)
@ -182,7 +182,7 @@ class MutablePriorityQueue(Queue.PriorityQueue):
self.mutex.acquire()
try:
lowest = self.queue and min(self.queue) or None
except:
except Exception:
lowest = None
utils.ERROR()
finally:
@ -203,7 +203,7 @@ class BackgroundWorker(object):
return
try:
task._run()
except:
except Exception:
utils.ERROR()
def abort(self):
@ -275,12 +275,12 @@ class BackgroundThreader:
self.name = name
self._queue = MutablePriorityQueue()
self._abort = False
self._priority = -1
self.priority = -1
self.workers = [worker(self._queue, 'queue.{0}:worker.{1}'.format(self.name, x)) for x in range(worker_count)]
def _nextPriority(self):
self._priority += 1
return self._priority
self.priority += 1
return self.priority
def abort(self):
self._abort = True
@ -298,13 +298,13 @@ class BackgroundThreader:
w.shutdown()
def addTask(self, task):
task._priority = self._nextPriority()
task.priority = self._nextPriority()
self._queue.put(task)
self.startWorkers()
def addTasks(self, tasks):
for t in tasks:
t._priority = self._nextPriority()
t.priority = self._nextPriority()
self._queue.put(t)
self.startWorkers()
@ -316,7 +316,7 @@ class BackgroundThreader:
p = lowest - len(tasks)
for t in tasks:
t._priority = p
t.priority = p
self._queue.put(t)
p += 1
@ -337,14 +337,14 @@ class BackgroundThreader:
if not lowest:
return None
return lowest._priority
return lowest.priority
def moveToFront(self, qitem):
lowest = self.getLowestPrority()
if lowest is None:
return
qitem._priority = lowest - 1
qitem.priority = lowest - 1
class ThreaderManager:

View file

@ -3,6 +3,7 @@
from __future__ import absolute_import, division, unicode_literals
from logging import getLogger
import requests
import requests.exceptions as exceptions
from . import utils, clientinfo, app
@ -39,16 +40,12 @@ class DownloadUtils():
def __init__(self):
self.__dict__ = self._shared_state
def setSSL(self, verifySSL=None, certificate=None):
def setSSL(self):
"""
verifySSL must be 'true' to enable certificate validation
certificate must be path to certificate or 'None'
"""
if verifySSL is None:
verifySSL = app.CONN.verify_ssl_cert
if certificate is None:
certificate = app.CONN.ssl_cert_path
verifySSL = app.CONN.verify_ssl_cert
certificate = app.CONN.ssl_cert_path
# Set the session's parameters
self.s.verify = verifySSL
if certificate:
@ -84,21 +81,23 @@ class DownloadUtils():
def stopSession(self):
try:
self.s.close()
except:
except Exception:
LOG.info("Requests session already closed")
try:
del self.s
except:
except AttributeError:
pass
LOG.info('Request session stopped')
def getHeader(self, options=None):
@staticmethod
def getHeader(options=None):
header = clientinfo.getXArgsDeviceInfo()
if options is not None:
header.update(options)
return header
def _doDownload(self, s, action_type, **kwargs):
@staticmethod
def _doDownload(s, action_type, **kwargs):
if action_type == "GET":
r = s.get(**kwargs)
elif action_type == "POST":
@ -114,7 +113,7 @@ class DownloadUtils():
def downloadUrl(self, url, action_type="GET", postBody=None,
parameters=None, authenticate=True, headerOptions=None,
verifySSL=True, timeout=None, return_response=False,
headerOverride=None):
headerOverride=None, reraise=False):
"""
Override SSL check with verifySSL=False
@ -172,39 +171,55 @@ class DownloadUtils():
r = self._doDownload(s, action_type, **kwargs)
# THE EXCEPTIONS
except requests.exceptions.SSLError as e:
except exceptions.SSLError as e:
LOG.warn("Invalid SSL certificate for: %s", url)
LOG.warn(e)
if reraise:
raise
except requests.exceptions.ConnectionError as e:
except exceptions.ConnectionError as e:
# Connection error
LOG.warn("Server unreachable at: %s", url)
LOG.warn(e)
if reraise:
raise
except requests.exceptions.Timeout as e:
except exceptions.Timeout as e:
LOG.warn("Server timeout at: %s", url)
LOG.warn(e)
if reraise:
raise
except requests.exceptions.HTTPError as e:
except exceptions.HTTPError as e:
LOG.warn('HTTP Error at %s', url)
LOG.warn(e)
if reraise:
raise
except requests.exceptions.TooManyRedirects as e:
except exceptions.TooManyRedirects as e:
LOG.warn("Too many redirects connecting to: %s", url)
LOG.warn(e)
if reraise:
raise
except requests.exceptions.RequestException as e:
except exceptions.RequestException as e:
LOG.warn("Unknown error connecting to: %s", url)
LOG.warn(e)
if reraise:
raise
except SystemExit:
LOG.info('SystemExit detected, aborting download')
self.stopSession()
if reraise:
raise
except:
except Exception:
LOG.warn('Unknown error while downloading. Traceback:')
import traceback
LOG.warn(traceback.format_exc())
if reraise:
raise
# THE RESPONSE #####
else:
@ -255,7 +270,7 @@ class DownloadUtils():
# xml response
r = utils.defused_etree.fromstring(r.content)
return r
except:
except Exception:
r.encoding = 'utf-8'
if r.text == '':
# Answer does not contain a body
@ -264,7 +279,7 @@ class DownloadUtils():
# UNICODE - JSON object
r = r.json()
return r
except:
except Exception:
if '200 OK' in r.text:
# Received fucked up OK from PMS on playstate
# update

View file

@ -9,7 +9,7 @@ from . import utils
from .utils import etree
from . import path_ops
from . import migration
from .downloadutils import DownloadUtils as DU
from .downloadutils import DownloadUtils as DU, exceptions
from . import plex_functions as PF
from . import plex_tv
from . import json_rpc as js
@ -70,46 +70,81 @@ class InitialSetup(object):
utils.window('plex_allows_mediaDeletion', value=value)
def enter_new_pms_address(self):
LOG.info('Start getting manual PMS address and port')
# "Enter your Plex Media Server's IP or URL. Examples are:"
utils.messageDialog(utils.lang(29999),
'%s\n%s\n%s' % (utils.lang(39215),
'192.168.1.2',
'plex.myServer.org'))
address = utils.dialog('input', "Enter PMS IP or URL")
if address == '':
# "Enter PMS IP or URL"
address = utils.dialog('input', utils.lang(39083))
if not address:
return False
port = utils.dialog('input', "Enter PMS port", '32400', type='{numeric}')
if port == '':
port = utils.dialog('input', utils.lang(39084), '32400', type='{numeric}')
if not port:
return False
url = '%s:%s' % (address, port)
# "Does your Plex Media Server support SSL connections?
# (https instead of http)"
# "Use HTTPS (SSL) connections? With Kodi 18 or later, HTTPS will likely
# not work!"
https = utils.yesno_dialog(utils.lang(29999), utils.lang(39217))
if https:
url = 'https://%s' % url
else:
url = 'http://%s' % url
https = 'true' if https else 'false'
machine_identifier = PF.GetMachineIdentifier(url)
if machine_identifier is None:
# "Error contacting url
# Abort (Yes) or save address anyway (No)"
if utils.yesno_dialog(utils.lang(29999),
'%s %s. %s' % (utils.lang(39218),
url,
utils.lang(39219))):
return False
else:
utils.settings('plex_machineIdentifier', '')
else:
utils.settings('plex_machineIdentifier', machine_identifier)
LOG.info('Set new PMS to https %s, address %s, port %s, machineId %s',
https, address, port, machine_identifier)
utils.settings('https', value=https)
utils.settings('ipaddress', value=address)
utils.settings('port', value=port)
# Chances are this is a local PMS, so disable SSL certificate check
utils.settings('sslverify', value='false')
# Try to connect first
error = False
try:
machine_identifier = PF.GetMachineIdentifier(url)
except exceptions.SSLError:
LOG.error('SSL cert error contacting %s', url)
# "SSL certificate failed to validate. Please check {0}
# for solutions."
utils.messageDialog(utils.lang(29999),
utils.lang(30503).format('github.com/croneter/PlexKodiConnect/issues'))
return
except Exception:
error = True
if error or machine_identifier is None:
LOG.error('Could not even get a machineIdentifier for %s', url)
# "Server is unreachable"
utils.messageDialog(utils.lang(29999), utils.lang(33002))
return
# Let's use the main account's token, not managed user token
token = utils.settings('plexToken')
xml = PF.pms_root(url, token)
if xml == 401:
LOG.error('Not yet authorized for %s', url)
# "User is unauthorized for server {0}",
# "Please sign in to plex.tv."
utils.messageDialog(utils.lang(29999),
'%s. %s' % (utils.lang(33010).format(address),
utils.lang(39014)))
return
try:
xml[0].attrib
except (IndexError, TypeError, AttributeError):
LOG.error('Could not get PMS root directory for %s', url)
# "Error contacting PMS"
utils.messageDialog(utils.lang(29999), utils.lang(39218))
return
pms = {
'baseURL': url,
'ip': address,
# Assume PMS is not local so we're not resetting verifyssl
'local': False,
'machineIdentifier': xml.get('machineIdentifier'),
'name': xml.get('friendlyName'),
# Assume that we own this PMS - no easy way to check
'owned': True,
'platform': xml.get('platform'),
'port': port,
# 'relay': True,
'scheme': 'https' if https else 'http',
'token': token,
'version': xml.get('version')
}
return pms
def plex_tv_sign_in(self):
"""
@ -177,7 +212,8 @@ class InitialSetup(object):
not set before
"""
answer = True
chk = PF.check_connection(app.CONN.server, verifySSL=False)
chk = PF.check_connection(app.CONN.server,
verifySSL=True if v.KODIVERSION >= 18 else False)
if chk is False:
LOG.warn('Could not reach PMS %s', app.CONN.server)
answer = False
@ -210,8 +246,8 @@ class InitialSetup(object):
if server['local']:
url = ('%s://%s:%s'
% (server['scheme'], server['ip'], server['port']))
# Deactive SSL verification if the server is local!
verifySSL = False
# Deactive SSL verification if the server is local for Kodi 17
verifySSL = True if v.KODIVERSION >= 18 else False
else:
url = server['baseURL']
verifySSL = True

View file

@ -52,12 +52,9 @@ class MusicMixin(object):
db_item['kodi_type'],
userdata['UserRating'])
if plex_type == v.PLEX_TYPE_SONG:
self.kodidb.set_resume(db_item['kodi_fileid'],
userdata['Resume'],
userdata['Runtime'],
userdata['PlayCount'],
userdata['LastPlayedDate'],
plex_type)
self.kodidb.set_playcount(userdata['PlayCount'],
userdata['LastPlayedDate'],
db_item['kodi_id'],)
return True
def remove(self, plex_id, plex_type=None):

View file

@ -459,6 +459,15 @@ class KodiMusicDB(common.KodiDBBase):
WHERE idSong = ?
''', (args))
@common.catch_operationalerrors
def set_playcount(self, *args):
self.cursor.execute('''
UPDATE song
SET iTimesPlayed = ?,
lastplayed = ?
WHERE idSong = ?
''', (args))
@common.catch_operationalerrors
def update_song_17(self, *args):
self.cursor.execute('''

View file

@ -694,7 +694,7 @@ class KodiVideoDB(common.KodiDBBase):
SET tag_id = ?
WHERE media_id = ? AND media_type = ? AND tag_id = ?
''', (newtag, kodiid, mediatype, oldtag,))
except:
except Exception:
# The new tag we are going to apply already exists for this item
# delete current tag instead
self.cursor.execute('''

View file

@ -41,7 +41,7 @@ class FanartThread(backgroundthread.KillableThread):
def run(self):
try:
self._run_internal()
except:
except Exception:
utils.ERROR(notify=True)
def _run_internal(self):

View file

@ -65,6 +65,10 @@ class FullSync(common.fullsync_mixin):
self.title = ''
self.section = None
self.section_name = None
self.section_type_text = None
self.context = None
self.get_children = None
self.successful = None
self.install_sync_done = utils.settings('SyncInstallRunDone') == 'true'
self.threader = backgroundthread.ThreaderManager(
worker=backgroundthread.NonstoppingBackgroundWorker,
@ -181,7 +185,7 @@ class FullSync(common.fullsync_mixin):
while True:
# Check Plex DB to see what we need to add/update
with PlexDB() as self.plexdb:
for i, (last, xml_item) in enumerate(loop):
for last, xml_item in loop:
if self.isCanceled():
return False
self.process_item(xml_item)
@ -323,6 +327,11 @@ class FullSync(common.fullsync_mixin):
if self.successful:
# Set timestamp for next sync - neglecting playstates!
utils.settings('lastfullsync', value=str(int(self.current_sync)))
# In order to not delete all your songs again
if app.SYNC.enable_music:
kinds.extend([
(v.PLEX_TYPE_SONG, v.PLEX_TYPE_ARTIST, itemtypes.Song, True),
])
# SYNC PLAYSTATE of ALL items (otherwise we won't pick up on items that
# were set to unwatched). Also mark all items on the PMS to be able
# to delete the ones still in Kodi
@ -428,7 +437,4 @@ class FullSync(common.fullsync_mixin):
def start(show_dialog, repair=False, callback=None):
"""
"""
# FullSync(repair, callback, show_dialog).start()
FullSync(repair, callback, show_dialog).run()

View file

@ -15,7 +15,8 @@ LOG = getLogger('PLEX.videonodes')
class VideoNodes(object):
def commonRoot(self, order, label, tagname, roottype=1):
@staticmethod
def commonRoot(order, label, tagname, roottype=1):
if roottype == 0:
# Index
@ -113,10 +114,7 @@ class VideoNodes(object):
label=tagname,
tagname=tagname,
roottype=0)
try:
utils.indent(root)
except:
pass
utils.indent(root)
etree.ElementTree(root).write(nodeXML, encoding="UTF-8")
nodetypes = {
@ -406,10 +404,7 @@ class VideoNodes(object):
rule = etree.SubElement(root,
'rule',
{'field': "inprogress", 'operator':"true"})
try:
utils.indent(root)
except:
pass
utils.indent(root)
etree.ElementTree(root).write(path_ops.encode_path(nodeXML),
encoding="UTF-8")
@ -464,13 +459,11 @@ class VideoNodes(object):
etree.SubElement(root, 'content').text = mediatype
try:
utils.indent(root)
except:
pass
utils.indent(root)
etree.ElementTree(root).write(nodeXML, encoding="UTF-8")
def clearProperties(self):
@staticmethod
def clearProperties():
LOG.info("Clearing nodes properties.")
plexprops = utils.window('Plex.nodes.total')

View file

@ -424,6 +424,8 @@ def _conclude_playback(playqueue, pos):
else:
listitem.setProperty('StartOffset', str(item.offset))
listitem.setProperty('resumetime', str(item.offset))
elif v.KODIVERSION >= 18:
listitem.setProperty('StartPercent', '0')
# Reset the resumable flag
transfer.send(listitem)
LOG.info('Done concluding playback')

View file

@ -495,12 +495,6 @@ class API(object):
"""
pass
def votecount(self):
"""
Not yet implemented
"""
pass
def tagline(self):
"""
Returns a shorter tagline or None
@ -1517,7 +1511,7 @@ class API(object):
return
try:
date = sub(r'(\d+)-(\d+)-(\d+)', r'\3.\2.\1', date)
except:
except Exception:
date = None
return date

View file

@ -282,7 +282,7 @@ class PlexCompanion(backgroundthread.KillableThread):
listener.MyHandler)
httpd.timeout = 0.95
break
except:
except Exception:
LOG.error("Unable to start PlexCompanion. Traceback:")
import traceback
LOG.error(traceback.print_exc())
@ -330,7 +330,7 @@ class PlexCompanion(backgroundthread.KillableThread):
subscription_manager.notify()
if not httpd:
message_count = 0
except:
except Exception:
LOG.warn("Error in loop, continuing anyway. Traceback:")
import traceback
LOG.warn(traceback.format_exc())

View file

@ -131,7 +131,11 @@ def check_connection(url, token=None, verifySSL=None):
if token is not None:
header_options = {'X-Plex-Token': token}
if verifySSL is True:
verifySSL = None if utils.settings('sslverify') == 'true' else False
if v.KODIVERSION >= 18:
# Always verify with Kodi >= 18
verifySSL = True
else:
verifySSL = True if utils.settings('sslverify') == 'true' else False
if 'plex.tv' in url:
url = 'https://plex.tv/api/home/users'
LOG.debug("Checking connection to server %s with verifySSL=%s",
@ -424,7 +428,7 @@ def _poke_pms(pms, queue):
xml = DU().downloadUrl('%s/identity' % url,
authenticate=False,
headerOptions={'X-Plex-Token': pms['token']},
verifySSL=False,
verifySSL=True if v.KODIVERSION >= 18 else False,
timeout=10)
try:
xml.attrib['machineIdentifier']
@ -804,14 +808,14 @@ def _pms_https_enabled(url):
"""
res = DU().downloadUrl('https://%s/identity' % url,
authenticate=False,
verifySSL=False)
verifySSL=True if v.KODIVERSION >= 18 else False)
try:
res.attrib
except AttributeError:
# Might have SSL deactivated. Try with http
res = DU().downloadUrl('http://%s/identity' % url,
authenticate=False,
verifySSL=False)
verifySSL=True if v.KODIVERSION >= 18 else False)
try:
res.attrib
except AttributeError:
@ -833,8 +837,9 @@ def GetMachineIdentifier(url):
"""
xml = DU().downloadUrl('%s/identity' % url,
authenticate=False,
verifySSL=False,
timeout=10)
verifySSL=True if v.KODIVERSION >= 18 else False,
timeout=10,
reraise=True)
try:
machineIdentifier = xml.attrib['machineIdentifier']
except (AttributeError, KeyError):
@ -937,6 +942,17 @@ def delete_item_from_pms(plexid):
return False
def pms_root(url, token):
"""
Retrieve the PMS' most basic settings by retrieving <url>/
"""
return DU().downloadUrl(
url,
authenticate=False,
verifySSL=True if v.KODIVERSION >= 18 else False,
headerOptions={'X-Plex-Token': token} if token else None)
def get_PMS_settings(url, token):
"""
Retrieve the PMS' settings via <url>/:/prefs
@ -946,7 +962,7 @@ def get_PMS_settings(url, token):
return DU().downloadUrl(
'%s/:/prefs' % url,
authenticate=False,
verifySSL=False,
verifySSL=True if v.KODIVERSION >= 18 else False,
headerOptions={'X-Plex-Token': token} if token else None)

View file

@ -70,7 +70,7 @@ class RequestMgr:
# Close connection just in case
try:
conn.close()
except:
except Exception:
pass
return False

View file

@ -93,7 +93,7 @@ class MyHandler(BaseHTTPRequestHandler):
self.end_headers()
self.wfile.write(body)
self.wfile.close()
except:
except Exception:
pass
def answer_request(self, send_data):

View file

@ -95,7 +95,7 @@ class plexgdm:
% (self.client_header, self.client_data),
self.client_register_group)
log.debug('(Re-)registering PKC Plex Companion successful')
except:
except Exception:
log.error("Unable to send registration message")
def client_update(self):
@ -109,14 +109,14 @@ class plexgdm:
update_sock.setsockopt(socket.SOL_SOCKET,
socket.SO_REUSEADDR,
1)
except:
except Exception:
pass
# Attempt to bind to the socket to recieve and send data. If we cant
# do this, then we cannot send registration
try:
update_sock.bind(('0.0.0.0', self.client_update_port))
except:
except Exception:
log.error("Unable to bind to port [%s] - Plex Companion will not "
"be registered. Change the Plex Companion update port!"
% self.client_update_port)
@ -165,7 +165,7 @@ class plexgdm:
update_sock.sendto("HTTP/1.0 200 OK\n%s"
% self.client_data,
addr)
except:
except Exception:
log.error("Unable to send client update message")
log.debug("Sending registration data HTTP/1.0 200 OK")
@ -180,7 +180,7 @@ class plexgdm:
update_sock.sendto("BYE %s\n%s"
% (self.client_header, self.client_data),
self.client_register_group)
except:
except Exception:
log.error("Unable to send client update message")
self.client_registered = False

View file

@ -269,14 +269,29 @@ class Service():
self.auth_running = False
def enter_new_pms_address(self):
if self.setup.enter_new_pms_address():
app.CONN.load()
app.ACCOUNT.reset_session()
app.ACCOUNT.set_unauthenticated()
self.server_has_been_online = False
self.welcome_msg = False
# Force a full sync
app.SYNC.run_lib_scan = 'full'
server = self.setup.enter_new_pms_address()
if not server:
return
if not self.log_out():
return False
# Save changes to to file
self.setup.save_pms_settings(server['baseURL'], server['token'])
self.setup.write_pms_to_settings(server)
if not v.KODIVERSION >= 18:
utils.settings('sslverify', value='false')
if not self.log_out():
return False
# Wipe Kodi and Plex database as well as playlists and video nodes
utils.wipe_database()
app.CONN.load()
app.ACCOUNT.reset_session()
app.ACCOUNT.set_unauthenticated()
self.server_has_been_online = False
self.welcome_msg = False
# Force a full sync
app.SYNC.run_lib_scan = 'full'
LOG.info("Choosing new PMS complete")
return True
def _do_auth(self):
LOG.info('Authenticating user')
@ -466,7 +481,7 @@ class Service():
PF.check_connection,
self.on_connection_check,
server,
verifySSL=True)
verifySSL=app.CONN.verify_ssl_cert)
backgroundthread.BGThreader.addTasksToFront([task])
continue
elif not app.ACCOUNT.authenticated:

View file

@ -146,7 +146,7 @@ class Sync(backgroundthread.KillableThread):
def run(self):
try:
self._run_internal()
except:
except Exception:
app.SYNC.db_scan = False
utils.window('plex_dbScan', clear=True)
utils.ERROR(txt='sync.py crashed', notify=True)

View file

@ -607,19 +607,22 @@ def indent(elem, level=0):
"""
Prettifies xml trees. Pass the etree root in
"""
i = "\n" + level * " "
if len(elem):
if not elem.text or not elem.text.strip():
elem.text = i + " "
if not elem.tail or not elem.tail.strip():
elem.tail = i
for elem in elem:
indent(elem, level + 1)
if not elem.tail or not elem.tail.strip():
elem.tail = i
else:
if level and (not elem.tail or not elem.tail.strip()):
elem.tail = i
try:
i = "\n" + level * " "
if len(elem):
if not elem.text or not elem.text.strip():
elem.text = i + " "
if not elem.tail or not elem.tail.strip():
elem.tail = i
for elem in elem:
indent(elem, level + 1)
if not elem.tail or not elem.tail.strip():
elem.tail = i
else:
if level and (not elem.tail or not elem.tail.strip()):
elem.tail = i
except Exception as err:
LOG.info('Indentation failed with: %s', err)
class XmlKodiSetting(object):

View file

@ -705,7 +705,7 @@ class WebSocket(object):
"""
try:
self.sock.shutdown(socket.SHUT_RDWR)
except:
except Exception:
pass
self._closeInternal()

View file

@ -237,7 +237,7 @@ class Alexa_Websocket(WebSocket):
LOG.error('%s: Unknown Alexa message received',
self.__class__.__name__)
return
except:
except Exception:
LOG.error('%s: Could not parse Alexa message',
self.__class__.__name__)
return

View file

@ -21,8 +21,10 @@
<category label="Plex">
<setting type="lsep" label="plex.tv"/>
<setting id="plex_status" label="39071" type="text" default="Not logged in to plex.tv" enable="false" /><!-- Current plex.tv status: -->
<setting id="plexLogin" label="39228" type="text" default="" enable="false" />
<setting id="plexLogin" label="39228" type="text" default="" enable="false" /><!-- Plex admin user -->
<setting id="username" label="39230" type="text" default="" enable="false" /><!-- Logged in Plex home user -->
<setting id="myplexlogin" label="39025" type="bool" default="true" /> <!-- Log into plex.tv on startup -->
<setting label="[COLOR yellow]$ADDON[plugin.video.plexkodiconnect 39231][/COLOR]" type="action" action="RunPlugin(plugin://plugin.video.plexkodiconnect?mode=switchuser)" option="close" /><!-- Change logged in Plex home user -->
<setting label="[COLOR yellow]$ADDON[plugin.video.plexkodiconnect 39209][/COLOR]" type="action" action="RunPlugin(plugin://plugin.video.plexkodiconnect?mode=togglePlexTV)" option="close" /><!-- Toggle plex.tv login (sign in or sign out) -->
<setting id="plexToken" label="plexToken" type="text" default="" visible="false" />
<setting type="sep" text=""/>
@ -47,7 +49,6 @@
<setting id="dbCreatedWithVersion" type="text" default="" visible="false"/>
<setting id="plexid" type="text" default="" visible="false"/>
<setting id="userid" type="text" default="" visible="false"/>
<setting id="username" type="text" default="" visible="false"/>
</category>
<category label="30506"><!-- Sync Options -->