internal static async ValueTask <ResultBox <T>?> TryUseExistingFromUse <T>( this IAsyncComputed <T>?existing, ComputeContext context, IComputed?usedBy, CancellationToken cancellationToken) { if (existing == null || !existing.IsConsistent()) { return(null); } var result = existing.MaybeOutput; if (result == null) { result = await existing.GetOutput(cancellationToken).ConfigureAwait(false); if (result == null) { return(null); } } context.TryCapture(existing); ((IComputedImpl?)usedBy)?.AddUsed((IComputedImpl)existing !); ((IComputedImpl?)existing)?.RenewTimeouts(); return(result); }
internal static async ValueTask <ResultBox <T>?> TryUseExistingAsync <T>( this IAsyncComputed <T>?existing, ComputeContext context, IComputed?usedBy, CancellationToken cancellationToken) { var callOptions = context.CallOptions; var useExisting = (callOptions & CallOptions.TryGetExisting) != 0; if (existing == null) { return(useExisting ? ResultBox <T> .Default : null); } if (!(useExisting || existing.IsConsistent())) { return(null); } var invalidate = (callOptions & CallOptions.Invalidate) == CallOptions.Invalidate; if (invalidate) { existing.Invalidate(); if ((callOptions & CallOptions.Capture) != 0) { Interlocked.Exchange(ref context.CapturedComputed, existing); } return(existing.MaybeOutput ?? ResultBox <T> .Default); } var result = existing.MaybeOutput; if (result == null) { result = await existing.GetOutputAsync(cancellationToken).ConfigureAwait(false); if (result == null) { return(null); } } if (!useExisting) { ((IComputedImpl?)usedBy)?.AddUsed((IComputedImpl)existing !); } if ((callOptions & CallOptions.Capture) != 0) { Interlocked.Exchange(ref context.CapturedComputed, existing); } ((IComputedImpl?)existing)?.RenewTimeouts(); return(result); }