Log a full_title field into the metadata table.

Create a clear_all_history_new endpoint to delete all old PlexPy session history IMMEDIATELY.
Add icon in history_new to indicate if video was transcoded or not.
Replace relatively inaccurate percent_completed with icons in history_new.
This commit is contained in:
Tim 2015-07-13 12:41:03 +02:00
parent 65b3930baa
commit 2b317f6fd4
6 changed files with 71 additions and 19 deletions

View file

@ -38,11 +38,12 @@ from plexpy import helpers
<th class="desktop" align='left' id="paused_counter">Paused</th> <th class="desktop" align='left' id="paused_counter">Paused</th>
<th class="desktop" align='left' id="stopped">Stopped</th> <th class="desktop" align='left' id="stopped">Stopped</th>
<th class="desktop" align='left' id="duration">Duration</th> <th class="desktop" align='left' id="duration">Duration</th>
<th class="desktop" align='left' id="percent_complete">Completed</th> <th class="desktop" align='left' id="percent_complete"></th>
<th class="never" align='left' id="grandparent_rating_key">grandparentRatingKey</th> <th class="never" align='left' id="grandparent_rating_key">grandparentRatingKey</th>
<th class="never" align='left' id="rating_key">RatingKey</th> <th class="never" align='left' id="rating_key">RatingKey</th>
<th class="never" align='left' id="user"></th> <th class="never" align='left' id="user"></th>
<th class="never" align='left' id="media_type"></th> <th class="never" align='left' id="media_type"></th>
<th class="never" align='left' id="video_decision"></th>
</tr> </tr>
</thead> </thead>
<tbody> <tbody>

View file

@ -90,7 +90,11 @@ history_table_options = {
"createdCell": function (td, cellData, rowData, row, col) { "createdCell": function (td, cellData, rowData, row, col) {
if (cellData !== '') { if (cellData !== '') {
if (rowData['media_type'] === 'movie' || rowData['media_type'] === 'episode') { if (rowData['media_type'] === 'movie' || rowData['media_type'] === 'episode') {
$(td).html('<div><div style="float: left;"><a href="info?rating_key=' + rowData['rating_key'] + '">' + cellData + '</a></div><div style="float: right; text-align: right; padding-right: 5px;"><i class="fa fa-video-camera"></i></div></div>'); var transcode_dec = '';
if (rowData['video_decision'] === 'transcode') {
transcode_dec = '<i class="fa fa-server"></i>&nbsp';
}
$(td).html('<div><div style="float: left;"><a href="info?rating_key=' + rowData['rating_key'] + '">' + cellData + '</a></div><div style="float: right; text-align: right; padding-right: 5px;">' + transcode_dec + '<i class="fa fa-video-camera"></i></div></div>');
} else if (rowData['media_type'] === 'track') { } else if (rowData['media_type'] === 'track') {
$(td).html('<div><div style="float: left;">' + cellData + '</div><div style="float: right; text-align: right; padding-right: 5px;"><i class="fa fa-music"></i></div></div>'); $(td).html('<div><div style="float: left;">' + cellData + '</div><div style="float: right; text-align: right; padding-right: 5px;"><i class="fa fa-music"></i></div></div>');
} else { } else {
@ -147,13 +151,18 @@ history_table_options = {
"targets": [10], "targets": [10],
"data":"percent_complete", "data":"percent_complete",
"render": function ( data, type, full ) { "render": function ( data, type, full ) {
if (data < 85) { if (data > 80) {
return '<span class="badge">'+Math.round(data)+'%</span>'; return '<i class="fa fa-lg fa-circle"></i>'
//return '<span class="badge">'+Math.round(data)+'%</span>';
} else if (data > 40) {
return '<i class="fa fa-lg fa-adjust"></i>'
//return '<span class="badge">100%</span>';
} else { } else {
return '<span class="badge">100%</span>'; return '<i class="fa fa-lg fa-circle-o"></i>'
} }
}, },
"searchable": false, "searchable": false,
"orderable": true,
"className": "no-wrap" "className": "no-wrap"
}, },
{ {
@ -179,8 +188,15 @@ history_table_options = {
"data":"user", "data":"user",
"searchable":false, "searchable":false,
"visible":false "visible":false
},
{
"targets": [15],
"data":"video_decision",
"searchable":false,
"visible":false
} }
], ],
"drawCallback": function (settings) { "drawCallback": function (settings) {
// Jump to top of page // Jump to top of page

View file

@ -405,8 +405,8 @@ def dbcheck():
c_db.execute( c_db.execute(
'CREATE TABLE IF NOT EXISTS session_history_metadata (id INTEGER PRIMARY KEY, ' 'CREATE TABLE IF NOT EXISTS session_history_metadata (id INTEGER PRIMARY KEY, '
'rating_key INTEGER, parent_rating_key INTEGER, grandparent_rating_key INTEGER, ' 'rating_key INTEGER, parent_rating_key INTEGER, grandparent_rating_key INTEGER, '
'title TEXT, parent_title TEXT, grandparent_title TEXT, media_index INTEGER, parent_media_index INTEGER, ' 'title TEXT, parent_title TEXT, grandparent_title TEXT, full_title TEXT, media_index INTEGER, '
'thumb TEXT, parent_thumb TEXT, grandparent_thumb TEXT, art TEXT, media_type TEXT, ' 'parent_media_index INTEGER, thumb TEXT, parent_thumb TEXT, grandparent_thumb TEXT, art TEXT, media_type TEXT, '
'year INTEGER, originally_available_at TEXT, added_at INTEGER, updated_at INTEGER, last_viewed_at INTEGER, ' 'year INTEGER, originally_available_at TEXT, added_at INTEGER, updated_at INTEGER, last_viewed_at INTEGER, '
'content_rating TEXT, summary TEXT, rating TEXT, duration INTEGER, guid TEXT, ' 'content_rating TEXT, summary TEXT, rating TEXT, duration INTEGER, guid TEXT, '
'directors TEXT, writers TEXT, actors TEXT, genres TEXT, studio TEXT)' 'directors TEXT, writers TEXT, actors TEXT, genres TEXT, studio TEXT)'
@ -547,6 +547,15 @@ def dbcheck():
'ALTER TABLE sessions ADD COLUMN transcode_height INTEGER' 'ALTER TABLE sessions ADD COLUMN transcode_height INTEGER'
) )
# Upgrade sessions table from earlier versions
try:
c_db.execute('SELECT full_title from session_history_metadata')
except sqlite3.OperationalError:
logger.debug(u"Altering database. Updating database table sessions.")
c_db.execute(
'ALTER TABLE session_history_metadata ADD COLUMN full_title TEXT'
)
conn_db.commit() conn_db.commit()
c_db.close() c_db.close()

View file

@ -148,7 +148,7 @@ class DataFactory(object):
'.user ELSE users.friendly_name END) as friendly_name', '.user ELSE users.friendly_name END) as friendly_name',
t1 + '.player', t1 + '.player',
t1 + '.ip_address', t1 + '.ip_address',
t2 + '.title', t2 + '.full_title',
t1 + '.started', t1 + '.started',
t1 + '.paused_counter', t1 + '.paused_counter',
t1 + '.stopped', t1 + '.stopped',
@ -160,7 +160,8 @@ class DataFactory(object):
t1 + '.grandparent_rating_key as grandparent_rating_key', t1 + '.grandparent_rating_key as grandparent_rating_key',
t1 + '.rating_key as rating_key', t1 + '.rating_key as rating_key',
t1 + '.user', t1 + '.user',
t2 + '.media_type' t2 + '.media_type',
t4 + '.video_decision'
] ]
try: try:
query = data_tables.ssp_query(table_name=t1, query = data_tables.ssp_query(table_name=t1,
@ -173,9 +174,11 @@ class DataFactory(object):
search_regex=search_regex, search_regex=search_regex,
custom_where=custom_where, custom_where=custom_where,
group_by='', group_by='',
join_type=['JOIN', 'JOIN'], join_type=['JOIN', 'JOIN', 'JOIN'],
join_table=[t3, t2], join_table=[t3, t2, t4],
join_evals=[[t1 + '.user_id', t3 + '.user_id'], [t1 + '.id', t2 + '.id']], join_evals=[[t1 + '.user_id', t3 + '.user_id'],
[t1 + '.id', t2 + '.id'],
[t1 + '.id', t4 + '.id']],
kwargs=kwargs) kwargs=kwargs)
except: except:
logger.warn("Unable to open PlexWatch database.") logger.warn("Unable to open PlexWatch database.")
@ -193,7 +196,7 @@ class DataFactory(object):
"friendly_name": item['friendly_name'], "friendly_name": item['friendly_name'],
"platform": item["player"], "platform": item["player"],
"ip_address": item["ip_address"], "ip_address": item["ip_address"],
"title": item["title"], "title": item["full_title"],
"started": item["started"], "started": item["started"],
"paused_counter": item["paused_counter"], "paused_counter": item["paused_counter"],
"stopped": item["stopped"], "stopped": item["stopped"],
@ -202,7 +205,8 @@ class DataFactory(object):
"grandparent_rating_key": item["grandparent_rating_key"], "grandparent_rating_key": item["grandparent_rating_key"],
"rating_key": item["rating_key"], "rating_key": item["rating_key"],
"user": item["user"], "user": item["user"],
"media_type": item["media_type"] "media_type": item["media_type"],
"video_decision": item["video_decision"],
} }
if item['paused_counter'] > 0: if item['paused_counter'] > 0:

View file

@ -130,6 +130,14 @@ def drop_session_db():
monitor_db = MonitorDatabase() monitor_db = MonitorDatabase()
monitor_db.action('DROP TABLE sessions') monitor_db.action('DROP TABLE sessions')
def clear_history_tables():
logger.debug(u"PlexPy Monitor :: Deleting all session_history records... No turning back now bub.")
monitor_db = MonitorDatabase()
monitor_db.action('DELETE FROM session_history')
monitor_db.action('DELETE FROM session_history_media_info')
monitor_db.action('DELETE FROM session_history_metadata')
monitor_db.action('VACUUM;')
def db_filename(filename="plexpy.db"): def db_filename(filename="plexpy.db"):
return os.path.join(plexpy.DATA_DIR, filename) return os.path.join(plexpy.DATA_DIR, filename)
@ -365,17 +373,25 @@ class MonitorProcessing(object):
actors = ";".join(metadata['actors']) actors = ";".join(metadata['actors'])
genres = ";".join(metadata['genres']) genres = ";".join(metadata['genres'])
# Build media item title
if session['media_type'] == 'episode' or session['media_type'] == 'track':
full_title = '%s - %s' % (metadata['grandparent_title'], metadata['title'])
elif session['media_type'] == 'movie':
full_title = metadata['title']
else:
full_title = metadata['title']
logger.debug(u"PlexPy Monitor :: Attempting to write to session_history_metadata table...") logger.debug(u"PlexPy Monitor :: Attempting to write to session_history_metadata table...")
query = 'INSERT INTO session_history_metadata (id, rating_key, parent_rating_key, ' \ query = 'INSERT INTO session_history_metadata (id, rating_key, parent_rating_key, ' \
'grandparent_rating_key, title, parent_title, grandparent_title, media_index, ' \ 'grandparent_rating_key, title, parent_title, grandparent_title, full_title, media_index, ' \
'parent_media_index, thumb, parent_thumb, grandparent_thumb, art, media_type, year, ' \ 'parent_media_index, thumb, parent_thumb, grandparent_thumb, art, media_type, year, ' \
'originally_available_at, added_at, updated_at, last_viewed_at, content_rating, summary, ' \ 'originally_available_at, added_at, updated_at, last_viewed_at, content_rating, summary, ' \
'rating, duration, guid, directors, writers, actors, genres, studio) VALUES ' \ 'rating, duration, guid, directors, writers, actors, genres, studio) VALUES ' \
'(?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)' '(?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)'
args = [last_id, session['rating_key'], session['parent_rating_key'], session['grandparent_rating_key'], args = [last_id, session['rating_key'], session['parent_rating_key'], session['grandparent_rating_key'],
session['title'], session['parent_title'], session['grandparent_title'], metadata['index'], session['title'], session['parent_title'], session['grandparent_title'], full_title,
metadata['parent_index'], metadata['thumb'], metadata['parent_thumb'], metadata['index'], metadata['parent_index'], metadata['thumb'], metadata['parent_thumb'],
metadata['grandparent_thumb'], metadata['art'], session['media_type'], metadata['year'], metadata['grandparent_thumb'], metadata['art'], session['media_type'], metadata['year'],
metadata['originally_available_at'], metadata['added_at'], metadata['updated_at'], metadata['originally_available_at'], metadata['added_at'], metadata['updated_at'],
metadata['last_viewed_at'], metadata['content_rating'], metadata['summary'], metadata['rating'], metadata['last_viewed_at'], metadata['content_rating'], metadata['summary'], metadata['rating'],

View file

@ -13,7 +13,7 @@
# You should have received a copy of the GNU General Public License # You should have received a copy of the GNU General Public License
# along with PlexPy. If not, see <http://www.gnu.org/licenses/>. # along with PlexPy. If not, see <http://www.gnu.org/licenses/>.
from plexpy import logger, notifiers, plextv, pmsconnect, plexwatch, db, common, log_reader, datafactory from plexpy import logger, notifiers, plextv, pmsconnect, plexwatch, db, common, log_reader, datafactory, monitor
from plexpy.helpers import checked, radio from plexpy.helpers import checked, radio
from mako.lookup import TemplateLookup from mako.lookup import TemplateLookup
@ -465,6 +465,12 @@ class WebInterface(object):
cherrypy.response.headers['Content-type'] = 'application/json' cherrypy.response.headers['Content-type'] = 'application/json'
return json.dumps(history) return json.dumps(history)
@cherrypy.expose
def clear_all_history_new(self, **kwargs):
monitor.clear_history_tables()
raise cherrypy.HTTPRedirect("history_new")
@cherrypy.expose @cherrypy.expose
def get_stream_details(self, rating_key=0, **kwargs): def get_stream_details(self, rating_key=0, **kwargs):