Migrate Display Preferences to EF Core
This commit is contained in:
parent
175e7b45e5
commit
ab396225ea
|
@ -11,6 +11,7 @@ using System.Xml;
|
|||
using Emby.Dlna.Didl;
|
||||
using Emby.Dlna.Service;
|
||||
using Jellyfin.Data.Entities;
|
||||
using Jellyfin.Data.Enums;
|
||||
using MediaBrowser.Common.Extensions;
|
||||
using MediaBrowser.Controller.Configuration;
|
||||
using MediaBrowser.Controller.Drawing;
|
||||
|
|
|
@ -554,8 +554,6 @@ namespace Emby.Server.Implementations
|
|||
serviceCollection.AddSingleton<IUserDataRepository, SqliteUserDataRepository>();
|
||||
serviceCollection.AddSingleton<IUserDataManager, UserDataManager>();
|
||||
|
||||
serviceCollection.AddSingleton<IDisplayPreferencesRepository, SqliteDisplayPreferencesRepository>();
|
||||
|
||||
serviceCollection.AddSingleton<IItemRepository, SqliteItemRepository>();
|
||||
|
||||
serviceCollection.AddSingleton<IAuthenticationRepository, AuthenticationRepository>();
|
||||
|
@ -650,7 +648,6 @@ namespace Emby.Server.Implementations
|
|||
_httpServer = Resolve<IHttpServer>();
|
||||
_httpClient = Resolve<IHttpClient>();
|
||||
|
||||
((SqliteDisplayPreferencesRepository)Resolve<IDisplayPreferencesRepository>()).Initialize();
|
||||
((AuthenticationRepository)Resolve<IAuthenticationRepository>()).Initialize();
|
||||
|
||||
SetStaticProperties();
|
||||
|
|
|
@ -7,6 +7,7 @@ using System.Linq;
|
|||
using System.Threading;
|
||||
using System.Threading.Tasks;
|
||||
using Jellyfin.Data.Entities;
|
||||
using Jellyfin.Data.Enums;
|
||||
using MediaBrowser.Common.Extensions;
|
||||
using MediaBrowser.Common.Progress;
|
||||
using MediaBrowser.Controller.Channels;
|
||||
|
|
|
@ -1,225 +0,0 @@
|
|||
#pragma warning disable CS1591
|
||||
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Globalization;
|
||||
using System.IO;
|
||||
using System.Text.Json;
|
||||
using System.Threading;
|
||||
using MediaBrowser.Common.Configuration;
|
||||
using MediaBrowser.Common.Extensions;
|
||||
using MediaBrowser.Common.Json;
|
||||
using MediaBrowser.Controller.Persistence;
|
||||
using MediaBrowser.Model.Entities;
|
||||
using MediaBrowser.Model.IO;
|
||||
using Microsoft.Extensions.Logging;
|
||||
using SQLitePCL.pretty;
|
||||
|
||||
namespace Emby.Server.Implementations.Data
|
||||
{
|
||||
/// <summary>
|
||||
/// Class SQLiteDisplayPreferencesRepository.
|
||||
/// </summary>
|
||||
public class SqliteDisplayPreferencesRepository : BaseSqliteRepository, IDisplayPreferencesRepository
|
||||
{
|
||||
private readonly IFileSystem _fileSystem;
|
||||
|
||||
private readonly JsonSerializerOptions _jsonOptions;
|
||||
|
||||
public SqliteDisplayPreferencesRepository(ILogger<SqliteDisplayPreferencesRepository> logger, IApplicationPaths appPaths, IFileSystem fileSystem)
|
||||
: base(logger)
|
||||
{
|
||||
_fileSystem = fileSystem;
|
||||
|
||||
_jsonOptions = JsonDefaults.GetOptions();
|
||||
|
||||
DbFilePath = Path.Combine(appPaths.DataPath, "displaypreferences.db");
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the name of the repository.
|
||||
/// </summary>
|
||||
/// <value>The name.</value>
|
||||
public string Name => "SQLite";
|
||||
|
||||
public void Initialize()
|
||||
{
|
||||
try
|
||||
{
|
||||
InitializeInternal();
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
Logger.LogError(ex, "Error loading database file. Will reset and retry.");
|
||||
|
||||
_fileSystem.DeleteFile(DbFilePath);
|
||||
|
||||
InitializeInternal();
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Opens the connection to the database.
|
||||
/// </summary>
|
||||
/// <returns>Task.</returns>
|
||||
private void InitializeInternal()
|
||||
{
|
||||
string[] queries =
|
||||
{
|
||||
"create table if not exists userdisplaypreferences (id GUID NOT NULL, userId GUID NOT NULL, client text NOT NULL, data BLOB NOT NULL)",
|
||||
"create unique index if not exists userdisplaypreferencesindex on userdisplaypreferences (id, userId, client)"
|
||||
};
|
||||
|
||||
using (var connection = GetConnection())
|
||||
{
|
||||
connection.RunQueries(queries);
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Save the display preferences associated with an item in the repo.
|
||||
/// </summary>
|
||||
/// <param name="displayPreferences">The display preferences.</param>
|
||||
/// <param name="userId">The user id.</param>
|
||||
/// <param name="client">The client.</param>
|
||||
/// <param name="cancellationToken">The cancellation token.</param>
|
||||
/// <exception cref="ArgumentNullException">item</exception>
|
||||
public void SaveDisplayPreferences(DisplayPreferences displayPreferences, Guid userId, string client, CancellationToken cancellationToken)
|
||||
{
|
||||
if (displayPreferences == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(displayPreferences));
|
||||
}
|
||||
|
||||
if (string.IsNullOrEmpty(displayPreferences.Id))
|
||||
{
|
||||
throw new ArgumentException("Display preferences has an invalid Id", nameof(displayPreferences));
|
||||
}
|
||||
|
||||
cancellationToken.ThrowIfCancellationRequested();
|
||||
|
||||
using (var connection = GetConnection())
|
||||
{
|
||||
connection.RunInTransaction(
|
||||
db => SaveDisplayPreferences(displayPreferences, userId, client, db),
|
||||
TransactionMode);
|
||||
}
|
||||
}
|
||||
|
||||
private void SaveDisplayPreferences(DisplayPreferences displayPreferences, Guid userId, string client, IDatabaseConnection connection)
|
||||
{
|
||||
var serialized = JsonSerializer.SerializeToUtf8Bytes(displayPreferences, _jsonOptions);
|
||||
|
||||
using (var statement = connection.PrepareStatement("replace into userdisplaypreferences (id, userid, client, data) values (@id, @userId, @client, @data)"))
|
||||
{
|
||||
statement.TryBind("@id", new Guid(displayPreferences.Id).ToByteArray());
|
||||
statement.TryBind("@userId", userId.ToByteArray());
|
||||
statement.TryBind("@client", client);
|
||||
statement.TryBind("@data", serialized);
|
||||
|
||||
statement.MoveNext();
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Save all display preferences associated with a user in the repo.
|
||||
/// </summary>
|
||||
/// <param name="displayPreferences">The display preferences.</param>
|
||||
/// <param name="userId">The user id.</param>
|
||||
/// <param name="cancellationToken">The cancellation token.</param>
|
||||
/// <exception cref="ArgumentNullException">item</exception>
|
||||
public void SaveAllDisplayPreferences(IEnumerable<DisplayPreferences> displayPreferences, Guid userId, CancellationToken cancellationToken)
|
||||
{
|
||||
if (displayPreferences == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(displayPreferences));
|
||||
}
|
||||
|
||||
cancellationToken.ThrowIfCancellationRequested();
|
||||
|
||||
using (var connection = GetConnection())
|
||||
{
|
||||
connection.RunInTransaction(
|
||||
db =>
|
||||
{
|
||||
foreach (var displayPreference in displayPreferences)
|
||||
{
|
||||
SaveDisplayPreferences(displayPreference, userId, displayPreference.Client, db);
|
||||
}
|
||||
},
|
||||
TransactionMode);
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the display preferences.
|
||||
/// </summary>
|
||||
/// <param name="displayPreferencesId">The display preferences id.</param>
|
||||
/// <param name="userId">The user id.</param>
|
||||
/// <param name="client">The client.</param>
|
||||
/// <returns>Task{DisplayPreferences}.</returns>
|
||||
/// <exception cref="ArgumentNullException">item</exception>
|
||||
public DisplayPreferences GetDisplayPreferences(string displayPreferencesId, Guid userId, string client)
|
||||
{
|
||||
if (string.IsNullOrEmpty(displayPreferencesId))
|
||||
{
|
||||
throw new ArgumentNullException(nameof(displayPreferencesId));
|
||||
}
|
||||
|
||||
var guidId = displayPreferencesId.GetMD5();
|
||||
|
||||
using (var connection = GetConnection(true))
|
||||
{
|
||||
using (var statement = connection.PrepareStatement("select data from userdisplaypreferences where id = @id and userId=@userId and client=@client"))
|
||||
{
|
||||
statement.TryBind("@id", guidId.ToByteArray());
|
||||
statement.TryBind("@userId", userId.ToByteArray());
|
||||
statement.TryBind("@client", client);
|
||||
|
||||
foreach (var row in statement.ExecuteQuery())
|
||||
{
|
||||
return Get(row);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return new DisplayPreferences
|
||||
{
|
||||
Id = guidId.ToString("N", CultureInfo.InvariantCulture)
|
||||
};
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets all display preferences for the given user.
|
||||
/// </summary>
|
||||
/// <param name="userId">The user id.</param>
|
||||
/// <returns>Task{DisplayPreferences}.</returns>
|
||||
/// <exception cref="ArgumentNullException">item</exception>
|
||||
public IEnumerable<DisplayPreferences> GetAllDisplayPreferences(Guid userId)
|
||||
{
|
||||
var list = new List<DisplayPreferences>();
|
||||
|
||||
using (var connection = GetConnection(true))
|
||||
using (var statement = connection.PrepareStatement("select data from userdisplaypreferences where userId=@userId"))
|
||||
{
|
||||
statement.TryBind("@userId", userId.ToByteArray());
|
||||
|
||||
foreach (var row in statement.ExecuteQuery())
|
||||
{
|
||||
list.Add(Get(row));
|
||||
}
|
||||
}
|
||||
|
||||
return list;
|
||||
}
|
||||
|
||||
private DisplayPreferences Get(IReadOnlyList<IResultSetValue> row)
|
||||
=> JsonSerializer.Deserialize<DisplayPreferences>(row[0].ToBlob(), _jsonOptions);
|
||||
|
||||
public void SaveDisplayPreferences(DisplayPreferences displayPreferences, string userId, string client, CancellationToken cancellationToken)
|
||||
=> SaveDisplayPreferences(displayPreferences, new Guid(userId), client, cancellationToken);
|
||||
|
||||
public DisplayPreferences GetDisplayPreferences(string displayPreferencesId, string userId, string client)
|
||||
=> GetDisplayPreferences(displayPreferencesId, new Guid(userId), client);
|
||||
}
|
||||
}
|
|
@ -9,6 +9,7 @@ using System.Text;
|
|||
using System.Text.Json;
|
||||
using System.Threading;
|
||||
using Emby.Server.Implementations.Playlists;
|
||||
using Jellyfin.Data.Enums;
|
||||
using MediaBrowser.Common.Extensions;
|
||||
using MediaBrowser.Common.Json;
|
||||
using MediaBrowser.Controller;
|
||||
|
|
|
@ -54,7 +54,7 @@
|
|||
<TargetFramework>netstandard2.1</TargetFramework>
|
||||
<GenerateAssemblyInfo>false</GenerateAssemblyInfo>
|
||||
<GenerateDocumentationFile>true</GenerateDocumentationFile>
|
||||
<TreatWarningsAsErrors Condition=" '$(Configuration)' == 'Release'" >true</TreatWarningsAsErrors>
|
||||
<TreatWarningsAsErrors Condition=" '$(Configuration)' == 'Release'">true</TreatWarningsAsErrors>
|
||||
</PropertyGroup>
|
||||
|
||||
<!-- Code Analyzers-->
|
||||
|
|
|
@ -3,7 +3,7 @@
|
|||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.IO;
|
||||
using Emby.Server.Implementations.Images;
|
||||
using Jellyfin.Data.Enums;
|
||||
using MediaBrowser.Common.Configuration;
|
||||
using MediaBrowser.Controller.Drawing;
|
||||
using MediaBrowser.Controller.Dto;
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
#pragma warning disable CS1591
|
||||
|
||||
using System.Collections.Generic;
|
||||
using Emby.Server.Implementations.Images;
|
||||
using Jellyfin.Data.Enums;
|
||||
using MediaBrowser.Common.Configuration;
|
||||
using MediaBrowser.Controller.Drawing;
|
||||
using MediaBrowser.Controller.Dto;
|
||||
|
|
|
@ -1,6 +1,7 @@
|
|||
#pragma warning disable CS1591
|
||||
|
||||
using System.Collections.Generic;
|
||||
using Jellyfin.Data.Enums;
|
||||
using MediaBrowser.Common.Configuration;
|
||||
using MediaBrowser.Controller.Drawing;
|
||||
using MediaBrowser.Controller.Dto;
|
||||
|
|
|
@ -50,7 +50,6 @@ using Microsoft.Extensions.Logging;
|
|||
using Episode = MediaBrowser.Controller.Entities.TV.Episode;
|
||||
using Genre = MediaBrowser.Controller.Entities.Genre;
|
||||
using Person = MediaBrowser.Controller.Entities.Person;
|
||||
using SortOrder = MediaBrowser.Model.Entities.SortOrder;
|
||||
using VideoResolver = Emby.Naming.Video.VideoResolver;
|
||||
|
||||
namespace Emby.Server.Implementations.Library
|
||||
|
|
|
@ -4,12 +4,12 @@ using System;
|
|||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using Jellyfin.Data.Entities;
|
||||
using Jellyfin.Data.Enums;
|
||||
using MediaBrowser.Controller.Dto;
|
||||
using MediaBrowser.Controller.Entities;
|
||||
using MediaBrowser.Controller.Entities.Audio;
|
||||
using MediaBrowser.Controller.Library;
|
||||
using MediaBrowser.Controller.Playlists;
|
||||
using MediaBrowser.Model.Entities;
|
||||
using MediaBrowser.Model.Querying;
|
||||
using MusicAlbum = MediaBrowser.Controller.Entities.Audio.MusicAlbum;
|
||||
|
||||
|
|
|
@ -4,12 +4,12 @@ using System;
|
|||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using Jellyfin.Data.Entities;
|
||||
using Jellyfin.Data.Enums;
|
||||
using MediaBrowser.Controller.Dto;
|
||||
using MediaBrowser.Controller.Entities;
|
||||
using MediaBrowser.Controller.Entities.Audio;
|
||||
using MediaBrowser.Controller.Extensions;
|
||||
using MediaBrowser.Controller.Library;
|
||||
using MediaBrowser.Model.Entities;
|
||||
using MediaBrowser.Model.Querying;
|
||||
using MediaBrowser.Model.Search;
|
||||
using Microsoft.Extensions.Logging;
|
||||
|
|
|
@ -12,6 +12,7 @@ using System.Threading;
|
|||
using System.Threading.Tasks;
|
||||
using System.Xml;
|
||||
using Emby.Server.Implementations.Library;
|
||||
using Jellyfin.Data.Enums;
|
||||
using MediaBrowser.Common.Configuration;
|
||||
using MediaBrowser.Common.Extensions;
|
||||
using MediaBrowser.Common.Net;
|
||||
|
|
72
Jellyfin.Data/Entities/DisplayPreferences.cs
Normal file
72
Jellyfin.Data/Entities/DisplayPreferences.cs
Normal file
|
@ -0,0 +1,72 @@
|
|||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.ComponentModel.DataAnnotations;
|
||||
using System.ComponentModel.DataAnnotations.Schema;
|
||||
using Jellyfin.Data.Enums;
|
||||
|
||||
namespace Jellyfin.Data.Entities
|
||||
{
|
||||
public class DisplayPreferences
|
||||
{
|
||||
public DisplayPreferences(string client, Guid userId)
|
||||
{
|
||||
RememberIndexing = false;
|
||||
ShowBackdrop = true;
|
||||
Client = client;
|
||||
UserId = userId;
|
||||
|
||||
HomeSections = new HashSet<HomeSection>();
|
||||
}
|
||||
|
||||
protected DisplayPreferences()
|
||||
{
|
||||
}
|
||||
|
||||
[Required]
|
||||
[DatabaseGenerated(DatabaseGeneratedOption.Identity)]
|
||||
public int Id { get; protected set; }
|
||||
|
||||
[Required]
|
||||
public Guid UserId { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the id of the associated item.
|
||||
/// </summary>
|
||||
/// <remarks>
|
||||
/// This is currently unused. In the future, this will allow us to have users set
|
||||
/// display preferences per item.
|
||||
/// </remarks>
|
||||
public Guid? ItemId { get; set; }
|
||||
|
||||
[Required]
|
||||
[MaxLength(64)]
|
||||
[StringLength(64)]
|
||||
public string Client { get; set; }
|
||||
|
||||
[Required]
|
||||
public bool RememberIndexing { get; set; }
|
||||
|
||||
[Required]
|
||||
public bool RememberSorting { get; set; }
|
||||
|
||||
[Required]
|
||||
public SortOrder SortOrder { get; set; }
|
||||
|
||||
[Required]
|
||||
public bool ShowSidebar { get; set; }
|
||||
|
||||
[Required]
|
||||
public bool ShowBackdrop { get; set; }
|
||||
|
||||
public string SortBy { get; set; }
|
||||
|
||||
public ViewType? ViewType { get; set; }
|
||||
|
||||
[Required]
|
||||
public ScrollDirection ScrollDirection { get; set; }
|
||||
|
||||
public IndexingKind? IndexBy { get; set; }
|
||||
|
||||
public virtual ICollection<HomeSection> HomeSections { get; protected set; }
|
||||
}
|
||||
}
|
21
Jellyfin.Data/Entities/HomeSection.cs
Normal file
21
Jellyfin.Data/Entities/HomeSection.cs
Normal file
|
@ -0,0 +1,21 @@
|
|||
using System;
|
||||
using System.ComponentModel.DataAnnotations;
|
||||
using System.ComponentModel.DataAnnotations.Schema;
|
||||
using Jellyfin.Data.Enums;
|
||||
|
||||
namespace Jellyfin.Data.Entities
|
||||
{
|
||||
public class HomeSection
|
||||
{
|
||||
[Key]
|
||||
[Required]
|
||||
[DatabaseGenerated(DatabaseGeneratedOption.Identity)]
|
||||
public int Id { get; protected set; }
|
||||
|
||||
public int DisplayPreferencesId { get; set; }
|
||||
|
||||
public int Order { get; set; }
|
||||
|
||||
public HomeSectionType Type { get; set; }
|
||||
}
|
||||
}
|
|
@ -349,6 +349,11 @@ namespace Jellyfin.Data.Entities
|
|||
/// </summary>
|
||||
public virtual ICollection<AccessSchedule> AccessSchedules { get; protected set; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the list of item display preferences.
|
||||
/// </summary>
|
||||
public virtual ICollection<DisplayPreferences> DisplayPreferences { get; protected set; }
|
||||
|
||||
/*
|
||||
/// <summary>
|
||||
/// Gets or sets the list of groups this user is a member of.
|
||||
|
|
53
Jellyfin.Data/Enums/HomeSectionType.cs
Normal file
53
Jellyfin.Data/Enums/HomeSectionType.cs
Normal file
|
@ -0,0 +1,53 @@
|
|||
namespace Jellyfin.Data.Enums
|
||||
{
|
||||
/// <summary>
|
||||
/// An enum representing the different options for the home screen sections.
|
||||
/// </summary>
|
||||
public enum HomeSectionType
|
||||
{
|
||||
/// <summary>
|
||||
/// My Media.
|
||||
/// </summary>
|
||||
SmallLibraryTiles = 0,
|
||||
|
||||
/// <summary>
|
||||
/// My Media Small.
|
||||
/// </summary>
|
||||
LibraryButtons = 1,
|
||||
|
||||
/// <summary>
|
||||
/// Active Recordings.
|
||||
/// </summary>
|
||||
ActiveRecordings = 2,
|
||||
|
||||
/// <summary>
|
||||
/// Continue Watching.
|
||||
/// </summary>
|
||||
Resume = 3,
|
||||
|
||||
/// <summary>
|
||||
/// Continue Listening.
|
||||
/// </summary>
|
||||
ResumeAudio = 4,
|
||||
|
||||
/// <summary>
|
||||
/// Latest Media.
|
||||
/// </summary>
|
||||
LatestMedia = 5,
|
||||
|
||||
/// <summary>
|
||||
/// Next Up.
|
||||
/// </summary>
|
||||
NextUp = 6,
|
||||
|
||||
/// <summary>
|
||||
/// Live TV.
|
||||
/// </summary>
|
||||
LiveTv = 7,
|
||||
|
||||
/// <summary>
|
||||
/// None.
|
||||
/// </summary>
|
||||
None = 8
|
||||
}
|
||||
}
|
20
Jellyfin.Data/Enums/IndexingKind.cs
Normal file
20
Jellyfin.Data/Enums/IndexingKind.cs
Normal file
|
@ -0,0 +1,20 @@
|
|||
namespace Jellyfin.Data.Enums
|
||||
{
|
||||
public enum IndexingKind
|
||||
{
|
||||
/// <summary>
|
||||
/// Index by the premiere date.
|
||||
/// </summary>
|
||||
PremiereDate,
|
||||
|
||||
/// <summary>
|
||||
/// Index by the production year.
|
||||
/// </summary>
|
||||
ProductionYear,
|
||||
|
||||
/// <summary>
|
||||
/// Index by the community rating.
|
||||
/// </summary>
|
||||
CommunityRating
|
||||
}
|
||||
}
|
|
@ -1,17 +1,17 @@
|
|||
namespace MediaBrowser.Model.Entities
|
||||
namespace Jellyfin.Data.Enums
|
||||
{
|
||||
/// <summary>
|
||||
/// Enum ScrollDirection.
|
||||
/// An enum representing the axis that should be scrolled.
|
||||
/// </summary>
|
||||
public enum ScrollDirection
|
||||
{
|
||||
/// <summary>
|
||||
/// The horizontal.
|
||||
/// Horizontal scrolling direction.
|
||||
/// </summary>
|
||||
Horizontal,
|
||||
|
||||
/// <summary>
|
||||
/// The vertical.
|
||||
/// Vertical scrolling direction.
|
||||
/// </summary>
|
||||
Vertical
|
||||
}
|
|
@ -1,17 +1,17 @@
|
|||
namespace MediaBrowser.Model.Entities
|
||||
namespace Jellyfin.Data.Enums
|
||||
{
|
||||
/// <summary>
|
||||
/// Enum SortOrder.
|
||||
/// An enum representing the sorting order.
|
||||
/// </summary>
|
||||
public enum SortOrder
|
||||
{
|
||||
/// <summary>
|
||||
/// The ascending.
|
||||
/// Sort in increasing order.
|
||||
/// </summary>
|
||||
Ascending,
|
||||
|
||||
/// <summary>
|
||||
/// The descending.
|
||||
/// Sort in decreasing order.
|
||||
/// </summary>
|
||||
Descending
|
||||
}
|
38
Jellyfin.Data/Enums/ViewType.cs
Normal file
38
Jellyfin.Data/Enums/ViewType.cs
Normal file
|
@ -0,0 +1,38 @@
|
|||
namespace Jellyfin.Data.Enums
|
||||
{
|
||||
/// <summary>
|
||||
/// An enum representing the type of view for a library or collection.
|
||||
/// </summary>
|
||||
public enum ViewType
|
||||
{
|
||||
/// <summary>
|
||||
/// Shows banners.
|
||||
/// </summary>
|
||||
Banner = 0,
|
||||
|
||||
/// <summary>
|
||||
/// Shows a list of content.
|
||||
/// </summary>
|
||||
List = 1,
|
||||
|
||||
/// <summary>
|
||||
/// Shows poster artwork.
|
||||
/// </summary>
|
||||
Poster = 2,
|
||||
|
||||
/// <summary>
|
||||
/// Shows poster artwork with a card containing the name and year.
|
||||
/// </summary>
|
||||
PosterCard = 3,
|
||||
|
||||
/// <summary>
|
||||
/// Shows a thumbnail.
|
||||
/// </summary>
|
||||
Thumb = 4,
|
||||
|
||||
/// <summary>
|
||||
/// Shows a thumbnail with a card containing the name and year.
|
||||
/// </summary>
|
||||
ThumbCard = 5
|
||||
}
|
||||
}
|
49
Jellyfin.Server.Implementations/DisplayPreferencesManager.cs
Normal file
49
Jellyfin.Server.Implementations/DisplayPreferencesManager.cs
Normal file
|
@ -0,0 +1,49 @@
|
|||
using System;
|
||||
using System.Linq;
|
||||
using Jellyfin.Data.Entities;
|
||||
using MediaBrowser.Controller;
|
||||
|
||||
namespace Jellyfin.Server.Implementations
|
||||
{
|
||||
/// <summary>
|
||||
/// Manages the storage and retrieval of display preferences through Entity Framework.
|
||||
/// </summary>
|
||||
public class DisplayPreferencesManager : IDisplayPreferencesManager
|
||||
{
|
||||
private readonly JellyfinDbProvider _dbProvider;
|
||||
|
||||
/// <summary>
|
||||
/// Initializes a new instance of the <see cref="DisplayPreferencesManager"/> class.
|
||||
/// </summary>
|
||||
/// <param name="dbProvider">The Jellyfin db provider.</param>
|
||||
public DisplayPreferencesManager(JellyfinDbProvider dbProvider)
|
||||
{
|
||||
_dbProvider = dbProvider;
|
||||
}
|
||||
|
||||
/// <inheritdoc />
|
||||
public DisplayPreferences GetDisplayPreferences(Guid userId, string client)
|
||||
{
|
||||
var dbContext = _dbProvider.CreateContext();
|
||||
var user = dbContext.Users.Find(userId);
|
||||
#pragma warning disable CA1307
|
||||
var prefs = user.DisplayPreferences.FirstOrDefault(pref => string.Equals(pref.Client, client));
|
||||
|
||||
if (prefs == null)
|
||||
{
|
||||
prefs = new DisplayPreferences(client, userId);
|
||||
user.DisplayPreferences.Add(prefs);
|
||||
}
|
||||
|
||||
return prefs;
|
||||
}
|
||||
|
||||
/// <inheritdoc />
|
||||
public void SaveChanges(DisplayPreferences preferences)
|
||||
{
|
||||
var dbContext = _dbProvider.CreateContext();
|
||||
dbContext.Update(preferences);
|
||||
dbContext.SaveChanges();
|
||||
}
|
||||
}
|
||||
}
|
|
@ -27,6 +27,8 @@ namespace Jellyfin.Server.Implementations
|
|||
|
||||
public virtual DbSet<ActivityLog> ActivityLogs { get; set; }
|
||||
|
||||
public virtual DbSet<DisplayPreferences> DisplayPreferences { get; set; }
|
||||
|
||||
public virtual DbSet<ImageInfo> ImageInfos { get; set; }
|
||||
|
||||
public virtual DbSet<Permission> Permissions { get; set; }
|
||||
|
|
403
Jellyfin.Server.Implementations/Migrations/20200630170339_AddDisplayPreferences.Designer.cs
generated
Normal file
403
Jellyfin.Server.Implementations/Migrations/20200630170339_AddDisplayPreferences.Designer.cs
generated
Normal file
|
@ -0,0 +1,403 @@
|
|||
#pragma warning disable CS1591
|
||||
|
||||
// <auto-generated />
|
||||
using System;
|
||||
using Jellyfin.Server.Implementations;
|
||||
using Microsoft.EntityFrameworkCore;
|
||||
using Microsoft.EntityFrameworkCore.Infrastructure;
|
||||
using Microsoft.EntityFrameworkCore.Migrations;
|
||||
using Microsoft.EntityFrameworkCore.Storage.ValueConversion;
|
||||
|
||||
namespace Jellyfin.Server.Implementations.Migrations
|
||||
{
|
||||
[DbContext(typeof(JellyfinDb))]
|
||||
[Migration("20200630170339_AddDisplayPreferences")]
|
||||
partial class AddDisplayPreferences
|
||||
{
|
||||
protected override void BuildTargetModel(ModelBuilder modelBuilder)
|
||||
{
|
||||
#pragma warning disable 612, 618
|
||||
modelBuilder
|
||||
.HasDefaultSchema("jellyfin")
|
||||
.HasAnnotation("ProductVersion", "3.1.5");
|
||||
|
||||
modelBuilder.Entity("Jellyfin.Data.Entities.AccessSchedule", b =>
|
||||
{
|
||||
b.Property<int>("Id")
|
||||
.ValueGeneratedOnAdd()
|
||||
.HasColumnType("INTEGER");
|
||||
|
||||
b.Property<int>("DayOfWeek")
|
||||
.HasColumnType("INTEGER");
|
||||
|
||||
b.Property<double>("EndHour")
|
||||
.HasColumnType("REAL");
|
||||
|
||||
b.Property<double>("StartHour")
|
||||
.HasColumnType("REAL");
|
||||
|
||||
b.Property<Guid>("UserId")
|
||||
.HasColumnType("TEXT");
|
||||
|
||||
b.HasKey("Id");
|
||||
|
||||
b.HasIndex("UserId");
|
||||
|
||||
b.ToTable("AccessSchedules");
|
||||
});
|
||||
|
||||
modelBuilder.Entity("Jellyfin.Data.Entities.ActivityLog", b =>
|
||||
{
|
||||
b.Property<int>("Id")
|
||||
.ValueGeneratedOnAdd()
|
||||
.HasColumnType("INTEGER");
|
||||
|
||||
b.Property<DateTime>("DateCreated")
|
||||
.HasColumnType("TEXT");
|
||||
|
||||
b.Property<string>("ItemId")
|
||||
.HasColumnType("TEXT")
|
||||
.HasMaxLength(256);
|
||||
|
||||
b.Property<int>("LogSeverity")
|
||||
.HasColumnType("INTEGER");
|
||||
|
||||
b.Property<string>("Name")
|
||||
.IsRequired()
|
||||
.HasColumnType("TEXT")
|
||||
.HasMaxLength(512);
|
||||
|
||||
b.Property<string>("Overview")
|
||||
.HasColumnType("TEXT")
|
||||
.HasMaxLength(512);
|
||||
|
||||
b.Property<uint>("RowVersion")
|
||||
.IsConcurrencyToken()
|
||||
.HasColumnType("INTEGER");
|
||||
|
||||
b.Property<string>("ShortOverview")
|
||||
.HasColumnType("TEXT")
|
||||
.HasMaxLength(512);
|
||||
|
||||
b.Property<string>("Type")
|
||||
.IsRequired()
|
||||
.HasColumnType("TEXT")
|
||||
.HasMaxLength(256);
|
||||
|
||||
b.Property<Guid>("UserId")
|
||||
.HasColumnType("TEXT");
|
||||
|
||||
b.HasKey("Id");
|
||||
|
||||
b.ToTable("ActivityLogs");
|
||||
});
|
||||
|
||||
modelBuilder.Entity("Jellyfin.Data.Entities.DisplayPreferences", b =>
|
||||
{
|
||||
b.Property<int>("Id")
|
||||
.ValueGeneratedOnAdd()
|
||||
.HasColumnType("INTEGER");
|
||||
|
||||
b.Property<string>("Client")
|
||||
.IsRequired()
|
||||
.HasColumnType("TEXT")
|
||||
.HasMaxLength(64);
|
||||
|
||||
b.Property<int?>("IndexBy")
|
||||
.HasColumnType("INTEGER");
|
||||
|
||||
b.Property<Guid?>("ItemId")
|
||||
.HasColumnType("TEXT");
|
||||
|
||||
b.Property<bool>("RememberIndexing")
|
||||
.HasColumnType("INTEGER");
|
||||
|
||||
b.Property<bool>("RememberSorting")
|
||||
.HasColumnType("INTEGER");
|
||||
|
||||
b.Property<int>("ScrollDirection")
|
||||
.HasColumnType("INTEGER");
|
||||
|
||||
b.Property<bool>("ShowBackdrop")
|
||||
.HasColumnType("INTEGER");
|
||||
|
||||
b.Property<bool>("ShowSidebar")
|
||||
.HasColumnType("INTEGER");
|
||||
|
||||
b.Property<string>("SortBy")
|
||||
.HasColumnType("TEXT");
|
||||
|
||||
b.Property<int>("SortOrder")
|
||||
.HasColumnType("INTEGER");
|
||||
|
||||
b.Property<Guid>("UserId")
|
||||
.HasColumnType("TEXT");
|
||||
|
||||
b.Property<int?>("ViewType")
|
||||
.HasColumnType("INTEGER");
|
||||
|
||||
b.HasKey("Id");
|
||||
|
||||
b.HasIndex("UserId");
|
||||
|
||||
b.ToTable("DisplayPreferences");
|
||||
});
|
||||
|
||||
modelBuilder.Entity("Jellyfin.Data.Entities.HomeSection", b =>
|
||||
{
|
||||
b.Property<int>("Id")
|
||||
.ValueGeneratedOnAdd()
|
||||
.HasColumnType("INTEGER");
|
||||
|
||||
b.Property<int>("DisplayPreferencesId")
|
||||
.HasColumnType("INTEGER");
|
||||
|
||||
b.Property<int>("Order")
|
||||
.HasColumnType("INTEGER");
|
||||
|
||||
b.Property<int>("Type")
|
||||
.HasColumnType("INTEGER");
|
||||
|
||||
b.HasKey("Id");
|
||||
|
||||
b.HasIndex("DisplayPreferencesId");
|
||||
|
||||
b.ToTable("HomeSection");
|
||||
});
|
||||
|
||||
modelBuilder.Entity("Jellyfin.Data.Entities.ImageInfo", b =>
|
||||
{
|
||||
b.Property<int>("Id")
|
||||
.ValueGeneratedOnAdd()
|
||||
.HasColumnType("INTEGER");
|
||||
|
||||
b.Property<DateTime>("LastModified")
|
||||
.HasColumnType("TEXT");
|
||||
|
||||
b.Property<string>("Path")
|
||||
.IsRequired()
|
||||
.HasColumnType("TEXT")
|
||||
.HasMaxLength(512);
|
||||
|
||||
b.Property<Guid?>("UserId")
|
||||
.HasColumnType("TEXT");
|
||||
|
||||
b.HasKey("Id");
|
||||
|
||||
b.HasIndex("UserId")
|
||||
.IsUnique();
|
||||
|
||||
b.ToTable("ImageInfos");
|
||||
});
|
||||
|
||||
modelBuilder.Entity("Jellyfin.Data.Entities.Permission", b =>
|
||||
{
|
||||
b.Property<int>("Id")
|
||||
.ValueGeneratedOnAdd()
|
||||
.HasColumnType("INTEGER");
|
||||
|
||||
b.Property<int>("Kind")
|
||||
.HasColumnType("INTEGER");
|
||||
|
||||
b.Property<Guid?>("Permission_Permissions_Guid")
|
||||
.HasColumnType("TEXT");
|
||||
|
||||
b.Property<uint>("RowVersion")
|
||||
.IsConcurrencyToken()
|
||||
.HasColumnType("INTEGER");
|
||||
|
||||
b.Property<bool>("Value")
|
||||
.HasColumnType("INTEGER");
|
||||
|
||||
b.HasKey("Id");
|
||||
|
||||
b.HasIndex("Permission_Permissions_Guid");
|
||||
|
||||
b.ToTable("Permissions");
|
||||
});
|
||||
|
||||
modelBuilder.Entity("Jellyfin.Data.Entities.Preference", b =>
|
||||
{
|
||||
b.Property<int>("Id")
|
||||
.ValueGeneratedOnAdd()
|
||||
.HasColumnType("INTEGER");
|
||||
|
||||
b.Property<int>("Kind")
|
||||
.HasColumnType("INTEGER");
|
||||
|
||||
b.Property<Guid?>("Preference_Preferences_Guid")
|
||||
.HasColumnType("TEXT");
|
||||
|
||||
b.Property<uint>("RowVersion")
|
||||
.IsConcurrencyToken()
|
||||
.HasColumnType("INTEGER");
|
||||
|
||||
b.Property<string>("Value")
|
||||
.IsRequired()
|
||||
.HasColumnType("TEXT")
|
||||
.HasMaxLength(65535);
|
||||
|
||||
b.HasKey("Id");
|
||||
|
||||
b.HasIndex("Preference_Preferences_Guid");
|
||||
|
||||
b.ToTable("Preferences");
|
||||
});
|
||||
|
||||
modelBuilder.Entity("Jellyfin.Data.Entities.User", b =>
|
||||
{
|
||||
b.Property<Guid>("Id")
|
||||
.ValueGeneratedOnAdd()
|
||||
.HasColumnType("TEXT");
|
||||
|
||||
b.Property<string>("AudioLanguagePreference")
|
||||
.HasColumnType("TEXT")
|
||||
.HasMaxLength(255);
|
||||
|
||||
b.Property<string>("AuthenticationProviderId")
|
||||
.IsRequired()
|
||||
.HasColumnType("TEXT")
|
||||
.HasMaxLength(255);
|
||||
|
||||
b.Property<bool>("DisplayCollectionsView")
|
||||
.HasColumnType("INTEGER");
|
||||
|
||||
b.Property<bool>("DisplayMissingEpisodes")
|
||||
.HasColumnType("INTEGER");
|
||||
|
||||
b.Property<string>("EasyPassword")
|
||||
.HasColumnType("TEXT")
|
||||
.HasMaxLength(65535);
|
||||
|
||||
b.Property<bool>("EnableAutoLogin")
|
||||
.HasColumnType("INTEGER");
|
||||
|
||||
b.Property<bool>("EnableLocalPassword")
|
||||
.HasColumnType("INTEGER");
|
||||
|
||||
b.Property<bool>("EnableNextEpisodeAutoPlay")
|
||||
.HasColumnType("INTEGER");
|
||||
|
||||
b.Property<bool>("EnableUserPreferenceAccess")
|
||||
.HasColumnType("INTEGER");
|
||||
|
||||
b.Property<bool>("HidePlayedInLatest")
|
||||
.HasColumnType("INTEGER");
|
||||
|
||||
b.Property<long>("InternalId")
|
||||
.HasColumnType("INTEGER");
|
||||
|
||||
b.Property<int>("InvalidLoginAttemptCount")
|
||||
.HasColumnType("INTEGER");
|
||||
|
||||
b.Property<DateTime?>("LastActivityDate")
|
||||
.HasColumnType("TEXT");
|
||||
|
||||
b.Property<DateTime?>("LastLoginDate")
|
||||
.HasColumnType("TEXT");
|
||||
|
||||
b.Property<int?>("LoginAttemptsBeforeLockout")
|
||||
.HasColumnType("INTEGER");
|
||||
|
||||
b.Property<int?>("MaxParentalAgeRating")
|
||||
.HasColumnType("INTEGER");
|
||||
|
||||
b.Property<bool>("MustUpdatePassword")
|
||||
.HasColumnType("INTEGER");
|
||||
|
||||
b.Property<string>("Password")
|
||||
.HasColumnType("TEXT")
|
||||
.HasMaxLength(65535);
|
||||
|
||||
b.Property<string>("PasswordResetProviderId")
|
||||
.IsRequired()
|
||||
.HasColumnType("TEXT")
|
||||
.HasMaxLength(255);
|
||||
|
||||
b.Property<bool>("PlayDefaultAudioTrack")
|
||||
.HasColumnType("INTEGER");
|
||||
|
||||
b.Property<bool>("RememberAudioSelections")
|
||||
.HasColumnType("INTEGER");
|
||||
|
||||
b.Property<bool>("RememberSubtitleSelections")
|
||||
.HasColumnType("INTEGER");
|
||||
|
||||
b.Property<int?>("RemoteClientBitrateLimit")
|
||||
.HasColumnType("INTEGER");
|
||||
|
||||
b.Property<uint>("RowVersion")
|
||||
.IsConcurrencyToken()
|
||||
.HasColumnType("INTEGER");
|
||||
|
||||
b.Property<string>("SubtitleLanguagePreference")
|
||||
.HasColumnType("TEXT")
|
||||
.HasMaxLength(255);
|
||||
|
||||
b.Property<int>("SubtitleMode")
|
||||
.HasColumnType("INTEGER");
|
||||
|
||||
b.Property<int>("SyncPlayAccess")
|
||||
.HasColumnType("INTEGER");
|
||||
|
||||
b.Property<string>("Username")
|
||||
.IsRequired()
|
||||
.HasColumnType("TEXT")
|
||||
.HasMaxLength(255);
|
||||
|
||||
b.HasKey("Id");
|
||||
|
||||
b.ToTable("Users");
|
||||
});
|
||||
|
||||
modelBuilder.Entity("Jellyfin.Data.Entities.AccessSchedule", b =>
|
||||
{
|
||||
b.HasOne("Jellyfin.Data.Entities.User", null)
|
||||
.WithMany("AccessSchedules")
|
||||
.HasForeignKey("UserId")
|
||||
.OnDelete(DeleteBehavior.Cascade)
|
||||
.IsRequired();
|
||||
});
|
||||
|
||||
modelBuilder.Entity("Jellyfin.Data.Entities.DisplayPreferences", b =>
|
||||
{
|
||||
b.HasOne("Jellyfin.Data.Entities.User", null)
|
||||
.WithMany("DisplayPreferences")
|
||||
.HasForeignKey("UserId")
|
||||
.OnDelete(DeleteBehavior.Cascade)
|
||||
.IsRequired();
|
||||
});
|
||||
|
||||
modelBuilder.Entity("Jellyfin.Data.Entities.HomeSection", b =>
|
||||
{
|
||||
b.HasOne("Jellyfin.Data.Entities.DisplayPreferences", null)
|
||||
.WithMany("HomeSections")
|
||||
.HasForeignKey("DisplayPreferencesId")
|
||||
.OnDelete(DeleteBehavior.Cascade)
|
||||
.IsRequired();
|
||||
});
|
||||
|
||||
modelBuilder.Entity("Jellyfin.Data.Entities.ImageInfo", b =>
|
||||
{
|
||||
b.HasOne("Jellyfin.Data.Entities.User", null)
|
||||
.WithOne("ProfileImage")
|
||||
.HasForeignKey("Jellyfin.Data.Entities.ImageInfo", "UserId");
|
||||
});
|
||||
|
||||
modelBuilder.Entity("Jellyfin.Data.Entities.Permission", b =>
|
||||
{
|
||||
b.HasOne("Jellyfin.Data.Entities.User", null)
|
||||
.WithMany("Permissions")
|
||||
.HasForeignKey("Permission_Permissions_Guid");
|
||||
});
|
||||
|
||||
modelBuilder.Entity("Jellyfin.Data.Entities.Preference", b =>
|
||||
{
|
||||
b.HasOne("Jellyfin.Data.Entities.User", null)
|
||||
.WithMany("Preferences")
|
||||
.HasForeignKey("Preference_Preferences_Guid");
|
||||
});
|
||||
#pragma warning restore 612, 618
|
||||
}
|
||||
}
|
||||
}
|
|
@ -0,0 +1,92 @@
|
|||
#pragma warning disable CS1591
|
||||
#pragma warning disable SA1601
|
||||
|
||||
using System;
|
||||
using Microsoft.EntityFrameworkCore.Migrations;
|
||||
|
||||
namespace Jellyfin.Server.Implementations.Migrations
|
||||
{
|
||||
public partial class AddDisplayPreferences : Migration
|
||||
{
|
||||
protected override void Up(MigrationBuilder migrationBuilder)
|
||||
{
|
||||
migrationBuilder.CreateTable(
|
||||
name: "DisplayPreferences",
|
||||
schema: "jellyfin",
|
||||
columns: table => new
|
||||
{
|
||||
Id = table.Column<int>(nullable: false)
|
||||
.Annotation("Sqlite:Autoincrement", true),
|
||||
UserId = table.Column<Guid>(nullable: false),
|
||||
ItemId = table.Column<Guid>(nullable: true),
|
||||
Client = table.Column<string>(maxLength: 64, nullable: false),
|
||||
RememberIndexing = table.Column<bool>(nullable: false),
|
||||
RememberSorting = table.Column<bool>(nullable: false),
|
||||
SortOrder = table.Column<int>(nullable: false),
|
||||
ShowSidebar = table.Column<bool>(nullable: false),
|
||||
ShowBackdrop = table.Column<bool>(nullable: false),
|
||||
SortBy = table.Column<string>(nullable: true),
|
||||
ViewType = table.Column<int>(nullable: true),
|
||||
ScrollDirection = table.Column<int>(nullable: false),
|
||||
IndexBy = table.Column<int>(nullable: true)
|
||||
},
|
||||
constraints: table =>
|
||||
{
|
||||
table.PrimaryKey("PK_DisplayPreferences", x => x.Id);
|
||||
table.ForeignKey(
|
||||
name: "FK_DisplayPreferences_Users_UserId",
|
||||
column: x => x.UserId,
|
||||
principalSchema: "jellyfin",
|
||||
principalTable: "Users",
|
||||
principalColumn: "Id",
|
||||
onDelete: ReferentialAction.Cascade);
|
||||
});
|
||||
|
||||
migrationBuilder.CreateTable(
|
||||
name: "HomeSection",
|
||||
schema: "jellyfin",
|
||||
columns: table => new
|
||||
{
|
||||
Id = table.Column<int>(nullable: false)
|
||||
.Annotation("Sqlite:Autoincrement", true),
|
||||
DisplayPreferencesId = table.Column<int>(nullable: false),
|
||||
Order = table.Column<int>(nullable: false),
|
||||
Type = table.Column<int>(nullable: false)
|
||||
},
|
||||
constraints: table =>
|
||||
{
|
||||
table.PrimaryKey("PK_HomeSection", x => x.Id);
|
||||
table.ForeignKey(
|
||||
name: "FK_HomeSection_DisplayPreferences_DisplayPreferencesId",
|
||||
column: x => x.DisplayPreferencesId,
|
||||
principalSchema: "jellyfin",
|
||||
principalTable: "DisplayPreferences",
|
||||
principalColumn: "Id",
|
||||
onDelete: ReferentialAction.Cascade);
|
||||
});
|
||||
|
||||
migrationBuilder.CreateIndex(
|
||||
name: "IX_DisplayPreferences_UserId",
|
||||
schema: "jellyfin",
|
||||
table: "DisplayPreferences",
|
||||
column: "UserId");
|
||||
|
||||
migrationBuilder.CreateIndex(
|
||||
name: "IX_HomeSection_DisplayPreferencesId",
|
||||
schema: "jellyfin",
|
||||
table: "HomeSection",
|
||||
column: "DisplayPreferencesId");
|
||||
}
|
||||
|
||||
protected override void Down(MigrationBuilder migrationBuilder)
|
||||
{
|
||||
migrationBuilder.DropTable(
|
||||
name: "HomeSection",
|
||||
schema: "jellyfin");
|
||||
|
||||
migrationBuilder.DropTable(
|
||||
name: "DisplayPreferences",
|
||||
schema: "jellyfin");
|
||||
}
|
||||
}
|
||||
}
|
|
@ -15,7 +15,7 @@ namespace Jellyfin.Server.Implementations.Migrations
|
|||
#pragma warning disable 612, 618
|
||||
modelBuilder
|
||||
.HasDefaultSchema("jellyfin")
|
||||
.HasAnnotation("ProductVersion", "3.1.4");
|
||||
.HasAnnotation("ProductVersion", "3.1.5");
|
||||
|
||||
modelBuilder.Entity("Jellyfin.Data.Entities.AccessSchedule", b =>
|
||||
{
|
||||
|
@ -88,6 +88,79 @@ namespace Jellyfin.Server.Implementations.Migrations
|
|||
b.ToTable("ActivityLogs");
|
||||
});
|
||||
|
||||
modelBuilder.Entity("Jellyfin.Data.Entities.DisplayPreferences", b =>
|
||||
{
|
||||
b.Property<int>("Id")
|
||||
.ValueGeneratedOnAdd()
|
||||
.HasColumnType("INTEGER");
|
||||
|
||||
b.Property<string>("Client")
|
||||
.IsRequired()
|
||||
.HasColumnType("TEXT")
|
||||
.HasMaxLength(64);
|
||||
|
||||
b.Property<int?>("IndexBy")
|
||||
.HasColumnType("INTEGER");
|
||||
|
||||
b.Property<Guid?>("ItemId")
|
||||
.HasColumnType("TEXT");
|
||||
|
||||
b.Property<bool>("RememberIndexing")
|
||||
.HasColumnType("INTEGER");
|
||||
|
||||
b.Property<bool>("RememberSorting")
|
||||
.HasColumnType("INTEGER");
|
||||
|
||||
b.Property<int>("ScrollDirection")
|
||||
.HasColumnType("INTEGER");
|
||||
|
||||
b.Property<bool>("ShowBackdrop")
|
||||
.HasColumnType("INTEGER");
|
||||
|
||||
b.Property<bool>("ShowSidebar")
|
||||
.HasColumnType("INTEGER");
|
||||
|
||||
b.Property<string>("SortBy")
|
||||
.HasColumnType("TEXT");
|
||||
|
||||
b.Property<int>("SortOrder")
|
||||
.HasColumnType("INTEGER");
|
||||
|
||||
b.Property<Guid>("UserId")
|
||||
.HasColumnType("TEXT");
|
||||
|
||||
b.Property<int?>("ViewType")
|
||||
.HasColumnType("INTEGER");
|
||||
|
||||
b.HasKey("Id");
|
||||
|
||||
b.HasIndex("UserId");
|
||||
|
||||
b.ToTable("DisplayPreferences");
|
||||
});
|
||||
|
||||
modelBuilder.Entity("Jellyfin.Data.Entities.HomeSection", b =>
|
||||
{
|
||||
b.Property<int>("Id")
|
||||
.ValueGeneratedOnAdd()
|
||||
.HasColumnType("INTEGER");
|
||||
|
||||
b.Property<int>("DisplayPreferencesId")
|
||||
.HasColumnType("INTEGER");
|
||||
|
||||
b.Property<int>("Order")
|
||||
.HasColumnType("INTEGER");
|
||||
|
||||
b.Property<int>("Type")
|
||||
.HasColumnType("INTEGER");
|
||||
|
||||
b.HasKey("Id");
|
||||
|
||||
b.HasIndex("DisplayPreferencesId");
|
||||
|
||||
b.ToTable("HomeSection");
|
||||
});
|
||||
|
||||
modelBuilder.Entity("Jellyfin.Data.Entities.ImageInfo", b =>
|
||||
{
|
||||
b.Property<int>("Id")
|
||||
|
@ -282,6 +355,24 @@ namespace Jellyfin.Server.Implementations.Migrations
|
|||
.IsRequired();
|
||||
});
|
||||
|
||||
modelBuilder.Entity("Jellyfin.Data.Entities.DisplayPreferences", b =>
|
||||
{
|
||||
b.HasOne("Jellyfin.Data.Entities.User", null)
|
||||
.WithMany("DisplayPreferences")
|
||||
.HasForeignKey("UserId")
|
||||
.OnDelete(DeleteBehavior.Cascade)
|
||||
.IsRequired();
|
||||
});
|
||||
|
||||
modelBuilder.Entity("Jellyfin.Data.Entities.HomeSection", b =>
|
||||
{
|
||||
b.HasOne("Jellyfin.Data.Entities.DisplayPreferences", null)
|
||||
.WithMany("HomeSections")
|
||||
.HasForeignKey("DisplayPreferencesId")
|
||||
.OnDelete(DeleteBehavior.Cascade)
|
||||
.IsRequired();
|
||||
});
|
||||
|
||||
modelBuilder.Entity("Jellyfin.Data.Entities.ImageInfo", b =>
|
||||
{
|
||||
b.HasOne("Jellyfin.Data.Entities.User", null)
|
||||
|
|
|
@ -9,6 +9,7 @@ using Jellyfin.Server.Implementations;
|
|||
using Jellyfin.Server.Implementations.Activity;
|
||||
using Jellyfin.Server.Implementations.Users;
|
||||
using MediaBrowser.Common.Net;
|
||||
using MediaBrowser.Controller;
|
||||
using MediaBrowser.Controller.Drawing;
|
||||
using MediaBrowser.Controller.Library;
|
||||
using MediaBrowser.Model.Activity;
|
||||
|
@ -73,6 +74,7 @@ namespace Jellyfin.Server
|
|||
|
||||
serviceCollection.AddSingleton<IActivityManager, ActivityManager>();
|
||||
serviceCollection.AddSingleton<IUserManager, UserManager>();
|
||||
serviceCollection.AddSingleton<IDisplayPreferencesManager, DisplayPreferencesManager>();
|
||||
|
||||
base.RegisterServices(serviceCollection);
|
||||
}
|
||||
|
|
|
@ -21,7 +21,8 @@ namespace Jellyfin.Server.Migrations
|
|||
typeof(Routines.MigrateActivityLogDb),
|
||||
typeof(Routines.RemoveDuplicateExtras),
|
||||
typeof(Routines.AddDefaultPluginRepository),
|
||||
typeof(Routines.MigrateUserDb)
|
||||
typeof(Routines.MigrateUserDb),
|
||||
typeof(Routines.MigrateDisplayPreferencesDb)
|
||||
};
|
||||
|
||||
/// <summary>
|
||||
|
|
|
@ -0,0 +1,118 @@
|
|||
using System;
|
||||
using System.IO;
|
||||
using System.Text.Json;
|
||||
using System.Text.Json.Serialization;
|
||||
using Jellyfin.Data.Entities;
|
||||
using Jellyfin.Data.Enums;
|
||||
using Jellyfin.Server.Implementations;
|
||||
using MediaBrowser.Controller;
|
||||
using MediaBrowser.Model.Entities;
|
||||
using Microsoft.Extensions.Logging;
|
||||
using SQLitePCL.pretty;
|
||||
|
||||
namespace Jellyfin.Server.Migrations.Routines
|
||||
{
|
||||
/// <summary>
|
||||
/// The migration routine for migrating the display preferences database to EF Core.
|
||||
/// </summary>
|
||||
public class MigrateDisplayPreferencesDb : IMigrationRoutine
|
||||
{
|
||||
private const string DbFilename = "displaypreferences.db";
|
||||
|
||||
private readonly ILogger<MigrateDisplayPreferencesDb> _logger;
|
||||
private readonly IServerApplicationPaths _paths;
|
||||
private readonly JellyfinDbProvider _provider;
|
||||
private readonly JsonSerializerOptions _jsonOptions;
|
||||
|
||||
/// <summary>
|
||||
/// Initializes a new instance of the <see cref="MigrateDisplayPreferencesDb"/> class.
|
||||
/// </summary>
|
||||
/// <param name="logger">The logger.</param>
|
||||
/// <param name="paths">The server application paths.</param>
|
||||
/// <param name="provider">The database provider.</param>
|
||||
public MigrateDisplayPreferencesDb(ILogger<MigrateDisplayPreferencesDb> logger, IServerApplicationPaths paths, JellyfinDbProvider provider)
|
||||
{
|
||||
_logger = logger;
|
||||
_paths = paths;
|
||||
_provider = provider;
|
||||
_jsonOptions = new JsonSerializerOptions();
|
||||
_jsonOptions.Converters.Add(new JsonStringEnumConverter());
|
||||
}
|
||||
|
||||
/// <inheritdoc />
|
||||
public Guid Id => Guid.Parse("06387815-C3CC-421F-A888-FB5F9992BEA8");
|
||||
|
||||
/// <inheritdoc />
|
||||
public string Name => "MigrateDisplayPreferencesDatabase";
|
||||
|
||||
/// <inheritdoc />
|
||||
public void Perform()
|
||||
{
|
||||
HomeSectionType[] defaults =
|
||||
{
|
||||
HomeSectionType.SmallLibraryTiles,
|
||||
HomeSectionType.Resume,
|
||||
HomeSectionType.ResumeAudio,
|
||||
HomeSectionType.LiveTv,
|
||||
HomeSectionType.NextUp,
|
||||
HomeSectionType.LatestMedia,
|
||||
HomeSectionType.None,
|
||||
};
|
||||
|
||||
var dbFilePath = Path.Combine(_paths.DataPath, DbFilename);
|
||||
using (var connection = SQLite3.Open(dbFilePath, ConnectionFlags.ReadOnly, null))
|
||||
{
|
||||
var dbContext = _provider.CreateContext();
|
||||
|
||||
var results = connection.Query("SELECT * FROM userdisplaypreferences");
|
||||
foreach (var result in results)
|
||||
{
|
||||
var dto = JsonSerializer.Deserialize<DisplayPreferencesDto>(result[3].ToString(), _jsonOptions);
|
||||
|
||||
var displayPreferences = new DisplayPreferences(result[2].ToString(), new Guid(result[1].ToBlob()))
|
||||
{
|
||||
ViewType = Enum.TryParse<ViewType>(dto.ViewType, true, out var viewType) ? viewType : (ViewType?)null,
|
||||
IndexBy = Enum.TryParse<IndexingKind>(dto.IndexBy, true, out var indexBy) ? indexBy : (IndexingKind?)null,
|
||||
ShowBackdrop = dto.ShowBackdrop,
|
||||
ShowSidebar = dto.ShowSidebar,
|
||||
SortBy = dto.SortBy,
|
||||
SortOrder = dto.SortOrder,
|
||||
RememberIndexing = dto.RememberIndexing,
|
||||
RememberSorting = dto.RememberSorting,
|
||||
ScrollDirection = dto.ScrollDirection
|
||||
};
|
||||
|
||||
for (int i = 0; i < 7; i++)
|
||||
{
|
||||
dto.CustomPrefs.TryGetValue("homesection" + i, out var homeSection);
|
||||
|
||||
displayPreferences.HomeSections.Add(new HomeSection
|
||||
{
|
||||
Order = i,
|
||||
Type = Enum.TryParse<HomeSectionType>(homeSection, true, out var type) ? type : defaults[i]
|
||||
});
|
||||
}
|
||||
|
||||
dbContext.Add(displayPreferences);
|
||||
}
|
||||
|
||||
dbContext.SaveChanges();
|
||||
}
|
||||
|
||||
try
|
||||
{
|
||||
File.Move(dbFilePath, dbFilePath + ".old");
|
||||
|
||||
var journalPath = dbFilePath + "-journal";
|
||||
if (File.Exists(journalPath))
|
||||
{
|
||||
File.Move(journalPath, dbFilePath + ".old-journal");
|
||||
}
|
||||
}
|
||||
catch (IOException e)
|
||||
{
|
||||
_logger.LogError(e, "Error renaming legacy display preferences database to 'displaypreferences.db.old'");
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
|
@ -3,6 +3,7 @@ using System.Collections.Generic;
|
|||
using System.Linq;
|
||||
using System.Threading;
|
||||
using System.Threading.Tasks;
|
||||
using Jellyfin.Data.Enums;
|
||||
using MediaBrowser.Api.UserLibrary;
|
||||
using MediaBrowser.Controller.Channels;
|
||||
using MediaBrowser.Controller.Configuration;
|
||||
|
@ -11,7 +12,6 @@ using MediaBrowser.Controller.Library;
|
|||
using MediaBrowser.Controller.Net;
|
||||
using MediaBrowser.Model.Channels;
|
||||
using MediaBrowser.Model.Dto;
|
||||
using MediaBrowser.Model.Entities;
|
||||
using MediaBrowser.Model.Querying;
|
||||
using MediaBrowser.Model.Services;
|
||||
using Microsoft.Extensions.Logging;
|
||||
|
|
|
@ -1,9 +1,10 @@
|
|||
using System.Threading;
|
||||
using System;
|
||||
using Jellyfin.Data.Entities;
|
||||
using Jellyfin.Data.Enums;
|
||||
using MediaBrowser.Controller;
|
||||
using MediaBrowser.Controller.Configuration;
|
||||
using MediaBrowser.Controller.Net;
|
||||
using MediaBrowser.Controller.Persistence;
|
||||
using MediaBrowser.Model.Entities;
|
||||
using MediaBrowser.Model.Serialization;
|
||||
using MediaBrowser.Model.Services;
|
||||
using Microsoft.Extensions.Logging;
|
||||
|
||||
|
@ -13,7 +14,7 @@ namespace MediaBrowser.Api
|
|||
/// Class UpdateDisplayPreferences.
|
||||
/// </summary>
|
||||
[Route("/DisplayPreferences/{DisplayPreferencesId}", "POST", Summary = "Updates a user's display preferences for an item")]
|
||||
public class UpdateDisplayPreferences : DisplayPreferences, IReturnVoid
|
||||
public class UpdateDisplayPreferences : DisplayPreferencesDto, IReturnVoid
|
||||
{
|
||||
/// <summary>
|
||||
/// Gets or sets the id.
|
||||
|
@ -27,7 +28,7 @@ namespace MediaBrowser.Api
|
|||
}
|
||||
|
||||
[Route("/DisplayPreferences/{Id}", "GET", Summary = "Gets a user's display preferences for an item")]
|
||||
public class GetDisplayPreferences : IReturn<DisplayPreferences>
|
||||
public class GetDisplayPreferences : IReturn<DisplayPreferencesDto>
|
||||
{
|
||||
/// <summary>
|
||||
/// Gets or sets the id.
|
||||
|
@ -50,28 +51,21 @@ namespace MediaBrowser.Api
|
|||
public class DisplayPreferencesService : BaseApiService
|
||||
{
|
||||
/// <summary>
|
||||
/// The _display preferences manager.
|
||||
/// The user manager.
|
||||
/// </summary>
|
||||
private readonly IDisplayPreferencesRepository _displayPreferencesManager;
|
||||
/// <summary>
|
||||
/// The _json serializer.
|
||||
/// </summary>
|
||||
private readonly IJsonSerializer _jsonSerializer;
|
||||
private readonly IDisplayPreferencesManager _displayPreferencesManager;
|
||||
|
||||
/// <summary>
|
||||
/// Initializes a new instance of the <see cref="DisplayPreferencesService" /> class.
|
||||
/// </summary>
|
||||
/// <param name="jsonSerializer">The json serializer.</param>
|
||||
/// <param name="displayPreferencesManager">The display preferences manager.</param>
|
||||
public DisplayPreferencesService(
|
||||
ILogger<DisplayPreferencesService> logger,
|
||||
IServerConfigurationManager serverConfigurationManager,
|
||||
IHttpResultFactory httpResultFactory,
|
||||
IJsonSerializer jsonSerializer,
|
||||
IDisplayPreferencesRepository displayPreferencesManager)
|
||||
IDisplayPreferencesManager displayPreferencesManager)
|
||||
: base(logger, serverConfigurationManager, httpResultFactory)
|
||||
{
|
||||
_jsonSerializer = jsonSerializer;
|
||||
_displayPreferencesManager = displayPreferencesManager;
|
||||
}
|
||||
|
||||
|
@ -81,9 +75,34 @@ namespace MediaBrowser.Api
|
|||
/// <param name="request">The request.</param>
|
||||
public object Get(GetDisplayPreferences request)
|
||||
{
|
||||
var result = _displayPreferencesManager.GetDisplayPreferences(request.Id, request.UserId, request.Client);
|
||||
var result = _displayPreferencesManager.GetDisplayPreferences(Guid.Parse(request.UserId), request.Client);
|
||||
|
||||
return ToOptimizedResult(result);
|
||||
if (result == null)
|
||||
{
|
||||
return null;
|
||||
}
|
||||
|
||||
var dto = new DisplayPreferencesDto
|
||||
{
|
||||
Client = result.Client,
|
||||
Id = result.UserId.ToString(),
|
||||
ViewType = result.ViewType?.ToString(),
|
||||
SortBy = result.SortBy,
|
||||
SortOrder = result.SortOrder,
|
||||
IndexBy = result.IndexBy?.ToString(),
|
||||
RememberIndexing = result.RememberIndexing,
|
||||
RememberSorting = result.RememberSorting,
|
||||
ScrollDirection = result.ScrollDirection,
|
||||
ShowBackdrop = result.ShowBackdrop,
|
||||
ShowSidebar = result.ShowSidebar
|
||||
};
|
||||
|
||||
foreach (var homeSection in result.HomeSections)
|
||||
{
|
||||
dto.CustomPrefs["homesection" + homeSection.Order] = homeSection.Type.ToString().ToLowerInvariant();
|
||||
}
|
||||
|
||||
return ToOptimizedResult(dto);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
|
@ -92,10 +111,43 @@ namespace MediaBrowser.Api
|
|||
/// <param name="request">The request.</param>
|
||||
public void Post(UpdateDisplayPreferences request)
|
||||
{
|
||||
// Serialize to json and then back so that the core doesn't see the request dto type
|
||||
var displayPreferences = _jsonSerializer.DeserializeFromString<DisplayPreferences>(_jsonSerializer.SerializeToString(request));
|
||||
HomeSectionType[] defaults =
|
||||
{
|
||||
HomeSectionType.SmallLibraryTiles,
|
||||
HomeSectionType.Resume,
|
||||
HomeSectionType.ResumeAudio,
|
||||
HomeSectionType.LiveTv,
|
||||
HomeSectionType.NextUp,
|
||||
HomeSectionType.LatestMedia,
|
||||
HomeSectionType.None,
|
||||
};
|
||||
|
||||
_displayPreferencesManager.SaveDisplayPreferences(displayPreferences, request.UserId, request.Client, CancellationToken.None);
|
||||
var prefs = _displayPreferencesManager.GetDisplayPreferences(Guid.Parse(request.UserId), request.Client);
|
||||
|
||||
prefs.ViewType = Enum.TryParse<ViewType>(request.ViewType, true, out var viewType) ? viewType : (ViewType?)null;
|
||||
prefs.IndexBy = Enum.TryParse<IndexingKind>(request.IndexBy, true, out var indexBy) ? indexBy : (IndexingKind?)null;
|
||||
prefs.ShowBackdrop = request.ShowBackdrop;
|
||||
prefs.ShowSidebar = request.ShowSidebar;
|
||||
prefs.SortBy = request.SortBy;
|
||||
prefs.SortOrder = request.SortOrder;
|
||||
prefs.RememberIndexing = request.RememberIndexing;
|
||||
prefs.RememberSorting = request.RememberSorting;
|
||||
prefs.ScrollDirection = request.ScrollDirection;
|
||||
prefs.HomeSections.Clear();
|
||||
|
||||
for (int i = 0; i < 7; i++)
|
||||
{
|
||||
if (request.CustomPrefs.TryGetValue("homesection" + i, out var homeSection))
|
||||
{
|
||||
prefs.HomeSections.Add(new HomeSection
|
||||
{
|
||||
Order = i,
|
||||
Type = Enum.TryParse<HomeSectionType>(homeSection, true, out var type) ? type : defaults[i]
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
_displayPreferencesManager.SaveChanges(prefs);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -3,6 +3,7 @@ using System.Collections.Generic;
|
|||
using System.Globalization;
|
||||
using System.Linq;
|
||||
using Jellyfin.Data.Entities;
|
||||
using Jellyfin.Data.Enums;
|
||||
using MediaBrowser.Common.Extensions;
|
||||
using MediaBrowser.Controller.Configuration;
|
||||
using MediaBrowser.Controller.Dto;
|
||||
|
|
|
@ -1,6 +1,7 @@
|
|||
using System;
|
||||
using System.Linq;
|
||||
using Jellyfin.Data.Entities;
|
||||
using Jellyfin.Data.Enums;
|
||||
using MediaBrowser.Controller.Configuration;
|
||||
using MediaBrowser.Controller.Dto;
|
||||
using MediaBrowser.Controller.Entities;
|
||||
|
|
|
@ -2,6 +2,7 @@ using System;
|
|||
using System.Collections.Generic;
|
||||
using System.Globalization;
|
||||
using System.Linq;
|
||||
using Jellyfin.Data.Enums;
|
||||
using MediaBrowser.Common.Extensions;
|
||||
using MediaBrowser.Controller.Configuration;
|
||||
using MediaBrowser.Controller.Dto;
|
||||
|
|
|
@ -1,5 +1,6 @@
|
|||
using System;
|
||||
using System.Linq;
|
||||
using Jellyfin.Data.Enums;
|
||||
using MediaBrowser.Model.Entities;
|
||||
using MediaBrowser.Model.Querying;
|
||||
using MediaBrowser.Model.Services;
|
||||
|
@ -466,8 +467,8 @@ namespace MediaBrowser.Api.UserLibrary
|
|||
|
||||
var sortOrderValue = sortOrders.Length > sortOrderIndex ? sortOrders[sortOrderIndex] : null;
|
||||
var sortOrder = string.Equals(sortOrderValue, "Descending", StringComparison.OrdinalIgnoreCase)
|
||||
? MediaBrowser.Model.Entities.SortOrder.Descending
|
||||
: MediaBrowser.Model.Entities.SortOrder.Ascending;
|
||||
? Jellyfin.Data.Enums.SortOrder.Descending
|
||||
: Jellyfin.Data.Enums.SortOrder.Ascending;
|
||||
|
||||
result[i] = new ValueTuple<string, SortOrder>(vals[i], sortOrder);
|
||||
}
|
||||
|
|
|
@ -3,6 +3,7 @@ using System.Collections.Generic;
|
|||
using System.Globalization;
|
||||
using System.Linq;
|
||||
using Jellyfin.Data.Entities;
|
||||
using Jellyfin.Data.Enums;
|
||||
using MediaBrowser.Controller.Configuration;
|
||||
using MediaBrowser.Controller.Entities.Movies;
|
||||
using MediaBrowser.Controller.Library;
|
||||
|
|
25
MediaBrowser.Controller/IDisplayPreferencesManager.cs
Normal file
25
MediaBrowser.Controller/IDisplayPreferencesManager.cs
Normal file
|
@ -0,0 +1,25 @@
|
|||
using System;
|
||||
using Jellyfin.Data.Entities;
|
||||
|
||||
namespace MediaBrowser.Controller
|
||||
{
|
||||
/// <summary>
|
||||
/// Manages the storage and retrieval of display preferences.
|
||||
/// </summary>
|
||||
public interface IDisplayPreferencesManager
|
||||
{
|
||||
/// <summary>
|
||||
/// Gets the display preferences for the user and client.
|
||||
/// </summary>
|
||||
/// <param name="userId">The user's id.</param>
|
||||
/// <param name="client">The client string.</param>
|
||||
/// <returns>The associated display preferences.</returns>
|
||||
DisplayPreferences GetDisplayPreferences(Guid userId, string client);
|
||||
|
||||
/// <summary>
|
||||
/// Saves changes to the provided display preferences.
|
||||
/// </summary>
|
||||
/// <param name="preferences">The display preferences to save.</param>
|
||||
void SaveChanges(DisplayPreferences preferences);
|
||||
}
|
||||
}
|
|
@ -3,6 +3,7 @@ using System.Collections.Generic;
|
|||
using System.Threading;
|
||||
using System.Threading.Tasks;
|
||||
using Jellyfin.Data.Entities;
|
||||
using Jellyfin.Data.Enums;
|
||||
using MediaBrowser.Controller.Dto;
|
||||
using MediaBrowser.Controller.Entities;
|
||||
using MediaBrowser.Controller.Entities.Audio;
|
||||
|
|
|
@ -1,53 +0,0 @@
|
|||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Threading;
|
||||
using MediaBrowser.Model.Entities;
|
||||
|
||||
namespace MediaBrowser.Controller.Persistence
|
||||
{
|
||||
/// <summary>
|
||||
/// Interface IDisplayPreferencesRepository.
|
||||
/// </summary>
|
||||
public interface IDisplayPreferencesRepository : IRepository
|
||||
{
|
||||
/// <summary>
|
||||
/// Saves display preferences for an item.
|
||||
/// </summary>
|
||||
/// <param name="displayPreferences">The display preferences.</param>
|
||||
/// <param name="userId">The user id.</param>
|
||||
/// <param name="client">The client.</param>
|
||||
/// <param name="cancellationToken">The cancellation token.</param>
|
||||
void SaveDisplayPreferences(
|
||||
DisplayPreferences displayPreferences,
|
||||
string userId,
|
||||
string client,
|
||||
CancellationToken cancellationToken);
|
||||
|
||||
/// <summary>
|
||||
/// Saves all display preferences for a user.
|
||||
/// </summary>
|
||||
/// <param name="displayPreferences">The display preferences.</param>
|
||||
/// <param name="userId">The user id.</param>
|
||||
/// <param name="cancellationToken">The cancellation token.</param>
|
||||
void SaveAllDisplayPreferences(
|
||||
IEnumerable<DisplayPreferences> displayPreferences,
|
||||
Guid userId,
|
||||
CancellationToken cancellationToken);
|
||||
|
||||
/// <summary>
|
||||
/// Gets the display preferences.
|
||||
/// </summary>
|
||||
/// <param name="displayPreferencesId">The display preferences id.</param>
|
||||
/// <param name="userId">The user id.</param>
|
||||
/// <param name="client">The client.</param>
|
||||
/// <returns>Task{DisplayPreferences}.</returns>
|
||||
DisplayPreferences GetDisplayPreferences(string displayPreferencesId, string userId, string client);
|
||||
|
||||
/// <summary>
|
||||
/// Gets all display preferences for the given user.
|
||||
/// </summary>
|
||||
/// <param name="userId">The user id.</param>
|
||||
/// <returns>Task{DisplayPreferences}.</returns>
|
||||
IEnumerable<DisplayPreferences> GetAllDisplayPreferences(Guid userId);
|
||||
}
|
||||
}
|
|
@ -6,6 +6,7 @@ using System.Text.Json.Serialization;
|
|||
using System.Threading;
|
||||
using System.Threading.Tasks;
|
||||
using Jellyfin.Data.Entities;
|
||||
using Jellyfin.Data.Enums;
|
||||
using MediaBrowser.Controller.Dto;
|
||||
using MediaBrowser.Controller.Entities;
|
||||
using MediaBrowser.Controller.Entities.Audio;
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
#pragma warning disable CS1591
|
||||
|
||||
using MediaBrowser.Model.Entities;
|
||||
using Jellyfin.Data.Enums;
|
||||
|
||||
namespace MediaBrowser.Model.Dlna
|
||||
{
|
||||
|
|
|
@ -1,22 +1,18 @@
|
|||
#nullable disable
|
||||
using System.Collections.Generic;
|
||||
using Jellyfin.Data.Enums;
|
||||
|
||||
namespace MediaBrowser.Model.Entities
|
||||
{
|
||||
/// <summary>
|
||||
/// Defines the display preferences for any item that supports them (usually Folders).
|
||||
/// </summary>
|
||||
public class DisplayPreferences
|
||||
public class DisplayPreferencesDto
|
||||
{
|
||||
/// <summary>
|
||||
/// The image scale.
|
||||
/// Initializes a new instance of the <see cref="DisplayPreferencesDto" /> class.
|
||||
/// </summary>
|
||||
private const double ImageScale = .9;
|
||||
|
||||
/// <summary>
|
||||
/// Initializes a new instance of the <see cref="DisplayPreferences" /> class.
|
||||
/// </summary>
|
||||
public DisplayPreferences()
|
||||
public DisplayPreferencesDto()
|
||||
{
|
||||
RememberIndexing = false;
|
||||
PrimaryImageHeight = 250;
|
|
@ -2,7 +2,7 @@
|
|||
#pragma warning disable CS1591
|
||||
|
||||
using System;
|
||||
using MediaBrowser.Model.Entities;
|
||||
using Jellyfin.Data.Enums;
|
||||
|
||||
namespace MediaBrowser.Model.LiveTv
|
||||
{
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
#pragma warning disable CS1591
|
||||
|
||||
using MediaBrowser.Model.Entities;
|
||||
using Jellyfin.Data.Enums;
|
||||
|
||||
namespace MediaBrowser.Model.LiveTv
|
||||
{
|
||||
|
|
Loading…
Reference in New Issue
Block a user