[feat] Sort query results
This commit is contained in:
@@ -24,7 +24,7 @@ public class VideoController(ILogger<VideoController> logger, ResourceService rs
|
||||
[HttpGet]
|
||||
public async Task<IActionResult> GetClass(string token)
|
||||
{
|
||||
var r = await rs.Query(VideoFolder, token, Ip);
|
||||
var r = (await rs.Query(VideoFolder, token, Ip))?.SortLikeWindows();
|
||||
|
||||
if(r == null)
|
||||
return StatusCode(401, new { message = "Unauthorized" });
|
||||
@@ -38,6 +38,7 @@ public class VideoController(ILogger<VideoController> logger, ResourceService rs
|
||||
var d = Helpers.SafePathCombine(VideoFolder, klass);
|
||||
if (d == null) return StatusCode(403, new { message = "403 Denied" });
|
||||
var r = await rs.Query(d, token, Ip);
|
||||
|
||||
if (r == null) return StatusCode(401, new { message = "Unauthorized" });
|
||||
|
||||
return Ok(r);
|
||||
@@ -64,6 +65,8 @@ public class VideoController(ILogger<VideoController> logger, ResourceService rs
|
||||
var r = await rs.Get(d, token, Ip);
|
||||
if (!r) return StatusCode(403, new { message = "403 Denied" });
|
||||
|
||||
_logger.LogInformation($"Cover found for {id}");
|
||||
|
||||
return PhysicalFile(d, "image/jpeg", enableRangeProcessing: true);
|
||||
}
|
||||
|
||||
|
||||
@@ -117,7 +117,7 @@ public class UserService
|
||||
Destroy(token);
|
||||
return null;
|
||||
}
|
||||
_logger.LogInformation($"Validated {userAndIp}");
|
||||
// _logger.LogInformation($"Validated {userAndIp}");
|
||||
return userAndIp?.Split('@')[0];
|
||||
}
|
||||
_logger.LogWarning($"Validation failed {token}");
|
||||
|
||||
@@ -1,4 +1,7 @@
|
||||
|
||||
using System.Globalization;
|
||||
using System.Text.RegularExpressions;
|
||||
|
||||
namespace Abyss.Components.Static;
|
||||
|
||||
public static class Helpers
|
||||
@@ -57,4 +60,121 @@ public enum PathType
|
||||
Directory,
|
||||
NotFound,
|
||||
AccessDenied
|
||||
}
|
||||
|
||||
|
||||
public static class StringArrayExtensions
|
||||
{
|
||||
public static string[] SortLikeWindows(this string[] array)
|
||||
{
|
||||
if (array == null) return null;
|
||||
if (array.Length == 0) return array;
|
||||
|
||||
Array.Sort(array, new WindowsFileNameComparer());
|
||||
return array;
|
||||
}
|
||||
|
||||
public static string[] SortLikeWindowsDescending(this string[] array)
|
||||
{
|
||||
if (array == null) return null;
|
||||
if (array.Length == 0) return array;
|
||||
|
||||
Array.Sort(array, new WindowsFileNameComparerDescending());
|
||||
return array;
|
||||
}
|
||||
|
||||
public static void SortLikeWindowsInPlace(this string[] array)
|
||||
{
|
||||
if (array == null || array.Length == 0) return;
|
||||
|
||||
Array.Sort(array, new WindowsFileNameComparer());
|
||||
}
|
||||
|
||||
public static void SortLikeWindowsDescendingInPlace(this string[] array)
|
||||
{
|
||||
if (array == null || array.Length == 0) return;
|
||||
|
||||
Array.Sort(array, new WindowsFileNameComparerDescending());
|
||||
}
|
||||
}
|
||||
|
||||
public class WindowsFileNameComparer : IComparer<string>
|
||||
{
|
||||
private static readonly Regex _regex = new Regex(@"(\d+|\D+)", RegexOptions.Compiled);
|
||||
private static readonly CompareInfo _compareInfo = CultureInfo.InvariantCulture.CompareInfo;
|
||||
|
||||
public int Compare(string? x, string? y)
|
||||
{
|
||||
if (x == null && y == null) return 0;
|
||||
if (x == null) return -1;
|
||||
if (y == null) return 1;
|
||||
if (ReferenceEquals(x, y)) return 0;
|
||||
|
||||
var partsX = _regex.Matches(x);
|
||||
var partsY = _regex.Matches(y);
|
||||
|
||||
int minLength = Math.Min(partsX.Count, partsY.Count);
|
||||
|
||||
for (int i = 0; i < minLength; i++)
|
||||
{
|
||||
string partX = partsX[i].Value;
|
||||
string partY = partsY[i].Value;
|
||||
|
||||
if (long.TryParse(partX, out long numX) && long.TryParse(partY, out long numY))
|
||||
{
|
||||
int comparison = numX.CompareTo(numY);
|
||||
if (comparison != 0) return comparison;
|
||||
}
|
||||
else
|
||||
{
|
||||
int comparison;
|
||||
if (ContainsChinese(partX) || ContainsChinese(partY))
|
||||
{
|
||||
comparison = _compareInfo.Compare(partX, partY, CompareOptions.IgnoreCase | CompareOptions.IgnoreNonSpace);
|
||||
}
|
||||
else
|
||||
{
|
||||
comparison = string.Compare(partX, partY, StringComparison.OrdinalIgnoreCase);
|
||||
}
|
||||
|
||||
if (comparison != 0) return comparison;
|
||||
}
|
||||
}
|
||||
|
||||
return partsX.Count.CompareTo(partsY.Count);
|
||||
}
|
||||
|
||||
private static bool ContainsChinese(string text)
|
||||
{
|
||||
if (string.IsNullOrEmpty(text)) return false;
|
||||
|
||||
foreach (char c in text)
|
||||
{
|
||||
if (c >= 0x4E00 && c <= 0x9FFF)
|
||||
return true;
|
||||
if (c >= 0x3400 && c <= 0x4DBF)
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
public class WindowsFileNameComparerDescending : IComparer<string>
|
||||
{
|
||||
private static readonly WindowsFileNameComparer _ascendingComparer = new WindowsFileNameComparer();
|
||||
|
||||
public int Compare(string x, string y)
|
||||
{
|
||||
return _ascendingComparer.Compare(y, x);
|
||||
}
|
||||
}
|
||||
|
||||
public static class StringNaturalCompare
|
||||
{
|
||||
private static readonly WindowsFileNameComparer _comparer = new WindowsFileNameComparer();
|
||||
|
||||
public static int Compare(string x, string y)
|
||||
{
|
||||
return _comparer.Compare(x, y);
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user