mirror of
https://github.com/FabInfra/capnproto-dotnetcore_Runtime.git
synced 2025-03-12 14:51:41 +01:00
refactored IResolvingCapability to hide ConsumedCapability
This commit is contained in:
parent
4bf0e970c2
commit
d7f937a9c0
@ -8,8 +8,15 @@ namespace Capnp.Rpc
|
||||
public interface IResolvingCapability
|
||||
{
|
||||
/// <summary>
|
||||
/// Will eventually give the resolved capability.
|
||||
/// Completes when the capability gets resolved.
|
||||
/// </summary>
|
||||
Task<ConsumedCapability?> WhenResolved { get; }
|
||||
Task WhenResolved { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Returns the resolved capability
|
||||
/// </summary>
|
||||
/// <typeparam name="T">Capability interface or <see cref="BareProxy"/></typeparam>
|
||||
/// <returns>the resolved capability, or null if it did not resolve yet</returns>
|
||||
T? GetResolvedCapability<T>() where T: class;
|
||||
}
|
||||
}
|
@ -17,10 +17,11 @@ namespace Capnp.Rpc
|
||||
}
|
||||
|
||||
readonly Task<Proxy>? _proxyTask;
|
||||
readonly Task<ConsumedCapability?> _capTask;
|
||||
|
||||
public LazyCapability(Task<ConsumedCapability?> capabilityTask)
|
||||
{
|
||||
WhenResolved = capabilityTask;
|
||||
_capTask = capabilityTask;
|
||||
}
|
||||
|
||||
public LazyCapability(Task<Proxy> proxyTask)
|
||||
@ -29,7 +30,7 @@ namespace Capnp.Rpc
|
||||
|
||||
async Task<ConsumedCapability?> AwaitCap() => (await _proxyTask!).ConsumedCap;
|
||||
|
||||
WhenResolved = AwaitCap();
|
||||
_capTask = AwaitCap();
|
||||
}
|
||||
|
||||
internal override void Freeze(out IRpcEndpoint? boundEndpoint)
|
||||
@ -40,7 +41,7 @@ namespace Capnp.Rpc
|
||||
|
||||
try
|
||||
{
|
||||
WhenResolved.Result?.Freeze(out boundEndpoint);
|
||||
_capTask.Result?.Freeze(out boundEndpoint);
|
||||
}
|
||||
catch (AggregateException exception)
|
||||
{
|
||||
@ -61,7 +62,7 @@ namespace Capnp.Rpc
|
||||
{
|
||||
if (WhenResolved.ReplacementTaskIsCompletedSuccessfully())
|
||||
{
|
||||
using var proxy = new Proxy(WhenResolved.Result);
|
||||
using var proxy = GetResolvedCapability<BareProxy>()!;
|
||||
return proxy.Export(endpoint, writer);
|
||||
}
|
||||
else
|
||||
@ -84,14 +85,33 @@ namespace Capnp.Rpc
|
||||
}
|
||||
}
|
||||
|
||||
public Task<ConsumedCapability?> WhenResolved { get; }
|
||||
public Task WhenResolved => _capTask;
|
||||
|
||||
public T? GetResolvedCapability<T>() where T: class
|
||||
{
|
||||
if (_capTask.IsCompleted)
|
||||
{
|
||||
try
|
||||
{
|
||||
return CapabilityReflection.CreateProxy<T>(_capTask.Result) as T;
|
||||
}
|
||||
catch (AggregateException exception)
|
||||
{
|
||||
throw exception.InnerException!;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
async Task<DeserializerState> CallImpl(ulong interfaceId, ushort methodId, DynamicSerializerState args, CancellationToken cancellationToken)
|
||||
{
|
||||
ConsumedCapability? cap;
|
||||
try
|
||||
{
|
||||
cap = await WhenResolved;
|
||||
cap = await _capTask;
|
||||
}
|
||||
catch
|
||||
{
|
||||
|
@ -21,9 +21,6 @@ namespace Capnp.Rpc
|
||||
public LocalAnswerCapability(Task<Proxy> proxyTask)
|
||||
{
|
||||
_whenResolvedProxy = proxyTask;
|
||||
|
||||
async Task<ConsumedCapability?> AwaitResolved() => (await _whenResolvedProxy).ConsumedCap;
|
||||
WhenResolved = AwaitResolved();
|
||||
}
|
||||
|
||||
public LocalAnswerCapability(Task<DeserializerState> answer, MemberAccessPath access):
|
||||
@ -42,7 +39,9 @@ namespace Capnp.Rpc
|
||||
}
|
||||
|
||||
|
||||
public Task<ConsumedCapability?> WhenResolved { get; private set; }
|
||||
public Task WhenResolved => _whenResolvedProxy;
|
||||
|
||||
public T? GetResolvedCapability<T>() where T : class => _whenResolvedProxy.GetResolvedCapability<T>();
|
||||
|
||||
internal override Action? Export(IRpcEndpoint endpoint, CapDescriptor.WRITER writer)
|
||||
{
|
||||
|
@ -16,11 +16,12 @@ namespace Capnp.Rpc
|
||||
{
|
||||
_remoteId = remoteId;
|
||||
|
||||
async Task<Proxy> AwaitProxy() => new Proxy(await WhenResolved);
|
||||
async Task<Proxy> AwaitProxy() => new Proxy(await _resolvedCap.Task);
|
||||
_whenResolvedProxy = AwaitProxy();
|
||||
}
|
||||
|
||||
public override Task<ConsumedCapability?> WhenResolved => _resolvedCap.Task;
|
||||
public override Task WhenResolved => _resolvedCap.Task;
|
||||
public override T? GetResolvedCapability<T>() where T: class => _whenResolvedProxy.GetResolvedCapability<T>();
|
||||
|
||||
internal override void Freeze(out IRpcEndpoint? boundEndpoint)
|
||||
{
|
||||
|
@ -32,18 +32,30 @@ namespace Capnp.Rpc
|
||||
bool _disposedValue = false;
|
||||
|
||||
/// <summary>
|
||||
/// Will eventually give the resolved capability, if this is a promised capability.
|
||||
/// Completes when the capability gets resolved.
|
||||
/// </summary>
|
||||
public Task<ConsumedCapability?> WhenResolved
|
||||
public Task WhenResolved
|
||||
{
|
||||
get
|
||||
{
|
||||
return ConsumedCap is IResolvingCapability resolving ?
|
||||
resolving.WhenResolved :
|
||||
Task.FromResult(ConsumedCap);
|
||||
resolving.WhenResolved : Task.CompletedTask;
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Returns the resolved capability
|
||||
/// </summary>
|
||||
/// <typeparam name="T">Capability interface or <see cref="BareProxy"/></typeparam>
|
||||
/// <returns>the resolved capability, or null if it did not resolve yet</returns>
|
||||
public T? GetResolvedCapability<T>() where T : class
|
||||
{
|
||||
if (ConsumedCap is IResolvingCapability resolving)
|
||||
return resolving.GetResolvedCapability<T>();
|
||||
else
|
||||
return CapabilityReflection.CreateProxy<T>(ConsumedCap) as T;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Underlying low-level capability
|
||||
/// </summary>
|
||||
|
@ -23,18 +23,6 @@ namespace Capnp.Rpc
|
||||
_question = question ?? throw new ArgumentNullException(nameof(question));
|
||||
_access = access ?? throw new ArgumentNullException(nameof(access));
|
||||
_whenResolvedProxy = proxyTask ?? throw new ArgumentNullException(nameof(proxyTask));
|
||||
|
||||
async Task<ConsumedCapability?> AwaitWhenResolved()
|
||||
{
|
||||
var proxy = await _whenResolvedProxy;
|
||||
|
||||
if (_question.IsTailCall)
|
||||
throw new InvalidOperationException("Question is a tail call, so won't resolve back.");
|
||||
|
||||
return proxy.ConsumedCap;
|
||||
}
|
||||
|
||||
WhenResolved = AwaitWhenResolved();
|
||||
}
|
||||
|
||||
static async Task<Proxy> TransferOwnershipToDummyProxy(PendingQuestion question, MemberAccessPath access)
|
||||
@ -81,7 +69,7 @@ namespace Capnp.Rpc
|
||||
{
|
||||
try
|
||||
{
|
||||
return WhenResolved.Result;
|
||||
return _whenResolvedProxy.Result.ConsumedCap;
|
||||
}
|
||||
catch (AggregateException exception)
|
||||
{
|
||||
@ -96,7 +84,9 @@ namespace Capnp.Rpc
|
||||
}
|
||||
}
|
||||
|
||||
public override Task<ConsumedCapability?> WhenResolved { get; }
|
||||
public override Task WhenResolved => _whenResolvedProxy;
|
||||
|
||||
public override T? GetResolvedCapability<T>() where T: class => _whenResolvedProxy.GetResolvedCapability<T>();
|
||||
|
||||
protected override void GetMessageTarget(MessageTarget.WRITER wr)
|
||||
{
|
||||
|
@ -16,7 +16,8 @@ namespace Capnp.Rpc
|
||||
ILogger Logger { get; } = Logging.CreateLogger<RemoteResolvingCapability>();
|
||||
#endif
|
||||
|
||||
public abstract Task<ConsumedCapability?> WhenResolved { get; }
|
||||
public abstract Task WhenResolved { get; }
|
||||
public abstract T? GetResolvedCapability<T>() where T : class;
|
||||
|
||||
protected RemoteResolvingCapability(IRpcEndpoint ep) : base(ep)
|
||||
{
|
||||
|
@ -9,7 +9,9 @@ namespace Capnp.Rpc
|
||||
{
|
||||
while (cap is IResolvingCapability resolving)
|
||||
{
|
||||
cap = await resolving.WhenResolved;
|
||||
await resolving.WhenResolved;
|
||||
using var proxy = resolving.GetResolvedCapability<BareProxy>()!;
|
||||
cap = proxy.ConsumedCap;
|
||||
}
|
||||
|
||||
return cap;
|
||||
@ -30,7 +32,9 @@ namespace Capnp.Rpc
|
||||
|
||||
try
|
||||
{
|
||||
var resolvedCap = await Unwrap(await cap.WhenResolved);
|
||||
await cap.WhenResolved;
|
||||
using var proxy = cap.GetResolvedCapability<BareProxy>()!;
|
||||
var resolvedCap = await Unwrap(proxy.ConsumedCap);
|
||||
endpoint.Resolve(preliminaryId, vine, () => resolvedCap!);
|
||||
}
|
||||
catch (System.Exception exception)
|
||||
@ -68,5 +72,24 @@ namespace Capnp.Rpc
|
||||
default: return BareProxy.FromImpl(obj);
|
||||
}
|
||||
}
|
||||
|
||||
public static T? GetResolvedCapability<T>(this Task<Proxy> proxyTask) where T: class
|
||||
{
|
||||
if (proxyTask.IsCompleted)
|
||||
{
|
||||
try
|
||||
{
|
||||
return proxyTask.Result.Cast<T>(false);
|
||||
}
|
||||
catch (AggregateException exception)
|
||||
{
|
||||
throw exception.InnerException!;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
return null;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
Loading…
x
Reference in New Issue
Block a user