Added unified interface for remote browsing.

This PR adds a single API endpoint for listing contents of remote source or backend. With this API, we can greatly simplify the FE as it does not need to know about webmodules for each provider, but can just use the single API.

To support this, the fulldisk module was updated slightly to return enumerable meta entries, similar to ms365 and gws providers.
This commit is contained in:
Kenneth Skovhede
2026-06-12 11:06:21 +02:00
parent 87b6f636fc
commit b67a73553a
11 changed files with 441 additions and 41 deletions
+2 -22
View File
@@ -1,14 +1,10 @@
using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.IO;
using System.IO.Pipelines;
using System.Linq;
using System.Text;
using System.Text.Json;
using System.Threading;
using System.Threading.Tasks;
using Duplicati.Library.Common.IO;
using Duplicati.Library.Interface;
using Duplicati.Library.Logging;
using Duplicati.Library.Utility;
@@ -54,7 +50,8 @@ public class WebModule : IWebModule
{
var res = new Dictionary<string, string>();
await foreach (var drive in SourceProvider.ListPhysicalDrives(cancellationToken))
AddDiskToResult(drive, res);
res[drive.Path] = JsonSerializer.Serialize(await drive.GetMinorMetadata(cancellationToken));
return res;
}
@@ -90,23 +87,6 @@ public class WebModule : IWebModule
return result;
}
private void AddDiskToResult(PhysicalDriveInfo drive, Dictionary<string, string> result)
{
// For now, we only allow picking full disks, not individual partitions
// var resultpath = Util.AppendDirSeparator(drive.Path);
var resultpath = drive.Path.TrimEnd(Path.DirectorySeparatorChar);
var metadata = new Dictionary<string, string?>
{
{ "diskimage:Number", drive.Number },
{ "diskimage:FriendlyName", drive.DisplayName },
{ "diskimage:Size", drive.Size.ToString() },
{ "diskimage:DevicePath", drive.Path },
{ "diskimage:Name", $"{drive.DisplayName} ({Library.Utility.Utility.FormatSizeString(drive.Size)})" },
};
result[resultpath] = JsonSerializer.Serialize(metadata);
}
public IDictionary<string, IDictionary<string, string>> GetLookups()
=> new Dictionary<string, IDictionary<string, string>>();
}