From 46ede471a9d262add29657b7e3e3350aa3bf0bc8 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Adam=20Slatinsk=C3=BD?= <43640724+slatinsky@users.noreply.github.com> Date: Mon, 9 Oct 2023 22:58:31 +0200 Subject: [PATCH] Remove CDN signature before hashing asset URL (#1138) --- .../Exporting/ExportAssetDownloader.cs | 25 +++++++++++++++++-- 1 file changed, 23 insertions(+), 2 deletions(-) diff --git a/DiscordChatExporter.Core/Exporting/ExportAssetDownloader.cs b/DiscordChatExporter.Core/Exporting/ExportAssetDownloader.cs index 2be9efd2..0ffdce82 100644 --- a/DiscordChatExporter.Core/Exporting/ExportAssetDownloader.cs +++ b/DiscordChatExporter.Core/Exporting/ExportAssetDownloader.cs @@ -7,6 +7,7 @@ using System.Text; using System.Text.RegularExpressions; using System.Threading; using System.Threading.Tasks; +using System.Web; using AsyncKeyedLock; using DiscordChatExporter.Core.Utils; using DiscordChatExporter.Core.Utils.Extensions; @@ -101,12 +102,32 @@ internal partial class ExportAssetDownloader internal partial class ExportAssetDownloader { - private static string GetUrlHash(string url) => - SHA256 + private static string GetUrlHash(string url) + { + // Strip out ex, is and hm query params from Discord CDN URLs to create a consistent hash + if ( + url.Contains("cdn.discordapp.com") + && url.Contains("ex") + && url.Contains("is") + && url.Contains("hm") + ) + { + var uriBuilder = new UriBuilder(url); + var query = HttpUtility.ParseQueryString(uriBuilder.Query); + query.Remove("ex"); + query.Remove("is"); + query.Remove("hm"); + uriBuilder.Query = query.ToString(); + url = uriBuilder.ToString(); + url = url.Replace(":443", ""); + } + + return SHA256 .HashData(Encoding.UTF8.GetBytes(url)) .ToHex() // 5 chars ought to be enough for anybody .Truncate(5); + } private static string GetFileNameFromUrl(string url) {