Compare commits

..

14 Commits

Author SHA1 Message Date
JonnyWong16
c19cc858bd v2.1.11-beta 2018-06-02 10:39:32 -07:00
JonnyWong16
668913fd60 Allow manual PMS URL override in config file for XML shortcuts 2018-06-02 09:55:39 -07:00
JonnyWong16
50c5407a46 Fix Monitor Remote Access checkbox (Plex server update chaged bool to int) 2018-06-02 09:32:05 -07:00
JonnyWong16
939755d3b7 Add Plex XML shortcuts to libraries, users, and sync headers 2018-06-02 08:58:55 -07:00
JonnyWong16
54f4696713 Refactor open Plex XML script 2018-06-02 08:53:53 -07:00
JonnyWong16
c85af521fe Add Plex XML shortcuts for metadata and server resources 2018-06-02 08:26:30 -07:00
JonnyWong16
917d19db85 Fix grouping or new plays not previously in history 2018-06-01 18:45:58 -07:00
JonnyWong16
7292f25eb9 Reword group play history setting 2018-05-31 09:10:44 -07:00
JonnyWong16
22a2ad4bc7 Fix progress percent in grouping logic 2018-05-31 08:34:58 -07:00
JonnyWong16
95e56f5ea5 Fix activity progress bar not updating in some cases 2018-05-31 08:33:50 -07:00
JonnyWong16
ed24232a0a Improve logic for grouping history items 2018-05-30 22:18:41 -07:00
JonnyWong16
15225faee7 Add filename to notification parameters 2018-05-30 21:52:18 -07:00
JonnyWong16
041a35a35a Fallback to title if missing index for update metadata 2018-05-30 21:46:31 -07:00
JonnyWong16
6d365c174a Update X-Plex headers 2018-05-30 21:39:45 -07:00
18 changed files with 109 additions and 45 deletions

View File

@@ -1,5 +1,17 @@
# Changelog # Changelog
## v2.1.11-beta (2018-06-02)
* Monitoring:
* Fix: Activity progress bar not updating in some cases.
* Fix: Monitory Remote Access setting disabled due to Plex Media Server API changes.
* Change: Improved logic for grouping history items without being successive plays.
* Notifications:
* New: Added filename to notification parameters.
* Other:
* Fix: Update metadata failing for tracks without track numbers.
## v2.1.10-beta (2018-05-28) ## v2.1.10-beta (2018-05-28)
* Monitoring: * Monitoring:

View File

@@ -292,6 +292,7 @@ ${next.modalIncludes()}
<script src="${http_root}js/pnotify.custom.min.js"></script> <script src="${http_root}js/pnotify.custom.min.js"></script>
<script src="${http_root}js/script.js${cache_param}"></script> <script src="${http_root}js/script.js${cache_param}"></script>
<script src="${http_root}js/jquery.qrcode.min.js"></script> <script src="${http_root}js/jquery.qrcode.min.js"></script>
<script src="${http_root}js/jquery.tripleclick.min.js"></script>
% if _session['user_group'] == 'admin' and BROWSER_NOTIFIERS: % if _session['user_group'] == 'admin' and BROWSER_NOTIFIERS:
<script src="${http_root}js/ajaxNotifications.js"></script> <script src="${http_root}js/ajaxNotifications.js"></script>
% endif % endif

View File

@@ -12,7 +12,7 @@
<div class="row"> <div class="row">
<div class="col-md-12"> <div class="col-md-12">
<div class="padded-header" id="current-activity-header"> <div class="padded-header" id="current-activity-header">
<h3><span id="sessions-shortcut">Activity</span> &nbsp;&nbsp; <h3><span id="sessions-xml">Activity</span> &nbsp;&nbsp;
<small> <small>
<span id="currentActivityHeader" style="display: none;"> <span id="currentActivityHeader" style="display: none;">
Streams: <span id="currentActivityHeader-streams"></span> | Streams: <span id="currentActivityHeader-streams"></span> |
@@ -236,7 +236,6 @@
<script src="${http_root}js/moment-with-locale.js"></script> <script src="${http_root}js/moment-with-locale.js"></script>
<script src="${http_root}js/jquery.scrollbar.min.js"></script> <script src="${http_root}js/jquery.scrollbar.min.js"></script>
<script src="${http_root}js/jquery.mousewheel.min.js"></script> <script src="${http_root}js/jquery.mousewheel.min.js"></script>
<script src="${http_root}js/jquery.tripleclick.min.js"></script>
<script> <script>
var date_format = 'YYYY-MM-DD'; var date_format = 'YYYY-MM-DD';
var time_format = 'hh:mm a'; var time_format = 'hh:mm a';
@@ -546,7 +545,7 @@
.attr('data-original-title', 'Transcoder Progress ' + s.transcode_progress + '%'); .attr('data-original-title', 'Transcoder Progress ' + s.transcode_progress + '%');
var progress_bar = $('#progress-bar-' + key); var progress_bar = $('#progress-bar-' + key);
progress_bar.data('state', s.state); progress_bar.data('state', s.state);
if (progress_bar.data('last_view_offset') && progress_bar.data('last_view_offset') !== s.view_offset) { if (progress_bar.data('last_view_offset') !== s.view_offset) {
progress_bar.data('last_view_offset', s.view_offset).data('view_offset', s.view_offset); progress_bar.data('last_view_offset', s.view_offset).data('view_offset', s.view_offset);
} }
@@ -694,10 +693,8 @@
}); });
}); });
$('#sessions-shortcut').on('tripleclick', function () { $('#sessions-xml').on('tripleclick', function () {
$.getJSON('return_sessions_url', function(sessions_url) { openPlexXML('/status/sessions');
window.open(sessions_url, '_blank');
});
}); });
% endif % endif
</script> </script>

View File

@@ -83,31 +83,31 @@ DOCUMENTATION :: END
<ul class="list-unstyled breadcrumb"> <ul class="list-unstyled breadcrumb">
% if data['media_type'] in ('movie', 'collection'): % if data['media_type'] in ('movie', 'collection'):
<li><a href="library?section_id=${data['section_id']}">${data['library_name']}</a></li> <li><a href="library?section_id=${data['section_id']}">${data['library_name']}</a></li>
<li class="active">${data['title']}</li> <li class="active metadata-xml">${data['title']}</li>
% elif data['media_type'] == 'show': % elif data['media_type'] == 'show':
<li><a href="library?section_id=${data['section_id']}">${data['library_name']}</a></li> <li><a href="library?section_id=${data['section_id']}">${data['library_name']}</a></li>
<li class="active">${data['title']}</li> <li class="active metadata-xml">${data['title']}</li>
% elif data['media_type'] == 'season': % elif data['media_type'] == 'season':
<li class="hidden-xs hidden-sm"><a href="library?section_id=${data['section_id']}">${data['library_name']}</a></li> <li class="hidden-xs hidden-sm"><a href="library?section_id=${data['section_id']}">${data['library_name']}</a></li>
<li><a href="info?rating_key=${data['parent_rating_key']}">${data['parent_title']}</a></li> <li><a href="info?rating_key=${data['parent_rating_key']}">${data['parent_title']}</a></li>
<li class="active">Season ${data['media_index']}</li> <li class="active metadata-xml">Season ${data['media_index']}</li>
% elif data['media_type'] == 'episode': % elif data['media_type'] == 'episode':
<li class="hidden-xs hidden-sm"><a href="library?section_id=${data['section_id']}">${data['library_name']}</a></li> <li class="hidden-xs hidden-sm"><a href="library?section_id=${data['section_id']}">${data['library_name']}</a></li>
<li class="hidden-xs hidden-sm"><a href="info?rating_key=${data['grandparent_rating_key']}">${data['grandparent_title']}</a></li> <li class="hidden-xs hidden-sm"><a href="info?rating_key=${data['grandparent_rating_key']}">${data['grandparent_title']}</a></li>
<li><a href="info?rating_key=${data['parent_rating_key']}">Season ${data['parent_media_index']}</a></li> <li><a href="info?rating_key=${data['parent_rating_key']}">Season ${data['parent_media_index']}</a></li>
<li class="active">Episode ${data['media_index']} - ${data['title']}</li> <li class="active metadata-xml">Episode ${data['media_index']} - ${data['title']}</li>
% elif data['media_type'] == 'artist': % elif data['media_type'] == 'artist':
<li><a href="library?section_id=${data['section_id']}">${data['library_name']}</a></li> <li><a href="library?section_id=${data['section_id']}">${data['library_name']}</a></li>
<li class="active">${data['title']}</li> <li class="active metadata-xml">${data['title']}</li>
% elif data['media_type'] == 'album': % elif data['media_type'] == 'album':
<li class="hidden-xs hidden-sm"><a href="library?section_id=${data['section_id']}">${data['library_name']}</a></li> <li class="hidden-xs hidden-sm"><a href="library?section_id=${data['section_id']}">${data['library_name']}</a></li>
<li><a href="info?rating_key=${data['parent_rating_key']}">${data['parent_title']}</a></li> <li><a href="info?rating_key=${data['parent_rating_key']}">${data['parent_title']}</a></li>
<li class="active">${data['title']}</li> <li class="active metadata-xml">${data['title']}</li>
% elif data['media_type'] == 'track': % elif data['media_type'] == 'track':
<li class="hidden-xs hidden-sm"><a href="library?section_id=${data['section_id']}">${data['library_name']}</a></li> <li class="hidden-xs hidden-sm"><a href="library?section_id=${data['section_id']}">${data['library_name']}</a></li>
<li class="hidden-xs hidden-sm"><a href="info?rating_key=${data['grandparent_rating_key']}">${data['grandparent_title']}</a></li> <li class="hidden-xs hidden-sm"><a href="info?rating_key=${data['grandparent_rating_key']}">${data['grandparent_title']}</a></li>
<li><a href="info?rating_key=${data['parent_rating_key']}">${data['parent_title']}</a></li> <li><a href="info?rating_key=${data['parent_rating_key']}">${data['parent_title']}</a></li>
<li class="active">Track ${data['media_index']} - ${data['title']}</li> <li class="active metadata-xml">Track ${data['media_index']} - ${data['title']}</li>
% endif % endif
</ul> </ul>
</div> </div>
@@ -703,6 +703,10 @@ DOCUMENTATION :: END
</script> </script>
% endif % endif
<script> <script>
$('.metadata-xml').on('tripleclick', function () {
openPlexXML("/library/metadata/${data['rating_key']}");
});
$("#airdate").html(moment($("#airdate").text()).format('MMM DD, YYYY')); $("#airdate").html(moment($("#airdate").text()).format('MMM DD, YYYY'));
$("#runtime").html(millisecondsToMinutes($("#runtime").text(), true)); $("#runtime").html(millisecondsToMinutes($("#runtime").text(), true));
$('div.art-face').animate({ opacity: 0.2 }, { duration: 1000 }); $('div.art-face').animate({ opacity: 0.2 }, { duration: 1000 });

View File

@@ -458,3 +458,10 @@ function capitalizeFirstLetter(string) {
$.fn.slideToggleBool = function(bool, options) { $.fn.slideToggleBool = function(bool, options) {
return bool ? $(this).slideDown(options) : $(this).slideUp(options); return bool ? $(this).slideDown(options) : $(this).slideUp(options);
}; };
function openPlexXML(endpoint, plextv, params) {
var data = $.extend({endpoint: endpoint, plextv: plextv}, params);
$.getJSON('return_plex_xml_url', data, function(xml_url) {
window.open(xml_url, '_blank');
});
}

View File

@@ -10,7 +10,7 @@
<div class='container-fluid'> <div class='container-fluid'>
<div class='table-card-header'> <div class='table-card-header'>
<div class="header-bar"> <div class="header-bar">
<span><i class="fa fa-book"></i> All Libraries</span> <span id="libraries-xml"><i class="fa fa-book"></i> All Libraries</span>
</div> </div>
<div class="button-bar"> <div class="button-bar">
% if _session['user_group'] == 'admin': % if _session['user_group'] == 'admin':
@@ -198,5 +198,9 @@
}); });
}); });
% endif % endif
$('#libraries-xml').on('tripleclick', function () {
openPlexXML('/library/sections/all');
});
</script> </script>
</%def> </%def>

View File

@@ -115,9 +115,9 @@
</div> </div>
<div class="checkbox advanced-setting"> <div class="checkbox advanced-setting">
<label> <label>
<input type="checkbox" id="group_history_tables" name="group_history_tables" value="1" ${config['group_history_tables']}> Group Successive Play History <input type="checkbox" id="group_history_tables" name="group_history_tables" value="1" ${config['group_history_tables']}> Group Play History
</label> </label>
<p class="help-block">Group successive play history by the same user as a single entry in the watch statistics, tables, and graphs.</p> <p class="help-block">Group play history for the same item and user as a single entry when progress is less than the watched percent.</p>
</div> </div>
<div class="checkbox advanced-setting"> <div class="checkbox advanced-setting">
<label> <label>
@@ -646,7 +646,7 @@
<div role="tabpanel" class="tab-pane" id="tabs-plex_media_server"> <div role="tabpanel" class="tab-pane" id="tabs-plex_media_server">
<div class="padded-header"> <div class="padded-header">
<h3>Plex Media Server <small style="color: #fff;">Version <span id="pms_version">${config['pms_version']}</span></small></h3> <h3 id="resources-xml">Plex Media Server <small style="color: #fff;">Version <span id="pms_version">${config['pms_version']}</span></small></h3>
</div> </div>
<div class="form-group has-feedback" id="pms_ip_group"> <div class="form-group has-feedback" id="pms_ip_group">
@@ -2358,7 +2358,7 @@ $(document).ready(function() {
data: { pref: 'PublishServerOnPlexOnlineKey' }, data: { pref: 'PublishServerOnPlexOnlineKey' },
async: true, async: true,
success: function(data) { success: function(data) {
if (data !== 'true') { if (data === 'false' || data === '0') {
$("#remoteAccessCheck").html("Remote access must be enabled on your Plex Server. <a target='_blank' href='${anon_url('https://support.plex.tv/hc/en-us/articles/200484543-Enabling-Remote-Access-for-a-Server')}'>Click here</a> for help."); $("#remoteAccessCheck").html("Remote access must be enabled on your Plex Server. <a target='_blank' href='${anon_url('https://support.plex.tv/hc/en-us/articles/200484543-Enabling-Remote-Access-for-a-Server')}'>Click here</a> for help.");
$("#monitor_remote_access").attr("checked", false).attr("disabled", true); $("#monitor_remote_access").attr("checked", false).attr("disabled", true);
} }
@@ -2753,6 +2753,10 @@ $(document).ready(function() {
body_container.animate({scrollTop: scroll_pos}); body_container.animate({scrollTop: scroll_pos});
} }
}); });
$('#resources-xml').on('tripleclick', function () {
openPlexXML('/api/resources', true, {includeHttps: 1});
});
}); });
</script> </script>
</%def> </%def>

View File

@@ -16,7 +16,7 @@
<div class='container-fluid'> <div class='container-fluid'>
<div class='table-card-header'> <div class='table-card-header'>
<div class="header-bar"> <div class="header-bar">
<span><i class="fa fa-cloud-download"></i> Synced Items</span> <span id="sync-xml"><i class="fa fa-cloud-download"></i> Synced Items</span>
</div> </div>
<div class="button-bar"> <div class="button-bar">
% if _session['user_group'] == 'admin': % if _session['user_group'] == 'admin':
@@ -185,5 +185,9 @@
$("#refresh-syncs-list").click(function() { $("#refresh-syncs-list").click(function() {
sync_table.ajax.reload(); sync_table.ajax.reload();
}); });
$('#sync-xml').on('tripleclick', function () {
openPlexXML('/servers/{machine_id}/sync_lists', true);
});
</script> </script>
</%def> </%def>

View File

@@ -10,7 +10,7 @@
<div class='container-fluid'> <div class='container-fluid'>
<div class='table-card-header'> <div class='table-card-header'>
<div class="header-bar"> <div class="header-bar">
<span><i class="fa fa-group"></i> All Users</span> <span id="users-xml"><i class="fa fa-group"></i> All Users</span>
</div> </div>
<div class="button-bar"> <div class="button-bar">
% if _session['user_group'] == 'admin': % if _session['user_group'] == 'admin':
@@ -202,5 +202,9 @@
}); });
}); });
% endif % endif
$('#users-xml').on('tripleclick', function () {
openPlexXML('/api/users', true);
});
</script> </script>
</%def> </%def>

View File

@@ -15,18 +15,13 @@
from collections import defaultdict from collections import defaultdict
import json import json
import threading
import time import time
import re
import plexpy import plexpy
import database import database
import datafactory import helpers
import libraries import libraries
import log_reader
import logger import logger
import notification_handler
import notifiers
import pmsconnect import pmsconnect
import users import users
@@ -272,14 +267,15 @@ class ActivityProcessor(object):
self.db.upsert(table_name='session_history', key_dict=keys, value_dict=values) self.db.upsert(table_name='session_history', key_dict=keys, value_dict=values)
# Check if we should group the session, select the last two rows from the user # Check if we should group the session, select the last two rows from the user
query = 'SELECT id, rating_key, view_offset, user_id, reference_id FROM session_history \ query = 'SELECT id, rating_key, view_offset, user_id, reference_id FROM session_history ' \
WHERE user_id = ? ORDER BY id DESC LIMIT 2 ' 'WHERE user_id = ? AND rating_key = ? ORDER BY id DESC LIMIT 2 '
args = [session['user_id']] args = [session['user_id'], session['rating_key']]
result = self.db.select(query=query, args=args) result = self.db.select(query=query, args=args)
new_session = prev_session = None new_session = prev_session = None
prev_progress_percent = media_watched_percent = 0
# Get the last insert row id # Get the last insert row id
last_id = self.db.last_insert_id() last_id = self.db.last_insert_id()
@@ -296,11 +292,23 @@ class ActivityProcessor(object):
'user_id': result[1]['user_id'], 'user_id': result[1]['user_id'],
'reference_id': result[1]['reference_id']} 'reference_id': result[1]['reference_id']}
watched_percent = {'movie': plexpy.CONFIG.MOVIE_WATCHED_PERCENT,
'episode': plexpy.CONFIG.TV_WATCHED_PERCENT,
'track': plexpy.CONFIG.MUSIC_WATCHED_PERCENT
}
prev_progress_percent = helpers.get_percent(prev_session['view_offset'], session['duration'])
media_watched_percent = watched_percent.get(session['media_type'], 0)
query = 'UPDATE session_history SET reference_id = ? WHERE id = ? ' query = 'UPDATE session_history SET reference_id = ? WHERE id = ? '
# If rating_key is the same in the previous session, then set the reference_id to the previous row, else set the reference_id to the new id
# If previous session view offset less than watched percent,
# and new session view offset is greater,
# then set the reference_id to the previous row,
# else set the reference_id to the new id
if prev_session is None and new_session is None: if prev_session is None and new_session is None:
args = [last_id, last_id] args = [last_id, last_id]
elif prev_session['rating_key'] == new_session['rating_key'] and prev_session['view_offset'] <= new_session['view_offset']: elif prev_progress_percent < media_watched_percent and \
prev_session['view_offset'] <= new_session['view_offset']:
args = [prev_session['reference_id'], new_session['id']] args = [prev_session['reference_id'], new_session['id']]
else: else:
args = [new_session['id'], new_session['id']] args = [new_session['id'], new_session['id']]

View File

@@ -23,6 +23,7 @@ PLATFORM = platform.system()
PLATFORM_RELEASE = platform.release() PLATFORM_RELEASE = platform.release()
PLATFORM_VERSION = platform.version() PLATFORM_VERSION = platform.version()
PLATFORM_LINUX_DISTRO = ' '.join(x for x in platform.linux_distribution() if x) PLATFORM_LINUX_DISTRO = ' '.join(x for x in platform.linux_distribution() if x)
PLATFORM_DEVICE_NAME = platform.node()
BRANCH = version.PLEXPY_BRANCH BRANCH = version.PLEXPY_BRANCH
RELEASE = version.PLEXPY_RELEASE_VERSION RELEASE = version.PLEXPY_RELEASE_VERSION
@@ -475,6 +476,7 @@ NOTIFICATION_PARAMETERS = [
{'name': 'Subtitle Language', 'type': 'str', 'value': 'subtitle_language', 'description': 'The subtitle language of the original media.'}, {'name': 'Subtitle Language', 'type': 'str', 'value': 'subtitle_language', 'description': 'The subtitle language of the original media.'},
{'name': 'Subtitle Language Code', 'type': 'str', 'value': 'subtitle_language_code', 'description': 'The subtitle language code of the original media.'}, {'name': 'Subtitle Language Code', 'type': 'str', 'value': 'subtitle_language_code', 'description': 'The subtitle language code of the original media.'},
{'name': 'File', 'type': 'str', 'value': 'file', 'description': 'The file path to the item.'}, {'name': 'File', 'type': 'str', 'value': 'file', 'description': 'The file path to the item.'},
{'name': 'Filename', 'type': 'str', 'value': 'filename', 'description': 'The file name of the item.'},
{'name': 'File Size', 'type': 'int', 'value': 'file_size', 'description': 'The file size of the item.'}, {'name': 'File Size', 'type': 'int', 'value': 'file_size', 'description': 'The file size of the item.'},
{'name': 'Section ID', 'type': 'int', 'value': 'section_id', 'description': 'The unique identifier for the library.'}, {'name': 'Section ID', 'type': 'int', 'value': 'section_id', 'description': 'The unique identifier for the library.'},
{'name': 'Rating Key', 'type': 'int', 'value': 'rating_key', 'description': 'The unique identifier for the movie, episode, or track.'}, {'name': 'Rating Key', 'type': 'int', 'value': 'rating_key', 'description': 'The unique identifier for the movie, episode, or track.'},

View File

@@ -54,6 +54,7 @@ _CONFIG_DEFINITIONS = {
'PMS_TOKEN': (str, 'PMS', ''), 'PMS_TOKEN': (str, 'PMS', ''),
'PMS_SSL': (int, 'PMS', 0), 'PMS_SSL': (int, 'PMS', 0),
'PMS_URL': (str, 'PMS', ''), 'PMS_URL': (str, 'PMS', ''),
'PMS_URL_OVERRIDE': (str, 'PMS', ''),
'PMS_URL_MANUAL': (int, 'PMS', 0), 'PMS_URL_MANUAL': (int, 'PMS', 0),
'PMS_USE_BIF': (int, 'PMS', 0), 'PMS_USE_BIF': (int, 'PMS', 0),
'PMS_UUID': (str, 'PMS', ''), 'PMS_UUID': (str, 'PMS', ''),

View File

@@ -65,7 +65,7 @@ class DataFactory(object):
columns = [ columns = [
'session_history.reference_id', 'session_history.reference_id',
'session_history.id', 'session_history.id',
'started AS date', 'MAX(started) AS date',
'MIN(started) AS started', 'MIN(started) AS started',
'MAX(stopped) AS stopped', 'MAX(stopped) AS stopped',
'SUM(CASE WHEN stopped > 0 THEN (stopped - started) ELSE 0 END) - \ 'SUM(CASE WHEN stopped > 0 THEN (stopped - started) ELSE 0 END) - \
@@ -1467,7 +1467,7 @@ class DataFactory(object):
result = monitor_db.select(query=query.format('parent_rating_key', 'rating_key'), result = monitor_db.select(query=query.format('parent_rating_key', 'rating_key'),
args=[item['parent_rating_key']]) args=[item['parent_rating_key']])
for item in result: for item in result:
key = item['media_index'] key = item['media_index'] if item['media_index'] else item['title']
children.update({key: {'rating_key': item['rating_key']}}) children.update({key: {'rating_key': item['rating_key']}})
key = item['parent_media_index'] if match_type == 'index' else item['parent_title'] key = item['parent_media_index'] if match_type == 'index' else item['parent_title']

View File

@@ -39,12 +39,13 @@ class HTTPHandler(object):
else: else:
self.urls = urls self.urls = urls
self.headers = {'X-Plex-Device-Name': 'Tautulli', self.headers = {'X-Plex-Product': 'Tautulli',
'X-Plex-Product': 'Tautulli',
'X-Plex-Version': plexpy.common.RELEASE, 'X-Plex-Version': plexpy.common.RELEASE,
'X-Plex-Client-Identifier': plexpy.CONFIG.PMS_UUID,
'X-Plex-Platform': plexpy.common.PLATFORM, 'X-Plex-Platform': plexpy.common.PLATFORM,
'X-Plex-Platform-Version': plexpy.common.PLATFORM_RELEASE, 'X-Plex-Platform-Version': plexpy.common.PLATFORM_RELEASE,
'X-Plex-Client-Identifier': plexpy.CONFIG.PMS_UUID, 'X-Plex-Device': 'Web',
'X-Plex-Device-Name': plexpy.common.PLATFORM_DEVICE_NAME
} }
self.token = token self.token = token

View File

@@ -883,6 +883,7 @@ def build_media_notify_params(notify_action=None, session=None, timeline=None, m
'subtitle_language': notify_params['subtitle_language'], 'subtitle_language': notify_params['subtitle_language'],
'subtitle_language_code': notify_params['subtitle_language_code'], 'subtitle_language_code': notify_params['subtitle_language_code'],
'file': notify_params['file'], 'file': notify_params['file'],
'filename': os.path.basename(notify_params['file']),
'file_size': helpers.humanFileSize(notify_params['file_size']), 'file_size': helpers.humanFileSize(notify_params['file_size']),
'indexes': notify_params['indexes'], 'indexes': notify_params['indexes'],
'section_id': notify_params['section_id'], 'section_id': notify_params['section_id'],

View File

@@ -2664,7 +2664,7 @@ class PmsConnect(object):
child_title = helpers.get_xml_attr(item, 'title') child_title = helpers.get_xml_attr(item, 'title')
if child_rating_key: if child_rating_key:
key = int(child_index) key = int(child_index) if child_index else child_title
children.update({key: {'rating_key': int(child_rating_key)}}) children.update({key: {'rating_key': int(child_rating_key)}})
key = int(parent_index) if match_type == 'index' else parent_title key = int(parent_index) if match_type == 'index' else parent_title

View File

@@ -1,2 +1,2 @@
PLEXPY_BRANCH = "beta" PLEXPY_BRANCH = "beta"
PLEXPY_RELEASE_VERSION = "v2.1.10-beta" PLEXPY_RELEASE_VERSION = "v2.1.11-beta"

View File

@@ -18,6 +18,7 @@ import json
import os import os
import shutil import shutil
import threading import threading
import urllib
import cherrypy import cherrypy
from cherrypy.lib.static import serve_file, serve_download from cherrypy.lib.static import serve_file, serve_download
@@ -273,8 +274,21 @@ class WebInterface(object):
@cherrypy.expose @cherrypy.expose
@cherrypy.tools.json_out() @cherrypy.tools.json_out()
@requireAuth(member_of("admin")) @requireAuth(member_of("admin"))
def return_sessions_url(self, **kwargs): def return_plex_xml_url(self, endpoint='', plextv=False, **kwargs):
return plexpy.CONFIG.PMS_URL + '/status/sessions?X-Plex-Token=' + plexpy.CONFIG.PMS_TOKEN kwargs['X-Plex-Token'] = plexpy.CONFIG.PMS_TOKEN
if plextv:
base_url = 'https://plex.tv'
else:
if plexpy.CONFIG.PMS_URL_OVERRIDE:
base_url = plexpy.CONFIG.PMS_URL_OVERRIDE
else:
base_url = plexpy.CONFIG.PMS_URL
if '{machine_id}' in endpoint:
endpoint = endpoint.format(machine_id=plexpy.CONFIG.PMS_IDENTIFIER)
return base_url + endpoint + '?' + urllib.urlencode(kwargs)
@cherrypy.expose @cherrypy.expose
@requireAuth() @requireAuth()