repo creation with initial code after cloning public repo

This commit is contained in:
2026-02-19 07:36:25 -05:00
commit 460884fea3
2860 changed files with 650825 additions and 0 deletions
@@ -0,0 +1,31 @@
#pragma warning disable CA1002, CA2227, CS1591
using System;
using System.Collections.Generic;
namespace MediaBrowser.Controller.Providers
{
public class AlbumInfo : ItemLookupInfo
{
public AlbumInfo()
{
ArtistProviderIds = new Dictionary<string, string>(StringComparer.OrdinalIgnoreCase);
SongInfos = new List<SongInfo>();
AlbumArtists = Array.Empty<string>();
}
/// <summary>
/// Gets or sets the album artist.
/// </summary>
/// <value>The album artist.</value>
public IReadOnlyList<string> AlbumArtists { get; set; }
/// <summary>
/// Gets or sets the artist provider ids.
/// </summary>
/// <value>The artist provider ids.</value>
public Dictionary<string, string> ArtistProviderIds { get; set; }
public List<SongInfo> SongInfos { get; set; }
}
}
@@ -0,0 +1,16 @@
#pragma warning disable CA1002, CA2227, CS1591
using System.Collections.Generic;
namespace MediaBrowser.Controller.Providers
{
public class ArtistInfo : ItemLookupInfo
{
public ArtistInfo()
{
SongInfos = new List<SongInfo>();
}
public List<SongInfo> SongInfos { get; set; }
}
}
@@ -0,0 +1,11 @@
#nullable disable
#pragma warning disable CS1591
namespace MediaBrowser.Controller.Providers
{
public class BookInfo : ItemLookupInfo
{
public string SeriesName { get; set; }
}
}
@@ -0,0 +1,8 @@
#pragma warning disable CS1591
namespace MediaBrowser.Controller.Providers
{
public class BoxSetInfo : ItemLookupInfo
{
}
}
@@ -0,0 +1,116 @@
#pragma warning disable CS1591
using System;
using System.Collections.Concurrent;
using System.Collections.Generic;
using System.Linq;
using MediaBrowser.Model.IO;
namespace MediaBrowser.Controller.Providers
{
public class DirectoryService : IDirectoryService
{
// TODO make static and switch to FastConcurrentLru.
private readonly ConcurrentDictionary<string, FileSystemMetadata[]> _cache = new(StringComparer.Ordinal);
private readonly ConcurrentDictionary<string, FileSystemMetadata> _fileCache = new(StringComparer.Ordinal);
private readonly ConcurrentDictionary<string, List<string>> _filePathCache = new(StringComparer.Ordinal);
private readonly IFileSystem _fileSystem;
public DirectoryService(IFileSystem fileSystem)
{
_fileSystem = fileSystem;
}
public FileSystemMetadata[] GetFileSystemEntries(string path)
{
return _cache.GetOrAdd(path, static (p, fileSystem) => fileSystem.GetFileSystemEntries(p).ToArray(), _fileSystem);
}
public List<FileSystemMetadata> GetDirectories(string path)
{
var list = new List<FileSystemMetadata>();
var items = GetFileSystemEntries(path);
for (var i = 0; i < items.Length; i++)
{
var item = items[i];
if (item.IsDirectory)
{
list.Add(item);
}
}
return list;
}
public List<FileSystemMetadata> GetFiles(string path)
{
var list = new List<FileSystemMetadata>();
var items = GetFileSystemEntries(path);
for (var i = 0; i < items.Length; i++)
{
var item = items[i];
if (!item.IsDirectory)
{
list.Add(item);
}
}
return list;
}
public FileSystemMetadata? GetFile(string path)
{
var entry = GetFileSystemEntry(path);
return entry is not null && !entry.IsDirectory ? entry : null;
}
public FileSystemMetadata? GetDirectory(string path)
{
var entry = GetFileSystemEntry(path);
return entry is not null && entry.IsDirectory ? entry : null;
}
public FileSystemMetadata? GetFileSystemEntry(string path)
{
if (!_fileCache.TryGetValue(path, out var result))
{
var file = _fileSystem.GetFileSystemInfo(path);
if (file?.Exists ?? false)
{
result = file;
_fileCache.TryAdd(path, result);
}
}
return result;
}
public IReadOnlyList<string> GetFilePaths(string path)
=> GetFilePaths(path, false);
public IReadOnlyList<string> GetFilePaths(string path, bool clearCache, bool sort = false)
{
if (clearCache)
{
_filePathCache.TryRemove(path, out _);
}
var filePaths = _filePathCache.GetOrAdd(path, static (p, fileSystem) => fileSystem.GetFilePaths(p).ToList(), _fileSystem);
if (sort)
{
filePaths.Sort();
}
return filePaths;
}
public bool IsAccessible(string path)
{
return _fileSystem.GetFileSystemEntryPaths(path).Any();
}
}
}
@@ -0,0 +1,44 @@
#nullable disable
#pragma warning disable CS1591
using System;
using System.IO;
using MediaBrowser.Model.Drawing;
using MediaBrowser.Model.MediaInfo;
namespace MediaBrowser.Controller.Providers
{
public class DynamicImageResponse
{
public string Path { get; set; }
public MediaProtocol Protocol { get; set; }
public Stream Stream { get; set; }
public ImageFormat Format { get; set; }
public bool HasImage { get; set; }
public void SetFormatFromMimeType(string mimeType)
{
if (mimeType.EndsWith("gif", StringComparison.OrdinalIgnoreCase))
{
Format = ImageFormat.Gif;
}
else if (mimeType.EndsWith("bmp", StringComparison.OrdinalIgnoreCase))
{
Format = ImageFormat.Bmp;
}
else if (mimeType.EndsWith("png", StringComparison.OrdinalIgnoreCase))
{
Format = ImageFormat.Png;
}
else
{
Format = ImageFormat.Jpg;
}
}
}
}
@@ -0,0 +1,29 @@
#nullable disable
#pragma warning disable CA2227, CS1591
using System;
using System.Collections.Generic;
using Jellyfin.Data.Enums;
namespace MediaBrowser.Controller.Providers
{
public class EpisodeInfo : ItemLookupInfo
{
public EpisodeInfo()
{
SeriesProviderIds = new Dictionary<string, string>(StringComparer.OrdinalIgnoreCase);
SeasonProviderIds = new Dictionary<string, string>(StringComparer.OrdinalIgnoreCase);
}
public Dictionary<string, string> SeriesProviderIds { get; set; }
public Dictionary<string, string> SeasonProviderIds { get; set; }
public int? IndexNumberEnd { get; set; }
public bool IsMissingEpisode { get; set; }
public string SeriesDisplayOrder { get; set; }
}
}
@@ -0,0 +1,26 @@
#pragma warning disable CS1591
using System.Threading;
using System.Threading.Tasks;
using MediaBrowser.Controller.Entities;
using MediaBrowser.Controller.Library;
namespace MediaBrowser.Controller.Providers
{
public interface ICustomMetadataProvider : IMetadataProvider
{
}
public interface ICustomMetadataProvider<TItemType> : IMetadataProvider<TItemType>, ICustomMetadataProvider
where TItemType : BaseItem
{
/// <summary>
/// Fetches the metadata asynchronously.
/// </summary>
/// <param name="item">The item.</param>
/// <param name="options">The <see cref="MetadataRefreshOptions"/>.</param>
/// <param name="cancellationToken">The <see cref="CancellationToken"/>.</param>
/// <returns>A <see cref="Task"/> fetching the <see cref="ItemUpdateType"/>.</returns>
Task<ItemUpdateType> FetchAsync(TItemType item, MetadataRefreshOptions options, CancellationToken cancellationToken);
}
}
@@ -0,0 +1,28 @@
#pragma warning disable CA1002, CA1819, CS1591
using System.Collections.Generic;
using MediaBrowser.Model.IO;
namespace MediaBrowser.Controller.Providers
{
public interface IDirectoryService
{
FileSystemMetadata[] GetFileSystemEntries(string path);
List<FileSystemMetadata> GetDirectories(string path);
List<FileSystemMetadata> GetFiles(string path);
FileSystemMetadata? GetFile(string path);
FileSystemMetadata? GetDirectory(string path);
FileSystemMetadata? GetFileSystemEntry(string path);
IReadOnlyList<string> GetFilePaths(string path);
IReadOnlyList<string> GetFilePaths(string path, bool clearCache, bool sort = false);
bool IsAccessible(string path);
}
}
@@ -0,0 +1,29 @@
#pragma warning disable CS1591
using System.Collections.Generic;
using System.Threading;
using System.Threading.Tasks;
using MediaBrowser.Controller.Entities;
using MediaBrowser.Model.Entities;
namespace MediaBrowser.Controller.Providers
{
public interface IDynamicImageProvider : IImageProvider
{
/// <summary>
/// Gets the supported images.
/// </summary>
/// <param name="item">The item.</param>
/// <returns>IEnumerable{ImageType}.</returns>
IEnumerable<ImageType> GetSupportedImages(BaseItem item);
/// <summary>
/// Gets the image.
/// </summary>
/// <param name="item">The item.</param>
/// <param name="type">The type.</param>
/// <param name="cancellationToken">The cancellation token.</param>
/// <returns>Task{DynamicImageResponse}.</returns>
Task<DynamicImageResponse> GetImage(BaseItem item, ImageType type, CancellationToken cancellationToken);
}
}
@@ -0,0 +1,41 @@
using System;
using MediaBrowser.Model.Entities;
using MediaBrowser.Model.Providers;
namespace MediaBrowser.Controller.Providers
{
/// <summary>
/// Represents an identifier for an external provider.
/// </summary>
public interface IExternalId
{
/// <summary>
/// Gets the display name of the provider associated with this ID type.
/// </summary>
string ProviderName { get; }
/// <summary>
/// Gets the unique key to distinguish this provider/type pair. This should be unique across providers.
/// </summary>
// TODO: This property is not actually unique across the concrete types at the moment. It should be updated to be unique.
string Key { get; }
/// <summary>
/// Gets the specific media type for this id. This is used to distinguish between the different
/// external id types for providers with multiple ids.
/// A null value indicates there is no specific media type associated with the external id, or this is the
/// default id for the external provider so there is no need to specify a type.
/// </summary>
/// <remarks>
/// This can be used along with the <see cref="ProviderName"/> to localize the external id on the client.
/// </remarks>
ExternalIdMediaType? Type { get; }
/// <summary>
/// Determines whether this id supports a given item type.
/// </summary>
/// <param name="item">The item.</param>
/// <returns>True if this item is supported, otherwise false.</returns>
bool Supports(IHasProviderIds item);
}
}
@@ -0,0 +1,22 @@
using System.Collections.Generic;
using MediaBrowser.Controller.Entities;
namespace MediaBrowser.Controller.Providers;
/// <summary>
/// Interface to include related urls for an item.
/// </summary>
public interface IExternalUrlProvider
{
/// <summary>
/// Gets the external service name.
/// </summary>
string Name { get; }
/// <summary>
/// Get the list of external urls.
/// </summary>
/// <param name="item">The item to get external urls for.</param>
/// <returns>The list of external urls.</returns>
IEnumerable<string> GetExternalUrls(BaseItem item);
}
@@ -0,0 +1,9 @@
namespace MediaBrowser.Controller.Providers
{
/// <summary>
/// This is a marker interface that will cause a provider to run even if an item is locked from changes.
/// </summary>
public interface IForcedProvider
{
}
}
@@ -0,0 +1,17 @@
#pragma warning disable CS1591
using MediaBrowser.Controller.Entities;
namespace MediaBrowser.Controller.Providers
{
public interface IHasItemChangeMonitor
{
/// <summary>
/// Determines whether the specified item has changed.
/// </summary>
/// <param name="item">The item.</param>
/// <param name="directoryService">The directory service.</param>
/// <returns><c>true</c> if the specified item has changed; otherwise, <c>false</c>.</returns>
bool HasChanged(BaseItem item, IDirectoryService directoryService);
}
}
@@ -0,0 +1,10 @@
#pragma warning disable CS1591
namespace MediaBrowser.Controller.Providers
{
public interface IHasLookupInfo<out TLookupInfoType>
where TLookupInfoType : ItemLookupInfo, new()
{
TLookupInfoType GetLookupInfo();
}
}
@@ -0,0 +1,14 @@
namespace MediaBrowser.Controller.Providers
{
/// <summary>
/// Interface IHasOrder.
/// </summary>
public interface IHasOrder
{
/// <summary>
/// Gets the order.
/// </summary>
/// <value>The order.</value>
int Order { get; }
}
}
@@ -0,0 +1,23 @@
using MediaBrowser.Controller.Entities;
namespace MediaBrowser.Controller.Providers
{
/// <summary>
/// Interface IImageProvider.
/// </summary>
public interface IImageProvider
{
/// <summary>
/// Gets the name.
/// </summary>
/// <value>The name.</value>
string Name { get; }
/// <summary>
/// Supports the specified item.
/// </summary>
/// <param name="item">The item.</param>
/// <returns><c>true</c> if the provider supports the item.</returns>
bool Supports(BaseItem item);
}
}
@@ -0,0 +1,15 @@
#pragma warning disable CS1591
using System.Collections.Generic;
using MediaBrowser.Controller.Entities;
namespace MediaBrowser.Controller.Providers
{
/// <summary>
/// This is just a marker interface.
/// </summary>
public interface ILocalImageProvider : IImageProvider
{
IEnumerable<LocalImageInfo> GetImages(BaseItem item, IDirectoryService directoryService);
}
}
@@ -0,0 +1,28 @@
#pragma warning disable CS1591
using System.Threading;
using System.Threading.Tasks;
using MediaBrowser.Controller.Entities;
namespace MediaBrowser.Controller.Providers
{
public interface ILocalMetadataProvider : IMetadataProvider
{
}
public interface ILocalMetadataProvider<TItemType> : IMetadataProvider<TItemType>, ILocalMetadataProvider
where TItemType : BaseItem
{
/// <summary>
/// Gets the metadata.
/// </summary>
/// <param name="info">The information.</param>
/// <param name="directoryService">The directory service.</param>
/// <param name="cancellationToken">The cancellation token.</param>
/// <returns>Task{MetadataResult{0}}.</returns>
Task<MetadataResult<TItemType>> GetMetadata(
ItemInfo info,
IDirectoryService directoryService,
CancellationToken cancellationToken);
}
}
@@ -0,0 +1,23 @@
#pragma warning disable CS1591
using MediaBrowser.Controller.Entities;
namespace MediaBrowser.Controller.Providers
{
/// <summary>
/// Marker interface.
/// </summary>
public interface IMetadataProvider
{
/// <summary>
/// Gets the name.
/// </summary>
/// <value>The name.</value>
string Name { get; }
}
public interface IMetadataProvider<TItemType> : IMetadataProvider
where TItemType : BaseItem
{
}
}
@@ -0,0 +1,42 @@
#pragma warning disable CS1591
using System;
using System.Threading;
using System.Threading.Tasks;
using MediaBrowser.Controller.Entities;
using MediaBrowser.Controller.Library;
namespace MediaBrowser.Controller.Providers
{
public interface IMetadataService
{
/// <summary>
/// Gets the order.
/// </summary>
/// <value>The order.</value>
int Order { get; }
/// <summary>
/// Determines whether this instance can refresh the specified item.
/// </summary>
/// <param name="item">The item.</param>
/// <returns><c>true</c> if this instance can refresh the specified item.</returns>
bool CanRefresh(BaseItem item);
/// <summary>
/// Determines whether this instance primarily targets the specified type.
/// </summary>
/// <param name="type">The type.</param>
/// <returns><c>true</c> if this instance primarily targets the specified type.</returns>
bool CanRefreshPrimary(Type type);
/// <summary>
/// Refreshes the metadata.
/// </summary>
/// <param name="item">The item.</param>
/// <param name="refreshOptions">The options.</param>
/// <param name="cancellationToken">The cancellation token.</param>
/// <returns>Task.</returns>
Task<ItemUpdateType> RefreshMetadata(BaseItem item, MetadataRefreshOptions refreshOptions, CancellationToken cancellationToken);
}
}
@@ -0,0 +1,8 @@
#pragma warning disable CS1591
namespace MediaBrowser.Controller.Providers
{
public interface IPreRefreshProvider : ICustomMetadataProvider
{
}
}
@@ -0,0 +1,222 @@
#nullable disable
#pragma warning disable CS1591
using System;
using System.Collections.Generic;
using System.IO;
using System.Threading;
using System.Threading.Tasks;
using Jellyfin.Data.Events;
using MediaBrowser.Controller.Entities;
using MediaBrowser.Controller.Library;
using MediaBrowser.Model.Configuration;
using MediaBrowser.Model.Entities;
using MediaBrowser.Model.Providers;
namespace MediaBrowser.Controller.Providers
{
/// <summary>
/// Interface IProviderManager.
/// </summary>
public interface IProviderManager
{
event EventHandler<GenericEventArgs<BaseItem>> RefreshStarted;
event EventHandler<GenericEventArgs<BaseItem>> RefreshCompleted;
event EventHandler<GenericEventArgs<Tuple<BaseItem, double>>> RefreshProgress;
/// <summary>
/// Queues the refresh.
/// </summary>
/// <param name="itemId">Item ID.</param>
/// <param name="options">MetadataRefreshOptions for operation.</param>
/// <param name="priority">RefreshPriority for operation.</param>
void QueueRefresh(Guid itemId, MetadataRefreshOptions options, RefreshPriority priority);
/// <summary>
/// Refreshes the full item.
/// </summary>
/// <param name="item">The item.</param>
/// <param name="options">The options.</param>
/// <param name="cancellationToken">The cancellation token.</param>
/// <returns>Task.</returns>
Task RefreshFullItem(BaseItem item, MetadataRefreshOptions options, CancellationToken cancellationToken);
/// <summary>
/// Refreshes the metadata.
/// </summary>
/// <param name="item">The item.</param>
/// <param name="options">The options.</param>
/// <param name="cancellationToken">The cancellation token.</param>
/// <returns>Task.</returns>
Task<ItemUpdateType> RefreshSingleItem(BaseItem item, MetadataRefreshOptions options, CancellationToken cancellationToken);
/// <summary>
/// Saves the image.
/// </summary>
/// <param name="item">The item.</param>
/// <param name="url">The URL.</param>
/// <param name="type">The type.</param>
/// <param name="imageIndex">Index of the image.</param>
/// <param name="cancellationToken">The cancellation token.</param>
/// <returns>Task.</returns>
Task SaveImage(BaseItem item, string url, ImageType type, int? imageIndex, CancellationToken cancellationToken);
/// <summary>
/// Saves the image.
/// </summary>
/// <param name="item">The item.</param>
/// <param name="source">The source.</param>
/// <param name="mimeType">Type of the MIME.</param>
/// <param name="type">The type.</param>
/// <param name="imageIndex">Index of the image.</param>
/// <param name="cancellationToken">The cancellation token.</param>
/// <returns>Task.</returns>
Task SaveImage(BaseItem item, Stream source, string mimeType, ImageType type, int? imageIndex, CancellationToken cancellationToken);
/// <summary>
/// Saves the image by giving the image path on filesystem.
/// This method will remove the image on the source path after saving it to the destination.
/// </summary>
/// <param name="item">Image to save.</param>
/// <param name="source">Source of image.</param>
/// <param name="mimeType">Mime type image.</param>
/// <param name="type">Type of image.</param>
/// <param name="imageIndex">Index of image.</param>
/// <param name="saveLocallyWithMedia">Option to save locally.</param>
/// <param name="cancellationToken">CancellationToken to use with operation.</param>
/// <returns>Task.</returns>
Task SaveImage(BaseItem item, string source, string mimeType, ImageType type, int? imageIndex, bool? saveLocallyWithMedia, CancellationToken cancellationToken);
Task SaveImage(Stream source, string mimeType, string path);
/// <summary>
/// Adds the metadata providers.
/// </summary>
/// <param name="imageProviders">Image providers to use.</param>
/// <param name="metadataServices">Metadata services to use.</param>
/// <param name="metadataProviders">Metadata providers to use.</param>
/// <param name="metadataSavers">Metadata savers to use.</param>
/// <param name="externalIds">External IDs to use.</param>
/// <param name="externalUrlProviders">The list of external url providers.</param>
void AddParts(
IEnumerable<IImageProvider> imageProviders,
IEnumerable<IMetadataService> metadataServices,
IEnumerable<IMetadataProvider> metadataProviders,
IEnumerable<IMetadataSaver> metadataSavers,
IEnumerable<IExternalId> externalIds,
IEnumerable<IExternalUrlProvider> externalUrlProviders);
/// <summary>
/// Gets the available remote images.
/// </summary>
/// <param name="item">The item.</param>
/// <param name="query">The query.</param>
/// <param name="cancellationToken">The cancellation token.</param>
/// <returns>Task{IEnumerable{RemoteImageInfo}}.</returns>
Task<IEnumerable<RemoteImageInfo>> GetAvailableRemoteImages(BaseItem item, RemoteImageQuery query, CancellationToken cancellationToken);
/// <summary>
/// Gets the image providers.
/// </summary>
/// <param name="item">The item.</param>
/// <returns>IEnumerable{ImageProviderInfo}.</returns>
IEnumerable<ImageProviderInfo> GetRemoteImageProviderInfo(BaseItem item);
/// <summary>
/// Gets the image providers for the provided item.
/// </summary>
/// <param name="item">The item.</param>
/// <param name="refreshOptions">The image refresh options.</param>
/// <returns>The image providers for the item.</returns>
IEnumerable<IImageProvider> GetImageProviders(BaseItem item, ImageRefreshOptions refreshOptions);
/// <summary>
/// Gets the metadata providers for the provided item.
/// </summary>
/// <param name="item">The item.</param>
/// <param name="libraryOptions">The library options.</param>
/// <typeparam name="T">The type of metadata provider.</typeparam>
/// <returns>The metadata providers.</returns>
IEnumerable<IMetadataProvider<T>> GetMetadataProviders<T>(BaseItem item, LibraryOptions libraryOptions)
where T : BaseItem;
/// <summary>
/// Gets the metadata savers for the provided item.
/// </summary>
/// <param name="item">The item.</param>
/// <param name="libraryOptions">The library options.</param>
/// <returns>The metadata savers.</returns>
IEnumerable<IMetadataSaver> GetMetadataSavers(BaseItem item, LibraryOptions libraryOptions);
/// <summary>
/// Gets all metadata plugins.
/// </summary>
/// <returns>IEnumerable{MetadataPlugin}.</returns>
MetadataPluginSummary[] GetAllMetadataPlugins();
/// <summary>
/// Gets the external urls.
/// </summary>
/// <param name="item">The item.</param>
/// <returns>IEnumerable{ExternalUrl}.</returns>
IEnumerable<ExternalUrl> GetExternalUrls(BaseItem item);
/// <summary>
/// Gets the external identifier infos.
/// </summary>
/// <param name="item">The item.</param>
/// <returns>IEnumerable{ExternalIdInfo}.</returns>
IEnumerable<ExternalIdInfo> GetExternalIdInfos(IHasProviderIds item);
/// <summary>
/// Saves the metadata.
/// </summary>
/// <param name="item">The item.</param>
/// <param name="updateType">Type of the update.</param>
/// <returns>The task object representing the asynchronous operation.</returns>
Task SaveMetadataAsync(BaseItem item, ItemUpdateType updateType);
/// <summary>
/// Saves the metadata.
/// </summary>
/// <param name="item">The item.</param>
/// <param name="updateType">Type of the update.</param>
/// <param name="savers">The metadata savers.</param>
/// <returns>The task object representing the asynchronous operation.</returns>
Task SaveMetadataAsync(BaseItem item, ItemUpdateType updateType, IEnumerable<string> savers);
/// <summary>
/// Gets the metadata options.
/// </summary>
/// <param name="item">The item.</param>
/// <returns>MetadataOptions.</returns>
MetadataOptions GetMetadataOptions(BaseItem item);
/// <summary>
/// Gets the remote search results.
/// </summary>
/// <typeparam name="TItemType">The type of the t item type.</typeparam>
/// <typeparam name="TLookupType">The type of the t lookup type.</typeparam>
/// <param name="searchInfo">The search information.</param>
/// <param name="cancellationToken">The cancellation token.</param>
/// <returns>Task{IEnumerable{SearchResult{``1}}}.</returns>
Task<IEnumerable<RemoteSearchResult>> GetRemoteSearchResults<TItemType, TLookupType>(
RemoteSearchQuery<TLookupType> searchInfo,
CancellationToken cancellationToken)
where TItemType : BaseItem, new()
where TLookupType : ItemLookupInfo;
HashSet<Guid> GetRefreshQueue();
void OnRefreshStart(BaseItem item);
void OnRefreshProgress(BaseItem item, double progress);
void OnRefreshComplete(BaseItem item);
double? GetRefreshProgress(Guid id);
}
}
@@ -0,0 +1,39 @@
using System.Collections.Generic;
using System.Net.Http;
using System.Threading;
using System.Threading.Tasks;
using MediaBrowser.Controller.Entities;
using MediaBrowser.Model.Entities;
using MediaBrowser.Model.Providers;
namespace MediaBrowser.Controller.Providers
{
/// <summary>
/// Interface IImageProvider.
/// </summary>
public interface IRemoteImageProvider : IImageProvider
{
/// <summary>
/// Gets the supported images.
/// </summary>
/// <param name="item">The item.</param>
/// <returns>IEnumerable{ImageType}.</returns>
IEnumerable<ImageType> GetSupportedImages(BaseItem item);
/// <summary>
/// Gets the images.
/// </summary>
/// <param name="item">The item.</param>
/// <param name="cancellationToken">The cancellation token.</param>
/// <returns>Task{IEnumerable{RemoteImageInfo}}.</returns>
Task<IEnumerable<RemoteImageInfo>> GetImages(BaseItem item, CancellationToken cancellationToken);
/// <summary>
/// Gets the image response.
/// </summary>
/// <param name="url">The URL.</param>
/// <param name="cancellationToken">The cancellation token.</param>
/// <returns>Task{HttpResponseInfo}.</returns>
Task<HttpResponseMessage> GetImageResponse(string url, CancellationToken cancellationToken);
}
}
@@ -0,0 +1,49 @@
using System.Collections.Generic;
using System.Threading;
using System.Threading.Tasks;
using MediaBrowser.Controller.Entities;
using MediaBrowser.Model.Providers;
namespace MediaBrowser.Controller.Providers
{
/// <summary>
/// Interface IRemoteMetadataProvider.
/// </summary>
public interface IRemoteMetadataProvider : IMetadataProvider
{
}
/// <summary>
/// Interface IRemoteMetadataProvider.
/// </summary>
/// <typeparam name="TItemType">The type of <see cref="BaseItem" />.</typeparam>
/// <typeparam name="TLookupInfoType">The type of <see cref="ItemLookupInfo" />.</typeparam>
public interface IRemoteMetadataProvider<TItemType, in TLookupInfoType> : IMetadataProvider<TItemType>, IRemoteMetadataProvider, IRemoteSearchProvider<TLookupInfoType>
where TItemType : BaseItem, IHasLookupInfo<TLookupInfoType>
where TLookupInfoType : ItemLookupInfo, new()
{
/// <summary>
/// Gets the metadata for a specific LookupInfoType.
/// </summary>
/// <param name="info">The LookupInfoType to get metadata for.</param>
/// <param name="cancellationToken">The <see cref="CancellationToken"/>.</param>
/// <returns>A task returning a MetadataResult for the specific LookupInfoType.</returns>
Task<MetadataResult<TItemType>> GetMetadata(TLookupInfoType info, CancellationToken cancellationToken);
}
/// <summary>
/// Interface IRemoteMetadataProvider.
/// </summary>
/// <typeparam name="TLookupInfoType">The type of <see cref="ItemLookupInfo" />.</typeparam>
public interface IRemoteSearchProvider<in TLookupInfoType> : IRemoteSearchProvider
where TLookupInfoType : ItemLookupInfo
{
/// <summary>
/// Gets the list of <see cref="RemoteSearchResult"/> for a specific LookupInfoType.
/// </summary>
/// <param name="searchInfo">The LookupInfoType to search for.</param>
/// <param name="cancellationToken">The <see cref="CancellationToken"/>.</param>
/// <returns>A task returning RemoteSearchResults for the searchInfo.</returns>
Task<IEnumerable<RemoteSearchResult>> GetSearchResults(TLookupInfoType searchInfo, CancellationToken cancellationToken);
}
}
@@ -0,0 +1,19 @@
#pragma warning disable CS1591
using System.Net.Http;
using System.Threading;
using System.Threading.Tasks;
namespace MediaBrowser.Controller.Providers
{
public interface IRemoteSearchProvider : IMetadataProvider
{
/// <summary>
/// Gets the image response.
/// </summary>
/// <param name="url">The URL.</param>
/// <param name="cancellationToken">The cancellation token.</param>
/// <returns>Task{HttpResponseInfo}.</returns>
Task<HttpResponseMessage> GetImageResponse(string url, CancellationToken cancellationToken);
}
}
@@ -0,0 +1,42 @@
#pragma warning disable CA1819, CS1591
using System;
using System.Collections.Generic;
using System.Linq;
using MediaBrowser.Model.Entities;
namespace MediaBrowser.Controller.Providers
{
public class ImageRefreshOptions
{
public ImageRefreshOptions(IDirectoryService directoryService)
{
ImageRefreshMode = MetadataRefreshMode.Default;
DirectoryService = directoryService;
ReplaceImages = Array.Empty<ImageType>();
IsAutomated = true;
}
public MetadataRefreshMode ImageRefreshMode { get; set; }
public IDirectoryService DirectoryService { get; private set; }
public bool ReplaceAllImages { get; set; }
public IReadOnlyList<ImageType> ReplaceImages { get; set; }
public bool IsAutomated { get; set; }
/// <summary>
/// Gets or sets a value indicating whether old metadata should be removed if it isn't replaced.
/// </summary>
public bool RemoveOldMetadata { get; set; }
public bool IsReplacingImage(ImageType type)
{
return ImageRefreshMode == MetadataRefreshMode.FullRefresh
&& (ReplaceAllImages || ReplaceImages.Contains(type));
}
}
}
@@ -0,0 +1,44 @@
#pragma warning disable CS1591
using System;
using MediaBrowser.Controller.Entities;
using MediaBrowser.Model.Entities;
namespace MediaBrowser.Controller.Providers
{
public class ItemInfo
{
public ItemInfo(BaseItem item)
{
Path = item.Path;
ParentId = item.ParentId;
IndexNumber = item.IndexNumber;
ContainingFolderPath = item.ContainingFolderPath;
IsInMixedFolder = item.IsInMixedFolder;
if (item is Video video)
{
VideoType = video.VideoType;
IsPlaceHolder = video.IsPlaceHolder;
}
ItemType = item.GetType();
}
public Type ItemType { get; set; }
public string Path { get; set; }
public Guid ParentId { get; set; }
public int? IndexNumber { get; set; }
public string ContainingFolderPath { get; set; }
public VideoType VideoType { get; set; }
public bool IsInMixedFolder { get; set; }
public bool IsPlaceHolder { get; set; }
}
}
@@ -0,0 +1,69 @@
#nullable disable
#pragma warning disable CA2227, CS1591
using System;
using System.Collections.Generic;
using MediaBrowser.Model.Entities;
namespace MediaBrowser.Controller.Providers
{
public class ItemLookupInfo : IHasProviderIds
{
public ItemLookupInfo()
{
IsAutomated = true;
ProviderIds = new Dictionary<string, string>(StringComparer.OrdinalIgnoreCase);
}
/// <summary>
/// Gets or sets the name.
/// </summary>
/// <value>The name.</value>
public string Name { get; set; }
/// <summary>
/// Gets or sets the original title.
/// </summary>
/// <value>The original title of the item.</value>
public string OriginalTitle { get; set; }
/// <summary>
/// Gets or sets the path.
/// </summary>
/// <value>The path.</value>
public string Path { get; set; }
/// <summary>
/// Gets or sets the metadata language.
/// </summary>
/// <value>The metadata language.</value>
public string MetadataLanguage { get; set; }
/// <summary>
/// Gets or sets the metadata country code.
/// </summary>
/// <value>The metadata country code.</value>
public string MetadataCountryCode { get; set; }
/// <summary>
/// Gets or sets the provider ids.
/// </summary>
/// <value>The provider ids.</value>
public Dictionary<string, string> ProviderIds { get; set; }
/// <summary>
/// Gets or sets the year.
/// </summary>
/// <value>The year.</value>
public int? Year { get; set; }
public int? IndexNumber { get; set; }
public int? ParentIndexNumber { get; set; }
public DateTime? PremiereDate { get; set; }
public bool IsAutomated { get; set; }
}
}
@@ -0,0 +1,16 @@
#nullable disable
#pragma warning disable CS1591
using MediaBrowser.Model.Entities;
using MediaBrowser.Model.IO;
namespace MediaBrowser.Controller.Providers
{
public class LocalImageInfo
{
public FileSystemMetadata FileInfo { get; set; }
public ImageType Type { get; set; }
}
}
@@ -0,0 +1,27 @@
#pragma warning disable CS1591
namespace MediaBrowser.Controller.Providers
{
public enum MetadataRefreshMode
{
/// <summary>
/// The none.
/// </summary>
None = 0,
/// <summary>
/// The validation only.
/// </summary>
ValidationOnly = 1,
/// <summary>
/// Providers will be executed based on default rules.
/// </summary>
Default = 2,
/// <summary>
/// All providers will be executed to search for new metadata.
/// </summary>
FullRefresh = 3
}
}
@@ -0,0 +1,77 @@
#nullable disable
#pragma warning disable CA1819, CS1591
using System;
using System.Linq;
using Jellyfin.Extensions;
using MediaBrowser.Controller.Entities;
using MediaBrowser.Model.Providers;
namespace MediaBrowser.Controller.Providers
{
public class MetadataRefreshOptions : ImageRefreshOptions
{
public MetadataRefreshOptions(IDirectoryService directoryService)
: base(directoryService)
{
MetadataRefreshMode = MetadataRefreshMode.Default;
}
public MetadataRefreshOptions(MetadataRefreshOptions copy)
: base(copy.DirectoryService)
{
MetadataRefreshMode = copy.MetadataRefreshMode;
ForceSave = copy.ForceSave;
ReplaceAllMetadata = copy.ReplaceAllMetadata;
EnableRemoteContentProbe = copy.EnableRemoteContentProbe;
IsAutomated = copy.IsAutomated;
ImageRefreshMode = copy.ImageRefreshMode;
ReplaceAllImages = copy.ReplaceAllImages;
RegenerateTrickplay = copy.RegenerateTrickplay;
ReplaceImages = copy.ReplaceImages;
SearchResult = copy.SearchResult;
RemoveOldMetadata = copy.RemoveOldMetadata;
if (copy.RefreshPaths is not null && copy.RefreshPaths.Length > 0)
{
RefreshPaths ??= Array.Empty<string>();
RefreshPaths = copy.RefreshPaths.ToArray();
}
}
/// <summary>
/// Gets or sets a value indicating whether all existing data should be overwritten with new data from providers
/// when paired with MetadataRefreshMode=FullRefresh.
/// </summary>
public bool ReplaceAllMetadata { get; set; }
/// <summary>
/// Gets or sets a value indicating whether all existing trickplay images should be overwritten
/// when paired with MetadataRefreshMode=FullRefresh.
/// </summary>
public bool RegenerateTrickplay { get; set; }
public MetadataRefreshMode MetadataRefreshMode { get; set; }
public RemoteSearchResult SearchResult { get; set; }
public string[] RefreshPaths { get; set; }
public bool ForceSave { get; set; }
public bool EnableRemoteContentProbe { get; set; }
public bool RefreshItem(BaseItem item)
{
if (RefreshPaths is not null && RefreshPaths.Length > 0)
{
return RefreshPaths.Contains(item.Path ?? string.Empty, StringComparison.OrdinalIgnoreCase);
}
return true;
}
}
}
@@ -0,0 +1,74 @@
#nullable disable
#pragma warning disable CA1002, CA2227, CS1591
using System.Collections.Generic;
using System.Linq;
using MediaBrowser.Controller.Entities;
using MediaBrowser.Model.Entities;
namespace MediaBrowser.Controller.Providers
{
public class MetadataResult<T>
{
// Images aren't always used so the allocation is a waste a lot of the time
private List<LocalImageInfo> _images;
private List<(string Url, ImageType Type)> _remoteImages;
private List<PersonInfo> _people;
public MetadataResult()
{
ResultLanguage = "en";
}
public List<LocalImageInfo> Images
{
get => _images ??= [];
set => _images = value;
}
public List<(string Url, ImageType Type)> RemoteImages
{
get => _remoteImages ??= [];
set => _remoteImages = value;
}
public IReadOnlyList<PersonInfo> People
{
get => _people;
set => _people = value?.ToList();
}
public bool HasMetadata { get; set; }
public T Item { get; set; }
public string ResultLanguage { get; set; }
public string Provider { get; set; }
public bool QueriedById { get; set; }
public void AddPerson(PersonInfo p)
{
People ??= new List<PersonInfo>();
PeopleHelper.AddPerson(_people, p);
}
/// <summary>
/// Not only does this clear, but initializes the list so that services can differentiate between a null list and zero people.
/// </summary>
public void ResetPeople()
{
if (People is null)
{
People = new List<PersonInfo>();
}
else
{
_people.Clear();
}
}
}
}
@@ -0,0 +1,8 @@
#pragma warning disable CS1591
namespace MediaBrowser.Controller.Providers
{
public class MovieInfo : ItemLookupInfo
{
}
}
@@ -0,0 +1,13 @@
#nullable disable
#pragma warning disable CS1591
using System.Collections.Generic;
namespace MediaBrowser.Controller.Providers
{
public class MusicVideoInfo : ItemLookupInfo
{
public IReadOnlyList<string> Artists { get; set; }
}
}
@@ -0,0 +1,8 @@
#pragma warning disable CS1591
namespace MediaBrowser.Controller.Providers
{
public class PersonLookupInfo : ItemLookupInfo
{
}
}
@@ -0,0 +1,23 @@
namespace MediaBrowser.Controller.Providers
{
/// <summary>
/// Provider refresh priority.
/// </summary>
public enum RefreshPriority
{
/// <summary>
/// High priority.
/// </summary>
High = 0,
/// <summary>
/// Normal priority.
/// </summary>
Normal = 1,
/// <summary>
/// Low priority.
/// </summary>
Low = 2
}
}
@@ -0,0 +1,27 @@
#nullable disable
#pragma warning disable CS1591
using System;
namespace MediaBrowser.Controller.Providers
{
public class RemoteSearchQuery<T>
where T : ItemLookupInfo
{
public T SearchInfo { get; set; }
public Guid ItemId { get; set; }
/// <summary>
/// Gets or sets the provider name to search within if set.
/// </summary>
public string SearchProviderName { get; set; }
/// <summary>
/// Gets or sets a value indicating whether disabled providers should be included.
/// </summary>
/// <value><c>true</c> if disabled providers should be included.</value>
public bool IncludeDisabledProviders { get; set; }
}
}
@@ -0,0 +1,20 @@
#pragma warning disable CA2227, CS1591
#nullable disable
using System;
using System.Collections.Generic;
namespace MediaBrowser.Controller.Providers
{
public class SeasonInfo : ItemLookupInfo
{
public SeasonInfo()
{
SeriesProviderIds = new Dictionary<string, string>(StringComparer.OrdinalIgnoreCase);
}
public Dictionary<string, string> SeriesProviderIds { get; set; }
public string SeriesDisplayOrder { get; set; }
}
}
@@ -0,0 +1,8 @@
#pragma warning disable CS1591
namespace MediaBrowser.Controller.Providers
{
public class SeriesInfo : ItemLookupInfo
{
}
}
@@ -0,0 +1,24 @@
#nullable disable
#pragma warning disable CS1591
using System;
using System.Collections.Generic;
namespace MediaBrowser.Controller.Providers
{
public class SongInfo : ItemLookupInfo
{
public SongInfo()
{
Artists = Array.Empty<string>();
AlbumArtists = Array.Empty<string>();
}
public IReadOnlyList<string> AlbumArtists { get; set; }
public string Album { get; set; }
public IReadOnlyList<string> Artists { get; set; }
}
}
@@ -0,0 +1,8 @@
#pragma warning disable CS1591
namespace MediaBrowser.Controller.Providers
{
public class TrailerInfo : ItemLookupInfo
{
}
}
@@ -0,0 +1,18 @@
namespace MediaBrowser.Controller.Providers
{
/// <summary>
/// Enum VideoContentType.
/// </summary>
public enum VideoContentType
{
/// <summary>
/// The episode.
/// </summary>
Episode = 0,
/// <summary>
/// The movie.
/// </summary>
Movie = 1
}
}