diff --git a/data/interfaces/default/css/plexwatch-tables.css b/data/interfaces/default/css/plexwatch-tables.css index a54dfc0e..07b85a0b 100644 --- a/data/interfaces/default/css/plexwatch-tables.css +++ b/data/interfaces/default/css/plexwatch-tables.css @@ -161,9 +161,7 @@ table.display { table.display thead th { white-space:nowrap; -padding: 0px 0px 0px 19px; -border-top: 1px solid #2d2d2d; -border-bottom: 1px solid #0e0e0e; +padding: 0px 0px 0px 18px; cursor: pointer; color: #999; background-color: #212121; @@ -180,6 +178,7 @@ table.display thead .sorting_asc, table.display thead .sorting_desc { cursor: pointer; *cursor: hand; + height: 35px; } table.display thead .sorting, table.display thead .sorting_asc, @@ -216,7 +215,7 @@ table.display tr.heading2 td { } table.display td { - padding: 5px 0 5px 20px; + padding: 5px 0 5px 5px; } table.display td.title { diff --git a/data/interfaces/default/edit_user.html b/data/interfaces/default/edit_user.html new file mode 100644 index 00000000..895292ff --- /dev/null +++ b/data/interfaces/default/edit_user.html @@ -0,0 +1,56 @@ +<%doc> +USAGE DOCUMENTATION :: PLEASE LEAVE THIS AT THE TOP OF THIS FILE + +For Mako templating syntax documentation please visit: http://docs.makotemplates.org/en/latest/ + +Filename: edit_user.html +Version: 0.1 +Variable names: data [list] + +data :: Usable parameters + +== Global keys == +user Return the real Plex username +friendly_name Returns the friendly edited Plex username + +DOCUMENTATION :: END + + +% if data is not None: + + + + + +% endif \ No newline at end of file diff --git a/data/interfaces/default/history.html b/data/interfaces/default/history.html index 0f34116e..4e8ad8a3 100644 --- a/data/interfaces/default/history.html +++ b/data/interfaces/default/history.html @@ -31,10 +31,10 @@ from plexpy import helpers ID Time User - Platform + Platform IP Address Title - Started + Started Paused Stopped Duration diff --git a/data/interfaces/default/home_stats.html b/data/interfaces/default/home_stats.html index 54f917f4..c71c47f4 100644 --- a/data/interfaces/default/home_stats.html +++ b/data/interfaces/default/home_stats.html @@ -28,6 +28,7 @@ users_watched Returns the count for the associated stat. == Only if 'stat_id' is 'top_user' == thumb Returns url of the user's gravatar. Returns '' if none exists. user Returns the username for the associated stat. +friendly_name Returns the friendly name of the user for the associated stat. == Only if 'stat_id' is 'top_platform' == platform_type Returns the platform name for the associated stat. @@ -112,12 +113,11 @@ DOCUMENTATION :: END

Most Active User

-
${a['rows'][0]['user']}
+
${a['rows'][0]['friendly_name']}

${a['rows'][0]['total_plays']}

-

plays

diff --git a/data/interfaces/default/info.html b/data/interfaces/default/info.html index ab3d0329..7b571059 100644 --- a/data/interfaces/default/info.html +++ b/data/interfaces/default/info.html @@ -190,10 +190,10 @@ from plexpy import helpers ID Time User - Platform + Platform IP Address Title - Started + Started Paused Stopped Duration diff --git a/data/interfaces/default/js/tables/user_ips.js b/data/interfaces/default/js/tables/user_ips.js index 808be44c..fe52a452 100644 --- a/data/interfaces/default/js/tables/user_ips.js +++ b/data/interfaces/default/js/tables/user_ips.js @@ -33,7 +33,7 @@ user_ip_table_options = { "targets": [1], "data":"ip_address", "width": "15%", - "className": "modal-control", + "className": "modal-control no-wrap", "createdCell": function (td, cellData, rowData, row, col) { if (isPrivateIP(cellData)) { if (cellData != '') { @@ -45,8 +45,7 @@ user_ip_table_options = { $(td).html(' ' + cellData +''); } }, - "width": "15%", - "className": "no-wrap" + "width": "15%" }, { "targets": [2], diff --git a/data/interfaces/default/js/tables/users.js b/data/interfaces/default/js/tables/users.js index 4d9d4ea4..e872e6d8 100644 --- a/data/interfaces/default/js/tables/users.js +++ b/data/interfaces/default/js/tables/users.js @@ -14,7 +14,7 @@ users_list_table_options = { "processing": false, "serverSide": true, "pageLength": 10, - "order": [ 0, 'asc'], + "order": [ 1, 'asc'], "ajax": { "url": "get_user_list" }, diff --git a/data/interfaces/default/user.html b/data/interfaces/default/user.html index 2b7b7356..54a5ea0d 100644 --- a/data/interfaces/default/user.html +++ b/data/interfaces/default/user.html @@ -10,6 +10,7 @@ Variable names: user [string] user :: Usable parameters user Returns the name of the user. +friendly_name Returns the friendly name of the user. DOCUMENTATION :: END @@ -35,7 +36,7 @@ from plexpy import helpers
- ${user} + ${friendly_name}
+
@@ -108,7 +112,7 @@ from plexpy import helpers

IP Addresses for - ${user} + ${friendly_name}

@@ -164,7 +168,7 @@ from plexpy import helpers

Watch History for - ${user} + ${friendly_name}

@@ -272,6 +276,19 @@ from plexpy import helpers } } }); + + // Load edit user modal + $("#toggle-edit-user-modal").click(function() { + $.ajax({ + url: 'edit_user', + data: {user: '${user}'}, + cache: false, + async: true, + complete: function(xhr, status) { + $("#edit-user-modal").html(xhr.responseText); + } + }); + }); }); diff --git a/plexpy/__init__.py b/plexpy/__init__.py index f456bb8c..07141e9b 100644 --- a/plexpy/__init__.py +++ b/plexpy/__init__.py @@ -307,6 +307,8 @@ def sig_handler(signum=None, frame=None): def dbcheck(): conn = sqlite3.connect(plexpy.CONFIG.PLEXWATCH_DATABASE) c = conn.cursor() + c.execute('CREATE TABLE IF NOT EXISTS plexpy_users (id INTEGER PRIMARY KEY AUTOINCREMENT, ' + 'username TEXT NOT NULL UNIQUE, friendly_name TEXT)') conn.commit() c.close() diff --git a/plexpy/plexwatch.py b/plexpy/plexwatch.py index 5e19939f..7f639c0e 100644 --- a/plexpy/plexwatch.py +++ b/plexpy/plexwatch.py @@ -660,11 +660,14 @@ class PlexWatch(object): elif 'top_users' in stat: top_users = [] try: - query = 'SELECT user, COUNT(id) as total_plays, MAX(time) as last_watch ' \ - 'FROM %s ' \ - 'WHERE datetime(stopped, "unixepoch", "localtime") >= datetime("now", "-%s days", "localtime") ' \ - 'GROUP BY user ' \ - 'ORDER BY total_plays DESC LIMIT 10' % (self.get_history_table_name(), time_range) + s = self.get_history_table_name() + query = 'SELECT user, (case when friendly_name is null then user else friendly_name end) as friendly_name,' \ + 'COUNT(' + s + '.id) as total_plays, MAX(time) as last_watch ' \ + 'FROM ' + s + ' ' \ + 'LEFT OUTER JOIN plexpy_users ON ' + s + '.user = plexpy_users.username ' \ + 'WHERE datetime(stopped, "unixepoch", "localtime") >= datetime("now", "-' + time_range + ' days", "localtime") '\ + 'GROUP BY ' + s + '.user ' \ + 'ORDER BY total_plays DESC LIMIT 10' result = myDB.select(query) except: logger.warn("Unable to open PlexWatch database.") @@ -673,8 +676,9 @@ class PlexWatch(object): for item in result: thumb = self.get_user_gravatar_image(item[0]) row = {'user': item[0], - 'total_plays': item[1], - 'last_play': item[2], + 'friendly_name': item[1], + 'total_plays': item[2], + 'last_play': item[3], 'thumb': thumb['user_thumb'] } top_users.append(row) @@ -875,6 +879,24 @@ class PlexWatch(object): 'series': [series_1_output]} return output + def set_user_friendly_name(self, user=None, friendly_name=None): + if user and friendly_name: + myDB = db.DBConnection() + + control_value_dict = {"username": user} + new_value_dict = {"friendly_name": friendly_name} + + myDB.upsert('plexpy_users', new_value_dict, control_value_dict) + + def get_user_friendly_name(self, user=None): + if user: + myDB = db.DBConnection() + + query = 'select friendly_name FROM plexpy_users WHERE username = "%s"' % user + result = myDB.select_single(query) + + return result + # Taken from: # https://stackoverflow.com/questions/18066269/group-by-and-aggregate-the-values-of-a-list-of-dictionaries-in-python @staticmethod diff --git a/plexpy/webserve.py b/plexpy/webserve.py index d756dbeb..aee82594 100644 --- a/plexpy/webserve.py +++ b/plexpy/webserve.py @@ -99,7 +99,42 @@ class WebInterface(object): @cherrypy.expose def user(self, user=None): - return serve_template(templatename="user.html", title="User", user=user) + try: + plex_watch = plexwatch.PlexWatch() + friendly_name = plex_watch.get_user_friendly_name(user) + except: + logger.warn("Unable to retrieve friendly name for user %s " % user) + friendly_name = user + + return serve_template(templatename="user.html", title="User", user=user, friendly_name=friendly_name) + + @cherrypy.expose + def edit_user(self, user=None, friendly_name=None, **kwargs): + if user and friendly_name: + try: + plex_watch = plexwatch.PlexWatch() + plex_watch.set_user_friendly_name(user, friendly_name) + status_message = "Successfully updated user." + return status_message + except: + status_message = "Failed to updated user." + return status_message + elif user and not friendly_name: + try: + plex_watch = plexwatch.PlexWatch() + result = {'user': user, + 'friendly_name': plex_watch.get_user_friendly_name(user) + } + status_message = "" + except: + result = {'user': user, + 'friendly_name': '' + } + status_message = "There was an error." + + return serve_template(templatename="edit_user.html", title="Edit User", data=result, status_message=status_message) + else: + return serve_template(templatename="edit_user.html", title="Edit User", data=user, status_message='Unknown error.') @cherrypy.expose def get_stream_data(self, row_id=None, user=None, **kwargs):