Skip to content

Commit 03b56b9

Browse files
committed
Add error dialogs on NotFound and AlreadyExists. Retry with StorageApi on long paths
1 parent bd66ddc commit 03b56b9

File tree

2 files changed

+78
-4
lines changed

2 files changed

+78
-4
lines changed

src/Files.Uwp/Filesystem/FilesystemOperations/FilesystemOperations.cs

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -172,7 +172,7 @@ await DialogDisplayHelper.ShowDialogAsync(
172172
ContentDialog dialog = new ContentDialog()
173173
{
174174
Title = "ErrorDialogThisActionCannotBeDone".GetLocalized(),
175-
Content = $"{"ErrorDialogTheDestinationFolder".GetLocalized()} ({destinationName}) {"ErrorDialogIsASubfolder".GetLocalized()} (sourceName)",
175+
Content = $"{"ErrorDialogTheDestinationFolder".GetLocalized()} ({destinationName}) {"ErrorDialogIsASubfolder".GetLocalized()} ({sourceName})",
176176
//PrimaryButtonText = "Skip".GetLocalized(),
177177
CloseButtonText = "Cancel".GetLocalized()
178178
};
@@ -358,7 +358,7 @@ await DialogDisplayHelper.ShowDialogAsync(
358358
ContentDialog dialog = new ContentDialog()
359359
{
360360
Title = "ErrorDialogThisActionCannotBeDone".GetLocalized(),
361-
Content = "ErrorDialogTheDestinationFolder".GetLocalized() + " (" + destinationName + ") " + "ErrorDialogIsASubfolder".GetLocalized() + " (" + sourceName + ")",
361+
Content = $"{"ErrorDialogTheDestinationFolder".GetLocalized()} ({destinationName}) {"ErrorDialogIsASubfolder".GetLocalized()} ({sourceName})",
362362
//PrimaryButtonText = "Skip".GetLocalized(),
363363
CloseButtonText = "Cancel".GetLocalized()
364364
};
@@ -789,7 +789,7 @@ await associatedInstance.FilesystemViewModel.GetFileFromPathAsync(iFilePath)
789789
{
790790
await DialogDisplayHelper.ShowDialogAsync("AccessDenied".GetLocalized(), "AccessDeniedDeleteDialog/Text".GetLocalized());
791791
}
792-
else if (((FileSystemStatusCode)fsResult).HasFlag(FileSystemStatusCode.Unauthorized))
792+
else if (((FileSystemStatusCode)fsResult).HasFlag(FileSystemStatusCode.NotFound))
793793
{
794794
await DialogDisplayHelper.ShowDialogAsync("FileNotFoundDialog/Title".GetLocalized(), "FileNotFoundDialog/Text".GetLocalized());
795795
}

src/Files.Uwp/Filesystem/FilesystemOperations/ShellFilesystemOperations.cs

Lines changed: 75 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -166,6 +166,19 @@ public async Task<IStorageHistory> CopyItemsAsync(IList<IStorageItemWithPath> so
166166
var lockingProcess = await WhoIsLockingAsync(failedSources.Select(x => x.HResult == HResult.COPYENGINE_E_SHARING_VIOLATION_SRC ? x.Source : x.Destination));
167167
await DialogDisplayHelper.ShowDialogAsync("FileInUseDeleteDialog/Title".GetLocalized(), lockingProcess != null ? string.Join(Environment.NewLine, lockingProcess.Select(x => $"Name: {x.Name}, PID: {x.Pid}")) : "");
168168
}
169+
else if (copyResult.Items.Any(x => HResult.Convert(x.HResult) == FileSystemStatusCode.NameTooLong))
170+
{
171+
// Retry with StorageFile API
172+
return await filesystemOperations.CopyItemsAsync(source, destination, collisions, progress, errorCode, cancellationToken);
173+
}
174+
else if (copyResult.Items.Any(x => HResult.Convert(x.HResult) == FileSystemStatusCode.NotFound))
175+
{
176+
await DialogDisplayHelper.ShowDialogAsync("FileNotFoundDialog/Title".GetLocalized(), "FileNotFoundDialog/Text".GetLocalized());
177+
}
178+
else if (copyResult.Items.Any(x => HResult.Convert(x.HResult) == FileSystemStatusCode.AlreadyExists))
179+
{
180+
await DialogDisplayHelper.ShowDialogAsync("ItemAlreadyExistsDialogTitle".GetLocalized(), "ItemAlreadyExistsDialogContent".GetLocalized());
181+
}
169182
errorCode?.Report(HResult.Convert(copyResult.Items.FirstOrDefault(x => !x.Succeeded)?.HResult));
170183
return null;
171184
}
@@ -254,6 +267,19 @@ public async Task<IStorageHistory> CopyItemsAsync(IList<IStorageItemWithPath> so
254267
return await CreateAsync(source, errorCode, cancellationToken);
255268
}
256269
}
270+
else if (createResult.Items.Any(x => HResult.Convert(x.HResult) == FileSystemStatusCode.NameTooLong))
271+
{
272+
// Retry with StorageFile API
273+
return await filesystemOperations.CreateAsync(source, errorCode, cancellationToken);
274+
}
275+
else if (createResult.Items.Any(x => HResult.Convert(x.HResult) == FileSystemStatusCode.NotFound))
276+
{
277+
await DialogDisplayHelper.ShowDialogAsync("FileNotFoundDialog/Title".GetLocalized(), "FileNotFoundDialog/Text".GetLocalized());
278+
}
279+
else if (createResult.Items.Any(x => HResult.Convert(x.HResult) == FileSystemStatusCode.AlreadyExists))
280+
{
281+
await DialogDisplayHelper.ShowDialogAsync("ItemAlreadyExistsDialogTitle".GetLocalized(), "ItemAlreadyExistsDialogContent".GetLocalized());
282+
}
257283
errorCode?.Report(HResult.Convert(createResult.Items.FirstOrDefault(x => !x.Succeeded)?.HResult));
258284
return (null, null);
259285
}
@@ -397,6 +423,10 @@ public async Task<IStorageHistory> DeleteItemsAsync(IList<IStorageItemWithPath>
397423
var lockingProcess = await WhoIsLockingAsync(failedSources.Select(x => x.HResult == HResult.COPYENGINE_E_SHARING_VIOLATION_SRC ? x.Source : x.Destination));
398424
await DialogDisplayHelper.ShowDialogAsync("FileInUseDeleteDialog/Title".GetLocalized(), lockingProcess != null ? string.Join(Environment.NewLine, lockingProcess.Select(x => $"Name: {x.Name}, PID: {x.Pid}")) : "");
399425
}
426+
else if (deleteResult.Items.Any(x => HResult.Convert(x.HResult) == FileSystemStatusCode.NotFound))
427+
{
428+
await DialogDisplayHelper.ShowDialogAsync("FileNotFoundDialog/Title".GetLocalized(), "FileNotFoundDialog/Text".GetLocalized());
429+
}
400430
errorCode?.Report(HResult.Convert(deleteResult.Items.FirstOrDefault(x => !x.Succeeded)?.HResult));
401431
return null;
402432
}
@@ -515,13 +545,32 @@ public async Task<IStorageHistory> MoveItemsAsync(IList<IStorageItemWithPath> so
515545
return await MoveItemsAsync(source, destination, collisions, progress, errorCode, cancellationToken);
516546
}
517547
}
548+
else if (source.Zip(destination, (src, dest) => (src, dest)).FirstOrDefault(x => x.src.ItemType == FilesystemItemType.Directory && PathNormalization.GetParentDir(x.dest).IsSubPathOf(x.src.Path)) is (IStorageItemWithPath, string) subtree)
549+
{
550+
var destName = subtree.dest.Split(Path.DirectorySeparatorChar, StringSplitOptions.RemoveEmptyEntries).Last();
551+
var srcName = subtree.src.Path.Split(Path.DirectorySeparatorChar, StringSplitOptions.RemoveEmptyEntries).Last();
552+
await DialogDisplayHelper.ShowDialogAsync("ErrorDialogThisActionCannotBeDone".GetLocalized(), $"{"ErrorDialogTheDestinationFolder".GetLocalized()} ({destName}) {"ErrorDialogIsASubfolder".GetLocalized()} ({srcName})");
553+
}
518554
else if (moveResult.Items.Any(x => HResult.Convert(x.HResult) == FileSystemStatusCode.InUse))
519555
{
520556
// TODO: proper dialog, retry
521557
var failedSources = moveResult.Items.Where(x => HResult.Convert(x.HResult) == FileSystemStatusCode.InUse);
522558
var lockingProcess = await WhoIsLockingAsync(failedSources.Select(x => x.HResult == HResult.COPYENGINE_E_SHARING_VIOLATION_SRC ? x.Source : x.Destination));
523559
await DialogDisplayHelper.ShowDialogAsync("FileInUseDeleteDialog/Title".GetLocalized(), lockingProcess != null ? string.Join(Environment.NewLine, lockingProcess.Select(x => $"Name: {x.Name}, PID: {x.Pid}")) : "");
524560
}
561+
else if (moveResult.Items.Any(x => HResult.Convert(x.HResult) == FileSystemStatusCode.NameTooLong))
562+
{
563+
// Retry with StorageFile API
564+
return await filesystemOperations.MoveItemsAsync(source, destination, collisions, progress, errorCode, cancellationToken);
565+
}
566+
else if (moveResult.Items.Any(x => HResult.Convert(x.HResult) == FileSystemStatusCode.NotFound))
567+
{
568+
await DialogDisplayHelper.ShowDialogAsync("FileNotFoundDialog/Title".GetLocalized(), "FileNotFoundDialog/Text".GetLocalized());
569+
}
570+
else if (moveResult.Items.Any(x => HResult.Convert(x.HResult) == FileSystemStatusCode.AlreadyExists))
571+
{
572+
await DialogDisplayHelper.ShowDialogAsync("ItemAlreadyExistsDialogTitle".GetLocalized(), "ItemAlreadyExistsDialogContent".GetLocalized());
573+
}
525574
errorCode?.Report(HResult.Convert(moveResult.Items.FirstOrDefault(x => !x.Succeeded)?.HResult));
526575
return null;
527576
}
@@ -586,6 +635,19 @@ public async Task<IStorageHistory> RenameAsync(IStorageItemWithPath source, stri
586635
var lockingProcess = await WhoIsLockingAsync(failedSources.Select(x => x.HResult == HResult.COPYENGINE_E_SHARING_VIOLATION_SRC ? x.Source : x.Destination));
587636
await DialogDisplayHelper.ShowDialogAsync("FileInUseDeleteDialog/Title".GetLocalized(), lockingProcess != null ? string.Join(Environment.NewLine, lockingProcess.Select(x => $"Name: {x.Name}, PID: {x.Pid}")) : "");
588637
}
638+
else if (renameResult.Items.Any(x => HResult.Convert(x.HResult) == FileSystemStatusCode.NameTooLong))
639+
{
640+
// Retry with StorageFile API
641+
return await filesystemOperations.RenameAsync(source, newName, collision, errorCode, cancellationToken);
642+
}
643+
else if (renameResult.Items.Any(x => HResult.Convert(x.HResult) == FileSystemStatusCode.NotFound))
644+
{
645+
await DialogDisplayHelper.ShowDialogAsync("RenameError/ItemDeleted/Title".GetLocalized(), "RenameError/ItemDeleted/Text".GetLocalized());
646+
}
647+
else if (renameResult.Items.Any(x => HResult.Convert(x.HResult) == FileSystemStatusCode.AlreadyExists))
648+
{
649+
await DialogDisplayHelper.ShowDialogAsync("ItemAlreadyExistsDialogTitle".GetLocalized(), "ItemAlreadyExistsDialogContent".GetLocalized());
650+
}
589651
errorCode?.Report(HResult.Convert(renameResult.Items.FirstOrDefault(x => !x.Succeeded)?.HResult));
590652
return null;
591653
}
@@ -681,6 +743,19 @@ public async Task<IStorageHistory> RestoreItemsFromTrashAsync(IList<IStorageItem
681743
var lockingProcess = await WhoIsLockingAsync(failedSources.Select(x => x.HResult == HResult.COPYENGINE_E_SHARING_VIOLATION_SRC ? x.Source : x.Destination));
682744
await DialogDisplayHelper.ShowDialogAsync("FileInUseDeleteDialog/Title".GetLocalized(), lockingProcess != null ? string.Join(Environment.NewLine, lockingProcess.Select(x => $"Name: {x.Name}, PID: {x.Pid}")) : "");
683745
}
746+
else if (moveResult.Items.Any(x => HResult.Convert(x.HResult) == FileSystemStatusCode.NameTooLong))
747+
{
748+
// Retry with StorageFile API
749+
return await filesystemOperations.RestoreItemsFromTrashAsync(source, destination, progress, errorCode, cancellationToken);
750+
}
751+
else if (moveResult.Items.Any(x => HResult.Convert(x.HResult) == FileSystemStatusCode.NotFound))
752+
{
753+
await DialogDisplayHelper.ShowDialogAsync("FileNotFoundDialog/Title".GetLocalized(), "FileNotFoundDialog/Text".GetLocalized());
754+
}
755+
else if (moveResult.Items.Any(x => HResult.Convert(x.HResult) == FileSystemStatusCode.AlreadyExists))
756+
{
757+
await DialogDisplayHelper.ShowDialogAsync("ItemAlreadyExistsDialogTitle".GetLocalized(), "ItemAlreadyExistsDialogContent".GetLocalized());
758+
}
684759
errorCode?.Report(HResult.Convert(moveResult.Items.FirstOrDefault(x => !x.Succeeded)?.HResult));
685760
return null;
686761
}
@@ -795,7 +870,6 @@ private struct HResult
795870
//public const int COPYENGINE_E_SAME_FILE = -2144927741;
796871
//public const int COPYENGINE_E_DEST_SAME_TREE = -2144927734;
797872
//public const int COPYENGINE_E_DEST_SUBTREE = -2144927735;
798-
//public const int COPYENGINE_E_DIFF_DIR = -2144927740;
799873

800874
public static FileSystemStatusCode Convert(int? hres)
801875
{

0 commit comments

Comments
 (0)