+ % else:
+
+
+
+ ${item['title']}
+
+
+ % endif
% endif
% endfor
diff --git a/plexpy/datafactory.py b/plexpy/datafactory.py
index 1e979cd2..7beec862 100644
--- a/plexpy/datafactory.py
+++ b/plexpy/datafactory.py
@@ -179,13 +179,6 @@ class DataFactory(object):
group_by = 'session_history.reference_id' if grouping else 'session_history.id'
sort_type = 'total_plays' if stats_type == 0 else 'total_duration'
- library_cond = ''
- if session.get_session_libraries():
- library_cond = 'AND ('
- for section_id in session.get_session_libraries():
- library_cond += 'session_history_metadata.section_id = %s OR ' % section_id
- library_cond = library_cond.rstrip(' OR ') + ') '
-
home_stats = []
for stat in stats_cards:
@@ -193,6 +186,7 @@ class DataFactory(object):
top_tv = []
try:
query = 'SELECT t.id, t.grandparent_title, t.grandparent_rating_key, t.grandparent_thumb, t.section_id, ' \
+ 't.media_type, t.content_rating, t.labels, ' \
'MAX(t.started) AS last_watch, COUNT(t.id) AS total_plays, SUM(t.d) AS total_duration ' \
'FROM (SELECT *, SUM(CASE WHEN stopped > 0 THEN (stopped - started) - ' \
' (CASE WHEN paused_counter IS NULL THEN 0 ELSE paused_counter END) ELSE 0 END) ' \
@@ -201,11 +195,11 @@ class DataFactory(object):
' JOIN session_history_metadata ON session_history_metadata.id = session_history.id ' \
' WHERE datetime(session_history.stopped, "unixepoch", "localtime") ' \
' >= datetime("now", "-%s days", "localtime") ' \
- ' AND session_history.media_type = "episode" %s' \
+ ' AND session_history.media_type = "episode" ' \
' GROUP BY %s) AS t ' \
'GROUP BY t.grandparent_title ' \
'ORDER BY %s DESC ' \
- 'LIMIT %s ' % (time_range, library_cond, group_by, sort_type, stats_count)
+ 'LIMIT %s ' % (time_range, group_by, sort_type, stats_count)
result = monitor_db.select(query)
except Exception as e:
logger.warn(u"PlexPy DataFactory :: Unable to execute database query for get_home_stats: top_tv: %s." % e)
@@ -221,6 +215,9 @@ class DataFactory(object):
'grandparent_thumb': item['grandparent_thumb'],
'thumb': '',
'section_id': item['section_id'],
+ 'media_type': item['media_type'],
+ 'content_rating': item['content_rating'],
+ 'labels': item['labels'].split(';') if item['labels'] else (),
'user': '',
'friendly_name': '',
'platform_type': '',
@@ -237,6 +234,7 @@ class DataFactory(object):
popular_tv = []
try:
query = 'SELECT t.id, t.grandparent_title, t.grandparent_rating_key, t.grandparent_thumb, t.section_id, ' \
+ 't.media_type, t.content_rating, t.labels, ' \
'COUNT(DISTINCT t.user_id) AS users_watched, ' \
'MAX(t.started) AS last_watch, COUNT(t.id) as total_plays, SUM(t.d) AS total_duration ' \
'FROM (SELECT *, SUM(CASE WHEN stopped > 0 THEN (stopped - started) - ' \
@@ -246,11 +244,11 @@ class DataFactory(object):
' JOIN session_history_metadata ON session_history_metadata.id = session_history.id ' \
' WHERE datetime(session_history.stopped, "unixepoch", "localtime") ' \
' >= datetime("now", "-%s days", "localtime") ' \
- ' AND session_history.media_type = "episode" %s' \
+ ' AND session_history.media_type = "episode" ' \
' GROUP BY %s) AS t ' \
'GROUP BY t.grandparent_title ' \
'ORDER BY users_watched DESC, %s DESC ' \
- 'LIMIT %s ' % (time_range, library_cond, group_by, sort_type, stats_count)
+ 'LIMIT %s ' % (time_range, group_by, sort_type, stats_count)
result = monitor_db.select(query)
except Exception as e:
logger.warn(u"PlexPy DataFactory :: Unable to execute database query for get_home_stats: popular_tv: %s." % e)
@@ -265,6 +263,9 @@ class DataFactory(object):
'grandparent_thumb': item['grandparent_thumb'],
'thumb': '',
'section_id': item['section_id'],
+ 'media_type': item['media_type'],
+ 'content_rating': item['content_rating'],
+ 'labels': item['labels'].split(';') if item['labels'] else (),
'user': '',
'friendly_name': '',
'platform_type': '',
@@ -280,6 +281,7 @@ class DataFactory(object):
top_movies = []
try:
query = 'SELECT t.id, t.full_title, t.rating_key, t.thumb, t.section_id, ' \
+ 't.media_type, t.content_rating, t.labels, ' \
'MAX(t.started) AS last_watch, COUNT(t.id) AS total_plays, SUM(t.d) AS total_duration ' \
'FROM (SELECT *, SUM(CASE WHEN stopped > 0 THEN (stopped - started) - ' \
' (CASE WHEN paused_counter IS NULL THEN 0 ELSE paused_counter END) ELSE 0 END) ' \
@@ -288,11 +290,11 @@ class DataFactory(object):
' JOIN session_history_metadata ON session_history_metadata.id = session_history.id ' \
' WHERE datetime(session_history.stopped, "unixepoch", "localtime") ' \
' >= datetime("now", "-%s days", "localtime") ' \
- ' AND session_history.media_type = "movie" %s' \
+ ' AND session_history.media_type = "movie" ' \
' GROUP BY %s) AS t ' \
'GROUP BY t.full_title ' \
'ORDER BY %s DESC ' \
- 'LIMIT %s ' % (time_range, library_cond, group_by, sort_type, stats_count)
+ 'LIMIT %s ' % (time_range, group_by, sort_type, stats_count)
result = monitor_db.select(query)
except Exception as e:
logger.warn(u"PlexPy DataFactory :: Unable to execute database query for get_home_stats: top_movies: %s." % e)
@@ -308,6 +310,9 @@ class DataFactory(object):
'grandparent_thumb': '',
'thumb': item['thumb'],
'section_id': item['section_id'],
+ 'media_type': item['media_type'],
+ 'content_rating': item['content_rating'],
+ 'labels': item['labels'].split(';') if item['labels'] else (),
'user': '',
'friendly_name': '',
'platform_type': '',
@@ -324,6 +329,7 @@ class DataFactory(object):
popular_movies = []
try:
query = 'SELECT t.id, t.full_title, t.rating_key, t.thumb, t.section_id, ' \
+ 't.media_type, t.content_rating, t.labels, ' \
'COUNT(DISTINCT t.user_id) AS users_watched, ' \
'MAX(t.started) AS last_watch, COUNT(t.id) as total_plays, SUM(t.d) AS total_duration ' \
'FROM (SELECT *, SUM(CASE WHEN stopped > 0 THEN (stopped - started) - ' \
@@ -333,11 +339,11 @@ class DataFactory(object):
' JOIN session_history_metadata ON session_history_metadata.id = session_history.id ' \
' WHERE datetime(session_history.stopped, "unixepoch", "localtime") ' \
' >= datetime("now", "-%s days", "localtime") ' \
- ' AND session_history.media_type = "movie" %s' \
+ ' AND session_history.media_type = "movie" ' \
' GROUP BY %s) AS t ' \
'GROUP BY t.full_title ' \
'ORDER BY users_watched DESC, %s DESC ' \
- 'LIMIT %s ' % (time_range, library_cond, group_by, sort_type, stats_count)
+ 'LIMIT %s ' % (time_range, group_by, sort_type, stats_count)
result = monitor_db.select(query)
except Exception as e:
logger.warn(u"PlexPy DataFactory :: Unable to execute database query for get_home_stats: popular_movies: %s." % e)
@@ -352,6 +358,9 @@ class DataFactory(object):
'grandparent_thumb': '',
'thumb': item['thumb'],
'section_id': item['section_id'],
+ 'media_type': item['media_type'],
+ 'content_rating': item['content_rating'],
+ 'labels': item['labels'].split(';') if item['labels'] else (),
'user': '',
'friendly_name': '',
'platform_type': '',
@@ -367,6 +376,7 @@ class DataFactory(object):
top_music = []
try:
query = 'SELECT t.id, t.grandparent_title, t.grandparent_rating_key, t.grandparent_thumb, t.section_id, ' \
+ 't.media_type, t.content_rating, t.labels, ' \
'MAX(t.started) AS last_watch, COUNT(t.id) AS total_plays, SUM(t.d) AS total_duration ' \
'FROM (SELECT *, SUM(CASE WHEN stopped > 0 THEN (stopped - started) - ' \
' (CASE WHEN paused_counter IS NULL THEN 0 ELSE paused_counter END) ELSE 0 END) ' \
@@ -375,11 +385,11 @@ class DataFactory(object):
' JOIN session_history_metadata ON session_history_metadata.id = session_history.id ' \
' WHERE datetime(session_history.stopped, "unixepoch", "localtime") ' \
' >= datetime("now", "-%s days", "localtime") ' \
- ' AND session_history.media_type = "track" %s' \
+ ' AND session_history.media_type = "track" ' \
' GROUP BY %s) AS t ' \
'GROUP BY t.grandparent_title ' \
'ORDER BY %s DESC ' \
- 'LIMIT %s ' % (time_range, library_cond, group_by, sort_type, stats_count)
+ 'LIMIT %s ' % (time_range, group_by, sort_type, stats_count)
result = monitor_db.select(query)
except Exception as e:
logger.warn(u"PlexPy DataFactory :: Unable to execute database query for get_home_stats: top_music: %s." % e)
@@ -395,6 +405,9 @@ class DataFactory(object):
'grandparent_thumb': item['grandparent_thumb'],
'thumb': '',
'section_id': item['section_id'],
+ 'media_type': item['media_type'],
+ 'content_rating': item['content_rating'],
+ 'labels': item['labels'].split(';') if item['labels'] else (),
'user': '',
'friendly_name': '',
'platform_type': '',
@@ -411,6 +424,7 @@ class DataFactory(object):
popular_music = []
try:
query = 'SELECT t.id, t.grandparent_title, t.grandparent_rating_key, t.grandparent_thumb, t.section_id, ' \
+ 't.media_type, t.content_rating, t.labels, ' \
'COUNT(DISTINCT t.user_id) AS users_watched, ' \
'MAX(t.started) AS last_watch, COUNT(t.id) as total_plays, SUM(t.d) AS total_duration ' \
'FROM (SELECT *, SUM(CASE WHEN stopped > 0 THEN (stopped - started) - ' \
@@ -420,11 +434,11 @@ class DataFactory(object):
' JOIN session_history_metadata ON session_history_metadata.id = session_history.id ' \
' WHERE datetime(session_history.stopped, "unixepoch", "localtime") ' \
' >= datetime("now", "-%s days", "localtime") ' \
- ' AND session_history.media_type = "track" %s' \
+ ' AND session_history.media_type = "track" ' \
' GROUP BY %s) AS t ' \
'GROUP BY t.grandparent_title ' \
'ORDER BY users_watched DESC, %s DESC ' \
- 'LIMIT %s ' % (time_range, library_cond, group_by, sort_type, stats_count)
+ 'LIMIT %s ' % (time_range, group_by, sort_type, stats_count)
result = monitor_db.select(query)
except Exception as e:
logger.warn(u"PlexPy DataFactory :: Unable to execute database query for get_home_stats: popular_music: %s." % e)
@@ -439,6 +453,9 @@ class DataFactory(object):
'grandparent_thumb': item['grandparent_thumb'],
'thumb': '',
'section_id': item['section_id'],
+ 'media_type': item['media_type'],
+ 'content_rating': item['content_rating'],
+ 'labels': item['labels'].split(';') if item['labels'] else (),
'user': '',
'friendly_name': '',
'platform_type': '',
@@ -501,7 +518,7 @@ class DataFactory(object):
home_stats.append({'stat_id': stat,
'stat_type': sort_type,
- 'rows': session.mask_session_info(top_users)})
+ 'rows': session.mask_session_info(top_users, mask_metadata=False)})
elif stat == 'top_platforms':
top_platform = []
@@ -547,13 +564,14 @@ class DataFactory(object):
home_stats.append({'stat_id': stat,
'stat_type': sort_type,
- 'rows': session.mask_session_info(top_platform)})
+ 'rows': session.mask_session_info(top_platform, mask_metadata=False)})
elif stat == 'last_watched':
last_watched = []
try:
query = 'SELECT t.id, t.full_title, t.rating_key, t.thumb, t.grandparent_thumb, ' \
't.user, t.user_id, t.custom_avatar_url as user_thumb, t.player, t.section_id, ' \
+ 't.media_type, t.content_rating, t.labels, ' \
'(CASE WHEN t.friendly_name IS NULL THEN t.username ELSE t.friendly_name END) ' \
' AS friendly_name, ' \
'MAX(t.started) AS last_watch, ' \
@@ -566,12 +584,12 @@ class DataFactory(object):
' WHERE datetime(session_history.stopped, "unixepoch", "localtime") ' \
' >= datetime("now", "-%s days", "localtime") ' \
' AND (session_history.media_type = "movie" ' \
- ' OR session_history_metadata.media_type = "episode") %s' \
+ ' OR session_history_metadata.media_type = "episode") ' \
' GROUP BY %s) AS t ' \
'WHERE percent_complete >= %s ' \
'GROUP BY t.id ' \
'ORDER BY last_watch DESC ' \
- 'LIMIT %s' % (time_range, library_cond, group_by, notify_watched_percent, stats_count)
+ 'LIMIT %s' % (time_range, group_by, notify_watched_percent, stats_count)
result = monitor_db.select(query)
except Exception as e:
logger.warn(u"PlexPy DataFactory :: Unable to execute database query for get_home_stats: last_watched: %s." % e)
@@ -593,6 +611,9 @@ class DataFactory(object):
'thumb': thumb,
'grandparent_thumb': item['grandparent_thumb'],
'section_id': item['section_id'],
+ 'media_type': item['media_type'],
+ 'content_rating': item['content_rating'],
+ 'labels': item['labels'].split(';') if item['labels'] else (),
'last_watch': item['last_watch'],
'player': item['player']
}
@@ -686,6 +707,9 @@ class DataFactory(object):
def get_library_stats(self, library_cards=[]):
monitor_db = database.MonitorDatabase()
+ if session.get_session_shared_libraries():
+ library_cards = session.get_session_shared_libraries()
+
library_stats = []
for id in library_cards:
@@ -718,7 +742,7 @@ class DataFactory(object):
}
library_stats.append(library)
- return session.filter_session_info(library_stats, filter_key='section_id')
+ return library_stats
def get_stream_details(self, row_id=None):
monitor_db = database.MonitorDatabase()
diff --git a/plexpy/datatables.py b/plexpy/datatables.py
index 88275b3c..293c3b59 100644
--- a/plexpy/datatables.py
+++ b/plexpy/datatables.py
@@ -92,12 +92,18 @@ class DataTables(object):
if isinstance(w[1], (list, tuple)) and len(w[1]):
c_where += '('
for w_ in w[1]:
- c_where += w[0] + ' = ? OR '
- args.append(w_)
+ if w_ == None:
+ c_where += w[0] + ' IS NULL OR '
+ else:
+ c_where += w[0] + ' = ? OR '
+ args.append(w_)
c_where = c_where.rstrip(' OR ') + ') AND '
else:
- c_where += w[0] + ' = ? AND '
- args.append(w[1])
+ if w[1] == None:
+ c_where += w[0] + ' IS NULL AND '
+ else:
+ c_where += w[0] + ' = ? AND '
+ args.append(w[1])
if c_where:
c_where = 'WHERE ' + c_where.rstrip(' AND ')
diff --git a/plexpy/libraries.py b/plexpy/libraries.py
index 24d9bd7a..f7228c92 100644
--- a/plexpy/libraries.py
+++ b/plexpy/libraries.py
@@ -182,8 +182,8 @@ class Libraries(object):
custom_where = [['library_sections.deleted_section', 0]]
- if session.get_session_libraries():
- custom_where.append(['library_sections.section_id', session.get_session_libraries()])
+ if session.get_session_shared_libraries():
+ custom_where.append(['library_sections.section_id', session.get_session_shared_libraries()])
columns = ['library_sections.section_id',
'library_sections.section_name',
@@ -210,6 +210,8 @@ class Libraries(object):
'session_history_metadata.year',
'session_history_metadata.media_index',
'session_history_metadata.parent_media_index',
+ 'session_history_metadata.content_rating',
+ 'session_history_metadata.labels',
'library_sections.do_notify',
'library_sections.do_notify_created',
'library_sections.keep_history'
@@ -271,6 +273,8 @@ class Libraries(object):
'year': item['year'],
'media_index': item['media_index'],
'parent_media_index': item['parent_media_index'],
+ 'content_rating': item['content_rating'],
+ 'labels': item['labels'].split(';') if item['labels'] else (),
'do_notify': helpers.checked(item['do_notify']),
'do_notify_created': helpers.checked(item['do_notify_created']),
'keep_history': helpers.checked(item['keep_history'])
@@ -280,7 +284,7 @@ class Libraries(object):
dict = {'recordsFiltered': query['filteredCount'],
'recordsTotal': query['totalCount'],
- 'data': rows,
+ 'data': session.mask_session_info(rows),
'draw': query['draw']
}
@@ -787,7 +791,7 @@ class Libraries(object):
query = 'SELECT session_history.id, session_history.media_type, ' \
'session_history.rating_key, session_history.parent_rating_key, session_history.grandparent_rating_key, ' \
'title, parent_title, grandparent_title, thumb, parent_thumb, grandparent_thumb, media_index, parent_media_index, ' \
- 'year, started, user ' \
+ 'year, started, user, content_rating, labels, section_id ' \
'FROM session_history_metadata ' \
'JOIN session_history ON session_history_metadata.id = session_history.id ' \
'WHERE section_id = ? ' \
@@ -822,11 +826,14 @@ class Libraries(object):
'parent_media_index': row['parent_media_index'],
'year': row['year'],
'time': row['started'],
- 'user': row['user']
+ 'user': row['user'],
+ 'section_id': row['section_id'],
+ 'content_rating': row['content_rating'],
+ 'labels': row['labels'].split(';') if row['labels'] else (),
}
recently_watched.append(recent_output)
- return recently_watched
+ return session.mask_session_info(recently_watched)
def get_sections(self):
monitor_db = database.MonitorDatabase()
diff --git a/plexpy/plextv.py b/plexpy/plextv.py
index 4a122baf..74e21881 100644
--- a/plexpy/plextv.py
+++ b/plexpy/plextv.py
@@ -131,9 +131,7 @@ class PlexTV(object):
self.password = password
self.ssl_verify = plexpy.CONFIG.VERIFY_SSL_CERT
- if token == 'admin':
- token = plexpy.CONFIG.PMS_TOKEN
- elif not token:
+ if not token:
# Check if we should use the admin token, or the guest server token
if session.get_session_user_id():
user_data = users.Users()
diff --git a/plexpy/pmsconnect.py b/plexpy/pmsconnect.py
index f0ac4b66..cbe2118b 100644
--- a/plexpy/pmsconnect.py
+++ b/plexpy/pmsconnect.py
@@ -112,9 +112,7 @@ class PmsConnect(object):
port = plexpy.CONFIG.PMS_PORT
self.protocol = 'http'
- if token == 'admin':
- token = plexpy.CONFIG.PMS_TOKEN
- elif not token:
+ if not token:
# Check if we should use the admin token, or the guest server token
if session.get_session_user_id():
user_data = users.Users()
@@ -1077,6 +1075,11 @@ class PmsConnect(object):
else:
machine_id = helpers.get_xml_attr(session.getElementsByTagName('Player')[0], 'machineIdentifier')
+ labels = []
+ if session.getElementsByTagName('Label'):
+ for label in session.getElementsByTagName('Label'):
+ labels.append(helpers.get_xml_attr(label, 'tag'))
+
session_output = {'session_key': helpers.get_xml_attr(session, 'sessionKey'),
'section_id': helpers.get_xml_attr(session, 'librarySectionID'),
'media_index': helpers.get_xml_attr(session, 'index'),
@@ -1102,6 +1105,8 @@ class PmsConnect(object):
'rating_key': helpers.get_xml_attr(session, 'ratingKey'),
'parent_rating_key': helpers.get_xml_attr(session, 'parentRatingKey'),
'grandparent_rating_key': helpers.get_xml_attr(session, 'grandparentRatingKey'),
+ 'content_rating': helpers.get_xml_attr(session, 'contentRating'),
+ 'labels': labels,
'transcode_key': transcode_key,
'throttled': throttled,
'transcode_progress': int(round(helpers.cast_to_float(transcode_progress), 0)),
@@ -1177,7 +1182,6 @@ class PmsConnect(object):
transcode_container = ''
transcode_protocol = ''
- media_info = session.getElementsByTagName('Media')[0]
if media_info.getElementsByTagName('Part'):
indexes = helpers.get_xml_attr(media_info.getElementsByTagName('Part')[0], 'indexes')
part_id = helpers.get_xml_attr(media_info.getElementsByTagName('Part')[0], 'id')
@@ -1202,6 +1206,11 @@ class PmsConnect(object):
else:
machine_id = helpers.get_xml_attr(session.getElementsByTagName('Player')[0], 'machineIdentifier')
+ labels = []
+ if session.getElementsByTagName('Label'):
+ for label in session.getElementsByTagName('Label'):
+ labels.append(helpers.get_xml_attr(label, 'tag'))
+
if helpers.get_xml_attr(session, 'type') == 'episode':
session_output = {'session_key': helpers.get_xml_attr(session, 'sessionKey'),
'section_id': helpers.get_xml_attr(session, 'librarySectionID'),
@@ -1228,6 +1237,8 @@ class PmsConnect(object):
'rating_key': helpers.get_xml_attr(session, 'ratingKey'),
'parent_rating_key': helpers.get_xml_attr(session, 'parentRatingKey'),
'grandparent_rating_key': helpers.get_xml_attr(session, 'grandparentRatingKey'),
+ 'content_rating': helpers.get_xml_attr(session, 'contentRating'),
+ 'labels': labels,
'transcode_key': transcode_key,
'throttled': throttled,
'transcode_progress': int(round(helpers.cast_to_float(transcode_progress), 0)),
@@ -1287,6 +1298,8 @@ class PmsConnect(object):
'rating_key': helpers.get_xml_attr(session, 'ratingKey'),
'parent_rating_key': helpers.get_xml_attr(session, 'parentRatingKey'),
'grandparent_rating_key': helpers.get_xml_attr(session, 'grandparentRatingKey'),
+ 'content_rating': helpers.get_xml_attr(session, 'contentRating'),
+ 'labels': labels,
'transcode_key': transcode_key,
'throttled': throttled,
'transcode_progress': int(round(helpers.cast_to_float(transcode_progress), 0)),
@@ -1346,6 +1359,8 @@ class PmsConnect(object):
'rating_key': helpers.get_xml_attr(session, 'ratingKey'),
'parent_rating_key': helpers.get_xml_attr(session, 'parentRatingKey'),
'grandparent_rating_key': helpers.get_xml_attr(session, 'grandparentRatingKey'),
+ 'content_rating': helpers.get_xml_attr(session, 'contentRating'),
+ 'labels': labels,
'transcode_key': transcode_key,
'throttled': throttled,
'transcode_progress': int(round(helpers.cast_to_float(transcode_progress), 0)),
@@ -1415,6 +1430,11 @@ class PmsConnect(object):
else:
machine_id = helpers.get_xml_attr(session.getElementsByTagName('Player')[0], 'machineIdentifier')
+ labels = []
+ if session.getElementsByTagName('Label'):
+ for label in session.getElementsByTagName('Label'):
+ labels.append(helpers.get_xml_attr(label, 'tag'))
+
session_output = {'session_key': helpers.get_xml_attr(session, 'sessionKey'),
'section_id': helpers.get_xml_attr(session, 'librarySectionID'),
'media_index': helpers.get_xml_attr(session, 'index'),
@@ -1440,6 +1460,8 @@ class PmsConnect(object):
'rating_key': helpers.get_xml_attr(session, 'ratingKey'),
'parent_rating_key': helpers.get_xml_attr(session, 'parentRatingKey'),
'grandparent_rating_key': helpers.get_xml_attr(session, 'grandparentRatingKey'),
+ 'content_rating': helpers.get_xml_attr(session, 'contentRating'),
+ 'labels': labels,
'transcode_key': transcode_key,
'throttled': throttled,
'transcode_progress': int(round(helpers.cast_to_float(transcode_progress), 0)),
diff --git a/plexpy/session.py b/plexpy/session.py
index f9047ac2..cd72257c 100644
--- a/plexpy/session.py
+++ b/plexpy/session.py
@@ -14,7 +14,6 @@
# along with PlexPy. If not, see
.
import cherrypy
-import threading
from plexpy import common
@@ -28,7 +27,6 @@ def get_session_info():
_session = {'user_id': None,
'user': None,
'user_group': 'admin',
- 'user_libraries': None,
'expiry': None}
try:
return cherrypy.session.get(SESSION_KEY, _session)
@@ -49,12 +47,49 @@ def get_session_user_id():
_session = get_session_info()
return str(_session['user_id']) if _session and _session['user_id'] else None
-def get_session_libraries():
+def get_session_shared_libraries():
"""
Returns a tuple of section_id for the current logged in session
"""
- _session = get_session_info()
- return _session['user_libraries'] if _session and _session['user_libraries'] else None
+ from plexpy import users
+ user_details = users.Users().get_details(user_id=get_session_user_id())
+ return user_details['shared_libraries']
+
+def get_session_library_filters():
+ """
+ Returns a dict of library filters for the current logged in session
+
+ {'content_rating': ('PG', 'R')
+ 'labels': ('label1', label2')},
+
+ """
+ from plexpy import users
+ filters = users.Users().get_filters(user_id=get_session_user_id())
+ return filters
+
+def get_session_library_filters_type(filters, media_type=None):
+ """
+ Returns a dict of library filters for the current logged in session
+
+ {'content_rating': ('PG', 'R')
+ 'labels': ('label1', label2')},
+
+ """
+ if media_type == 'movie':
+ filters = filters.get('filter_movies', ())
+ elif media_type == 'show' or media_type == 'season' or media_type == 'episode':
+ filters = filters.get('filter_tv', ())
+ elif media_type == 'artist' or media_type == 'album' or media_type == 'track':
+ filters = filters.get('filter_music', ())
+ elif media_type == 'photo' or media_type == 'photoAlbum' or media_type == 'picture':
+ filters = filters.get('filter_photos', ())
+ else:
+ filters = filters.get('filter_all', ())
+
+ content_rating = filters.get('content_rating', ())
+ labels = filters.get('labels', ())
+
+ return content_rating, tuple(f.lower() for f in labels)
def allow_session_user(user_id):
"""
@@ -69,74 +104,11 @@ def allow_session_library(section_id):
"""
Returns True or False if the section_id is allowed for the current logged in session
"""
- session_library_ids = get_session_libraries()
+ session_library_ids = get_session_shared_libraries()
if session_library_ids and str(section_id) not in session_library_ids:
return False
return True
-def filter_session_info(list_of_dicts, filter_key=None):
- """
- Filters a list of dictionary items to only return the info for the current logged in session
- """
- session_user_id = get_session_user_id()
- session_library_ids = get_session_libraries()
-
- list_of_dicts = friendly_name_to_username(list_of_dicts)
-
- if filter_key == 'user_id' and session_user_id:
- return [d for d in list_of_dicts if str(d.get('user_id','')) == session_user_id]
-
- elif filter_key == 'section_id' and session_library_ids:
- return [d for d in list_of_dicts if str(d.get('section_id','')) in session_library_ids]
-
- return list_of_dicts
-
-def mask_session_info(list_of_dicts, mask_metadata=True):
- """
- Masks user info in a list of dictionary items to only display info for the current logged in session
- """
- session_user = get_session_user()
- session_user_id = get_session_user_id()
- session_library_ids = get_session_libraries()
-
- keys_to_mask = {'user_id': '',
- 'user': 'Plex User',
- 'friendly_name': 'Plex User',
- 'user_thumb': common.DEFAULT_USER_THUMB,
- 'ip_address': 'N/A',
- 'machine_id': '',
- 'player': 'Player'
- }
-
- metadata_to_mask = {'media_index': '',
- 'parent_media_index': '',
- 'art': common.DEFAULT_ART,
- 'parent_thumb': common.DEFAULT_POSTER_THUMB,
- 'grandparent_thumb': common.DEFAULT_POSTER_THUMB,
- 'thumb': common.DEFAULT_POSTER_THUMB,
- 'bif_thumb': '',
- 'grandparent_title': '',
- 'parent_title': '',
- 'title': '',
- 'rating_key': '',
- 'parent_rating_key': '',
- 'grandparent_rating_key': '',
- 'year': ''
- }
-
- list_of_dicts = friendly_name_to_username(list_of_dicts)
-
- for d in list_of_dicts:
- if session_user_id and not (str(d.get('user_id')) == session_user_id or d.get('user') == session_user):
- for k, v in keys_to_mask.iteritems():
- if k in d: d[k] = keys_to_mask[k]
-
- if mask_metadata and session_library_ids and str(d.get('section_id','')) not in session_library_ids:
- for k, v in metadata_to_mask.iteritems():
- if k in d: d[k] = metadata_to_mask[k]
-
- return list_of_dicts
-
def friendly_name_to_username(list_of_dicts):
"""
Reverts the friendly name back to the username of the current logged in session
@@ -149,4 +121,125 @@ def friendly_name_to_username(list_of_dicts):
if 'friendly_name' in d and d['friendly_name'] != session_user:
d['friendly_name'] = session_user
+ return list_of_dicts
+
+def filter_session_info(list_of_dicts, filter_key=None):
+ """
+ Filters a list of dictionary items to only return the info for the current logged in session
+ """
+ session_user_id = get_session_user_id()
+
+ if not session_user_id:
+ return list_of_dicts
+
+ session_library_ids = get_session_shared_libraries()
+ session_library_filters = get_session_library_filters()
+
+ list_of_dicts = friendly_name_to_username(list_of_dicts)
+
+ if filter_key == 'user_id' and session_user_id:
+ return [d for d in list_of_dicts if str(d.get('user_id','')) == session_user_id]
+
+ elif filter_key == 'section_id' and session_library_ids:
+ new_list_of_dicts = []
+
+ for d in list_of_dicts:
+ if str(d.get('section_id','')) not in session_library_ids:
+ continue
+
+ if d.get('media_type'):
+ f_content_rating, f_labels = get_session_library_filters_type(session_library_filters,
+ media_type=d['media_type'])
+
+ d_content_rating = d.get('content_rating', '').lower()
+ d_labels = tuple(f.lower() for f in d.get('labels', ()))
+
+ if (not f_content_rating or set(d_content_rating).intersection(set(f_content_rating))) and \
+ (not f_labels or set(d_labels).intersection(set(f_labels))):
+ continue
+
+ new_list_of_dicts.append(d)
+
+ return new_list_of_dicts
+
+ return list_of_dicts
+
+def mask_session_info(list_of_dicts, mask_metadata=True):
+ """
+ Masks user info in a list of dictionary items to only display info for the current logged in session
+ """
+ session_user_id = get_session_user_id()
+
+ if not session_user_id:
+ return list_of_dicts
+
+ session_user = get_session_user()
+ session_library_ids = get_session_shared_libraries()
+ session_library_filters = get_session_library_filters()
+
+ keys_to_mask = {'user_id': '',
+ 'user': 'Plex User',
+ 'friendly_name': 'Plex User',
+ 'user_thumb': common.DEFAULT_USER_THUMB,
+ 'ip_address': 'N/A',
+ 'machine_id': '',
+ 'player': 'Player'
+ }
+
+ metadata_to_mask = {'media_index': '0',
+ 'parent_media_index': '0',
+ 'art': common.DEFAULT_ART,
+ 'parent_thumb': common.DEFAULT_POSTER_THUMB,
+ 'grandparent_thumb': common.DEFAULT_POSTER_THUMB,
+ 'thumb': common.DEFAULT_POSTER_THUMB,
+ 'bif_thumb': '',
+ 'grandparent_title': 'Title',
+ 'parent_title': 'Title',
+ 'title': 'Title',
+ 'rating_key': '',
+ 'parent_rating_key': '',
+ 'grandparent_rating_key': '',
+ 'year': '',
+ 'last_played': 'Title'
+ }
+
+ list_of_dicts = friendly_name_to_username(list_of_dicts)
+
+ for d in list_of_dicts:
+ if session_user_id and not (str(d.get('user_id')) == session_user_id or d.get('user') == session_user):
+ for k, v in keys_to_mask.iteritems():
+ if k in d: d[k] = keys_to_mask[k]
+
+ if not mask_metadata:
+ continue
+
+ if str(d.get('section_id','')) not in session_library_ids:
+ for k, v in metadata_to_mask.iteritems():
+ if k in d: d[k] = metadata_to_mask[k]
+ continue
+
+ media_type = d.get('media_type')
+ if media_type:
+ f_content_rating, f_labels = get_session_library_filters_type(session_library_filters,
+ media_type=d['media_type'])
+
+ if not f_content_rating and not f_labels:
+ continue
+
+ d_content_rating = d.get('content_rating', '')
+ d_labels = tuple(f.lower() for f in d.get('labels', ()))
+
+ if not f_content_rating and f_labels:
+ if set(d_labels).intersection(set(f_labels)):
+ continue
+ elif f_content_rating and not f_labels:
+ if d_content_rating in f_content_rating:
+ continue
+ elif f_content_rating and f_labels:
+ if d_content_rating in f_content_rating or set(d_labels).intersection(set(f_labels)):
+ continue
+
+ for k, v in metadata_to_mask.iteritems():
+ if k in d: d[k] = metadata_to_mask[k]
+
return list_of_dicts
\ No newline at end of file
diff --git a/plexpy/users.py b/plexpy/users.py
index 1b89e8c9..0add1508 100644
--- a/plexpy/users.py
+++ b/plexpy/users.py
@@ -16,73 +16,6 @@
import plexpy
from plexpy import logger, datatables, common, database, helpers, session
-def user_login(username=None, password=None):
- from plexpy import plextv
-
- if not username and not password:
- return None
-
- user_data = Users()
-
- # Try to login to Plex.tv to check if the user has a vaild account
- plex_tv = plextv.PlexTV(username=username, password=password)
- plex_user = plex_tv.get_token()
- if plex_user:
- user_token = plex_user['auth_token']
- user_id = plex_user['user_id']
-
- # Retrieve user token from the database and check against the Plex.tv token.
- # Also Make sure 'allow_guest' access is enabled for the user.
- # The user tokens should match if it is the same PlexPy install.
- tokens = user_data.get_tokens(user_id=user_id)
- if not tokens:
- # The user is not in the database
- return None
- elif not tokens['allow_guest'] or not user_token == tokens['user_token']:
- # Guest access is disabled, or user tokens don't match
- return None
-
- # Otherwise it is a new user or token is no longer valid.
- # Check if the user is in the database, not deleted, and 'allow_guest' access.
- user_details = user_data.get_details(user_id=user_id)
- if user_id == str(user_details['user_id']) and \
- not user_details['deleted_user'] and user_details['allow_guest']:
-
- # The user is in the database, so try to retrieve a new server token.
- # If a server token is returned, then the user is a valid friend
- plex_tv = plextv.PlexTV(token=user_token)
- server_token = plex_tv.get_server_token()
- if server_token:
-
- # Register the new user / update the access tokens.
- monitor_db = database.MonitorDatabase()
- try:
- logger.debug(u"PlexPy Users :: Regestering tokens for user '%s' in the database." % username)
- result = monitor_db.action('UPDATE users SET user_token = ?, server_token = ? WHERE user_id = ?',
- [user_token, server_token, user_id])
-
- if result:
- # Successful login
- return True
- else:
- logger.warn(u"PlexPy Users :: Unable to register user '%s' in database." % username)
- return None
- except Exception as e:
- logger.warn(u"PlexPy Users :: Unable to register user '%s' in database: %s." % (username, e))
- return None
- else:
- logger.warn(u"PlexPy Users :: Unable to retrieve Plex.tv server token for user '%s'." % username)
- return None
- else:
- logger.warn(u"PlexPy Users :: Unable to register user '%s'. User not in the database." % username)
- return None
- else:
- logger.warn(u"PlexPy Users :: Unable to retrieve Plex.tv user token for user '%s'." % username)
- return None
-
- return None
-
-
class Users(object):
def __init__(self):
@@ -333,7 +266,8 @@ class Users(object):
'is_restricted': 0,
'do_notify': 0,
'keep_history': 1,
- 'allow_guest': 0
+ 'allow_guest': 0,
+ 'shared_libraries': ()
}
if not user_id and not user and not email:
@@ -345,19 +279,22 @@ class Users(object):
try:
if str(user_id).isdigit():
query = 'SELECT user_id, username, friendly_name, thumb AS user_thumb, custom_avatar_url AS custom_thumb, ' \
- 'email, is_home_user, is_allow_sync, is_restricted, do_notify, keep_history, deleted_user, allow_guest ' \
+ 'email, is_home_user, is_allow_sync, is_restricted, do_notify, keep_history, deleted_user, ' \
+ 'allow_guest, shared_libraries ' \
'FROM users ' \
'WHERE user_id = ? '
result = monitor_db.select(query, args=[user_id])
elif user:
query = 'SELECT user_id, username, friendly_name, thumb AS user_thumb, custom_avatar_url AS custom_thumb, ' \
- 'email, is_home_user, is_allow_sync, is_restricted, do_notify, keep_history, deleted_user, allow_guest ' \
+ 'email, is_home_user, is_allow_sync, is_restricted, do_notify, keep_history, deleted_user, ' \
+ 'allow_guest, shared_libraries ' \
'FROM users ' \
'WHERE username = ? '
result = monitor_db.select(query, args=[user])
elif email:
query = 'SELECT user_id, username, friendly_name, thumb AS user_thumb, custom_avatar_url AS custom_thumb, ' \
- 'email, is_home_user, is_allow_sync, is_restricted, do_notify, keep_history, deleted_user, allow_guest ' \
+ 'email, is_home_user, is_allow_sync, is_restricted, do_notify, keep_history, deleted_user, ' \
+ 'allow_guest, shared_libraries ' \
'FROM users ' \
'WHERE email = ? '
result = monitor_db.select(query, args=[email])
@@ -395,7 +332,8 @@ class Users(object):
'do_notify': item['do_notify'],
'keep_history': item['keep_history'],
'deleted_user': item['deleted_user'],
- 'allow_guest': item['allow_guest']
+ 'allow_guest': item['allow_guest'],
+ 'shared_libraries': tuple(item['shared_libraries'].split(';'))
}
return user_details
@@ -691,3 +629,33 @@ class Users(object):
return None
return None
+
+ def get_filters(self, user_id=None):
+ import urlparse
+
+ if not user_id:
+ return {}
+
+ try:
+ monitor_db = database.MonitorDatabase()
+ query = 'SELECT filter_all, filter_movies, filter_tv, filter_music, filter_photos FROM users ' \
+ 'WHERE user_id = ?'
+ result = monitor_db.select_single(query, args=[user_id])
+ except Exception as e:
+ logger.warn(u"PlexPy Users :: Unable to execute database query for get_filters: %s." % e)
+ result = {}
+
+ filters_list = {}
+ for k, v in result.iteritems():
+ filters = {}
+
+ for f in v.split('|'):
+ if 'contentRating=' in f or 'label=' in f:
+ filters.update(dict(urlparse.parse_qsl(f)))
+
+ filters['content_rating'] = tuple(f for f in filters.pop('contentRating', '').split(',') if f)
+ filters['labels'] = tuple(f for f in filters.pop('label', '').split(',') if f)
+
+ filters_list[k] = filters
+
+ return filters_list
\ No newline at end of file
diff --git a/plexpy/webauth.py b/plexpy/webauth.py
index 878e79a1..394ee2ba 100644
--- a/plexpy/webauth.py
+++ b/plexpy/webauth.py
@@ -26,12 +26,78 @@ import re
import plexpy
from plexpy import logger
-from plexpy.users import Users, user_login
+from plexpy.database import MonitorDatabase
+from plexpy.users import Users
+from plexpy.plextv import PlexTV
from plexpy.pmsconnect import PmsConnect
SESSION_KEY = '_cp_username'
+def user_login(username=None, password=None):
+ if not username and not password:
+ return None
+
+ user_data = Users()
+
+ # Try to login to Plex.tv to check if the user has a vaild account
+ plex_tv = PlexTV(username=username, password=password)
+ plex_user = plex_tv.get_token()
+ if plex_user:
+ user_token = plex_user['auth_token']
+ user_id = plex_user['user_id']
+
+ # Retrieve user token from the database and check against the Plex.tv token.
+ # Also Make sure 'allow_guest' access is enabled for the user.
+ # The user tokens should match if it is the same PlexPy install.
+ tokens = user_data.get_tokens(user_id=user_id)
+ if not tokens:
+ # The user is not in the database
+ return None
+ elif not tokens['allow_guest'] or not user_token == tokens['user_token']:
+ # Guest access is disabled, or user tokens don't match
+ return None
+
+ # Otherwise it is a new user or token is no longer valid.
+ # Check if the user is in the database, not deleted, and 'allow_guest' access.
+ user_details = user_data.get_details(user_id=user_id)
+ if user_id == str(user_details['user_id']) and \
+ not user_details['deleted_user'] and user_details['allow_guest']:
+
+ # The user is in the database, so try to retrieve a new server token.
+ # If a server token is returned, then the user is a valid friend
+ plex_tv = PlexTV(token=user_token)
+ server_token = plex_tv.get_server_token()
+ if server_token:
+
+ # Register the new user / update the access tokens.
+ monitor_db = MonitorDatabase()
+ try:
+ logger.debug(u"PlexPy Users :: Regestering tokens for user '%s' in the database." % username)
+ result = monitor_db.action('UPDATE users SET user_token = ?, server_token = ? WHERE user_id = ?',
+ [user_token, server_token, user_id])
+
+ if result:
+ # Successful login
+ return True
+ else:
+ logger.warn(u"PlexPy Users :: Unable to register user '%s' in database." % username)
+ return None
+ except Exception as e:
+ logger.warn(u"PlexPy Users :: Unable to register user '%s' in database: %s." % (username, e))
+ return None
+ else:
+ logger.warn(u"PlexPy Users :: Unable to retrieve Plex.tv server token for user '%s'." % username)
+ return None
+ else:
+ logger.warn(u"PlexPy Users :: Unable to register user '%s'. User not in the database." % username)
+ return None
+ else:
+ logger.warn(u"PlexPy Users :: Unable to retrieve Plex.tv user token for user '%s'." % username)
+ return None
+
+ return None
+
def check_credentials(username, password):
"""Verifies credentials for username and password.
Returns True and the user group on success or False and no user group"""
@@ -151,16 +217,10 @@ class AuthController(object):
user_details = Users().get_details(email=username)
else:
user_details = Users().get_details(user=username)
+
user_id = user_details['user_id']
-
- user_tokens = Users().get_tokens(user_id=user_details['user_id'])
- server_token = user_tokens['server_token']
-
- library_details = PmsConnect(token=server_token).get_server_children()
- user_libraries = tuple(d['section_id'] for d in library_details['libraries_list'])
else:
user_id = None
- user_libraries = None
expiry = datetime.now() + (timedelta(days=30) if remember_me == '1' else timedelta(minutes=60))
@@ -169,7 +229,6 @@ class AuthController(object):
cherrypy.session[SESSION_KEY] = {'user_id': user_id,
'user': username,
'user_group': user_group,
- 'user_libraries': user_libraries,
'expiry': expiry}
self.on_login(username)
diff --git a/plexpy/webserve.py b/plexpy/webserve.py
index e5cde339..11a7c57b 100644
--- a/plexpy/webserve.py
+++ b/plexpy/webserve.py
@@ -29,7 +29,7 @@ from plexpy import logger, notifiers, plextv, pmsconnect, common, log_reader, \
datafactory, graphs, users, libraries, database, web_socket
from plexpy.api2 import API2
from plexpy.helpers import checked, addtoapi, get_ip, create_https_certificates
-from plexpy.session import get_session_info, allow_session_user, allow_session_library
+from plexpy.session import get_session_info, get_session_user_id, allow_session_user, allow_session_library
from plexpy.webauth import AuthController, requireAuth, member_of, name_is, SESSION_KEY
@@ -182,7 +182,7 @@ class WebInterface(object):
def get_current_activity(self, **kwargs):
try:
- pms_connect = pmsconnect.PmsConnect()
+ pms_connect = pmsconnect.PmsConnect(token=plexpy.CONFIG.PMS_TOKEN)
result = pms_connect.get_current_activity()
data_factory = datafactory.DataFactory()
@@ -205,7 +205,7 @@ class WebInterface(object):
def get_current_activity_header(self, **kwargs):
try:
- pms_connect = pmsconnect.PmsConnect()
+ pms_connect = pmsconnect.PmsConnect(token=plexpy.CONFIG.PMS_TOKEN)
result = pms_connect.get_current_activity()
except:
return serve_template(templatename="current_activity_header.html", data=None)
@@ -468,7 +468,7 @@ class WebInterface(object):
return serve_template(templatename="library_recently_added.html", data=None, title="Recently Added")
@cherrypy.expose
- @requireAuth()
+ @requireAuth(member_of("admin"))
@addtoapi()
def get_library_media_info(self, section_id=None, section_type=None, rating_key=None, refresh='', **kwargs):
@@ -1864,7 +1864,10 @@ class WebInterface(object):
return serve_template(templatename="info.html", data=metadata, title="Info", config=config, source=source)
else:
- return self.update_metadata(rating_key, query)
+ if get_session_user_id():
+ raise cherrypy.HTTPRedirect(plexpy.HTTP_ROOT)
+ else:
+ return self.update_metadata(rating_key, query)
@cherrypy.expose
@requireAuth()