diff --git a/app/MindWork AI Studio/Dialogs/ReviewAttachmentsDialog.razor b/app/MindWork AI Studio/Dialogs/ReviewAttachmentsDialog.razor
index cf245df1..3528d5fc 100644
--- a/app/MindWork AI Studio/Dialogs/ReviewAttachmentsDialog.razor
+++ b/app/MindWork AI Studio/Dialogs/ReviewAttachmentsDialog.razor
@@ -31,7 +31,7 @@
@{
var currentFolder = string.Empty;
- foreach (var fileAttachment in this.DocumentPaths)
+ foreach (var fileAttachment in this.OrderedAttachments)
{
var folderPath = Path.GetDirectoryName(fileAttachment.FilePath);
if (folderPath != currentFolder)
diff --git a/app/MindWork AI Studio/Dialogs/ReviewAttachmentsDialog.razor.cs b/app/MindWork AI Studio/Dialogs/ReviewAttachmentsDialog.razor.cs
index 026a11ef..0efcaa0a 100644
--- a/app/MindWork AI Studio/Dialogs/ReviewAttachmentsDialog.razor.cs
+++ b/app/MindWork AI Studio/Dialogs/ReviewAttachmentsDialog.razor.cs
@@ -73,6 +73,21 @@ public partial class ReviewAttachmentsDialog : MSGComponentBase
: "border-dashed border-2 rounded-lg pa-2 mud-border-lines-default";
}
+ ///
+ /// The attachments, sorted by their folder and, within it, by their file name.
+ ///
+ ///
+ /// The list below starts a new heading whenever the folder changes from one attachment to the
+ /// next, which names every folder exactly once -- but only as long as the attachments of a
+ /// folder arrive together. The set behind them keeps no order of its own to guarantee that:
+ /// removing one attachment already scrambles it, and one attached while this dialog is open
+ /// lands at its end, giving its folder a second heading further down. Sorting here is what that
+ /// list assumes anyway.
+ ///
+ private IEnumerable OrderedAttachments => this.DocumentPaths
+ .OrderBy(attachment => Path.GetDirectoryName(attachment.FilePath) ?? string.Empty, StringComparer.OrdinalIgnoreCase)
+ .ThenBy(attachment => attachment.FileName, StringComparer.OrdinalIgnoreCase);
+
///
/// Attaches what the user dropped onto this dialog and answers which files that became.
///