feat(client): add rendezvous traversal coordinators (#12)
quality-gate / quality (push) Successful in 56s

This commit is contained in:
KyuubiYoru
2026-07-16 08:39:05 +02:00
parent 6d076c281a
commit b4b6072fe1
28 changed files with 2949 additions and 57 deletions
@@ -42,6 +42,10 @@ public static class RendezvousClientResult
public sealed class PublishedSession
{
private readonly object _timingGate = new();
private DateTimeOffset _expiresAt;
private int _leaseRenewAfterSeconds;
internal PublishedSession(RegisterSessionResponse response)
{
ListingId = response.ListingId;
@@ -49,8 +53,8 @@ public sealed class PublishedSession
LeaseToken = response.LeaseToken;
HostPresenceHandle = response.HostPresenceHandle;
HostPresenceCapability = response.HostPresenceCapability;
ExpiresAt = response.ExpiresAt;
LeaseRenewAfterSeconds = response.LeaseRenewAfterSeconds;
_expiresAt = response.ExpiresAt;
_leaseRenewAfterSeconds = response.LeaseRenewAfterSeconds;
HostPresenceRefreshAfterSeconds = response.HostPresenceRefreshAfterSeconds;
}
@@ -59,8 +63,41 @@ public sealed class PublishedSession
public string LeaseToken { get; }
public MediationHandle HostPresenceHandle { get; }
public string HostPresenceCapability { get; }
public DateTimeOffset ExpiresAt { get; internal set; }
public int LeaseRenewAfterSeconds { get; internal set; }
public DateTimeOffset ExpiresAt
{
get
{
lock (_timingGate)
{
return _expiresAt;
}
}
internal set
{
lock (_timingGate)
{
_expiresAt = value;
}
}
}
public int LeaseRenewAfterSeconds
{
get
{
lock (_timingGate)
{
return _leaseRenewAfterSeconds;
}
}
internal set
{
lock (_timingGate)
{
_leaseRenewAfterSeconds = value;
}
}
}
public int HostPresenceRefreshAfterSeconds { get; }
public override string ToString() => $"[PublishedSession {ListingId}; credentials redacted]";
@@ -109,6 +146,28 @@ public interface IRendezvousSessionBrowserClient
CancellationToken cancellationToken = default);
}
public interface IRendezvousJoinClient
{
Task<RendezvousClientResult<CreateJoinAttemptResponse>> CreateAsync(
CreateJoinAttemptRequest request,
CancellationToken cancellationToken = default);
Task<RendezvousClientResult<bool>> CancelAsync(
CreateJoinAttemptResponse attempt,
CancellationToken cancellationToken = default);
Task<RendezvousClientResult<BrowseHostJoinAttemptsResponse>> BrowseForHostAsync(
PublishedSession session,
int pageSize = ContractLimits.BrowserPageMaxItems,
string? cursor = null,
CancellationToken cancellationToken = default);
Task<RendezvousClientResult<IReadOnlyList<HostJoinAttempt>>> BrowseAllForHostAsync(
PublishedSession session,
int maximumPages = 100,
CancellationToken cancellationToken = default);
}
public interface IRendezvousDelay
{
Task DelayAsync(TimeSpan delay, CancellationToken cancellationToken);