Merge pull request #17019 from Shadowghost/enforce-parental

Enforce parental filtering on additional endpoints
This commit is contained in:
Bond-009
2026-06-05 18:28:55 +02:00
committed by GitHub
6 changed files with 20 additions and 22 deletions

View File

@@ -1987,7 +1987,8 @@ namespace Emby.Server.Implementations.Library
query.TopParentIds.Length == 0 && query.TopParentIds.Length == 0 &&
string.IsNullOrEmpty(query.AncestorWithPresentationUniqueKey) && string.IsNullOrEmpty(query.AncestorWithPresentationUniqueKey) &&
string.IsNullOrEmpty(query.SeriesPresentationUniqueKey) && string.IsNullOrEmpty(query.SeriesPresentationUniqueKey) &&
query.ItemIds.Length == 0) query.ItemIds.Length == 0 &&
query.OwnerIds.Length == 0)
{ {
var userViews = UserViewManager.GetUserViews(new UserViewQuery var userViews = UserViewManager.GetUserViews(new UserViewQuery
{ {

View File

@@ -232,7 +232,7 @@ public class TvShowsController : BaseJellyfinApiController
if (seasonId.HasValue) // Season id was supplied. Get episodes by season id. if (seasonId.HasValue) // Season id was supplied. Get episodes by season id.
{ {
var item = _libraryManager.GetItemById<BaseItem>(seasonId.Value); var item = _libraryManager.GetItemById<BaseItem>(seasonId.Value, user);
if (item is not Season seasonItem) if (item is not Season seasonItem)
{ {
return NotFound("No season exists with Id " + seasonId); return NotFound("No season exists with Id " + seasonId);
@@ -242,7 +242,7 @@ public class TvShowsController : BaseJellyfinApiController
} }
else if (season.HasValue) // Season number was supplied. Get episodes by season number else if (season.HasValue) // Season number was supplied. Get episodes by season number
{ {
var series = _libraryManager.GetItemById<Series>(seriesId); var series = _libraryManager.GetItemById<Series>(seriesId, user);
if (series is null) if (series is null)
{ {
return NotFound("Series not found"); return NotFound("Series not found");
@@ -258,7 +258,7 @@ public class TvShowsController : BaseJellyfinApiController
} }
else // No season number or season id was supplied. Returning all episodes. else // No season number or season id was supplied. Returning all episodes.
{ {
if (_libraryManager.GetItemById<BaseItem>(seriesId) is not Series series) if (_libraryManager.GetItemById<BaseItem>(seriesId, user) is not Series series)
{ {
return NotFound("Series not found"); return NotFound("Series not found");
} }

View File

@@ -429,14 +429,8 @@ public class UserLibraryController : BaseJellyfinApiController
} }
var dtoOptions = new DtoOptions(); var dtoOptions = new DtoOptions();
if (item is IHasTrailers hasTrailers)
{
var trailers = hasTrailers.LocalTrailers;
return Ok(_dtoService.GetBaseItemDtos(trailers, dtoOptions, user, item).AsEnumerable());
}
return Ok(item.GetExtras() return Ok(item.GetExtras([ExtraType.Trailer], user)
.Where(e => e.ExtraType == ExtraType.Trailer)
.Select(i => _dtoService.GetBaseItemDto(i, dtoOptions, user, item))); .Select(i => _dtoService.GetBaseItemDto(i, dtoOptions, user, item)));
} }
@@ -487,7 +481,7 @@ public class UserLibraryController : BaseJellyfinApiController
var dtoOptions = new DtoOptions(); var dtoOptions = new DtoOptions();
return Ok(item return Ok(item
.GetExtras() .GetExtras(user)
.Where(i => i.ExtraType.HasValue && BaseItem.DisplayExtraTypes.Contains(i.ExtraType.Value)) .Where(i => i.ExtraType.HasValue && BaseItem.DisplayExtraTypes.Contains(i.ExtraType.Value))
.Select(i => _dtoService.GetBaseItemDto(i, dtoOptions, user, item))); .Select(i => _dtoService.GetBaseItemDto(i, dtoOptions, user, item)));
} }

View File

@@ -116,7 +116,7 @@ public class VideosController : BaseJellyfinApiController
BaseItemDto[] items; BaseItemDto[] items;
if (item is Video video) if (item is Video video)
{ {
items = video.GetAdditionalParts() items = video.GetAdditionalParts(user)
.Select(i => _dtoService.GetBaseItemDto(i, dtoOptions, user, video)) .Select(i => _dtoService.GetBaseItemDto(i, dtoOptions, user, video))
.ToArray(); .ToArray();
} }

View File

@@ -2718,7 +2718,7 @@ namespace MediaBrowser.Controller.Entities
public IReadOnlyList<BaseItem> GetThemeSongs(User user, IEnumerable<(ItemSortBy SortBy, SortOrder SortOrder)> orderBy) public IReadOnlyList<BaseItem> GetThemeSongs(User user, IEnumerable<(ItemSortBy SortBy, SortOrder SortOrder)> orderBy)
{ {
return LibraryManager.Sort(GetExtras().Where(e => e.ExtraType == Model.Entities.ExtraType.ThemeSong), user, orderBy).ToArray(); return LibraryManager.Sort(GetExtras(user).Where(e => e.ExtraType == Model.Entities.ExtraType.ThemeSong), user, orderBy).ToArray();
} }
public IReadOnlyList<BaseItem> GetThemeVideos(User user = null) public IReadOnlyList<BaseItem> GetThemeVideos(User user = null)
@@ -2728,16 +2728,17 @@ namespace MediaBrowser.Controller.Entities
public IReadOnlyList<BaseItem> GetThemeVideos(User user, IEnumerable<(ItemSortBy SortBy, SortOrder SortOrder)> orderBy) public IReadOnlyList<BaseItem> GetThemeVideos(User user, IEnumerable<(ItemSortBy SortBy, SortOrder SortOrder)> orderBy)
{ {
return LibraryManager.Sort(GetExtras().Where(e => e.ExtraType == Model.Entities.ExtraType.ThemeVideo), user, orderBy).ToArray(); return LibraryManager.Sort(GetExtras(user).Where(e => e.ExtraType == Model.Entities.ExtraType.ThemeVideo), user, orderBy).ToArray();
} }
/// <summary> /// <summary>
/// Get all extras associated with this item, sorted by <see cref="SortName"/>. /// Get all extras associated with this item, sorted by <see cref="SortName"/>.
/// </summary> /// </summary>
/// <param name="user">The user to apply parental restrictions for, or <c>null</c> to skip restriction checks.</param>
/// <returns>An enumerable containing the items.</returns> /// <returns>An enumerable containing the items.</returns>
public IEnumerable<BaseItem> GetExtras() public IEnumerable<BaseItem> GetExtras(User user = null)
{ {
return LibraryManager.GetItemList(new InternalItemsQuery() return LibraryManager.GetItemList(new InternalItemsQuery(user)
{ {
OwnerIds = [Id], OwnerIds = [Id],
OrderBy = [(ItemSortBy.SortName, SortOrder.Ascending)] OrderBy = [(ItemSortBy.SortName, SortOrder.Ascending)]
@@ -2748,10 +2749,11 @@ namespace MediaBrowser.Controller.Entities
/// Get all extras with specific types that are associated with this item. /// Get all extras with specific types that are associated with this item.
/// </summary> /// </summary>
/// <param name="extraTypes">The types of extras to retrieve.</param> /// <param name="extraTypes">The types of extras to retrieve.</param>
/// <param name="user">The user to apply parental restrictions for, or <c>null</c> to skip restriction checks.</param>
/// <returns>An enumerable containing the extras.</returns> /// <returns>An enumerable containing the extras.</returns>
public IEnumerable<BaseItem> GetExtras(IReadOnlyCollection<ExtraType> extraTypes) public IEnumerable<BaseItem> GetExtras(IReadOnlyCollection<ExtraType> extraTypes, User user = null)
{ {
return LibraryManager.GetItemList(new InternalItemsQuery() return LibraryManager.GetItemList(new InternalItemsQuery(user)
{ {
OwnerIds = [Id], OwnerIds = [Id],
ExtraTypes = extraTypes.ToArray(), ExtraTypes = extraTypes.ToArray(),

View File

@@ -10,6 +10,7 @@ using System.Text.Json.Serialization;
using System.Threading; using System.Threading;
using System.Threading.Tasks; using System.Threading.Tasks;
using Jellyfin.Data.Enums; using Jellyfin.Data.Enums;
using Jellyfin.Database.Implementations.Entities;
using Jellyfin.Extensions; using Jellyfin.Extensions;
using MediaBrowser.Controller.Library; using MediaBrowser.Controller.Library;
using MediaBrowser.Controller.LiveTv; using MediaBrowser.Controller.LiveTv;
@@ -390,13 +391,13 @@ namespace MediaBrowser.Controller.Entities
/// <summary> /// <summary>
/// Gets the additional parts. /// Gets the additional parts.
/// </summary> /// </summary>
/// <param name="user">The user to apply parental restrictions for, or <c>null</c> to skip restriction checks.</param>
/// <returns>IEnumerable{Video}.</returns> /// <returns>IEnumerable{Video}.</returns>
public IOrderedEnumerable<Video> GetAdditionalParts() public IOrderedEnumerable<Video> GetAdditionalParts(User user = null)
{ {
return GetAdditionalPartIds() return GetAdditionalPartIds()
.Select(i => LibraryManager.GetItemById(i)) .Select(i => LibraryManager.GetItemById<Video>(i, user))
.Where(i => i is not null) .Where(i => i is not null)
.OfType<Video>()
.OrderBy(i => i.SortName); .OrderBy(i => i.SortName);
} }