瀏覽代碼

Fix get sessions with api key (#12696)

gnattu 8 月之前
父節點
當前提交
75bbd30296

+ 36 - 8
Emby.Server.Implementations/Session/SessionManager.cs

@@ -1858,15 +1858,38 @@ namespace Emby.Server.Implementations.Session
             Guid userId,
             string deviceId,
             int? activeWithinSeconds,
-            Guid? controllableUserToCheck)
+            Guid? controllableUserToCheck,
+            bool isApiKey)
         {
             var result = Sessions;
-            var user = _userManager.GetUserById(userId);
             if (!string.IsNullOrEmpty(deviceId))
             {
                 result = result.Where(i => string.Equals(i.DeviceId, deviceId, StringComparison.OrdinalIgnoreCase));
             }
 
+            var userCanControlOthers = false;
+            var userIsAdmin = false;
+            User user = null;
+
+            if (isApiKey)
+            {
+                userCanControlOthers = true;
+                userIsAdmin = true;
+            }
+            else if (!userId.IsEmpty())
+            {
+                user = _userManager.GetUserById(userId);
+                if (user is not null)
+                {
+                    userCanControlOthers = user.HasPermission(PermissionKind.EnableRemoteControlOfOtherUsers);
+                    userIsAdmin = user.HasPermission(PermissionKind.IsAdministrator);
+                }
+                else
+                {
+                    return [];
+                }
+            }
+
             if (!controllableUserToCheck.IsNullOrEmpty())
             {
                 result = result.Where(i => i.SupportsRemoteControl);
@@ -1883,29 +1906,34 @@ namespace Emby.Server.Implementations.Session
                     result = result.Where(i => !i.UserId.IsEmpty());
                 }
 
-                if (!user.HasPermission(PermissionKind.EnableRemoteControlOfOtherUsers))
+                if (!userCanControlOthers)
                 {
                     // User cannot control other user's sessions, validate user id.
-                    result = result.Where(i => i.UserId.IsEmpty() || i.ContainsUser(user.Id));
+                    result = result.Where(i => i.UserId.IsEmpty() || i.ContainsUser(userId));
                 }
 
                 result = result.Where(i =>
                 {
-                    if (!string.IsNullOrWhiteSpace(i.DeviceId) && !_deviceManager.CanAccessDevice(user, i.DeviceId))
+                    if (isApiKey)
+                    {
+                        return true;
+                    }
+
+                    if (user is null)
                     {
                         return false;
                     }
 
-                    return true;
+                    return string.IsNullOrWhiteSpace(i.DeviceId) || _deviceManager.CanAccessDevice(user, i.DeviceId);
                 });
             }
-            else if (!user.HasPermission(PermissionKind.IsAdministrator))
+            else if (!userIsAdmin)
             {
                 // Request isn't from administrator, limit to "own" sessions.
                 result = result.Where(i => i.UserId.IsEmpty() || i.ContainsUser(userId));
             }
 
-            if (!user.HasPermission(PermissionKind.IsAdministrator))
+            if (!userIsAdmin)
             {
                 // Don't report acceleration type for non-admin users.
                 result = result.Select(r =>

+ 2 - 1
Jellyfin.Api/Controllers/SessionController.cs

@@ -62,7 +62,8 @@ public class SessionController : BaseJellyfinApiController
             User.GetUserId(),
             deviceId,
             activeWithinSeconds,
-            controllableUserToCheck);
+            controllableUserToCheck,
+            User.GetIsApiKey());
 
         return Ok(result);
     }

+ 2 - 1
MediaBrowser.Controller/Session/ISessionManager.cs

@@ -300,8 +300,9 @@ namespace MediaBrowser.Controller.Session
         /// <param name="deviceId">The device id.</param>
         /// <param name="activeWithinSeconds">Active within session limit.</param>
         /// <param name="controllableUserToCheck">Filter for sessions remote controllable for this user.</param>
+        /// <param name="isApiKey">Is the request authenticated with API key.</param>
         /// <returns>IReadOnlyList{SessionInfoDto}.</returns>
-        IReadOnlyList<SessionInfoDto> GetSessions(Guid userId, string deviceId, int? activeWithinSeconds, Guid? controllableUserToCheck);
+        IReadOnlyList<SessionInfoDto> GetSessions(Guid userId, string deviceId, int? activeWithinSeconds, Guid? controllableUserToCheck, bool isApiKey);
 
         /// <summary>
         /// Gets the session by authentication token.