-
Notifications
You must be signed in to change notification settings - Fork 11
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
feat(copy): introduces CopyGraphOptions with events support #145
base: main
Are you sure you want to change the base?
feat(copy): introduces CopyGraphOptions with events support #145
Conversation
…ries Signed-off-by: Leonardo Chaia <[email protected]>
847ecb0
to
6817504
Compare
Signed-off-by: Leonardo Chaia <[email protected]>
This is a work in progress. Seems to be working running locally. Tests are failing and need more work. |
Signed-off-by: Leonardo Chaia <[email protected]>
Signed-off-by: Leonardo Chaia <[email protected]>
Hi. I propose concurrency support is implemented in a separate PR. Otherwise this should be ready to review :+ Leo. |
Example usage: List<string> knownReferences = [];
foreach (var toReplicate in toReplicateArray)
{
var copyOpts = new CopyOptions()
{
MountFrom = _ => knownReferences.ToArray(),
};
copyOpts.OnCopySkipped += d => this.logger.LogTrace("{Digest}: Already exists.", d.Digest);
copyOpts.OnPreCopy += d => this.logger.LogTrace("{Digest}: Copying..", d.Digest);
copyOpts.OnPostCopy += d => this.logger.LogTrace("{Digest}: Copied", d.Digest);
copyOpts.OnMounted += (d, from) => this.logger.LogTrace("{Digest}: Mounted from {From}", d.Digest, from);
await sourceRepository.CopyAsync(
toReplicate.SourceImage,
destinationRepository,
toReplicate.DestinationImage,
cancellationToken,
copyOpts);
knownReferences.Add(toReplicate.DestinationImage);
} |
Hi all, any feedback is appreciated 🥇 Thanks! |
Codecov ReportAttention: Patch coverage is
Additional details and impacted files@@ Coverage Diff @@
## main #145 +/- ##
==========================================
+ Coverage 81.70% 82.62% +0.92%
==========================================
Files 35 37 +2
Lines 1104 1128 +24
Branches 128 134 +6
==========================================
+ Hits 902 932 +30
+ Misses 146 139 -7
- Partials 56 57 +1 ☔ View full report in Codecov by Sentry. |
Hi @leonardochaia , thank you for your contribution! Sorry for the delay. We need a bit more time to review your PR, but we’ll provide feedback as soon as we can. Thank you for your understanding! |
Do we want to move the mounting support to a separate PR as well? |
Hi @Wwwsylvia , thanks for the review. I'll apply the changes and report back. My goal is getting the mounting support when copying graphs since we are using this to replicate a bunch of images between registries and need to make it faster. |
@leonardochaia Sounds good. Thank you! |
Signed-off-by: Leonardo Chaia <[email protected]>
Signed-off-by: Leonardo Chaia <[email protected]>
PR simplified to only introduce the CopyGraphOptions. Next step is to update the tests to cover the events. Separate PRs/issues to be created:
|
Usually CancellationToken is left as the last parameter, however, that would introduce a breaking change. Are we good with introducing a breaking change?
EDIT: Disregard, I've added an overload to keep the CancellationToken last but also support the current signature |
Signed-off-by: Leonardo Chaia <[email protected]>
Signed-off-by: Leonardo Chaia <[email protected]>
Quick update, I've converted this PR to only include the Next steps:
|
…tions Signed-off-by: Leonardo Chaia <[email protected]>
Signed-off-by: Leonardo Chaia <[email protected]>
Build should be fixed, tests passed locally. @Wwwsylvia thanks for creating the issues, JIC: only // CopyOptions contains parameters for [oras.Copy].
type CopyOptions struct {
CopyGraphOptions
// MapRoot maps the resolved root node to a desired root node for copy.
// When MapRoot is provided, the descriptor resolved from the source
// reference will be passed to MapRoot, and the mapped descriptor will be
// used as the root node for copy.
MapRoot func(ctx context.Context, src content.ReadOnlyStorage, root ocispec.Descriptor) (ocispec.Descriptor, error)
} When Thanks! |
@leonardochaia The Since Update:
Oh I might have misunderstood. I'm good with leaving |
Hi @Wwwsylvia , sorry I meant to say Thanks! |
Signed-off-by: Leonardo Chaia <[email protected]>
…nto feat/improve-copy-performance
This should be good to go. Once this is merged I'll create a separate PR to support mounting when copying 🥇 |
Signed-off-by: Leonardo Chaia <[email protected]>
…nto feat/improve-copy-performance
Signed-off-by: Leonardo Chaia <[email protected]>
Signed-off-by: Leonardo Chaia <[email protected]>
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
LGTM
Signed-off-by: Leonardo Chaia <[email protected]>
Signed-off-by: Leonardo Chaia <[email protected]>
…us event handlers. Signed-off-by: Leonardo Chaia <[email protected]>
Signed-off-by: Leonardo Chaia <[email protected]>
Signed-off-by: Leonardo Chaia <[email protected]>
internal Task OnCopySkippedAsync(Descriptor descriptor) | ||
{ | ||
CopySkipped?.Invoke(descriptor); | ||
return CopySkippedAsync?.Invoke(descriptor) ?? Task.CompletedTask; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Do you mean InvokeAsync
?
internal Task OnPreCopyAsync(Descriptor descriptor) | ||
{ | ||
PreCopy?.Invoke(descriptor); | ||
return PreCopyAsync?.InvokeAsync(descriptor) ?? Task.CompletedTask; | ||
} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
In the PoC that plays with SomeEvent
, we set up the tasks for the async events before invoking the sync event handler. While in this implementation we first invoke the sync event and then the async events. I think the PoC approach is more efficient. I'm wondering if we can achieve something similar with a reusable extension method.
How about something like this:
internal static IEnumerable<Task> InvokeAsyncEvents<TEventArgs>(
this Func<TEventArgs, Task>? eventDelegate, TEventArgs args)
{
if (eventDelegate == null)
{
return [Task.CompletedTask];
}
return eventDelegate.GetInvocationList()
.Select(d => (Task?)d.DynamicInvoke(args) ?? Task.CompletedTask);
}
internal Task OnPreCopyAsync(Descriptor descriptor)
{
var tasks = PreCopyAsync.InvokeAsyncEvents(descriptor);
PreCopy?.Invoke(descriptor);
return Task.WhenAll(tasks);
}
Naming is hard though...
What this PR does / why we need it
This PR improves
CopyAsync
andCopyGraphAsync
to include theCopyGraphOptions
, inspired fromoras-go
.The current implementation:
CopyOptions
events, likeOnPreCopy
, these were implemented in the form ofAction<T>
sPending items
Which issue(s) this PR resolves / fixes
Please check the following list