From 488429ea8dc2aab31fa6ac185081baa184cfb44c Mon Sep 17 00:00:00 2001 From: Ben Olden-Cooligan Date: Fri, 12 Jan 2024 19:25:41 -0800 Subject: [PATCH] Escl: Change device ID to be just the UUID --- NAPS2.Escl.Tests/ClientServerTests.cs | 6 ++++-- NAPS2.Escl.Usb/EsclUsbContext.cs | 3 ++- NAPS2.Escl/Client/EsclService.cs | 2 +- NAPS2.Escl/Client/EsclServiceLocator.cs | 7 ++++--- .../Remoting/ScanServerIntegrationTests.cs | 8 +++----- NAPS2.Sdk/Scan/Internal/Escl/EsclScanDriver.cs | 13 ++++++++++--- 6 files changed, 24 insertions(+), 15 deletions(-) diff --git a/NAPS2.Escl.Tests/ClientServerTests.cs b/NAPS2.Escl.Tests/ClientServerTests.cs index 8d9f84fd1..02e04371e 100644 --- a/NAPS2.Escl.Tests/ClientServerTests.cs +++ b/NAPS2.Escl.Tests/ClientServerTests.cs @@ -13,6 +13,7 @@ public class ClientServerTests { var job = Substitute.For(); using var server = new EsclServer(); + var uuid = Guid.NewGuid().ToString("D"); var deviceConfig = new EsclDeviceConfig { Capabilities = new EsclCapabilities @@ -20,7 +21,7 @@ public class ClientServerTests Version = "2.0", MakeAndModel = "HP Blah", SerialNumber = "123abc", - Uuid = Guid.NewGuid().ToString("D") + Uuid = uuid }, CreateJob = _ => job }; @@ -34,7 +35,8 @@ public class ClientServerTests RemoteEndpoint = IPAddress.IPv6Loopback, Port = deviceConfig.Port, RootUrl = "eSCL", - Tls = false + Tls = false, + Uuid = uuid }); var caps = await client.GetCapabilities(); Assert.Equal("2.0", caps.Version); diff --git a/NAPS2.Escl.Usb/EsclUsbContext.cs b/NAPS2.Escl.Usb/EsclUsbContext.cs index 490d4a4f6..e0bf30cc6 100644 --- a/NAPS2.Escl.Usb/EsclUsbContext.cs +++ b/NAPS2.Escl.Usb/EsclUsbContext.cs @@ -53,7 +53,8 @@ public class EsclUsbContext : IDisposable RemoteEndpoint = IPAddress.Loopback, Port = port, RootUrl = "eSCL", - Tls = false + Tls = false, + Uuid = Guid.Empty.ToString("D") }); Task.Run(ProxyLoop); } diff --git a/NAPS2.Escl/Client/EsclService.cs b/NAPS2.Escl/Client/EsclService.cs index 82b2b3a24..f44f5cc22 100644 --- a/NAPS2.Escl/Client/EsclService.cs +++ b/NAPS2.Escl/Client/EsclService.cs @@ -43,7 +43,7 @@ public class EsclService /// /// A unique identifier for the physical scanner device. /// - public string? Uuid { get; init; } + public required string Uuid { get; init; } /// /// The make and model of the scanner. diff --git a/NAPS2.Escl/Client/EsclServiceLocator.cs b/NAPS2.Escl/Client/EsclServiceLocator.cs index 73e34430d..0126cdaeb 100644 --- a/NAPS2.Escl/Client/EsclServiceLocator.cs +++ b/NAPS2.Escl/Client/EsclServiceLocator.cs @@ -115,9 +115,10 @@ public class EsclServiceLocator : IDisposable } } } - if ((ipv4 == null && ipv6 == null) || port == -1 || host == null) + string? uuid = Get(props, "uuid"); + if ((ipv4 == null && ipv6 == null) || port == -1 || host == null || uuid == null) { - throw new ArgumentException(); + throw new ArgumentException("Missing host/IP/port/uuid"); } return new EsclService @@ -128,6 +129,7 @@ public class EsclServiceLocator : IDisposable RemoteEndpoint = args.RemoteEndPoint.Address, Port = port, Tls = isTls, + Uuid = uuid, ScannerName = props["ty"], RootUrl = props["rs"], TxtVersion = Get(props, "txtvers"), @@ -136,7 +138,6 @@ public class EsclServiceLocator : IDisposable Thumbnail = Get(props, "representation"), Note = Get(props, "note"), MimeTypes = Get(props, "pdl")?.Split(','), - Uuid = Get(props, "uuid"), ColorOptions = Get(props, "cs")?.Split(','), SourceOptions = Get(props, "is"), DuplexSupported = Get(props, "duplex")?.ToUpperInvariant() == "T" diff --git a/NAPS2.Sdk.Tests/Remoting/ScanServerIntegrationTests.cs b/NAPS2.Sdk.Tests/Remoting/ScanServerIntegrationTests.cs index cab027d8b..4ff4440c2 100644 --- a/NAPS2.Sdk.Tests/Remoting/ScanServerIntegrationTests.cs +++ b/NAPS2.Sdk.Tests/Remoting/ScanServerIntegrationTests.cs @@ -38,10 +38,8 @@ public class ScanServerIntegrationTests : ContextualTests // Set up a client ScanController for scanning through EsclScanDriver -> network -> ScanServer _client = new ScanController(ScanningContext); - // This device won't match exactly the real device from GetDeviceList but it includes the UUID which is enough - // for EsclScanDriver to correctly identify the server for scanning. var uuid = new ScanServerDevice { Device = serverDevice, Name = displayName }.GetUuid(_server.InstanceId); - _clientDevice = new ScanDevice(Driver.Escl, $"|{uuid}", displayName); + _clientDevice = new ScanDevice(Driver.Escl, uuid, displayName); } public override void Dispose() @@ -54,9 +52,9 @@ public class ScanServerIntegrationTests : ContextualTests public async Task FindDevice() { var devices = await _client.GetDeviceList(Driver.Escl); - // The device name is suffixed with the IP so we just check the prefix matches (and vice versa for ID) + // The device name is suffixed with the IP so we just check the prefix matches Assert.Contains(devices, - device => device.Name.StartsWith(_clientDevice.Name) && device.ID.EndsWith(_clientDevice.ID)); + device => device.Name.StartsWith(_clientDevice.Name) && device.ID == _clientDevice.ID); } [Fact] diff --git a/NAPS2.Sdk/Scan/Internal/Escl/EsclScanDriver.cs b/NAPS2.Sdk/Scan/Internal/Escl/EsclScanDriver.cs index 82705466c..791869fd2 100644 --- a/NAPS2.Sdk/Scan/Internal/Escl/EsclScanDriver.cs +++ b/NAPS2.Sdk/Scan/Internal/Escl/EsclScanDriver.cs @@ -21,10 +21,16 @@ internal class EsclScanDriver : IScanDriver public static string GetUuid(ScanDevice device) { var parts = device.ID.Split('|'); + if (parts.Length == 1) + { + // Current IDs are just the UUID + return parts[0]; + } if (parts.Length != 2) { throw new ArgumentException("Invalid ESCL device ID"); } + // Old IDs have both the IP and UUID separated by "|" return parts[1]; } @@ -40,14 +46,15 @@ internal class EsclScanDriver : IScanDriver var localIPsTask = options.ExcludeLocalIPs ? LocalIPsHelper.Get() : null; using var locator = new EsclServiceLocator(service => { - // Store both the IP and UUID so we can preferentially find by the IP, but also fall back to looking for - // the UUID in case the IP changed var ip = service.IpV4 ?? service.IpV6!; if (options.ExcludeLocalIPs && localIPsTask!.Result.Contains(ip.ToString())) { return; } - var id = $"{ip}|{service.Uuid}"; + // TODO: When we implement scanner capabilities, store all the connection information in there so we can + // try and connect directly before querying for a potentially-updated-IP (and then back-propagate the new + // connection info). + var id = service.Uuid; var name = string.IsNullOrEmpty(service.ScannerName) ? $"{ip}" : $"{service.ScannerName} ({ip})";