Merge branch 'beta-version' into plex_for_kodi
This commit is contained in:
commit
517f41b534
7 changed files with 58 additions and 53 deletions
|
@ -1,5 +1,5 @@
|
||||||
[![stable version](https://img.shields.io/badge/stable_version-2.4.3-blue.svg?maxAge=60&style=flat) ](https://github.com/croneter/binary_repo/raw/master/stable/repository.plexkodiconnect/repository.plexkodiconnect-1.0.2.zip)
|
[![stable version](https://img.shields.io/badge/stable_version-2.4.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.4.5-red.svg?maxAge=60&style=flat) ](https://github.com/croneter/binary_repo/raw/master/beta/repository.plexkodiconnectbeta/repository.plexkodiconnectbeta-1.0.2.zip)
|
[![beta version](https://img.shields.io/badge/beta_version-2.4.6-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)
|
[![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)
|
[![FAQ](https://img.shields.io/badge/wiki-FAQ-brightgreen.svg?maxAge=60&style=flat)](https://github.com/croneter/PlexKodiConnect/wiki/faq)
|
||||||
|
|
10
addon.xml
10
addon.xml
|
@ -1,5 +1,5 @@
|
||||||
<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
|
<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
|
||||||
<addon id="plugin.video.plexkodiconnect" name="PlexKodiConnect" version="2.4.5" provider-name="croneter">
|
<addon id="plugin.video.plexkodiconnect" name="PlexKodiConnect" version="2.4.6" provider-name="croneter">
|
||||||
<requires>
|
<requires>
|
||||||
<import addon="xbmc.python" version="2.1.0"/>
|
<import addon="xbmc.python" version="2.1.0"/>
|
||||||
<import addon="script.module.requests" version="2.9.1" />
|
<import addon="script.module.requests" version="2.9.1" />
|
||||||
|
@ -74,7 +74,13 @@
|
||||||
<summary lang="uk_UA">Нативна інтеграція Plex в Kodi</summary>
|
<summary lang="uk_UA">Нативна інтеграція Plex в Kodi</summary>
|
||||||
<description lang="uk_UA">Підключає Kodi до серверу Plex. Цей плагін передбачає, що ви керуєте всіма своїми відео за допомогою Plex (і ніяк не Kodi). Ви можете втратити дані, які вже зберігаються у відео та музичних БД Kodi (оскільки цей плагін безпосередньо їх змінює). Використовуйте на свій страх і ризик!</description>
|
<description lang="uk_UA">Підключає Kodi до серверу Plex. Цей плагін передбачає, що ви керуєте всіма своїми відео за допомогою Plex (і ніяк не Kodi). Ви можете втратити дані, які вже зберігаються у відео та музичних БД Kodi (оскільки цей плагін безпосередньо їх змінює). Використовуйте на свій страх і ризик!</description>
|
||||||
<disclaimer lang="uk_UA">Використовуйте на свій ризик</disclaimer>
|
<disclaimer lang="uk_UA">Використовуйте на свій ризик</disclaimer>
|
||||||
<news>version 2.4.5 (beta only):
|
<news>version 2.4.6 (beta only):
|
||||||
|
- Fix PKC not starting up on Enigma
|
||||||
|
- Fix sync issues if video lies in root of file system
|
||||||
|
- Make sure we retain a dummy first music artist entry
|
||||||
|
- Increase logging
|
||||||
|
|
||||||
|
version 2.4.5 (beta only):
|
||||||
- Fix playback not starting up at all
|
- Fix playback not starting up at all
|
||||||
- Rewire Kodi library refreshs
|
- Rewire Kodi library refreshs
|
||||||
- Wipe Kodi database on first PKC run to more reliably install PKC
|
- Wipe Kodi database on first PKC run to more reliably install PKC
|
||||||
|
|
|
@ -1,3 +1,9 @@
|
||||||
|
version 2.4.6 (beta only):
|
||||||
|
- Fix PKC not starting up on Enigma
|
||||||
|
- Fix sync issues if video lies in root of file system
|
||||||
|
- Make sure we retain a dummy first music artist entry
|
||||||
|
- Increase logging
|
||||||
|
|
||||||
version 2.4.5 (beta only):
|
version 2.4.5 (beta only):
|
||||||
- Fix playback not starting up at all
|
- Fix playback not starting up at all
|
||||||
- Rewire Kodi library refreshs
|
- Rewire Kodi library refreshs
|
||||||
|
|
|
@ -145,6 +145,7 @@ class Movies(Items):
|
||||||
# If the item doesn't exist, we'll add it to the database
|
# If the item doesn't exist, we'll add it to the database
|
||||||
update_item = True
|
update_item = True
|
||||||
itemid = api.plex_id()
|
itemid = api.plex_id()
|
||||||
|
LOG.debug('Adding movie with plex_id %s', itemid)
|
||||||
# Cannot parse XML, abort
|
# Cannot parse XML, abort
|
||||||
if not itemid:
|
if not itemid:
|
||||||
LOG.error("Cannot parse XML data for movie")
|
LOG.error("Cannot parse XML data for movie")
|
||||||
|
@ -485,6 +486,7 @@ class TVShows(Items):
|
||||||
api = API(item)
|
api = API(item)
|
||||||
update_item = True
|
update_item = True
|
||||||
itemid = api.plex_id()
|
itemid = api.plex_id()
|
||||||
|
LOG.debug('Adding show with plex_id %s', itemid)
|
||||||
if not itemid:
|
if not itemid:
|
||||||
LOG.error("Cannot parse XML data for TV show")
|
LOG.error("Cannot parse XML data for TV show")
|
||||||
return
|
return
|
||||||
|
@ -690,6 +692,7 @@ class TVShows(Items):
|
||||||
"""
|
"""
|
||||||
api = API(item)
|
api = API(item)
|
||||||
plex_id = api.plex_id()
|
plex_id = api.plex_id()
|
||||||
|
LOG.debug('Adding season with plex_id %s', plex_id)
|
||||||
if not plex_id:
|
if not plex_id:
|
||||||
LOG.error('Error getting plex_id for season, skipping')
|
LOG.error('Error getting plex_id for season, skipping')
|
||||||
return
|
return
|
||||||
|
@ -740,6 +743,7 @@ class TVShows(Items):
|
||||||
api = API(item)
|
api = API(item)
|
||||||
update_item = True
|
update_item = True
|
||||||
itemid = api.plex_id()
|
itemid = api.plex_id()
|
||||||
|
LOG.debug('Adding episode with plex_id %s', itemid)
|
||||||
if not itemid:
|
if not itemid:
|
||||||
LOG.error('Error getting itemid for episode, skipping')
|
LOG.error('Error getting itemid for episode, skipping')
|
||||||
return
|
return
|
||||||
|
@ -1131,6 +1135,7 @@ class Music(Items):
|
||||||
|
|
||||||
update_item = True
|
update_item = True
|
||||||
itemid = api.plex_id()
|
itemid = api.plex_id()
|
||||||
|
LOG.debug('Adding artist with plex_id %s', itemid)
|
||||||
plex_dbitem = plex_db.getItem_byId(itemid)
|
plex_dbitem = plex_db.getItem_byId(itemid)
|
||||||
try:
|
try:
|
||||||
artistid = plex_dbitem[0]
|
artistid = plex_dbitem[0]
|
||||||
|
@ -1222,6 +1227,7 @@ class Music(Items):
|
||||||
|
|
||||||
update_item = True
|
update_item = True
|
||||||
plex_id = api.plex_id()
|
plex_id = api.plex_id()
|
||||||
|
LOG.debug('Adding album with plex_id %s', plex_id)
|
||||||
if not plex_id:
|
if not plex_id:
|
||||||
LOG.error('Error processing Album, skipping')
|
LOG.error('Error processing Album, skipping')
|
||||||
return
|
return
|
||||||
|
@ -1382,9 +1388,9 @@ class Music(Items):
|
||||||
plex_db = self.plex_db
|
plex_db = self.plex_db
|
||||||
artwork = self.artwork
|
artwork = self.artwork
|
||||||
api = API(item)
|
api = API(item)
|
||||||
|
|
||||||
update_item = True
|
update_item = True
|
||||||
itemid = api.plex_id()
|
itemid = api.plex_id()
|
||||||
|
LOG.debug('Adding song with plex_id %s', itemid)
|
||||||
if not itemid:
|
if not itemid:
|
||||||
LOG.error('Error processing Song; skipping')
|
LOG.error('Error processing Song; skipping')
|
||||||
return
|
return
|
||||||
|
|
|
@ -5,13 +5,9 @@ Connect to the Kodi databases (video and music) and operate on them
|
||||||
"""
|
"""
|
||||||
from __future__ import absolute_import, division, unicode_literals
|
from __future__ import absolute_import, division, unicode_literals
|
||||||
from logging import getLogger
|
from logging import getLogger
|
||||||
from ntpath import dirname
|
|
||||||
from sqlite3 import IntegrityError
|
from sqlite3 import IntegrityError
|
||||||
|
|
||||||
from . import artwork
|
from . import artwork, utils, variables as v, state, path_ops
|
||||||
from . import utils
|
|
||||||
from . import variables as v
|
|
||||||
from . import state
|
|
||||||
|
|
||||||
###############################################################################
|
###############################################################################
|
||||||
|
|
||||||
|
@ -104,17 +100,30 @@ class KodiDBMethods(object):
|
||||||
1,
|
1,
|
||||||
0))
|
0))
|
||||||
|
|
||||||
|
def setup_music_db_dummy_entries(self):
|
||||||
|
"""
|
||||||
|
Kodi Krypton Krypton has some dummy first entries that we might've
|
||||||
|
deleted
|
||||||
|
idArtist: 1 strArtist: [Missing Tag]
|
||||||
|
strMusicBrainzArtistID: Artist Tag Missing
|
||||||
|
"""
|
||||||
|
query = '''
|
||||||
|
INSERT OR REPLACE INTO artist(
|
||||||
|
idArtist, strArtist, strMusicBrainzArtistID)
|
||||||
|
VALUES (?, ?, ?)
|
||||||
|
'''
|
||||||
|
self.cursor.execute(query, (1,
|
||||||
|
'[Missing Tag]',
|
||||||
|
'Artist Tag Missing'))
|
||||||
|
|
||||||
def parent_path_id(self, path):
|
def parent_path_id(self, path):
|
||||||
"""
|
"""
|
||||||
Video DB: Adds all subdirectories to path table while setting a "trail"
|
Video DB: Adds all subdirectories to path table while setting a "trail"
|
||||||
of parent path ids
|
of parent path ids
|
||||||
"""
|
"""
|
||||||
if "\\" in path:
|
parentpath = path_ops.path.abspath(
|
||||||
# Local path
|
path_ops.path.join(path,
|
||||||
parentpath = "%s\\" % dirname(dirname(path))
|
path_ops.decode_path(path_ops.path.pardir)))
|
||||||
else:
|
|
||||||
# Network path
|
|
||||||
parentpath = "%s/" % dirname(dirname(path))
|
|
||||||
pathid = self.get_path(parentpath)
|
pathid = self.get_path(parentpath)
|
||||||
if pathid is None:
|
if pathid is None:
|
||||||
self.cursor.execute("SELECT COALESCE(MAX(idPath),0) FROM path")
|
self.cursor.execute("SELECT COALESCE(MAX(idPath),0) FROM path")
|
||||||
|
@ -125,6 +134,8 @@ class KodiDBMethods(object):
|
||||||
VALUES (?, ?, ?)
|
VALUES (?, ?, ?)
|
||||||
'''
|
'''
|
||||||
self.cursor.execute(query, (pathid, parentpath, datetime))
|
self.cursor.execute(query, (pathid, parentpath, datetime))
|
||||||
|
if parentpath != path:
|
||||||
|
# In case we end up having media in the filesystem root, C:\
|
||||||
parent_id = self.parent_path_id(parentpath)
|
parent_id = self.parent_path_id(parentpath)
|
||||||
query = 'UPDATE path SET idParentPath = ? WHERE idPath = ?'
|
query = 'UPDATE path SET idParentPath = ? WHERE idPath = ?'
|
||||||
self.cursor.execute(query, (parent_id, pathid))
|
self.cursor.execute(query, (parent_id, pathid))
|
||||||
|
@ -297,11 +308,13 @@ class KodiDBMethods(object):
|
||||||
(path_id,))
|
(path_id,))
|
||||||
|
|
||||||
def _modify_link_and_table(self, kodi_id, kodi_type, entries, link_table,
|
def _modify_link_and_table(self, kodi_id, kodi_type, entries, link_table,
|
||||||
table, key):
|
table, key, first_id=None):
|
||||||
|
first_id = first_id if first_id is not None else 1
|
||||||
query = '''
|
query = '''
|
||||||
SELECT %s FROM %s WHERE name = ? COLLATE NOCASE LIMIT 1
|
SELECT %s FROM %s WHERE name = ? COLLATE NOCASE LIMIT 1
|
||||||
''' % (key, table)
|
''' % (key, table)
|
||||||
query_id = 'SELECT COALESCE(MAX(%s), 0) FROM %s' % (key, table)
|
query_id = ('SELECT COALESCE(MAX(%s), %s) FROM %s'
|
||||||
|
% (key, first_id - 1, table))
|
||||||
query_new = ('INSERT INTO %s(%s, name) values(?, ?)'
|
query_new = ('INSERT INTO %s(%s, name) values(?, ?)'
|
||||||
% (table, key))
|
% (table, key))
|
||||||
entry_ids = []
|
entry_ids = []
|
||||||
|
@ -911,12 +924,8 @@ class KodiDBMethods(object):
|
||||||
except TypeError:
|
except TypeError:
|
||||||
# Krypton has a dummy first entry idArtist: 1 strArtist:
|
# Krypton has a dummy first entry idArtist: 1 strArtist:
|
||||||
# [Missing Tag] strMusicBrainzArtistID: Artist Tag Missing
|
# [Missing Tag] strMusicBrainzArtistID: Artist Tag Missing
|
||||||
if v.KODIVERSION >= 17:
|
|
||||||
self.cursor.execute(
|
self.cursor.execute(
|
||||||
"SELECT COALESCE(MAX(idArtist),1) FROM artist")
|
"SELECT COALESCE(MAX(idArtist),1) FROM artist")
|
||||||
else:
|
|
||||||
self.cursor.execute(
|
|
||||||
"SELECT COALESCE(MAX(idArtist),0) FROM artist")
|
|
||||||
artistid = self.cursor.fetchone()[0] + 1
|
artistid = self.cursor.fetchone()[0] + 1
|
||||||
query = '''
|
query = '''
|
||||||
INSERT INTO artist(idArtist, strArtist,
|
INSERT INTO artist(idArtist, strArtist,
|
||||||
|
|
|
@ -1543,9 +1543,13 @@ class LibrarySync(Thread):
|
||||||
LOG.info("Db version: %s", utils.settings('dbCreatedWithVersion'))
|
LOG.info("Db version: %s", utils.settings('dbCreatedWithVersion'))
|
||||||
|
|
||||||
LOG.info('Refreshing video nodes and playlists now')
|
LOG.info('Refreshing video nodes and playlists now')
|
||||||
# Setup the paths for addon-paths (even when using direct paths)
|
|
||||||
with kodidb.GetKodiDB('video') as kodi_db:
|
with kodidb.GetKodiDB('video') as kodi_db:
|
||||||
|
# Setup the paths for addon-paths (even when using direct paths)
|
||||||
kodi_db.setup_path_table()
|
kodi_db.setup_path_table()
|
||||||
|
with kodidb.GetKodiDB('music') as kodi_db:
|
||||||
|
# Hack for a dummy genre entry - even when we're not using
|
||||||
|
# Plex Music
|
||||||
|
kodi_db.setup_music_db_dummy_entries()
|
||||||
utils.window('plex_dbScan', clear=True)
|
utils.window('plex_dbScan', clear=True)
|
||||||
state.DB_SCAN = False
|
state.DB_SCAN = False
|
||||||
playlist_monitor = None
|
playlist_monitor = None
|
||||||
|
|
|
@ -5,7 +5,6 @@ Various functions and decorators for PKC
|
||||||
"""
|
"""
|
||||||
from __future__ import absolute_import, division, unicode_literals
|
from __future__ import absolute_import, division, unicode_literals
|
||||||
from logging import getLogger
|
from logging import getLogger
|
||||||
from cProfile import Profile
|
|
||||||
from pstats import Stats
|
from pstats import Stats
|
||||||
from sqlite3 import connect, OperationalError
|
from sqlite3 import connect, OperationalError
|
||||||
from datetime import datetime, timedelta
|
from datetime import datetime, timedelta
|
||||||
|
@ -580,31 +579,6 @@ def reset(ask_user=True):
|
||||||
reboot_kodi()
|
reboot_kodi()
|
||||||
|
|
||||||
|
|
||||||
def profiling(sortby="cumulative"):
|
|
||||||
"""
|
|
||||||
Will print results to Kodi log. Must be enabled in the Python source code
|
|
||||||
"""
|
|
||||||
def decorator(func):
|
|
||||||
"""
|
|
||||||
decorator construct
|
|
||||||
"""
|
|
||||||
def wrapper(*args, **kwargs):
|
|
||||||
"""
|
|
||||||
wrapper construct
|
|
||||||
"""
|
|
||||||
profile = Profile()
|
|
||||||
profile.enable()
|
|
||||||
result = func(*args, **kwargs)
|
|
||||||
profile.disable()
|
|
||||||
string_io = StringIO()
|
|
||||||
stats = Stats(profile, stream=string_io).sort_stats(sortby)
|
|
||||||
stats.print_stats()
|
|
||||||
LOG.info(string_io.getvalue())
|
|
||||||
return result
|
|
||||||
return wrapper
|
|
||||||
return decorator
|
|
||||||
|
|
||||||
|
|
||||||
def compare_version(current, minimum):
|
def compare_version(current, minimum):
|
||||||
"""
|
"""
|
||||||
Returns True if current is >= then minimum. False otherwise. Returns True
|
Returns True if current is >= then minimum. False otherwise. Returns True
|
||||||
|
|
Loading…
Reference in a new issue