Merge remote-tracking branch 'jellyfinorigin/master' into feature/DatabaseRefactor

This commit is contained in:
JPVenson 2025-03-01 14:16:49 +00:00
commit feea5af2f3
24 changed files with 122 additions and 142 deletions

View File

@ -27,11 +27,11 @@ jobs:
dotnet-version: '9.0.x'
- name: Initialize CodeQL
uses: github/codeql-action/init@9e8d0789d4a0fa9ceb6b1738f7e269594bdd67f0 # v3.28.9
uses: github/codeql-action/init@b56ba49b26e50535fa1e7f7db0f4f7b4bf65d80d # v3.28.10
with:
languages: ${{ matrix.language }}
queries: +security-extended
- name: Autobuild
uses: github/codeql-action/autobuild@9e8d0789d4a0fa9ceb6b1738f7e269594bdd67f0 # v3.28.9
uses: github/codeql-action/autobuild@b56ba49b26e50535fa1e7f7db0f4f7b4bf65d80d # v3.28.10
- name: Perform CodeQL Analysis
uses: github/codeql-action/analyze@9e8d0789d4a0fa9ceb6b1738f7e269594bdd67f0 # v3.28.9
uses: github/codeql-action/analyze@b56ba49b26e50535fa1e7f7db0f4f7b4bf65d80d # v3.28.10

View File

@ -26,7 +26,7 @@ jobs:
dotnet build Jellyfin.Server -o ./out
- name: Upload Head
uses: actions/upload-artifact@65c4c4a1ddee5b72f698fdd19549f0f0fb45cf08 # v4.6.0
uses: actions/upload-artifact@4cec3d8aa04e39d1a68397de0c4cd6fb9dce8ec1 # v4.6.1
with:
name: abi-head
retention-days: 14
@ -65,7 +65,7 @@ jobs:
dotnet build Jellyfin.Server -o ./out
- name: Upload Head
uses: actions/upload-artifact@65c4c4a1ddee5b72f698fdd19549f0f0fb45cf08 # v4.6.0
uses: actions/upload-artifact@4cec3d8aa04e39d1a68397de0c4cd6fb9dce8ec1 # v4.6.1
with:
name: abi-base
retention-days: 14
@ -85,13 +85,13 @@ jobs:
steps:
- name: Download abi-head
uses: actions/download-artifact@fa0a91b85d4f404e444e00e005971372dc801d16 # v4.1.8
uses: actions/download-artifact@cc203385981b70ca67e1cc392babf9cc229d5806 # v4.1.9
with:
name: abi-head
path: abi-head
- name: Download abi-base
uses: actions/download-artifact@fa0a91b85d4f404e444e00e005971372dc801d16 # v4.1.8
uses: actions/download-artifact@cc203385981b70ca67e1cc392babf9cc229d5806 # v4.1.9
with:
name: abi-base
path: abi-base

View File

@ -27,7 +27,7 @@ jobs:
- name: Generate openapi.json
run: dotnet test tests/Jellyfin.Server.Integration.Tests/Jellyfin.Server.Integration.Tests.csproj -c Release --filter "Jellyfin.Server.Integration.Tests.OpenApiSpecTests"
- name: Upload openapi.json
uses: actions/upload-artifact@65c4c4a1ddee5b72f698fdd19549f0f0fb45cf08 # v4.6.0
uses: actions/upload-artifact@4cec3d8aa04e39d1a68397de0c4cd6fb9dce8ec1 # v4.6.1
with:
name: openapi-head
retention-days: 14
@ -61,7 +61,7 @@ jobs:
- name: Generate openapi.json
run: dotnet test tests/Jellyfin.Server.Integration.Tests/Jellyfin.Server.Integration.Tests.csproj -c Release --filter "Jellyfin.Server.Integration.Tests.OpenApiSpecTests"
- name: Upload openapi.json
uses: actions/upload-artifact@65c4c4a1ddee5b72f698fdd19549f0f0fb45cf08 # v4.6.0
uses: actions/upload-artifact@4cec3d8aa04e39d1a68397de0c4cd6fb9dce8ec1 # v4.6.1
with:
name: openapi-base
retention-days: 14
@ -80,12 +80,12 @@ jobs:
- openapi-base
steps:
- name: Download openapi-head
uses: actions/download-artifact@fa0a91b85d4f404e444e00e005971372dc801d16 # v4.1.8
uses: actions/download-artifact@cc203385981b70ca67e1cc392babf9cc229d5806 # v4.1.9
with:
name: openapi-head
path: openapi-head
- name: Download openapi-base
uses: actions/download-artifact@fa0a91b85d4f404e444e00e005971372dc801d16 # v4.1.8
uses: actions/download-artifact@cc203385981b70ca67e1cc392babf9cc229d5806 # v4.1.9
with:
name: openapi-base
path: openapi-base
@ -158,7 +158,7 @@ jobs:
run: |-
echo "JELLYFIN_VERSION=$(date +'%Y%m%d%H%M%S')" >> $GITHUB_ENV
- name: Download openapi-head
uses: actions/download-artifact@fa0a91b85d4f404e444e00e005971372dc801d16 # v4.1.8
uses: actions/download-artifact@cc203385981b70ca67e1cc392babf9cc229d5806 # v4.1.9
with:
name: openapi-head
path: openapi-head
@ -172,7 +172,7 @@ jobs:
strip_components: 1
target: "/srv/incoming/openapi/unstable/jellyfin-openapi-${{ env.JELLYFIN_VERSION }}"
- name: Move openapi.json (unstable) into place
uses: appleboy/ssh-action@7eaf76671a0d7eec5d98ee897acda4f968735a17 # v1.2.0
uses: appleboy/ssh-action@8faa84277b88b6cd1455986f459aa66cf72bc8a3 # v1.2.1
with:
host: "${{ secrets.REPO_HOST }}"
username: "${{ secrets.REPO_USER }}"
@ -220,7 +220,7 @@ jobs:
run: |-
echo "JELLYFIN_VERSION=${GITHUB_REF#refs/tags/v}" >> $GITHUB_ENV
- name: Download openapi-head
uses: actions/download-artifact@fa0a91b85d4f404e444e00e005971372dc801d16 # v4.1.8
uses: actions/download-artifact@cc203385981b70ca67e1cc392babf9cc229d5806 # v4.1.9
with:
name: openapi-head
path: openapi-head
@ -234,7 +234,7 @@ jobs:
strip_components: 1
target: "/srv/incoming/openapi/stable/jellyfin-openapi-${{ env.JELLYFIN_VERSION }}"
- name: Move openapi.json (stable) into place
uses: appleboy/ssh-action@7eaf76671a0d7eec5d98ee897acda4f968735a17 # v1.2.0
uses: appleboy/ssh-action@8faa84277b88b6cd1455986f459aa66cf72bc8a3 # v1.2.1
with:
host: "${{ secrets.REPO_HOST }}"
username: "${{ secrets.REPO_USER }}"

View File

@ -79,7 +79,7 @@
<PackageVersion Include="System.Text.Json" Version="9.0.2" />
<PackageVersion Include="System.Threading.Tasks.Dataflow" Version="9.0.2" />
<PackageVersion Include="TagLibSharp" Version="2.3.0" />
<PackageVersion Include="z440.atl.core" Version="6.16.0" />
<PackageVersion Include="z440.atl.core" Version="6.17.0" />
<PackageVersion Include="TMDbLib" Version="2.2.0" />
<PackageVersion Include="UTF.Unknown" Version="2.5.1" />
<PackageVersion Include="Xunit.Priority" Version="1.1.6" />

View File

@ -204,7 +204,7 @@ namespace Emby.Server.Implementations.Collections
{
if (_libraryManager.GetItemById(collectionId) is not BoxSet collection)
{
throw new ArgumentException("No collection exists with the supplied Id");
throw new ArgumentException("No collection exists with the supplied collectionId " + collectionId);
}
List<BaseItem>? itemList = null;
@ -218,7 +218,7 @@ namespace Emby.Server.Implementations.Collections
if (item is null)
{
throw new ArgumentException("No item exists with the supplied Id");
throw new ArgumentException("No item exists with the supplied Id " + id);
}
if (!currentLinkedChildrenIds.Contains(id))

View File

@ -458,6 +458,7 @@ namespace Emby.Server.Implementations.Library
foreach (var child in children)
{
_itemRepository.DeleteItem(child.Id);
_cache.TryRemove(child.Id, out _);
}
_cache.TryRemove(item.Id, out _);
@ -2631,15 +2632,6 @@ namespace Emby.Server.Implementations.Library
{
episode.ParentIndexNumber = season.IndexNumber;
}
else
{
/*
Anime series don't generally have a season in their file name, however,
TVDb needs a season to correctly get the metadata.
Hence, a null season needs to be filled with something. */
// FIXME perhaps this would be better for TVDb parser to ask for season 1 if no season is specified
episode.ParentIndexNumber = 1;
}
if (episode.ParentIndexNumber.HasValue)
{

View File

@ -13,7 +13,7 @@
"DeviceOnlineWithName": "{0} belépett",
"FailedLoginAttemptWithUserName": "Sikertelen bejelentkezési kísérlet innen: {0}",
"Favorites": "Kedvencek",
"Folders": "Könyvtárak",
"Folders": "Mappák",
"Genres": "Műfajok",
"HeaderAlbumArtists": "Albumelőadók",
"HeaderContinueWatching": "Megtekintés folytatása",

View File

@ -58,8 +58,8 @@
"NotificationOptionServerRestartRequired": "Riavvio del server necessario",
"NotificationOptionTaskFailed": "Operazione pianificata fallita",
"NotificationOptionUserLockedOut": "Utente bloccato",
"NotificationOptionVideoPlayback": "La riproduzione video è iniziata",
"NotificationOptionVideoPlaybackStopped": "La riproduzione video è stata interrotta",
"NotificationOptionVideoPlayback": "Riproduzione video iniziata",
"NotificationOptionVideoPlaybackStopped": "Riproduzione video interrotta",
"Photos": "Foto",
"Playlists": "Playlist",
"Plugin": "Plugin",

View File

@ -116,6 +116,7 @@ public partial class AudioNormalizationTask : IScheduledTask
{
a.LUFS = await CalculateLUFSAsync(
string.Format(CultureInfo.InvariantCulture, "-f concat -safe 0 -i \"{0}\"", tempFile),
OperatingSystem.IsWindows(), // Wait for process to exit on Windows before we try deleting the concat file
cancellationToken).ConfigureAwait(false);
}
finally
@ -142,7 +143,10 @@ public partial class AudioNormalizationTask : IScheduledTask
continue;
}
t.LUFS = await CalculateLUFSAsync(string.Format(CultureInfo.InvariantCulture, "-i \"{0}\"", t.Path.Replace("\"", "\\\"", StringComparison.Ordinal)), cancellationToken).ConfigureAwait(false);
t.LUFS = await CalculateLUFSAsync(
string.Format(CultureInfo.InvariantCulture, "-i \"{0}\"", t.Path.Replace("\"", "\\\"", StringComparison.Ordinal)),
false,
cancellationToken).ConfigureAwait(false);
}
_itemRepository.SaveItems(tracks, cancellationToken);
@ -162,7 +166,7 @@ public partial class AudioNormalizationTask : IScheduledTask
];
}
private async Task<float?> CalculateLUFSAsync(string inputArgs, CancellationToken cancellationToken)
private async Task<float?> CalculateLUFSAsync(string inputArgs, bool waitForExit, CancellationToken cancellationToken)
{
var args = $"-hide_banner {inputArgs} -af ebur128=framelog=verbose -f null -";
@ -189,18 +193,28 @@ public partial class AudioNormalizationTask : IScheduledTask
}
using var reader = process.StandardError;
float? lufs = null;
await foreach (var line in reader.ReadAllLinesAsync(cancellationToken))
{
Match match = LUFSRegex().Match(line);
if (match.Success)
{
return float.Parse(match.Groups[1].ValueSpan, CultureInfo.InvariantCulture.NumberFormat);
lufs = float.Parse(match.Groups[1].ValueSpan, CultureInfo.InvariantCulture.NumberFormat);
break;
}
}
_logger.LogError("Failed to find LUFS value in output");
return null;
if (lufs is null)
{
_logger.LogError("Failed to find LUFS value in output");
}
if (waitForExit)
{
await process.WaitForExitAsync(cancellationToken).ConfigureAwait(false);
}
return lufs;
}
}
}

View File

@ -212,20 +212,4 @@ public class SystemController : BaseJellyfinApiController
FileStream stream = new FileStream(file.FullName, FileMode.Open, FileAccess.Read, fileShare, IODefaults.FileStreamBufferSize, FileOptions.Asynchronous);
return File(stream, "text/plain; charset=utf-8");
}
/// <summary>
/// Gets wake on lan information.
/// </summary>
/// <response code="200">Information retrieved.</response>
/// <returns>An <see cref="IEnumerable{WakeOnLanInfo}"/> with the WakeOnLan infos.</returns>
[HttpGet("WakeOnLanInfo")]
[Authorize]
[Obsolete("This endpoint is obsolete.")]
[ProducesResponseType(StatusCodes.Status200OK)]
public ActionResult<IEnumerable<WakeOnLanInfo>> GetWakeOnLanInfo()
{
var result = _networkManager.GetMacAddresses()
.Select(i => new WakeOnLanInfo(i));
return Ok(result);
}
}

View File

@ -114,7 +114,7 @@ namespace Jellyfin.Server.Implementations.Users
// This is some regex that matches only on unicode "word" characters, as well as -, _ and @
// In theory this will cut out most if not all 'control' characters which should help minimize any weirdness
// Usernames can contain letters (a-z + whatever else unicode is cool with), numbers (0-9), at-signs (@), dashes (-), underscores (_), apostrophes ('), periods (.) and spaces ( )
[GeneratedRegex(@"^[\w\ \-'._@+]+$")]
[GeneratedRegex(@"^(?!\s)[\w\ \-'._@+]+(?<!\s)$")]
private static partial Regex ValidUsernameRegex();
/// <inheritdoc/>

View File

@ -94,12 +94,6 @@ namespace MediaBrowser.Common.Net
/// <returns>IP address to use, or loopback address if all else fails.</returns>
string GetBindAddress(string source, out int? port);
/// <summary>
/// Get a list of all the MAC addresses associated with active interfaces.
/// </summary>
/// <returns>List of MAC addresses.</returns>
IReadOnlyList<PhysicalAddress> GetMacAddresses();
/// <summary>
/// Returns true if the address is part of the user defined LAN.
/// </summary>

View File

@ -1203,6 +1203,11 @@ namespace MediaBrowser.Controller.Entities
return false;
}
if (request.Is4K.HasValue)
{
return false;
}
if (request.IsHD.HasValue)
{
return false;

View File

@ -84,6 +84,11 @@ namespace MediaBrowser.Model.Entities
/// <summary>
/// The TvMaze provider.
/// </summary>
TvMaze = 19
TvMaze = 19,
/// <summary>
/// The MusicBrainz recording provider.
/// </summary>
MusicBrainzRecording = 20,
}
}

View File

@ -71,6 +71,11 @@ namespace MediaBrowser.Model.Providers
/// <summary>
/// A book.
/// </summary>
Book = 13
Book = 13,
/// <summary>
/// A music recording.
/// </summary>
Recording = 14
}
}

View File

@ -1,47 +0,0 @@
using System.Net.NetworkInformation;
namespace MediaBrowser.Model.System
{
/// <summary>
/// Provides the MAC address and port for wake-on-LAN functionality.
/// </summary>
public class WakeOnLanInfo
{
/// <summary>
/// Initializes a new instance of the <see cref="WakeOnLanInfo" /> class.
/// </summary>
/// <param name="macAddress">The MAC address.</param>
public WakeOnLanInfo(PhysicalAddress macAddress) : this(macAddress.ToString())
{
}
/// <summary>
/// Initializes a new instance of the <see cref="WakeOnLanInfo" /> class.
/// </summary>
/// <param name="macAddress">The MAC address.</param>
public WakeOnLanInfo(string macAddress) : this()
{
MacAddress = macAddress;
}
/// <summary>
/// Initializes a new instance of the <see cref="WakeOnLanInfo" /> class.
/// </summary>
public WakeOnLanInfo()
{
Port = 9;
}
/// <summary>
/// Gets the MAC address of the device.
/// </summary>
/// <value>The MAC address.</value>
public string? MacAddress { get; }
/// <summary>
/// Gets or sets the wake-on-LAN port.
/// </summary>
/// <value>The wake-on-LAN port.</value>
public int Port { get; set; }
}
}

View File

@ -19,6 +19,7 @@ using MediaBrowser.Model.Entities;
using MediaBrowser.Model.Extensions;
using MediaBrowser.Model.MediaInfo;
using Microsoft.Extensions.Logging;
using static Jellyfin.Extensions.StringExtensions;
namespace MediaBrowser.Providers.MediaInfo
{
@ -400,6 +401,24 @@ namespace MediaBrowser.Providers.MediaInfo
}
}
if (options.ReplaceAllMetadata || !audio.TryGetProviderId(MetadataProvider.MusicBrainzRecording, out _))
{
if ((track.AdditionalFields.TryGetValue("MUSICBRAINZ_TRACKID", out var recordingMbId)
|| track.AdditionalFields.TryGetValue("MusicBrainz Track Id", out recordingMbId))
&& !string.IsNullOrEmpty(recordingMbId))
{
audio.TrySetProviderId(MetadataProvider.MusicBrainzRecording, recordingMbId);
}
else if (track.AdditionalFields.TryGetValue("UFID", out var ufIdValue) && !string.IsNullOrEmpty(ufIdValue))
{
// If tagged with MB Picard, the format is 'http://musicbrainz.org\0<recording MBID>'
if (ufIdValue.Contains("musicbrainz.org", StringComparison.OrdinalIgnoreCase))
{
audio.TrySetProviderId(MetadataProvider.MusicBrainzRecording, ufIdValue.AsSpan().RightPart('\0').ToString());
}
}
}
// Save extracted lyrics if they exist,
// and if the audio doesn't yet have lyrics.
var lyrics = track.Lyrics.SynchronizedLyrics.Count > 0 ? track.Lyrics.FormatSynchToLRC() : track.Lyrics.UnsynchronizedLyrics;

View File

@ -0,0 +1,27 @@
using MediaBrowser.Controller.Entities.Audio;
using MediaBrowser.Controller.Providers;
using MediaBrowser.Model.Entities;
using MediaBrowser.Model.Providers;
namespace MediaBrowser.Providers.Plugins.MusicBrainz;
/// <summary>
/// MusicBrainz recording id.
/// </summary>
public class MusicBrainzRecordingId : IExternalId
{
/// <inheritdoc />
public string ProviderName => "MusicBrainz";
/// <inheritdoc />
public string Key => MetadataProvider.MusicBrainzRecording.ToString();
/// <inheritdoc />
public ExternalIdMediaType? Type => ExternalIdMediaType.Recording;
/// <inheritdoc />
public string UrlFormatString => Plugin.Instance!.Configuration.Server + "/recording/{0}";
/// <inheritdoc />
public bool Supports(IHasProviderIds item) => item is Audio;
}

View File

@ -55,13 +55,12 @@ namespace MediaBrowser.Providers.Plugins.Omdb
if (info.SeriesProviderIds.TryGetValue(MetadataProvider.Imdb.ToString(), out string? seriesImdbId)
&& !string.IsNullOrEmpty(seriesImdbId)
&& info.IndexNumber.HasValue
&& info.ParentIndexNumber.HasValue)
&& info.IndexNumber.HasValue)
{
result.HasMetadata = await _omdbProvider.FetchEpisodeData(
result,
info.IndexNumber.Value,
info.ParentIndexNumber.Value,
info.ParentIndexNumber ?? 1,
info.GetProviderId(MetadataProvider.Imdb),
seriesImdbId,
info.MetadataLanguage,

View File

@ -63,10 +63,10 @@ namespace MediaBrowser.Providers.Plugins.Tmdb.TV
return Enumerable.Empty<RemoteImageInfo>();
}
var seasonNumber = episode.ParentIndexNumber;
var seasonNumber = episode.ParentIndexNumber ?? 1;
var episodeNumber = episode.IndexNumber;
if (!seasonNumber.HasValue || !episodeNumber.HasValue)
if (!episodeNumber.HasValue)
{
return Enumerable.Empty<RemoteImageInfo>();
}
@ -75,7 +75,7 @@ namespace MediaBrowser.Providers.Plugins.Tmdb.TV
// TODO use image languages if All Languages isn't toggled, but there's currently no way to get that value in here
var episodeResult = await _tmdbClientManager
.GetEpisodeAsync(seriesTmdbId, seasonNumber.Value, episodeNumber.Value, series.DisplayOrder, null, null, cancellationToken)
.GetEpisodeAsync(seriesTmdbId, seasonNumber, episodeNumber.Value, series.DisplayOrder, null, null, cancellationToken)
.ConfigureAwait(false);
var stills = episodeResult?.Images?.Stills;

View File

@ -47,7 +47,7 @@ namespace MediaBrowser.Providers.Plugins.Tmdb.TV
public async Task<IEnumerable<RemoteSearchResult>> GetSearchResults(EpisodeInfo searchInfo, CancellationToken cancellationToken)
{
// The search query must either provide an episode number or date
if (!searchInfo.IndexNumber.HasValue || !searchInfo.ParentIndexNumber.HasValue)
if (!searchInfo.IndexNumber.HasValue)
{
return Enumerable.Empty<RemoteSearchResult>();
}
@ -96,10 +96,10 @@ namespace MediaBrowser.Providers.Plugins.Tmdb.TV
return metadataResult;
}
var seasonNumber = info.ParentIndexNumber;
var seasonNumber = info.ParentIndexNumber ?? 1;
var episodeNumber = info.IndexNumber;
if (!seasonNumber.HasValue || !episodeNumber.HasValue)
if (!episodeNumber.HasValue)
{
return metadataResult;
}
@ -112,7 +112,7 @@ namespace MediaBrowser.Providers.Plugins.Tmdb.TV
List<TvEpisode>? result = null;
for (int? episode = startindex; episode <= endindex; episode++)
{
var episodeInfo = await _tmdbClientManager.GetEpisodeAsync(seriesTmdbId, seasonNumber.Value, episode.Value, info.SeriesDisplayOrder, info.MetadataLanguage, TmdbUtils.GetImageLanguagesParam(info.MetadataLanguage), cancellationToken).ConfigureAwait(false);
var episodeInfo = await _tmdbClientManager.GetEpisodeAsync(seriesTmdbId, seasonNumber, episode.Value, info.SeriesDisplayOrder, info.MetadataLanguage, TmdbUtils.GetImageLanguagesParam(info.MetadataLanguage), cancellationToken).ConfigureAwait(false);
if (episodeInfo is not null)
{
(result ??= new List<TvEpisode>()).Add(episodeInfo);
@ -156,7 +156,7 @@ namespace MediaBrowser.Providers.Plugins.Tmdb.TV
else
{
episodeResult = await _tmdbClientManager
.GetEpisodeAsync(seriesTmdbId, seasonNumber.Value, episodeNumber.Value, info.SeriesDisplayOrder, info.MetadataLanguage, TmdbUtils.GetImageLanguagesParam(info.MetadataLanguage), cancellationToken)
.GetEpisodeAsync(seriesTmdbId, seasonNumber, episodeNumber.Value, info.SeriesDisplayOrder, info.MetadataLanguage, TmdbUtils.GetImageLanguagesParam(info.MetadataLanguage), cancellationToken)
.ConfigureAwait(false);
}

View File

@ -4,6 +4,8 @@ using Jellyfin.Data.Entities;
using Jellyfin.Data.Entities.Security;
using Jellyfin.Data.Interfaces;
using Microsoft.EntityFrameworkCore;
using Microsoft.EntityFrameworkCore.Metadata.Builders;
using Microsoft.EntityFrameworkCore.Metadata.Conventions;
using Microsoft.Extensions.Logging;
namespace Jellyfin.Server.Implementations;

View File

@ -49,11 +49,6 @@ public class NetworkManager : INetworkManager, IDisposable
/// </summary>
private bool _eventfire;
/// <summary>
/// List of all interface MAC addresses.
/// </summary>
private IReadOnlyList<PhysicalAddress> _macAddresses;
/// <summary>
/// Dictionary containing interface addresses and their subnets.
/// </summary>
@ -91,7 +86,6 @@ public class NetworkManager : INetworkManager, IDisposable
_startupConfig = startupConfig;
_initLock = new();
_interfaces = new List<IPData>();
_macAddresses = new List<PhysicalAddress>();
_publishedServerUrls = new List<PublishedServerUriOverride>();
_networkEventLock = new();
_remoteAddressFilter = new List<IPNetwork>();
@ -215,7 +209,6 @@ public class NetworkManager : INetworkManager, IDisposable
/// <summary>
/// Generate a list of all the interface ip addresses and submasks where that are in the active/unknown state.
/// Generate a list of all active mac addresses that aren't loopback addresses.
/// </summary>
private void InitializeInterfaces()
{
@ -224,7 +217,6 @@ public class NetworkManager : INetworkManager, IDisposable
_logger.LogDebug("Refreshing interfaces.");
var interfaces = new List<IPData>();
var macAddresses = new List<PhysicalAddress>();
try
{
@ -236,13 +228,6 @@ public class NetworkManager : INetworkManager, IDisposable
try
{
var ipProperties = adapter.GetIPProperties();
var mac = adapter.GetPhysicalAddress();
// Populate MAC list
if (adapter.NetworkInterfaceType != NetworkInterfaceType.Loopback && !PhysicalAddress.None.Equals(mac))
{
macAddresses.Add(mac);
}
// Populate interface list
foreach (var info in ipProperties.UnicastAddresses)
@ -302,7 +287,6 @@ public class NetworkManager : INetworkManager, IDisposable
_logger.LogDebug("Discovered {NumberOfInterfaces} interfaces.", interfaces.Count);
_logger.LogDebug("Interfaces addresses: {Addresses}", interfaces.OrderByDescending(s => s.AddressFamily == AddressFamily.InterNetwork).Select(s => s.Address.ToString()));
_macAddresses = macAddresses;
_interfaces = interfaces;
}
}
@ -711,13 +695,6 @@ public class NetworkManager : INetworkManager, IDisposable
return true;
}
/// <inheritdoc/>
public IReadOnlyList<PhysicalAddress> GetMacAddresses()
{
// Populated in construction - so always has values.
return _macAddresses;
}
/// <inheritdoc/>
public IReadOnlyList<IPData> GetLoopbacks()
{

View File

@ -23,6 +23,10 @@ namespace Jellyfin.Server.Implementations.Tests.Users
[InlineData(" ")]
[InlineData("")]
[InlineData("special characters like & $ ? are not allowed")]
[InlineData("thishasaspaceontheend ")]
[InlineData(" thishasaspaceatthestart")]
[InlineData(" thishasaspaceatbothends ")]
[InlineData(" this has a space at both ends and inbetween ")]
public void ThrowIfInvalidUsername_WhenInvalidUsername_ThrowsArgumentException(string username)
{
Assert.Throws<ArgumentException>(() => UserManager.ThrowIfInvalidUsername(username));