feat(dcl+ui): rename BrowseOpcUaNode -> ConnectionName-keyed; implement site handler + dialog failure mapping

- BrowseOpcUaNodeCommand: int DataConnectionId -> string ConnectionName
  (site DataConnectionManagerActor indexes children by name; CentralUI
  already has the connection name in scope via the dropdown — no extra
  plumbing across the trust boundary).
- IOpcUaBrowseService / OpcUaBrowseService: parameter renamed accordingly.
- OpcUaBrowserDialog: collapse the duplicate ConnectionName parameters
  (display label and routing key are the same string).
- Task 10: DataConnectionManagerActor forwards BrowseOpcUaNodeCommand to
  its child by name (owns ConnectionNotFound); DataConnectionActor adds
  the receive across all three lifecycle states (Connecting / Connected
  / Reconnecting) and maps adapter outcomes to BrowseFailureKind
  (NotBrowsable / ConnectionNotConnected / Timeout / ServerError).
- Task 17: SetFailure in OpcUaBrowserDialog implements the full
  BrowseFailureKind switch with friendly UI messages.
- Tests: DataConnectionManagerBrowseHandlerTests covers ConnectionNotFound,
  NotBrowsable, success, and ConnectionNotConnectedException paths.
This commit is contained in:
Joseph Doherty
2026-05-28 12:09:43 -04:00
parent 6999aedc60
commit d285174597
7 changed files with 313 additions and 13 deletions
@@ -21,17 +21,17 @@ public interface IOpcUaBrowseService
{
/// <summary>
/// Enumerates the immediate children of an OPC UA node on the live server
/// backing <paramref name="dataConnectionId"/> at <paramref name="siteId"/>.
/// backing <paramref name="connectionName"/> at <paramref name="siteId"/>.
/// Pass <c>null</c> for <paramref name="parentNodeId"/> to browse from the
/// server root (ObjectsFolder).
/// </summary>
/// <param name="siteId">The target site identifier.</param>
/// <param name="dataConnectionId">Id of the site-local data connection to browse against.</param>
/// <param name="connectionName">Name of the site-local data connection to browse against — the site's <c>DataConnectionManagerActor</c> indexes its children by name.</param>
/// <param name="parentNodeId">Node to browse, or <c>null</c> to browse from the server root.</param>
/// <param name="cancellationToken">Cancellation token.</param>
Task<BrowseOpcUaNodeResult> BrowseChildrenAsync(
string siteId,
int dataConnectionId,
string connectionName,
string? parentNodeId,
CancellationToken cancellationToken = default);
}
@@ -37,7 +37,7 @@ public sealed class OpcUaBrowseService : IOpcUaBrowseService
/// <inheritdoc/>
public async Task<BrowseOpcUaNodeResult> BrowseChildrenAsync(
string siteId,
int dataConnectionId,
string connectionName,
string? parentNodeId,
CancellationToken cancellationToken = default)
{
@@ -56,7 +56,7 @@ public sealed class OpcUaBrowseService : IOpcUaBrowseService
{
return await _communication.BrowseOpcUaNodeAsync(
siteId,
new BrowseOpcUaNodeCommand(dataConnectionId, parentNodeId),
new BrowseOpcUaNodeCommand(connectionName, parentNodeId),
cancellationToken);
}
catch (TimeoutException ex)