using System;
using System.Collections.Generic;
using ArchestrA;
using ZB.MOM.WW.OtOpcUa.Historian.Aveva;
using ZB.MOM.WW.OtOpcUa.Host.Configuration;
namespace ZB.MOM.WW.OtOpcUa.Historian.Aveva.Tests
{
///
/// Fake Historian connection factory for tests. Controls whether connections
/// succeed, fail, or timeout without requiring the real Historian SDK runtime.
///
internal sealed class FakeHistorianConnectionFactory : IHistorianConnectionFactory
{
///
/// Exception thrown on every CreateAndConnect call unless a more specific rule in
/// or fires first.
///
public Exception? ConnectException { get; set; }
public int ConnectCallCount { get; private set; }
public Action? OnConnect { get; set; }
///
/// Per-server-name override: if the requested config.ServerName has an entry
/// whose value is non-null, that exception is thrown instead of the global
/// . Lets tests script cluster failover behavior like
/// "node A always fails; node B always succeeds".
///
public Dictionary ServerBehaviors { get; } =
new Dictionary(StringComparer.OrdinalIgnoreCase);
///
/// Ordered history of server names passed to CreateAndConnect so tests can assert the
/// picker's iteration order and failover sequence.
///
public List ConnectHistory { get; } = new List();
public HistorianAccess CreateAndConnect(HistorianConfiguration config, HistorianConnectionType type)
{
ConnectCallCount++;
ConnectHistory.Add(config.ServerName);
if (ServerBehaviors.TryGetValue(config.ServerName, out var serverException) && serverException != null)
throw serverException;
if (OnConnect != null)
{
OnConnect(ConnectCallCount);
}
else if (ConnectException != null)
{
throw ConnectException;
}
// Return a HistorianAccess that is not actually connected.
// ReadRawAsync etc. will fail when they try to use it, which exercises
// the HandleConnectionError → reconnect path.
return new HistorianAccess();
}
}
}