mirror of
https://github.com/Tautulli/Tautulli.git
synced 2025-07-31 12:00:08 -07:00
Merge branch 'dev'
This commit is contained in:
commit
965fd170bd
15 changed files with 664 additions and 271 deletions
13
CHANGELOG.md
13
CHANGELOG.md
|
@ -1,5 +1,18 @@
|
|||
# Changelog
|
||||
|
||||
## v1.3.8 (2016-02-21)
|
||||
|
||||
* Fix: Regression unable to clear HTTP password.
|
||||
* Fix: Remove media tags from script arguments for server notifications.
|
||||
* Fix: Encode poster titles to UTF-8 for Imgur upload.
|
||||
* Fix: Allow notifications to send without poster if Imgur upload fails.
|
||||
* Add: Notification Logs table in the Logs tab.
|
||||
* Add: Toggle in settings to enable posters in notifications. (Disabled by default.)
|
||||
* Change: Save Imgur poster URL to database so upload is not needed every time.
|
||||
* Change: Notify log in database to log each event as a separate entry.
|
||||
* Change: Monitor remote access is unchecked if remote access is disabled on server.
|
||||
|
||||
|
||||
## v1.3.7 (2016-02-20)
|
||||
|
||||
* Fix: Verifying server with SSL enabled.
|
||||
|
|
|
@ -3,10 +3,43 @@
|
|||
## Issues
|
||||
In case you read this because you are posting an issue, please take a minute and conside the things below. The issue tracker is not a support forum. It is primarily intended to submit bugs, improvements or feature requests. However, we are glad to help you, and make sure the problem is not caused by PlexPy, but don't expect step-by-step answers.
|
||||
|
||||
* Use the search function. Chances are that your problem is already discussed. Do not append to (closed) issues if your problem does not fit the discussion.
|
||||
* Visit the [Troubleshooting](../../wiki/TroubleShooting) wiki first.
|
||||
* Use [proper formatting](https://help.github.com/articles/github-flavored-markdown/). Paste your logs in code blocks.
|
||||
* Close your issue if you resolved it.
|
||||
##### Many issues can simply be solved by:
|
||||
|
||||
- Making sure you update to the latest version.
|
||||
- Turning your device off and on again.
|
||||
- Analyzing your logs, you just might find the solution yourself!
|
||||
- Using the **search** function to see if this issue has already been reported/solved.
|
||||
- Checking the [Wiki](https://github.com/drzoidberg33/plexpy/wiki) for
|
||||
[ [Installation] ](https://github.com/drzoidberg33/plexpy/wiki/Installation) and
|
||||
[ [FAQs] ](https://github.com/drzoidberg33/plexpy/wiki/Frequently-Asked-Questions-(FAQ)).
|
||||
- For basic questions try asking on [Gitter](https://gitter.im/drzoidberg33/plexpy) or the [Plex Forums](https://forums.plex.tv/discussion/169591/plexpy-another-plex-monitoring-program) first before opening an issue.
|
||||
|
||||
##### If nothing has worked:
|
||||
|
||||
1. Open a new issue on the GitHub [issue tracker](http://github.com/drzoidberg33/plexpy/issues).
|
||||
2. Provide a clear title to easily help identify your problem.
|
||||
3. Use proper [markdown syntax](https://help.github.com/articles/github-flavored-markdown) to structure your post (i.e. code/log in code blocks).
|
||||
4. Make sure you provide the following information:
|
||||
- [ ] Version
|
||||
- [ ] Branch
|
||||
- [ ] Commit hash
|
||||
- [ ] Operating system
|
||||
- [ ] Python version
|
||||
- [ ] What you did?
|
||||
- [ ] What happened?
|
||||
- [ ] What you expected?
|
||||
- [ ] How can we reproduce your issue?
|
||||
- [ ] What are your (relevant) settings?
|
||||
- [ ] Include a link to your **FULL** (not just a few lines!) log file that has the error. Please use [Gist](http://gist.github.com) or [Pastebin](http://pastebin.com/).
|
||||
5. Close your issue when it's solved! If you found the solution yourself please comment so that others benefit from it.
|
||||
|
||||
## Feature Requests
|
||||
|
||||
1. Search for similar existing 'issues', feature requests can be recognized by the blue `enhancement` label.
|
||||
2. If a similar request exists, post a comment (+1, or add a new idea to the existing request).
|
||||
3. If no similar requests exist, you can create a new one.
|
||||
4. Provide a clear title to easily identify the feature request.
|
||||
5. Tag your feature request with `[Feature Request]` so it can be identified easily.
|
||||
|
||||
## Pull Requests
|
||||
If you think you can contribute code to the PlexPy repository, do not hesitate to submit a pull request.
|
||||
|
|
|
@ -50,9 +50,11 @@ This project is based on code from [Headphones](https://github.com/rembo10/headp
|
|||
2. Provide a clear title to easily help identify your problem.
|
||||
3. Use proper [markdown syntax](https://help.github.com/articles/github-flavored-markdown) to structure your post (i.e. code/log in code blocks).
|
||||
4. Make sure you provide the following information:
|
||||
- [ ] Version
|
||||
- [ ] Branch
|
||||
- [ ] Version/Commit hash
|
||||
- [ ] Your operating system and python version
|
||||
- [ ] Commit hash
|
||||
- [ ] Operating system
|
||||
- [ ] Python version
|
||||
- [ ] What you did?
|
||||
- [ ] What happened?
|
||||
- [ ] What you expected?
|
||||
|
|
89
data/interfaces/default/js/tables/notification_logs.js
Normal file
89
data/interfaces/default/js/tables/notification_logs.js
Normal file
|
@ -0,0 +1,89 @@
|
|||
notification_log_table_options = {
|
||||
"destroy": true,
|
||||
"serverSide": true,
|
||||
"processing": false,
|
||||
"pagingType": "bootstrap",
|
||||
"order": [ 0, 'desc'],
|
||||
"pageLength": 50,
|
||||
"stateSave": false,
|
||||
"language": {
|
||||
"search":"Search: ",
|
||||
"lengthMenu":"Show _MENU_ lines per page",
|
||||
"emptyTable": "No log information available",
|
||||
"info":"Showing _START_ to _END_ of _TOTAL_ lines",
|
||||
"infoEmpty":"Showing 0 to 0 of 0 lines",
|
||||
"infoFiltered":"(filtered from _MAX_ total lines)"},
|
||||
"columnDefs": [
|
||||
{
|
||||
"targets": [0],
|
||||
"data": "timestamp",
|
||||
"createdCell": function (td, cellData, rowData, row, col) {
|
||||
if (cellData !== '') {
|
||||
$(td).html(moment(cellData, "X").format('YYYY-MM-DD HH:mm:ss'));
|
||||
}
|
||||
},
|
||||
"width": "10%",
|
||||
"className": "no-wrap hidden-xs"
|
||||
},
|
||||
{
|
||||
"targets": [1],
|
||||
"data": "agent_name",
|
||||
"createdCell": function (td, cellData, rowData, row, col) {
|
||||
if (cellData !== '') {
|
||||
$(td).html(cellData);
|
||||
}
|
||||
},
|
||||
"width": "7%",
|
||||
"className": "no-wrap hidden-sm hidden-xs"
|
||||
},
|
||||
{
|
||||
"targets": [2],
|
||||
"data": "notify_action",
|
||||
"createdCell": function (td, cellData, rowData, row, col) {
|
||||
if (cellData !== '') {
|
||||
$(td).html(cellData);
|
||||
}
|
||||
},
|
||||
"width": "5%"
|
||||
},
|
||||
{
|
||||
"targets": [3],
|
||||
"data": "subject_text",
|
||||
"createdCell": function (td, cellData, rowData, row, col) {
|
||||
if (cellData !== '') {
|
||||
$(td).html(cellData);
|
||||
}
|
||||
},
|
||||
"width": "20%"
|
||||
},
|
||||
{
|
||||
"targets": [4],
|
||||
"data": "body_text",
|
||||
"createdCell": function (td, cellData, rowData, row, col) {
|
||||
if (cellData !== '') {
|
||||
$(td).html(cellData);
|
||||
}
|
||||
},
|
||||
"width": "38%"
|
||||
},
|
||||
{
|
||||
"targets": [5],
|
||||
"data": "script_args",
|
||||
"createdCell": function (td, cellData, rowData, row, col) {
|
||||
if (cellData !== '') {
|
||||
$(td).html(cellData);
|
||||
}
|
||||
},
|
||||
"width": "20%"
|
||||
}
|
||||
],
|
||||
"drawCallback": function (settings) {
|
||||
// Jump to top of page
|
||||
//$('html,body').scrollTop(0);
|
||||
$('#ajaxMsg').fadeOut();
|
||||
},
|
||||
"preDrawCallback": function(settings) {
|
||||
var msg = "<i class='fa fa-refresh fa-spin'></i> Fetching rows...";
|
||||
showMsg(msg, false, false, 0)
|
||||
}
|
||||
}
|
|
@ -30,6 +30,7 @@ from plexpy import helpers
|
|||
<li role="presentation" class="active"><a id="plexpy-logs-btn" href="#tabs-1" aria-controls="tabs-1" role="tab" data-toggle="tab">PlexPy Logs</a></li>
|
||||
<li role="presentation"><a id="plex-logs-btn" href="#tabs-2" aria-controls="tabs-2" role="tab" data-toggle="tab">Plex Media Server Logs</a></li>
|
||||
<li role="presentation"><a id="plex-scanner-logs-btn" href="#tabs-3" aria-controls="tabs-3" role="tab" data-toggle="tab">Plex Media Scanner Logs</a></li>
|
||||
<li role="presentation"><a id="notification-logs-btn" href="#tabs-4" aria-controls="tabs-4" role="tab" data-toggle="tab">Notification Logs</a></li>
|
||||
</ul>
|
||||
<div class="tab-content">
|
||||
<div role="tabpanel" class="tab-pane active" id="tabs-1">
|
||||
|
@ -67,8 +68,22 @@ from plexpy import helpers
|
|||
<th align='left' id="plex_scanner_message">Message</th>
|
||||
</tr>
|
||||
</thead>
|
||||
<tbody>
|
||||
</tbody>
|
||||
<tbody></tbody>
|
||||
</table>
|
||||
</div>
|
||||
<div role="tabpanel" class="tab-pane" id="tabs-4">
|
||||
<table class="display" id="notification_log_table" width="100%">
|
||||
<thead>
|
||||
<tr>
|
||||
<th align='left' id="notification_timestamp">Timestamp</th>
|
||||
<th align='left' id="notification_agent_name">Agent</th>
|
||||
<th align='left' id="notification_action">Action</th>
|
||||
<th align='left' id="notification_poster_url">Subject Text</th>
|
||||
<th align='left' id="notification_poster_url">Body Text</th>
|
||||
<th align='left' id="notification_poster_url">Script Args</th>
|
||||
</tr>
|
||||
</thead>
|
||||
<tbody></tbody>
|
||||
</table>
|
||||
</div>
|
||||
</div>
|
||||
|
@ -94,8 +109,10 @@ from plexpy import helpers
|
|||
<script src="interfaces/default/js/jquery.dataTables.min.js"></script>
|
||||
<script src="interfaces/default/js/dataTables.bootstrap.min.js"></script>
|
||||
<script src="interfaces/default/js/dataTables.bootstrap.pagination.js"></script>
|
||||
<script src="interfaces/default/js/moment-with-locale.js"></script>
|
||||
<script src="interfaces/default/js/tables/logs.js"></script>
|
||||
<script src="interfaces/default/js/tables/plex_logs.js"></script>
|
||||
<script src="interfaces/default/js/tables/notification_logs.js"></script>
|
||||
<script>
|
||||
|
||||
$(document).ready(function() {
|
||||
|
@ -105,44 +122,63 @@ from plexpy import helpers
|
|||
|
||||
function LoadPlexPyLogs() {
|
||||
log_table_options.ajax = {
|
||||
"url": "getLog"
|
||||
url: "getLog"
|
||||
}
|
||||
log_table = $('#log_table').DataTable(log_table_options);
|
||||
}
|
||||
|
||||
function LoadPlexLogs() {
|
||||
plex_log_table_options.ajax = {
|
||||
"url": "get_plex_log?log_type=server"
|
||||
url: "get_plex_log?log_type=server"
|
||||
}
|
||||
plex_log_table = $('#plex_log_table').DataTable(plex_log_table_options);
|
||||
}
|
||||
|
||||
function LoadPlexScannerLogs() {
|
||||
plex_log_table_options.ajax = {
|
||||
"url": "get_plex_log?log_type=scanner"
|
||||
url: "get_plex_log?log_type=scanner"
|
||||
}
|
||||
plex_scanner_log_table = $('#plex_scanner_log_table').DataTable(plex_log_table_options);
|
||||
}
|
||||
|
||||
$("#plexpy-logs-btn").click(function() {
|
||||
function LoadNotificationLogs() {
|
||||
notification_log_table_options.ajax = {
|
||||
url: "get_notification_log",
|
||||
type: 'post',
|
||||
data: function (d) {
|
||||
return {
|
||||
json_data: JSON.stringify(d)
|
||||
};
|
||||
}
|
||||
}
|
||||
notification_log_table = $('#notification_log_table').DataTable(notification_log_table_options);
|
||||
}
|
||||
|
||||
$("#plexpy-logs-btn").click(function () {
|
||||
$("#clear-logs").show();
|
||||
LoadPlexPyLogs();
|
||||
clearSearchButton('log_table', log_table);
|
||||
});
|
||||
|
||||
$("#plex-logs-btn").click(function() {
|
||||
$("#plex-logs-btn").click(function () {
|
||||
$("#clear-logs").hide();
|
||||
LoadPlexLogs();
|
||||
clearSearchButton('plex_log_table', plex_log_table);
|
||||
});
|
||||
|
||||
$("#plex-scanner-logs-btn").click(function() {
|
||||
$("#plex-scanner-logs-btn").click(function () {
|
||||
$("#clear-logs").hide();
|
||||
LoadPlexScannerLogs();
|
||||
clearSearchButton('plex_scanner_log_table', plex_scanner_log_table);
|
||||
});
|
||||
|
||||
$("#clear-logs").click(function() {
|
||||
$("#notification-logs-btn").click(function () {
|
||||
$("#clear-logs").hide();
|
||||
LoadNotificationLogs();
|
||||
clearSearchButton('notification_log_table', notification_log_table);
|
||||
});
|
||||
|
||||
$("#clear-logs").click(function () {
|
||||
var r = confirm("Are you sure you want to clear the PlexPy log?");
|
||||
if (r == true) {
|
||||
window.location.href = "clearLogs";
|
||||
|
|
|
@ -64,13 +64,6 @@ from plexpy import helpers
|
|||
</label>
|
||||
<p class="help-block">Trigger notification when a media item is added to the Plex Media Server.</p>
|
||||
</div>
|
||||
<div class="checkbox">
|
||||
<label>
|
||||
<input type="checkbox" data-size="small" data-id="${data['id']}" data-config-name="${data['config_prefix']}_on_extdown" ${helpers.checked(data['on_extdown'])} class="toggle-switches">
|
||||
Notify on Plex remote access down
|
||||
</label>
|
||||
<p class="help-block">Trigger notification when the Plex Media Server cannot be reached externally.</p>
|
||||
</div>
|
||||
<div class="checkbox">
|
||||
<label>
|
||||
<input type="checkbox" data-size="small" data-id="${data['id']}" data-config-name="${data['config_prefix']}_on_intdown" ${helpers.checked(data['on_intdown'])} class="toggle-switches">
|
||||
|
@ -78,13 +71,6 @@ from plexpy import helpers
|
|||
</label>
|
||||
<p class="help-block">Trigger notification when the Plex Media Server cannot be reached internally.</p>
|
||||
</div>
|
||||
<div class="checkbox">
|
||||
<label>
|
||||
<input type="checkbox" data-size="small" data-id="${data['id']}" data-config-name="${data['config_prefix']}_on_extup" ${helpers.checked(data['on_extup'])} class="toggle-switches">
|
||||
Notify on Plex remote access back up
|
||||
</label>
|
||||
<p class="help-block">Trigger notification when the Plex Media Server can be reached externally after being down.</p>
|
||||
</div>
|
||||
<div class="checkbox">
|
||||
<label>
|
||||
<input type="checkbox" data-size="small" data-id="${data['id']}" data-config-name="${data['config_prefix']}_on_intup" ${helpers.checked(data['on_intup'])} class="toggle-switches">
|
||||
|
@ -92,6 +78,20 @@ from plexpy import helpers
|
|||
</label>
|
||||
<p class="help-block">Trigger notification when the Plex Media Server can be reached internally after being down.</p>
|
||||
</div>
|
||||
<div class="checkbox">
|
||||
<label>
|
||||
<input type="checkbox" data-size="small" data-id="${data['id']}" data-config-name="${data['config_prefix']}_on_extdown" ${helpers.checked(data['on_extdown'])} class="toggle-switches">
|
||||
Notify on Plex remote access down
|
||||
</label>
|
||||
<p class="help-block">Trigger notification when the Plex Media Server cannot be reached externally.</p>
|
||||
</div>
|
||||
<div class="checkbox">
|
||||
<label>
|
||||
<input type="checkbox" data-size="small" data-id="${data['id']}" data-config-name="${data['config_prefix']}_on_extup" ${helpers.checked(data['on_extup'])} class="toggle-switches">
|
||||
Notify on Plex remote access back up
|
||||
</label>
|
||||
<p class="help-block">Trigger notification when the Plex Media Server can be reached externally after being down.</p>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
|
|
@ -68,7 +68,7 @@ available_notification_agents = sorted(notifiers.available_notification_agents()
|
|||
<td><a class="no-highlight" href="${anon_url('https://github.com/drzoidberg33/plexpy/tree/%s' % plexpy.CONFIG.GIT_BRANCH)}">${plexpy.CONFIG.GIT_BRANCH}</a></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>Git Hash:</td>
|
||||
<td>Git Commit Hash:</td>
|
||||
<td><a class="no-highlight" href="${anon_url('https://github.com/drzoidberg33/plexpy/commit/%s' % plexpy.CURRENT_VERSION)}">${plexpy.CURRENT_VERSION}</a></td>
|
||||
</tr>
|
||||
% endif
|
||||
|
@ -571,10 +571,9 @@ available_notification_agents = sorted(notifiers.available_notification_agents()
|
|||
</div>
|
||||
<div class="checkbox">
|
||||
<label>
|
||||
<input type="checkbox" id="get_file_sizes" name="get_file_sizes" value="1" ${config['get_file_sizes']}> Calculate Total File Sizes [experimental]
|
||||
<input type="checkbox" id="get_file_sizes" name="get_file_sizes" value="1" ${config['get_file_sizes']}> Calculate Total File Sizes <span style="color: #eb8600; padding-left: 10px;">[experimental]</span>
|
||||
</label>
|
||||
<p class="help-block">Enable if you want PlexPy to calculate the total file size for TV Shows/Seasons and Artists/Albums on the media info tables.<br />
|
||||
This is currently experimental.</p>
|
||||
<p class="help-block">Enable if you want PlexPy to calculate the total file size for TV Shows/Seasons and Artists/Albums on the media info tables.</p>
|
||||
</div>
|
||||
<div class="form-group">
|
||||
<label for="anon_redirect">Anonymous Redirect</label>
|
||||
|
@ -610,10 +609,9 @@ available_notification_agents = sorted(notifiers.available_notification_agents()
|
|||
</div>
|
||||
<div class="checkbox">
|
||||
<label>
|
||||
<input type="checkbox" class="monitor-settings" id="monitoring_use_websocket" name="monitoring_use_websocket" value="1" ${config['monitoring_use_websocket']}> Use Websocket (requires restart) [experimental]
|
||||
<input type="checkbox" class="monitor-settings" id="monitoring_use_websocket" name="monitoring_use_websocket" value="1" ${config['monitoring_use_websocket']}> Use Websocket (requires restart) <span style="color: #eb8600; padding-left: 10px;">[experimental]</span>
|
||||
</label>
|
||||
<p class="help-block">Instead of polling the server at regular intervals let the server tell us when something happens.<br />
|
||||
This is currently experimental.</p>
|
||||
<p class="help-block">Instead of polling the server at regular intervals let the server tell PlexPy when something happens.</p>
|
||||
</div>
|
||||
<div class="checkbox">
|
||||
<label>
|
||||
|
@ -715,6 +713,13 @@ available_notification_agents = sorted(notifiers.available_notification_agents()
|
|||
</label>
|
||||
</div>
|
||||
|
||||
<div class="checkbox" style="padding-top: 15px;">
|
||||
<label>
|
||||
<input type="checkbox" name="notify_upload_posters" id="notify_upload_posters" value="1" ${config['notify_upload_posters']}> Enable Posters in Notifications
|
||||
</label>
|
||||
<p class="help-block">Allow PlexPy to upload Plex poster to Imgur for notifications.</p>
|
||||
</div>
|
||||
|
||||
<div class="padded-header">
|
||||
<h3>Current Activity Notifications</h3>
|
||||
</div>
|
||||
|
@ -892,23 +897,6 @@ available_notification_agents = sorted(notifiers.available_notification_agents()
|
|||
</li>
|
||||
</ul>
|
||||
</li>
|
||||
<li>
|
||||
<div class="link"><i class="fa fa-server fa-fw"></i> Plex Remote Access Down<i class="fa fa-chevron-down"></i></div>
|
||||
<ul class="submenu">
|
||||
<li>
|
||||
<div class="form-group">
|
||||
<label for="notify_on_extdown_subject_text">Subject Line</label>
|
||||
<input class="form-control" type="text" id="notify_on_extdown_subject_text" name="notify_on_extdown_subject_text" value="${config['notify_on_extdown_subject_text']}" data-parsley-trigger="change" required>
|
||||
<p class="help-block">Set a custom subject line.</p>
|
||||
</div>
|
||||
<div class="form-group">
|
||||
<label for="notify_on_extdown_body_text">Message Body</label>
|
||||
<textarea class="form-control" id="notify_on_extdown_body_text" name="notify_on_extdown_body_text" data-parsley-trigger="change" data-autoresize required>${config['notify_on_extdown_body_text']}</textarea>
|
||||
<p class="help-block">Set a custom body.</p>
|
||||
</div>
|
||||
</li>
|
||||
</ul>
|
||||
</li>
|
||||
<li>
|
||||
<div class="link"><i class="fa fa-server fa-fw"></i> Plex Server Down<i class="fa fa-chevron-down"></i></div>
|
||||
<ul class="submenu">
|
||||
|
@ -926,23 +914,6 @@ available_notification_agents = sorted(notifiers.available_notification_agents()
|
|||
</li>
|
||||
</ul>
|
||||
</li>
|
||||
<li>
|
||||
<div class="link"><i class="fa fa-server fa-fw"></i> Plex Remote Access Back Up<i class="fa fa-chevron-down"></i></div>
|
||||
<ul class="submenu">
|
||||
<li>
|
||||
<div class="form-group">
|
||||
<label for="notify_on_extup_subject_text">Subject Line</label>
|
||||
<input class="form-control" type="text" id="notify_on_extup_subject_text" name="notify_on_extup_subject_text" value="${config['notify_on_extup_subject_text']}" data-parsley-trigger="change" required>
|
||||
<p class="help-block">Set a custom subject line.</p>
|
||||
</div>
|
||||
<div class="form-group">
|
||||
<label for="notify_on_extup_body_text">Message Body</label>
|
||||
<textarea class="form-control" id="notify_on_extup_body_text" name="notify_on_extup_body_text" data-parsley-trigger="change" data-autoresize required>${config['notify_on_extup_body_text']}</textarea>
|
||||
<p class="help-block">Set a custom body.</p>
|
||||
</div>
|
||||
</li>
|
||||
</ul>
|
||||
</li>
|
||||
<li>
|
||||
<div class="link"><i class="fa fa-server fa-fw"></i> Plex Server Back Up<i class="fa fa-chevron-down"></i></div>
|
||||
<ul class="submenu">
|
||||
|
@ -960,6 +931,40 @@ available_notification_agents = sorted(notifiers.available_notification_agents()
|
|||
</li>
|
||||
</ul>
|
||||
</li>
|
||||
<li>
|
||||
<div class="link"><i class="fa fa-server fa-fw"></i> Plex Remote Access Down<i class="fa fa-chevron-down"></i></div>
|
||||
<ul class="submenu">
|
||||
<li>
|
||||
<div class="form-group">
|
||||
<label for="notify_on_extdown_subject_text">Subject Line</label>
|
||||
<input class="form-control" type="text" id="notify_on_extdown_subject_text" name="notify_on_extdown_subject_text" value="${config['notify_on_extdown_subject_text']}" data-parsley-trigger="change" required>
|
||||
<p class="help-block">Set a custom subject line.</p>
|
||||
</div>
|
||||
<div class="form-group">
|
||||
<label for="notify_on_extdown_body_text">Message Body</label>
|
||||
<textarea class="form-control" id="notify_on_extdown_body_text" name="notify_on_extdown_body_text" data-parsley-trigger="change" data-autoresize required>${config['notify_on_extdown_body_text']}</textarea>
|
||||
<p class="help-block">Set a custom body.</p>
|
||||
</div>
|
||||
</li>
|
||||
</ul>
|
||||
</li>
|
||||
<li>
|
||||
<div class="link"><i class="fa fa-server fa-fw"></i> Plex Remote Access Back Up<i class="fa fa-chevron-down"></i></div>
|
||||
<ul class="submenu">
|
||||
<li>
|
||||
<div class="form-group">
|
||||
<label for="notify_on_extup_subject_text">Subject Line</label>
|
||||
<input class="form-control" type="text" id="notify_on_extup_subject_text" name="notify_on_extup_subject_text" value="${config['notify_on_extup_subject_text']}" data-parsley-trigger="change" required>
|
||||
<p class="help-block">Set a custom subject line.</p>
|
||||
</div>
|
||||
<div class="form-group">
|
||||
<label for="notify_on_extup_body_text">Message Body</label>
|
||||
<textarea class="form-control" id="notify_on_extup_body_text" name="notify_on_extup_body_text" data-parsley-trigger="change" data-autoresize required>${config['notify_on_extup_body_text']}</textarea>
|
||||
<p class="help-block">Set a custom body.</p>
|
||||
</div>
|
||||
</li>
|
||||
</ul>
|
||||
</li>
|
||||
</ul>
|
||||
<ul id="accordion-scripts" class="accordion list-unstyled">
|
||||
<li>
|
||||
|
@ -1482,8 +1487,7 @@ available_notification_agents = sorted(notifiers.available_notification_agents()
|
|||
</tr>
|
||||
<tr>
|
||||
<td><strong>{poster_url}</strong></td>
|
||||
<td>A URL for the movie or TV show poster.
|
||||
<p class="small-muted">(PMS agent must be Freebase or TheTVDB)</p></td>
|
||||
<td>A URL for the movie, TV show, or album poster.</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td><strong>{imdb_id}</strong></td>
|
||||
|
@ -1947,6 +1951,7 @@ $(document).ready(function() {
|
|||
if (data !== 'true') {
|
||||
$("#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("disabled", true);
|
||||
$("#monitor_remote_access").attr("checked", false);
|
||||
}
|
||||
}
|
||||
});
|
||||
|
|
|
@ -443,10 +443,10 @@ def dbcheck():
|
|||
|
||||
# notify_log table :: This is a table which logs notifications sent
|
||||
c_db.execute(
|
||||
'CREATE TABLE IF NOT EXISTS notify_log (id INTEGER PRIMARY KEY AUTOINCREMENT, '
|
||||
'session_key INTEGER, rating_key INTEGER, user_id INTEGER, user TEXT, '
|
||||
'agent_id INTEGER, agent_name TEXT, on_play INTEGER, on_stop INTEGER, on_watched INTEGER, '
|
||||
'on_pause INTEGER, on_resume INTEGER, on_buffer INTEGER, on_created INTEGER)'
|
||||
'CREATE TABLE IF NOT EXISTS notify_log (id INTEGER PRIMARY KEY AUTOINCREMENT, timestamp INTEGER, '
|
||||
'session_key INTEGER, rating_key INTEGER, parent_rating_key INTEGER, grandparent_rating_key INTEGER, '
|
||||
'user_id INTEGER, user TEXT, agent_id INTEGER, agent_name TEXT, notify_action TEXT, '
|
||||
'subject_text TEXT, body_text TEXT, script_args TEXT, poster_url TEXT)'
|
||||
)
|
||||
|
||||
# library_sections table :: This table keeps record of the servers library sections
|
||||
|
@ -724,6 +724,53 @@ def dbcheck():
|
|||
'ALTER TABLE notify_log ADD COLUMN on_created INTEGER'
|
||||
)
|
||||
|
||||
# Upgrade notify_log table from earlier versions
|
||||
try:
|
||||
c_db.execute('SELECT poster_url FROM notify_log')
|
||||
except sqlite3.OperationalError:
|
||||
logger.debug(u"Altering database. Updating database table notify_log.")
|
||||
c_db.execute(
|
||||
'ALTER TABLE notify_log ADD COLUMN poster_url TEXT'
|
||||
)
|
||||
|
||||
# Upgrade notify_log table from earlier versions (populate table with data from notify_log)
|
||||
try:
|
||||
c_db.execute('SELECT timestamp FROM notify_log')
|
||||
except sqlite3.OperationalError:
|
||||
logger.debug(u"Altering database. Updating database table notify_log.")
|
||||
c_db.execute(
|
||||
'CREATE TABLE IF NOT EXISTS notify_log_temp (id INTEGER PRIMARY KEY AUTOINCREMENT, timestamp INTEGER, '
|
||||
'session_key INTEGER, rating_key INTEGER, parent_rating_key INTEGER, grandparent_rating_key INTEGER, '
|
||||
'user_id INTEGER, user TEXT, agent_id INTEGER, agent_name TEXT, notify_action TEXT, '
|
||||
'subject_text TEXT, body_text TEXT, script_args TEXT, poster_url TEXT)'
|
||||
)
|
||||
c_db.execute(
|
||||
'INSERT INTO notify_log_temp (session_key, rating_key, user_id, user, agent_id, agent_name, '
|
||||
'poster_url, timestamp, notify_action) '
|
||||
'SELECT session_key, rating_key, user_id, user, agent_id, agent_name, poster_url, timestamp, '
|
||||
'notify_action FROM notify_log_temp '
|
||||
'UNION ALL SELECT session_key, rating_key, user_id, user, agent_id, agent_name, poster_url, '
|
||||
'on_play, "play" FROM notify_log WHERE on_play '
|
||||
'UNION ALL SELECT session_key, rating_key, user_id, user, agent_id, agent_name, poster_url, '
|
||||
'on_stop, "stop" FROM notify_log WHERE on_stop '
|
||||
'UNION ALL SELECT session_key, rating_key, user_id, user, agent_id, agent_name, poster_url, '
|
||||
'on_watched, "watched" FROM notify_log WHERE on_watched '
|
||||
'UNION ALL SELECT session_key, rating_key, user_id, user, agent_id, agent_name, poster_url, '
|
||||
'on_pause, "pause" FROM notify_log WHERE on_pause '
|
||||
'UNION ALL SELECT session_key, rating_key, user_id, user, agent_id, agent_name, poster_url, '
|
||||
'on_resume, "resume" FROM notify_log WHERE on_resume '
|
||||
'UNION ALL SELECT session_key, rating_key, user_id, user, agent_id, agent_name, poster_url, '
|
||||
'on_buffer, "buffer" FROM notify_log WHERE on_buffer '
|
||||
'UNION ALL SELECT session_key, rating_key, user_id, user, agent_id, agent_name, poster_url, '
|
||||
'on_created, "created" FROM notify_log WHERE on_created '
|
||||
'ORDER BY timestamp ')
|
||||
c_db.execute(
|
||||
'DROP TABLE notify_log'
|
||||
)
|
||||
c_db.execute(
|
||||
'ALTER TABLE notify_log_temp RENAME TO notify_log'
|
||||
)
|
||||
|
||||
# Upgrade library_sections table from earlier versions (remove UNIQUE constraint on section_id)
|
||||
try:
|
||||
result = c_db.execute('SELECT SQL FROM sqlite_master WHERE type="table" AND name="library_sections"').fetchone()
|
||||
|
|
|
@ -191,6 +191,7 @@ _CONFIG_DEFINITIONS = {
|
|||
'NMA_ON_EXTUP': (int, 'NMA', 0),
|
||||
'NMA_ON_INTUP': (int, 'NMA', 0),
|
||||
'NOTIFY_CONSECUTIVE': (int, 'Monitoring', 1),
|
||||
'NOTIFY_UPLOAD_POSTERS': (int, 'Monitoring', 0),
|
||||
'NOTIFY_RECENTLY_ADDED': (int, 'Monitoring', 0),
|
||||
'NOTIFY_RECENTLY_ADDED_GRANDPARENT': (int, 'Monitoring', 0),
|
||||
'NOTIFY_RECENTLY_ADDED_DELAY': (int, 'Monitoring', 60),
|
||||
|
|
|
@ -843,19 +843,45 @@ class DataFactory(object):
|
|||
def get_session_ip(self, session_key=''):
|
||||
monitor_db = database.MonitorDatabase()
|
||||
|
||||
ip_address = 'N/A'
|
||||
|
||||
if session_key:
|
||||
try:
|
||||
query = 'SELECT ip_address FROM sessions WHERE session_key = %d' % int(session_key)
|
||||
result = monitor_db.select(query)
|
||||
except Exception as e:
|
||||
logger.warn(u"PlexPy DataFactory :: Unable to execute database query for get_session_ip: %s." % e)
|
||||
return ip_address
|
||||
else:
|
||||
return None
|
||||
|
||||
ip_address = 'N/A'
|
||||
return ip_address
|
||||
|
||||
for item in result:
|
||||
ip_address = item['ip_address']
|
||||
|
||||
return ip_address
|
||||
|
||||
def get_poster_url(self, rating_key=''):
|
||||
monitor_db = database.MonitorDatabase()
|
||||
|
||||
poster_url = ''
|
||||
|
||||
if rating_key:
|
||||
try:
|
||||
query = 'SELECT id, poster_url FROM notify_log ' \
|
||||
'WHERE rating_key = %d OR parent_rating_key = %d OR grandparent_rating_key = %d ' \
|
||||
'ORDER BY id DESC LIMIT 1' % (int(rating_key), int(rating_key), int(rating_key))
|
||||
result = monitor_db.select(query)
|
||||
except Exception as e:
|
||||
logger.warn(u"PlexPy DataFactory :: Unable to execute database query for get_poster_url: %s." % e)
|
||||
return poster_url
|
||||
else:
|
||||
return poster_url
|
||||
|
||||
for item in result:
|
||||
poster_url = item['poster_url']
|
||||
|
||||
return poster_url
|
||||
|
||||
def get_search_query(self, rating_key=''):
|
||||
monitor_db = database.MonitorDatabase()
|
||||
|
||||
|
@ -1095,3 +1121,71 @@ class DataFactory(object):
|
|||
old_rating_key]
|
||||
|
||||
monitor_db.action(query=query, args=args)
|
||||
|
||||
def get_notification_log(self, kwargs=None):
|
||||
data_tables = datatables.DataTables()
|
||||
|
||||
columns = ['notify_log.id',
|
||||
'notify_log.timestamp',
|
||||
'notify_log.session_key',
|
||||
'notify_log.rating_key',
|
||||
'notify_log.user_id',
|
||||
'notify_log.user',
|
||||
'notify_log.agent_id',
|
||||
'notify_log.agent_name',
|
||||
'notify_log.notify_action',
|
||||
'notify_log.subject_text',
|
||||
'notify_log.body_text',
|
||||
'notify_log.script_args',
|
||||
'notify_log.poster_url',
|
||||
]
|
||||
try:
|
||||
query = data_tables.ssp_query(table_name='notify_log',
|
||||
columns=columns,
|
||||
custom_where=[],
|
||||
group_by=[],
|
||||
join_types=[],
|
||||
join_tables=[],
|
||||
join_evals=[],
|
||||
kwargs=kwargs)
|
||||
except Exception as e:
|
||||
logger.warn(u"PlexPy DataFactory :: Unable to execute database query for get_notification_log: %s." % e)
|
||||
return {'recordsFiltered': 0,
|
||||
'recordsTotal': 0,
|
||||
'draw': 0,
|
||||
'data': 'null',
|
||||
'error': 'Unable to execute database query.'}
|
||||
|
||||
notifications = query['result']
|
||||
|
||||
rows = []
|
||||
for item in notifications:
|
||||
if item['body_text']:
|
||||
body_text = item['body_text'].replace('\r\n', '<br />').replace('\n', '<br />')
|
||||
else:
|
||||
body_text = ''
|
||||
|
||||
row = {'id': item['id'],
|
||||
'timestamp': item['timestamp'],
|
||||
'session_key': item['session_key'],
|
||||
'rating_key': item['rating_key'],
|
||||
'user_id': item['user_id'],
|
||||
'user': item['user'],
|
||||
'agent_id': item['agent_id'],
|
||||
'agent_name': item['agent_name'],
|
||||
'notify_action': item['notify_action'],
|
||||
'subject_text': item['subject_text'],
|
||||
'body_text': body_text,
|
||||
'script_args': item['script_args'],
|
||||
'poster_url': item['poster_url']
|
||||
}
|
||||
|
||||
rows.append(row)
|
||||
|
||||
dict = {'recordsFiltered': query['filteredCount'],
|
||||
'recordsTotal': query['totalCount'],
|
||||
'data': rows,
|
||||
'draw': query['draw']
|
||||
}
|
||||
|
||||
return dict
|
|
@ -543,9 +543,10 @@ def uploadToImgur(imgPath, imgTitle=''):
|
|||
data = {'type': 'base64',
|
||||
'image': base64.b64encode(img)}
|
||||
if imgTitle:
|
||||
data['title'] = imgTitle
|
||||
data['name'] = imgTitle + '.jpg'
|
||||
data['title'] = imgTitle.encode('utf-8')
|
||||
data['name'] = imgTitle.encode('utf-8') + '.jpg'
|
||||
|
||||
try:
|
||||
request = urllib2.Request('https://api.imgur.com/3/image', headers=headers, data=urllib.urlencode(data))
|
||||
response = urllib2.urlopen(request)
|
||||
response = json.loads(response.read())
|
||||
|
@ -557,5 +558,7 @@ def uploadToImgur(imgPath, imgTitle=''):
|
|||
logger.warn(u"PlexPy Helpers :: Unable to upload image to Imgur: %s" % response.reason)
|
||||
else:
|
||||
logger.warn(u"PlexPy Helpers :: Unable to upload image to Imgur.")
|
||||
except urllib2.HTTPError as e:
|
||||
logger.warn(u"PlexPy Helpers :: Unable to upload image to Imgur: %s" % e)
|
||||
|
||||
return img_url
|
|
@ -20,7 +20,7 @@ import re
|
|||
import time
|
||||
import urllib
|
||||
|
||||
from plexpy import logger, config, notifiers, database, helpers, plextv, pmsconnect
|
||||
from plexpy import logger, config, notifiers, database, helpers, plextv, pmsconnect, datafactory
|
||||
import plexpy
|
||||
|
||||
|
||||
|
@ -50,168 +50,201 @@ def notify(stream_data=None, notify_action=None):
|
|||
for agent in notifiers.available_notification_agents():
|
||||
if agent['on_play'] and notify_action == 'play':
|
||||
# Build and send notification
|
||||
notify_strings = build_notify_text(session=stream_data, state=notify_action)
|
||||
notify_strings, metadata = build_notify_text(session=stream_data, notify_action=notify_action)
|
||||
notifiers.send_notification(agent_id=agent['id'],
|
||||
subject=notify_strings[0],
|
||||
body=notify_strings[1],
|
||||
notify_action=notify_action,
|
||||
script_args=notify_strings[2],
|
||||
metadata=notify_strings[3])
|
||||
notify_action=notify_action,
|
||||
metadata=metadata)
|
||||
|
||||
# Set the notification state in the db
|
||||
set_notify_state(session=stream_data, state=notify_action, agent_info=agent)
|
||||
set_notify_state(session=stream_data,
|
||||
notify_action=notify_action,
|
||||
agent_info=agent,
|
||||
notify_strings=notify_strings,
|
||||
metadata=metadata)
|
||||
|
||||
elif agent['on_stop'] and notify_action == 'stop' \
|
||||
and (plexpy.CONFIG.NOTIFY_CONSECUTIVE or progress_percent < plexpy.CONFIG.NOTIFY_WATCHED_PERCENT):
|
||||
# Build and send notification
|
||||
notify_strings = build_notify_text(session=stream_data, state=notify_action)
|
||||
notify_strings, metadata = build_notify_text(session=stream_data, notify_action=notify_action)
|
||||
notifiers.send_notification(agent_id=agent['id'],
|
||||
subject=notify_strings[0],
|
||||
body=notify_strings[1],
|
||||
notify_action=notify_action,
|
||||
script_args=notify_strings[2],
|
||||
metadata=notify_strings[3])
|
||||
notify_action=notify_action,
|
||||
metadata=metadata)
|
||||
|
||||
set_notify_state(session=stream_data, state=notify_action, agent_info=agent)
|
||||
# Set the notification state in the db
|
||||
set_notify_state(session=stream_data,
|
||||
notify_action=notify_action,
|
||||
agent_info=agent,
|
||||
notify_strings=notify_strings,
|
||||
metadata=metadata)
|
||||
|
||||
elif agent['on_pause'] and notify_action == 'pause' \
|
||||
and (plexpy.CONFIG.NOTIFY_CONSECUTIVE or progress_percent < 99):
|
||||
# Build and send notification
|
||||
notify_strings = build_notify_text(session=stream_data, state=notify_action)
|
||||
notify_strings, metadata = build_notify_text(session=stream_data, notify_action=notify_action)
|
||||
notifiers.send_notification(agent_id=agent['id'],
|
||||
subject=notify_strings[0],
|
||||
body=notify_strings[1],
|
||||
notify_action=notify_action,
|
||||
script_args=notify_strings[2],
|
||||
metadata=notify_strings[3])
|
||||
notify_action=notify_action,
|
||||
metadata=metadata)
|
||||
|
||||
set_notify_state(session=stream_data, state=notify_action, agent_info=agent)
|
||||
# Set the notification state in the db
|
||||
set_notify_state(session=stream_data,
|
||||
notify_action=notify_action,
|
||||
agent_info=agent,
|
||||
notify_strings=notify_strings,
|
||||
metadata=metadata)
|
||||
|
||||
elif agent['on_resume'] and notify_action == 'resume' \
|
||||
and (plexpy.CONFIG.NOTIFY_CONSECUTIVE or progress_percent < 99):
|
||||
# Build and send notification
|
||||
notify_strings = build_notify_text(session=stream_data, state=notify_action)
|
||||
notify_strings, metadata = build_notify_text(session=stream_data, notify_action=notify_action)
|
||||
notifiers.send_notification(agent_id=agent['id'],
|
||||
subject=notify_strings[0],
|
||||
body=notify_strings[1],
|
||||
notify_action=notify_action,
|
||||
script_args=notify_strings[2],
|
||||
metadata=notify_strings[3])
|
||||
notify_action=notify_action,
|
||||
metadata=metadata)
|
||||
|
||||
set_notify_state(session=stream_data, state=notify_action, agent_info=agent)
|
||||
# Set the notification state in the db
|
||||
set_notify_state(session=stream_data,
|
||||
notify_action=notify_action,
|
||||
agent_info=agent,
|
||||
notify_strings=notify_strings,
|
||||
metadata=metadata)
|
||||
|
||||
elif agent['on_buffer'] and notify_action == 'buffer':
|
||||
# Build and send notification
|
||||
notify_strings = build_notify_text(session=stream_data, state=notify_action)
|
||||
notify_strings, metadata = build_notify_text(session=stream_data, notify_action=notify_action)
|
||||
notifiers.send_notification(agent_id=agent['id'],
|
||||
subject=notify_strings[0],
|
||||
body=notify_strings[1],
|
||||
script_args=notify_strings[2],
|
||||
notify_action=notify_action,
|
||||
script_args=notify_strings[2])
|
||||
metadata=metadata)
|
||||
|
||||
set_notify_state(session=stream_data, state=notify_action, agent_info=agent)
|
||||
# Set the notification state in the db
|
||||
set_notify_state(session=stream_data,
|
||||
notify_action=notify_action,
|
||||
agent_info=agent,
|
||||
notify_strings=notify_strings,
|
||||
metadata=metadata)
|
||||
|
||||
elif agent['on_watched'] and notify_action == 'watched':
|
||||
# Get the current states for notifications from our db
|
||||
notify_states = get_notify_state(session=stream_data)
|
||||
|
||||
# If there is nothing in the notify_log for our agent id but it is enabled we should notify
|
||||
if not any(d['agent_id'] == agent['id'] for d in notify_states):
|
||||
if not any(d['agent_id'] == agent['id'] and d['notify_action'] == notify_action for d in notify_states):
|
||||
# Build and send notification
|
||||
notify_strings = build_notify_text(session=stream_data, state=notify_action)
|
||||
notify_strings, metadata = build_notify_text(session=stream_data, notify_action=notify_action)
|
||||
notifiers.send_notification(agent_id=agent['id'],
|
||||
subject=notify_strings[0],
|
||||
body=notify_strings[1],
|
||||
notify_action=notify_action,
|
||||
script_args=notify_strings[2],
|
||||
metadata=notify_strings[3])
|
||||
notify_action=notify_action,
|
||||
metadata=metadata)
|
||||
|
||||
# Set the notification state in the db
|
||||
set_notify_state(session=stream_data, state=notify_action, agent_info=agent)
|
||||
|
||||
else:
|
||||
# Check in our notify log if the notification has already been sent
|
||||
for notify_state in notify_states:
|
||||
if not notify_state['on_watched'] and (notify_state['agent_id'] == agent['id']):
|
||||
# Build and send notification
|
||||
notify_strings = build_notify_text(session=stream_data, state=notify_action)
|
||||
notifiers.send_notification(agent_id=agent['id'],
|
||||
subject=notify_strings[0],
|
||||
body=notify_strings[1],
|
||||
set_notify_state(session=stream_data,
|
||||
notify_action=notify_action,
|
||||
script_args=notify_strings[2],
|
||||
metadata=notify_strings[3])
|
||||
|
||||
# Set the notification state in the db
|
||||
set_notify_state(session=stream_data, state=notify_action, agent_info=agent)
|
||||
agent_info=agent,
|
||||
notify_strings=notify_strings,
|
||||
metadata=metadata)
|
||||
|
||||
elif (stream_data['media_type'] == 'track' and plexpy.CONFIG.MUSIC_NOTIFY_ENABLE):
|
||||
|
||||
for agent in notifiers.available_notification_agents():
|
||||
if agent['on_play'] and notify_action == 'play':
|
||||
# Build and send notification
|
||||
notify_strings = build_notify_text(session=stream_data, state=notify_action)
|
||||
notify_strings, metadata = build_notify_text(session=stream_data, notify_action=notify_action)
|
||||
notifiers.send_notification(agent_id=agent['id'],
|
||||
subject=notify_strings[0],
|
||||
body=notify_strings[1],
|
||||
notify_action=notify_action,
|
||||
script_args=notify_strings[2],
|
||||
metadata=notify_strings[3])
|
||||
notify_action=notify_action,
|
||||
metadata=metadata)
|
||||
|
||||
# Set the notification state in the db
|
||||
set_notify_state(session=stream_data, state=notify_action, agent_info=agent)
|
||||
set_notify_state(session=stream_data,
|
||||
notify_action=notify_action,
|
||||
agent_info=agent,
|
||||
notify_strings=notify_strings,
|
||||
metadata=metadata)
|
||||
|
||||
elif agent['on_stop'] and notify_action == 'stop':
|
||||
# Build and send notification
|
||||
notify_strings = build_notify_text(session=stream_data, state=notify_action)
|
||||
notify_strings, metadata = build_notify_text(session=stream_data, notify_action=notify_action)
|
||||
notifiers.send_notification(agent_id=agent['id'],
|
||||
subject=notify_strings[0],
|
||||
body=notify_strings[1],
|
||||
notify_action=notify_action,
|
||||
script_args=notify_strings[2],
|
||||
metadata=notify_strings[3])
|
||||
notify_action=notify_action,
|
||||
metadata=metadata)
|
||||
|
||||
# Set the notification state in the db
|
||||
set_notify_state(session=stream_data, state=notify_action, agent_info=agent)
|
||||
set_notify_state(session=stream_data,
|
||||
notify_action=notify_action,
|
||||
agent_info=agent,
|
||||
notify_strings=notify_strings,
|
||||
metadata=metadata)
|
||||
|
||||
elif agent['on_pause'] and notify_action == 'pause':
|
||||
# Build and send notification
|
||||
notify_strings = build_notify_text(session=stream_data, state=notify_action)
|
||||
notify_strings, metadata = build_notify_text(session=stream_data, notify_action=notify_action)
|
||||
notifiers.send_notification(agent_id=agent['id'],
|
||||
subject=notify_strings[0],
|
||||
body=notify_strings[1],
|
||||
notify_action=notify_action,
|
||||
script_args=notify_strings[2],
|
||||
metadata=notify_strings[3])
|
||||
notify_action=notify_action,
|
||||
metadata=metadata)
|
||||
|
||||
# Set the notification state in the db
|
||||
set_notify_state(session=stream_data, state=notify_action, agent_info=agent)
|
||||
set_notify_state(session=stream_data,
|
||||
notify_action=notify_action,
|
||||
agent_info=agent,
|
||||
notify_strings=notify_strings,
|
||||
metadata=metadata)
|
||||
|
||||
elif agent['on_resume'] and notify_action == 'resume':
|
||||
# Build and send notification
|
||||
notify_strings = build_notify_text(session=stream_data, state=notify_action)
|
||||
notify_strings, metadata = build_notify_text(session=stream_data, notify_action=notify_action)
|
||||
notifiers.send_notification(agent_id=agent['id'],
|
||||
subject=notify_strings[0],
|
||||
body=notify_strings[1],
|
||||
notify_action=notify_action,
|
||||
script_args=notify_strings[2],
|
||||
metadata=notify_strings[3])
|
||||
notify_action=notify_action,
|
||||
metadata=metadata)
|
||||
|
||||
# Set the notification state in the db
|
||||
set_notify_state(session=stream_data, state=notify_action, agent_info=agent)
|
||||
set_notify_state(session=stream_data,
|
||||
notify_action=notify_action,
|
||||
agent_info=agent,
|
||||
notify_strings=notify_strings,
|
||||
metadata=metadata)
|
||||
|
||||
elif agent['on_buffer'] and notify_action == 'buffer':
|
||||
# Build and send notification
|
||||
notify_strings = build_notify_text(session=stream_data, state=notify_action)
|
||||
notify_strings, metadata = build_notify_text(session=stream_data, notify_action=notify_action)
|
||||
notifiers.send_notification(agent_id=agent['id'],
|
||||
subject=notify_strings[0],
|
||||
body=notify_strings[1],
|
||||
notify_action=notify_action,
|
||||
script_args=notify_strings[2],
|
||||
metadata=notify_strings[3])
|
||||
notify_action=notify_action,
|
||||
metadata=metadata)
|
||||
|
||||
# Set the notification state in the db
|
||||
set_notify_state(session=stream_data, state=notify_action, agent_info=agent)
|
||||
set_notify_state(session=stream_data,
|
||||
notify_action=notify_action,
|
||||
agent_info=agent,
|
||||
notify_strings=notify_strings,
|
||||
metadata=metadata)
|
||||
|
||||
elif stream_data['media_type'] == 'clip':
|
||||
pass
|
||||
|
@ -227,133 +260,142 @@ def notify_timeline(timeline_data=None, notify_action=None):
|
|||
for agent in notifiers.available_notification_agents():
|
||||
if agent['on_created'] and notify_action == 'created':
|
||||
# Build and send notification
|
||||
notify_strings = build_notify_text(timeline=timeline_data, state=notify_action)
|
||||
notify_strings, metadata = build_notify_text(timeline=timeline_data, notify_action=notify_action)
|
||||
notifiers.send_notification(agent_id=agent['id'],
|
||||
subject=notify_strings[0],
|
||||
body=notify_strings[1],
|
||||
notify_action=notify_action,
|
||||
script_args=notify_strings[2],
|
||||
metadata=notify_strings[3])
|
||||
notify_action=notify_action,
|
||||
metadata=metadata)
|
||||
|
||||
# Set the notification state in the db
|
||||
set_notify_state(session=timeline_data, state=notify_action, agent_info=agent)
|
||||
set_notify_state(session=stream_data,
|
||||
notify_action=notify_action,
|
||||
agent_info=agent,
|
||||
notify_strings=notify_strings,
|
||||
metadata=metadata)
|
||||
|
||||
elif not timeline_data and notify_action:
|
||||
for agent in notifiers.available_notification_agents():
|
||||
if agent['on_extdown'] and notify_action == 'extdown':
|
||||
# Build and send notification
|
||||
notify_strings = build_server_notify_text(state=notify_action)
|
||||
notify_strings = build_server_notify_text(notify_action=notify_action)
|
||||
notifiers.send_notification(agent_id=agent['id'],
|
||||
subject=notify_strings[0],
|
||||
body=notify_strings[1],
|
||||
script_args=notify_strings[2],
|
||||
notify_action=notify_action)
|
||||
|
||||
# Set the notification state in the db
|
||||
set_notify_state(session={},
|
||||
notify_action=notify_action,
|
||||
script_args=notify_strings[2])
|
||||
agent_info=agent,
|
||||
notify_strings=notify_strings,
|
||||
metadata={})
|
||||
|
||||
if agent['on_intdown'] and notify_action == 'intdown':
|
||||
# Build and send notification
|
||||
notify_strings = build_server_notify_text(state=notify_action)
|
||||
notify_strings = build_server_notify_text(notify_action=notify_action)
|
||||
notifiers.send_notification(agent_id=agent['id'],
|
||||
subject=notify_strings[0],
|
||||
body=notify_strings[1],
|
||||
script_args=notify_strings[2],
|
||||
notify_action=notify_action)
|
||||
|
||||
# Set the notification state in the db
|
||||
set_notify_state(session={},
|
||||
notify_action=notify_action,
|
||||
script_args=notify_strings[2])
|
||||
agent_info=agent,
|
||||
notify_strings=notify_strings,
|
||||
metadata={})
|
||||
|
||||
if agent['on_extup'] and notify_action == 'extup':
|
||||
# Build and send notification
|
||||
notify_strings = build_server_notify_text(state=notify_action)
|
||||
notify_strings = build_server_notify_text(notify_action=notify_action)
|
||||
notifiers.send_notification(agent_id=agent['id'],
|
||||
subject=notify_strings[0],
|
||||
body=notify_strings[1],
|
||||
script_args=notify_strings[2],
|
||||
notify_action=notify_action)
|
||||
|
||||
# Set the notification state in the db
|
||||
set_notify_state(session={},
|
||||
notify_action=notify_action,
|
||||
script_args=notify_strings[2])
|
||||
agent_info=agent,
|
||||
notify_strings=notify_strings,
|
||||
metadata={})
|
||||
|
||||
if agent['on_intup'] and notify_action == 'intup':
|
||||
# Build and send notification
|
||||
notify_strings = build_server_notify_text(state=notify_action)
|
||||
notify_strings = build_server_notify_text(notify_action=notify_action)
|
||||
notifiers.send_notification(agent_id=agent['id'],
|
||||
subject=notify_strings[0],
|
||||
body=notify_strings[1],
|
||||
script_args=notify_strings[2],
|
||||
notify_action=notify_action)
|
||||
|
||||
# Set the notification state in the db
|
||||
set_notify_state(session={},
|
||||
notify_action=notify_action,
|
||||
script_args=notify_strings[2])
|
||||
agent_info=agent,
|
||||
notify_strings=notify_strings,
|
||||
metadata={})
|
||||
|
||||
else:
|
||||
logger.debug(u"PlexPy NotificationHandler :: Notify timeline called but incomplete data received.")
|
||||
|
||||
|
||||
def get_notify_state(session):
|
||||
monitor_db = database.MonitorDatabase()
|
||||
result = monitor_db.select('SELECT on_play, on_stop, on_pause, on_resume, on_buffer, on_watched, agent_id '
|
||||
result = monitor_db.select('SELECT timestamp, notify_action, agent_id '
|
||||
'FROM notify_log '
|
||||
'WHERE session_key = ? '
|
||||
'AND rating_key = ? '
|
||||
'AND user = ? '
|
||||
'AND user_id = ? '
|
||||
'ORDER BY id DESC',
|
||||
args=[session['session_key'], session['rating_key'], session['user']])
|
||||
args=[session['session_key'], session['rating_key'], session['user_id']])
|
||||
notify_states = []
|
||||
for item in result:
|
||||
notify_state = {'on_play': item['on_play'],
|
||||
'on_stop': item['on_stop'],
|
||||
'on_pause': item['on_pause'],
|
||||
'on_resume': item['on_resume'],
|
||||
'on_buffer': item['on_buffer'],
|
||||
'on_watched': item['on_watched'],
|
||||
notify_state = {'timestamp': item['timestamp'],
|
||||
'notify_action': item['notify_action'],
|
||||
'agent_id': item['agent_id']}
|
||||
notify_states.append(notify_state)
|
||||
|
||||
return notify_states
|
||||
|
||||
|
||||
def get_notify_state_timeline(timeline):
|
||||
monitor_db = database.MonitorDatabase()
|
||||
result = monitor_db.select('SELECT on_created, agent_id '
|
||||
'FROM notify_log '
|
||||
'WHERE rating_key = ? '
|
||||
'ORDER BY id DESC',
|
||||
args=[timeline['rating_key']])
|
||||
notify_states = []
|
||||
for item in result:
|
||||
notify_state = {'on_created': item['on_created'],
|
||||
'agent_id': item['agent_id']}
|
||||
notify_states.append(notify_state)
|
||||
def set_notify_state(session, notify_action, agent_info, notify_strings, metadata):
|
||||
|
||||
return notify_states
|
||||
|
||||
|
||||
def set_notify_state(session, state, agent_info):
|
||||
|
||||
if session and state and agent_info:
|
||||
if notify_action and agent_info:
|
||||
monitor_db = database.MonitorDatabase()
|
||||
|
||||
if state == 'play':
|
||||
values = {'on_play': int(time.time())}
|
||||
elif state == 'stop':
|
||||
values = {'on_stop': int(time.time())}
|
||||
elif state == 'pause':
|
||||
values = {'on_pause': int(time.time())}
|
||||
elif state == 'resume':
|
||||
values = {'on_resume': int(time.time())}
|
||||
elif state == 'buffer':
|
||||
values = {'on_buffer': int(time.time())}
|
||||
elif state == 'watched':
|
||||
values = {'on_watched': int(time.time())}
|
||||
elif state == 'created':
|
||||
values = {'on_created': int(time.time())}
|
||||
if notify_strings[2]:
|
||||
script_args = '[' + ', '.join(notify_strings[2]) + ']'
|
||||
else:
|
||||
return
|
||||
script_args = None
|
||||
|
||||
if state == 'created':
|
||||
keys = {'rating_key': session['rating_key'],
|
||||
keys = {'timestamp': int(time.time()),
|
||||
'session_key': session.get('session_key', None),
|
||||
'rating_key': session.get('rating_key', None),
|
||||
'user_id': session.get('user_id', None),
|
||||
'agent_id': agent_info['id'],
|
||||
'agent_name': agent_info['name']}
|
||||
else:
|
||||
keys = {'session_key': session['session_key'],
|
||||
'rating_key': session['rating_key'],
|
||||
'user_id': session['user_id'],
|
||||
'user': session['user'],
|
||||
'agent_id': agent_info['id'],
|
||||
'agent_name': agent_info['name']}
|
||||
'notify_action': notify_action}
|
||||
|
||||
values = {'parent_rating_key': session.get('parent_rating_key', None),
|
||||
'grandparent_rating_key': session.get('grandparent_rating_key', None),
|
||||
'user': session.get('user', None),
|
||||
'agent_name': agent_info['name'],
|
||||
'subject_text': notify_strings[0],
|
||||
'body_text': notify_strings[1],
|
||||
'script_args': script_args,
|
||||
'poster_url': metadata.get('poster_url', None)}
|
||||
|
||||
monitor_db.upsert(table_name='notify_log', key_dict=keys, value_dict=values)
|
||||
else:
|
||||
logger.error(u"PlexPy NotificationHandler :: Unable to set notify state.")
|
||||
|
||||
|
||||
def build_notify_text(session=None, timeline=None, state=None):
|
||||
def build_notify_text(session=None, timeline=None, notify_action=None):
|
||||
# Get time formats
|
||||
date_format = plexpy.CONFIG.DATE_FORMAT.replace('Do','').replace('zz','')
|
||||
time_format = plexpy.CONFIG.TIME_FORMAT.replace('Do','').replace('zz','')
|
||||
|
@ -459,7 +501,7 @@ def build_notify_text(session=None, timeline=None, state=None):
|
|||
else:
|
||||
transcode_decision = 'Direct Play'
|
||||
|
||||
if state != 'play':
|
||||
if notify_action != 'play':
|
||||
stream_duration = int((time.time() -
|
||||
helpers.cast_to_int(session.get('started', 0)) -
|
||||
helpers.cast_to_int(session.get('paused_counter', 0))) / 60)
|
||||
|
@ -504,22 +546,36 @@ def build_notify_text(session=None, timeline=None, state=None):
|
|||
|
||||
if metadata['media_type'] == 'movie' or metadata['media_type'] == 'show' or metadata['media_type'] == 'artist':
|
||||
thumb = metadata['thumb']
|
||||
poster_key = metadata['rating_key']
|
||||
poster_title = metadata['title']
|
||||
elif metadata['media_type'] == 'episode':
|
||||
thumb = metadata['grandparent_thumb']
|
||||
poster_key = metadata['grandparent_rating_key']
|
||||
poster_title = metadata['grandparent_title']
|
||||
elif metadata['media_type'] == 'track':
|
||||
thumb = metadata['parent_thumb']
|
||||
poster_key = metadata['parent_rating_key']
|
||||
poster_title = metadata['parent_title']
|
||||
else:
|
||||
thumb = None
|
||||
|
||||
if thumb:
|
||||
# Try to retrieve a poster_url from the database
|
||||
data_factory = datafactory.DataFactory()
|
||||
poster_url = data_factory.get_poster_url(rating_key=poster_key)
|
||||
|
||||
# If no previous poster_url
|
||||
if not poster_url and plexpy.CONFIG.NOTIFY_UPLOAD_POSTERS:
|
||||
# Retrieve the poster from Plex and cache to file
|
||||
urllib.urlretrieve(plexpy.CONFIG.PMS_URL + thumb + '?X-Plex-Token=' + plexpy.CONFIG.PMS_TOKEN,
|
||||
os.path.join(plexpy.CONFIG.CACHE_DIR, 'cache-poster.jpg'))
|
||||
# Upload thumb to Imgur and get link
|
||||
metadata['poster_url'] = helpers.uploadToImgur(os.path.join(plexpy.CONFIG.CACHE_DIR, 'cache-poster.jpg'), full_title)
|
||||
poster_url = helpers.uploadToImgur(os.path.join(plexpy.CONFIG.CACHE_DIR, 'cache-poster.jpg'), poster_title)
|
||||
|
||||
metadata['poster_url'] = poster_url
|
||||
|
||||
# Fix metadata params for notify recently added grandparent
|
||||
if state == 'created' and plexpy.CONFIG.NOTIFY_RECENTLY_ADDED_GRANDPARENT:
|
||||
if notify_action == 'created' and plexpy.CONFIG.NOTIFY_RECENTLY_ADDED_GRANDPARENT:
|
||||
show_name = metadata['title']
|
||||
episode_name = ''
|
||||
artist_name = metadata['title']
|
||||
|
@ -535,7 +591,7 @@ def build_notify_text(session=None, timeline=None, state=None):
|
|||
available_params = {# Global paramaters
|
||||
'server_name': server_name,
|
||||
'server_uptime': server_uptime,
|
||||
'action': state.title(),
|
||||
'action': notify_action.title(),
|
||||
'datestamp': arrow.now().format(date_format),
|
||||
'timestamp': arrow.now().format(time_format),
|
||||
# Stream parameters
|
||||
|
@ -628,7 +684,7 @@ def build_notify_text(session=None, timeline=None, state=None):
|
|||
except Exception as e:
|
||||
logger.error(u"PlexPy Notifier :: Unable to parse custom script arguments %s. Using fallback." % e)
|
||||
|
||||
if state == 'play':
|
||||
if notify_action == 'play':
|
||||
# Default body text
|
||||
body_text = '%s (%s) started playing %s' % (session['friendly_name'],
|
||||
session['player'],
|
||||
|
@ -649,10 +705,10 @@ def build_notify_text(session=None, timeline=None, state=None):
|
|||
except:
|
||||
logger.error(u"PlexPy NotificationHandler :: Unable to parse custom notification body. Using fallback.")
|
||||
|
||||
return [subject_text, body_text, script_args, metadata]
|
||||
return [subject_text, body_text, script_args], metadata
|
||||
else:
|
||||
return [subject_text, body_text, script_args, metadata]
|
||||
elif state == 'stop':
|
||||
return [subject_text, body_text, script_args], metadata
|
||||
elif notify_action == 'stop':
|
||||
# Default body text
|
||||
body_text = '%s (%s) has stopped %s' % (session['friendly_name'],
|
||||
session['player'],
|
||||
|
@ -673,10 +729,10 @@ def build_notify_text(session=None, timeline=None, state=None):
|
|||
except:
|
||||
logger.error(u"PlexPy NotificationHandler :: Unable to parse custom notification body. Using fallback.")
|
||||
|
||||
return [subject_text, body_text, script_args, metadata]
|
||||
return [subject_text, body_text, script_args], metadata
|
||||
else:
|
||||
return [subject_text, body_text, script_args, metadata]
|
||||
elif state == 'pause':
|
||||
return [subject_text, body_text, script_args], metadata
|
||||
elif notify_action == 'pause':
|
||||
# Default body text
|
||||
body_text = '%s (%s) has paused %s' % (session['friendly_name'],
|
||||
session['player'],
|
||||
|
@ -697,10 +753,10 @@ def build_notify_text(session=None, timeline=None, state=None):
|
|||
except:
|
||||
logger.error(u"PlexPy NotificationHandler :: Unable to parse custom notification body. Using fallback.")
|
||||
|
||||
return [subject_text, body_text, script_args, metadata]
|
||||
return [subject_text, body_text, script_args], metadata
|
||||
else:
|
||||
return [subject_text, body_text, script_args, metadata]
|
||||
elif state == 'resume':
|
||||
return [subject_text, body_text, script_args], metadata
|
||||
elif notify_action == 'resume':
|
||||
# Default body text
|
||||
body_text = '%s (%s) has resumed %s' % (session['friendly_name'],
|
||||
session['player'],
|
||||
|
@ -721,10 +777,10 @@ def build_notify_text(session=None, timeline=None, state=None):
|
|||
except:
|
||||
logger.error(u"PlexPy NotificationHandler :: Unable to parse custom notification body. Using fallback.")
|
||||
|
||||
return [subject_text, body_text, script_args, metadata]
|
||||
return [subject_text, body_text, script_args], metadata
|
||||
else:
|
||||
return [subject_text, body_text, script_args, metadata]
|
||||
elif state == 'buffer':
|
||||
return [subject_text, body_text, script_args], metadata
|
||||
elif notify_action == 'buffer':
|
||||
# Default body text
|
||||
body_text = '%s (%s) is buffering %s' % (session['friendly_name'],
|
||||
session['player'],
|
||||
|
@ -745,10 +801,10 @@ def build_notify_text(session=None, timeline=None, state=None):
|
|||
except:
|
||||
logger.error(u"PlexPy NotificationHandler :: Unable to parse custom notification body. Using fallback.")
|
||||
|
||||
return [subject_text, body_text, script_args, metadata]
|
||||
return [subject_text, body_text, script_args], metadata
|
||||
else:
|
||||
return [subject_text, body_text, script_args, metadata]
|
||||
elif state == 'watched':
|
||||
return [subject_text, body_text, script_args], metadata
|
||||
elif notify_action == 'watched':
|
||||
# Default body text
|
||||
body_text = '%s (%s) has watched %s' % (session['friendly_name'],
|
||||
session['player'],
|
||||
|
@ -769,10 +825,10 @@ def build_notify_text(session=None, timeline=None, state=None):
|
|||
except:
|
||||
logger.error(u"PlexPy NotificationHandler :: Unable to parse custom notification body. Using fallback.")
|
||||
|
||||
return [subject_text, body_text, script_args, metadata]
|
||||
return [subject_text, body_text, script_args], metadata
|
||||
else:
|
||||
return [subject_text, body_text, script_args, metadata]
|
||||
elif state == 'created':
|
||||
return [subject_text, body_text, script_args], metadata
|
||||
elif notify_action == 'created':
|
||||
# Default body text
|
||||
body_text = '%s was recently added to Plex.' % full_title
|
||||
|
||||
|
@ -791,14 +847,14 @@ def build_notify_text(session=None, timeline=None, state=None):
|
|||
except:
|
||||
logger.error(u"PlexPy NotificationHandler :: Unable to parse custom notification body. Using fallback.")
|
||||
|
||||
return [subject_text, body_text, script_args, metadata]
|
||||
return [subject_text, body_text, script_args], metadata
|
||||
else:
|
||||
return [subject_text, body_text, script_args, metadata]
|
||||
return [subject_text, body_text, script_args], metadata
|
||||
else:
|
||||
return None
|
||||
|
||||
|
||||
def build_server_notify_text(state=None):
|
||||
def build_server_notify_text(notify_action=None):
|
||||
# Get time formats
|
||||
date_format = plexpy.CONFIG.DATE_FORMAT.replace('Do','').replace('zz','')
|
||||
time_format = plexpy.CONFIG.TIME_FORMAT.replace('Do','').replace('zz','')
|
||||
|
@ -817,6 +873,8 @@ def build_server_notify_text(state=None):
|
|||
logger.error(u"PlexPy NotificationHandler :: Unable to retrieve server uptime.")
|
||||
server_uptime = 'N/A'
|
||||
|
||||
pattern = re.compile('\n*<tv>[^>]+.</tv>\n*|\n*<movie>[^>]+.</movie>\n*|\n*?<music>[^>]+.</music>\n*', re.IGNORECASE | re.DOTALL)
|
||||
|
||||
on_extdown_subject = plexpy.CONFIG.NOTIFY_ON_EXTDOWN_SUBJECT_TEXT
|
||||
on_extdown_body = plexpy.CONFIG.NOTIFY_ON_EXTDOWN_BODY_TEXT
|
||||
on_intdown_subject = plexpy.CONFIG.NOTIFY_ON_INTDOWN_SUBJECT_TEXT
|
||||
|
@ -825,12 +883,12 @@ def build_server_notify_text(state=None):
|
|||
on_extup_body = plexpy.CONFIG.NOTIFY_ON_EXTUP_BODY_TEXT
|
||||
on_intup_subject = plexpy.CONFIG.NOTIFY_ON_INTUP_SUBJECT_TEXT
|
||||
on_intup_body = plexpy.CONFIG.NOTIFY_ON_INTUP_BODY_TEXT
|
||||
script_args_text = plexpy.CONFIG.NOTIFY_SCRIPTS_ARGS_TEXT
|
||||
script_args_text = strip_tag(re.sub(pattern, '', plexpy.CONFIG.NOTIFY_SCRIPTS_ARGS_TEXT))
|
||||
|
||||
available_params = {# Global paramaters
|
||||
'server_name': server_name,
|
||||
'server_uptime': server_uptime,
|
||||
'action': state.title(),
|
||||
'action': notify_action.title(),
|
||||
'datestamp': arrow.now().format(date_format),
|
||||
'timestamp': arrow.now().format(time_format)}
|
||||
|
||||
|
@ -848,7 +906,7 @@ def build_server_notify_text(state=None):
|
|||
except Exception as e:
|
||||
logger.error(u"PlexPy Notifier :: Unable to parse custom script arguments %s. Using fallback." % e)
|
||||
|
||||
if state == 'extdown':
|
||||
if notify_action == 'extdown':
|
||||
# Default body text
|
||||
body_text = 'The Plex Media Server remote access is down.'
|
||||
|
||||
|
@ -871,7 +929,7 @@ def build_server_notify_text(state=None):
|
|||
else:
|
||||
return [subject_text, body_text, script_args]
|
||||
|
||||
elif state == 'intdown':
|
||||
elif notify_action == 'intdown':
|
||||
# Default body text
|
||||
body_text = 'The Plex Media Server is down.'
|
||||
|
||||
|
@ -893,7 +951,7 @@ def build_server_notify_text(state=None):
|
|||
return [subject_text, body_text, script_args]
|
||||
else:
|
||||
return [subject_text, body_text, script_args]
|
||||
if state == 'extup':
|
||||
if notify_action == 'extup':
|
||||
# Default body text
|
||||
body_text = 'The Plex Media Server remote access is back up.'
|
||||
|
||||
|
@ -915,7 +973,7 @@ def build_server_notify_text(state=None):
|
|||
return [subject_text, body_text, script_args]
|
||||
else:
|
||||
return [subject_text, body_text, script_args]
|
||||
elif state == 'intup':
|
||||
elif notify_action == 'intup':
|
||||
# Default body text
|
||||
body_text = 'The Plex Media Server is back up.'
|
||||
|
||||
|
|
|
@ -1,2 +1,2 @@
|
|||
PLEXPY_VERSION = "master"
|
||||
PLEXPY_RELEASE_VERSION = "1.3.7"
|
||||
PLEXPY_RELEASE_VERSION = "1.3.8"
|
||||
|
|
|
@ -39,11 +39,13 @@ def run():
|
|||
|
||||
if plexpy.CONFIG.PMS_SSL and plexpy.CONFIG.PMS_URL[:5] == 'https':
|
||||
uri = plexpy.CONFIG.PMS_URL.replace('https://', 'wss://') + '/:/websockets/notifications'
|
||||
secure = ' secure'
|
||||
else:
|
||||
uri = 'ws://%s:%s/:/websockets/notifications' % (
|
||||
plexpy.CONFIG.PMS_IP,
|
||||
plexpy.CONFIG.PMS_PORT
|
||||
)
|
||||
secure = ''
|
||||
|
||||
# Set authentication token (if one is available)
|
||||
if plexpy.CONFIG.PMS_TOKEN:
|
||||
|
@ -55,7 +57,7 @@ def run():
|
|||
# Try an open the websocket connection - if it fails after 15 retries fallback to polling
|
||||
while not ws_connected and reconnects <= 15:
|
||||
try:
|
||||
logger.info(u'PlexPy WebSocket :: Opening websocket, connection attempt %s.' % str(reconnects + 1))
|
||||
logger.info(u'PlexPy WebSocket :: Opening%s websocket, connection attempt %s.' % (secure, str(reconnects + 1)))
|
||||
ws = create_connection(uri)
|
||||
reconnects = 0
|
||||
ws_connected = True
|
||||
|
|
|
@ -1082,6 +1082,15 @@ class WebInterface(object):
|
|||
cherrypy.response.headers['Content-type'] = 'application/json'
|
||||
return json.dumps(log_lines)
|
||||
|
||||
@cherrypy.expose
|
||||
@addtoapi()
|
||||
def get_notification_log(self, **kwargs):
|
||||
data_factory = datafactory.DataFactory()
|
||||
notifications = data_factory.get_notification_log(kwargs=kwargs)
|
||||
|
||||
cherrypy.response.headers['Content-type'] = 'application/json'
|
||||
return json.dumps(notifications)
|
||||
|
||||
@cherrypy.expose
|
||||
def clearLogs(self):
|
||||
plexpy.LOG_LIST = []
|
||||
|
@ -1183,6 +1192,7 @@ class WebInterface(object):
|
|||
"logging_ignore_interval": plexpy.CONFIG.LOGGING_IGNORE_INTERVAL,
|
||||
"pms_is_remote": checked(plexpy.CONFIG.PMS_IS_REMOTE),
|
||||
"notify_consecutive": checked(plexpy.CONFIG.NOTIFY_CONSECUTIVE),
|
||||
"notify_upload_posters": checked(plexpy.CONFIG.NOTIFY_UPLOAD_POSTERS),
|
||||
"notify_recently_added": checked(plexpy.CONFIG.NOTIFY_RECENTLY_ADDED),
|
||||
"notify_recently_added_grandparent": checked(plexpy.CONFIG.NOTIFY_RECENTLY_ADDED_GRANDPARENT),
|
||||
"notify_recently_added_delay": plexpy.CONFIG.NOTIFY_RECENTLY_ADDED_DELAY,
|
||||
|
@ -1235,7 +1245,7 @@ class WebInterface(object):
|
|||
"tv_notify_on_pause", "movie_notify_on_pause", "music_notify_on_pause",
|
||||
"refresh_libraries_on_startup", "refresh_users_on_startup",
|
||||
"ip_logging_enable", "movie_logging_enable", "tv_logging_enable", "music_logging_enable",
|
||||
"pms_is_remote", "home_stats_type", "group_history_tables", "notify_consecutive",
|
||||
"pms_is_remote", "home_stats_type", "group_history_tables", "notify_consecutive", "notify_upload_posters",
|
||||
"notify_recently_added", "notify_recently_added_grandparent", "monitor_remote_access", "get_file_sizes"
|
||||
]
|
||||
for checked_config in checked_configs:
|
||||
|
@ -1245,7 +1255,7 @@ class WebInterface(object):
|
|||
|
||||
# If http password exists in config, do not overwrite when blank value received
|
||||
if kwargs.get('http_password'):
|
||||
if kwargs['http_password'].strip() == '' and plexpy.CONFIG.HTTP_PASSWORD != '':
|
||||
if kwargs['http_password'] == ' ' and plexpy.CONFIG.HTTP_PASSWORD != '':
|
||||
kwargs['http_password'] = plexpy.CONFIG.HTTP_PASSWORD
|
||||
|
||||
for plain_config, use_config in [(x[4:], x) for x in kwargs if x.startswith('use_')]:
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue