From 6689d837d6dcfa0925efdbd9c76a7e1fe4f7cc54 Mon Sep 17 00:00:00 2001 From: gnattu Date: Mon, 13 May 2024 05:12:07 +0800 Subject: [PATCH] Fix absolute path checking on windows (#11570) --- .../IO/ManagedFileSystem.cs | 17 ++++------ .../IO/ManagedFileSystemTests.cs | 33 ++++++++++++------- 2 files changed, 28 insertions(+), 22 deletions(-) diff --git a/Emby.Server.Implementations/IO/ManagedFileSystem.cs b/Emby.Server.Implementations/IO/ManagedFileSystem.cs index 67854a2a7a..d5afac2663 100644 --- a/Emby.Server.Implementations/IO/ManagedFileSystem.cs +++ b/Emby.Server.Implementations/IO/ManagedFileSystem.cs @@ -80,12 +80,14 @@ namespace Emby.Server.Implementations.IO public virtual string MakeAbsolutePath(string folderPath, string filePath) { // path is actually a stream - if (string.IsNullOrWhiteSpace(filePath) || filePath.Contains("://", StringComparison.Ordinal)) + if (string.IsNullOrWhiteSpace(filePath)) { return filePath; } - if (filePath.Length > 3 && filePath[1] == ':' && filePath[2] == '/') + var isAbsolutePath = Path.IsPathRooted(filePath) && (!OperatingSystem.IsWindows() || filePath[0] != '\\'); + + if (isAbsolutePath) { // absolute local path return filePath; @@ -97,17 +99,10 @@ namespace Emby.Server.Implementations.IO return filePath; } - var firstChar = filePath[0]; - if (firstChar == '/') - { - // for this we don't really know - return filePath; - } - var filePathSpan = filePath.AsSpan(); - // relative path - if (firstChar == '\\') + // relative path on windows + if (filePath[0] == '\\') { filePathSpan = filePathSpan.Slice(1); } diff --git a/tests/Jellyfin.Server.Implementations.Tests/IO/ManagedFileSystemTests.cs b/tests/Jellyfin.Server.Implementations.Tests/IO/ManagedFileSystemTests.cs index d991f55748..95a5b8179c 100644 --- a/tests/Jellyfin.Server.Implementations.Tests/IO/ManagedFileSystemTests.cs +++ b/tests/Jellyfin.Server.Implementations.Tests/IO/ManagedFileSystemTests.cs @@ -20,26 +20,37 @@ namespace Jellyfin.Server.Implementations.Tests.IO _sut = _fixture.Create(); } - [Theory] + [SkippableTheory] [InlineData("/Volumes/Library/Sample/Music/Playlists/", "../Beethoven/Misc/Moonlight Sonata.mp3", "/Volumes/Library/Sample/Music/Beethoven/Misc/Moonlight Sonata.mp3")] [InlineData("/Volumes/Library/Sample/Music/Playlists/", "../../Beethoven/Misc/Moonlight Sonata.mp3", "/Volumes/Library/Sample/Beethoven/Misc/Moonlight Sonata.mp3")] [InlineData("/Volumes/Library/Sample/Music/Playlists/", "Beethoven/Misc/Moonlight Sonata.mp3", "/Volumes/Library/Sample/Music/Playlists/Beethoven/Misc/Moonlight Sonata.mp3")] - public void MakeAbsolutePathCorrectlyHandlesRelativeFilePaths( + [InlineData("/Volumes/Library/Sample/Music/Playlists/", "/mnt/Beethoven/Misc/Moonlight Sonata.mp3", "/mnt/Beethoven/Misc/Moonlight Sonata.mp3")] + public void MakeAbsolutePathCorrectlyHandlesRelativeFilePathsOnUnixLike( string folderPath, string filePath, string expectedAbsolutePath) { + Skip.If(OperatingSystem.IsWindows()); + + var generatedPath = _sut.MakeAbsolutePath(folderPath, filePath); + Assert.Equal(expectedAbsolutePath, generatedPath); + } + + [SkippableTheory] + [InlineData(@"C:\\Volumes\Library\Sample\Music\Playlists\", @"..\Beethoven\Misc\Moonlight Sonata.mp3", @"C:\Volumes\Library\Sample\Music\Beethoven\Misc\Moonlight Sonata.mp3")] + [InlineData(@"C:\\Volumes\Library\Sample\Music\Playlists\", @"..\..\Beethoven\Misc\Moonlight Sonata.mp3", @"C:\Volumes\Library\Sample\Beethoven\Misc\Moonlight Sonata.mp3")] + [InlineData(@"C:\\Volumes\Library\Sample\Music\Playlists\", @"Beethoven\Misc\Moonlight Sonata.mp3", @"C:\Volumes\Library\Sample\Music\Playlists\Beethoven\Misc\Moonlight Sonata.mp3")] + [InlineData(@"C:\\Volumes\Library\Sample\Music\Playlists\", @"D:\\Beethoven\Misc\Moonlight Sonata.mp3", @"D:\\Beethoven\Misc\Moonlight Sonata.mp3")] + public void MakeAbsolutePathCorrectlyHandlesRelativeFilePathsOnWindows( + string folderPath, + string filePath, + string expectedAbsolutePath) + { + Skip.If(!OperatingSystem.IsWindows()); + var generatedPath = _sut.MakeAbsolutePath(folderPath, filePath); - if (OperatingSystem.IsWindows()) - { - var expectedWindowsPath = expectedAbsolutePath.Replace('/', '\\'); - Assert.Equal(expectedWindowsPath, generatedPath.Split(':')[1]); - } - else - { - Assert.Equal(expectedAbsolutePath, generatedPath); - } + Assert.Equal(expectedAbsolutePath, generatedPath); } [Theory]