-
Notifications
You must be signed in to change notification settings - Fork 43
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
Add begin and wait API for LRO #811
Comments
Another option as discussed offline is to provide a wrapper that customers use to get the same behavior. type OperationWaiter[TResult any] struct {
poller *runtime.Poller[TResult]
err error
}
func (ow OperationWaiter[TResult]) Wait(ctx context.Context, freq time.Duration) (TResult, error) {
if ow.err != nil {
return *new(TResult), ow.err
}
return ow.poller.PollUntilDone(ctx, freq)
}
func NewOperationWaiter[TResult any](poller *runtime.Poller[TResult], err error) OperationWaiter[TResult] {
return OperationWaiter[TResult]{poller: poller, err: err}
} This would allow callers to condense an LRO into a one-line call. result, err := NewOperationWaiter(client.BeginSomeLRO(context.Background(), nil)).Wait(context.Background(), time.Second) |
Based on our user study, true feelings of the LRO and none LRO operation is that they make the code look inconsistent. I know we have customer who write infra level code that would be ok with detailed control but there is customer who write none infra level code, consistency and easy to understand is one of their priorities, for those LRO operation, can we provide a none LRO-look-like call as an alternative? |
We've noticed that it usually happened that service change an operation from synchronized to asynchronized which cause Go SDK breaking changes. In order to prevent such breaking changes, I'd prefer to generate both synchronized and asynchronized function for LRO. Besides preventing breaking changes, it could also give a simple usage for customer who does not care of the LRO undelaying logic. @jhendrixMSFT @JeffreyRichter What do you think? |
It's an interesting idea. Do you have an idea of how many breaking changes are caused by this? |
Among current 7 Go mgmt. SDK packages which have v2+ version, 2 of them have the breaking of such change. And I have met more during my swagger review work. Here are some examples: |
Got another one from SQL. Azure/azure-rest-api-specs#19953 |
So first, let me say that services should not make this specific breaking change and so there should not be a lot of these. So, my concern is that if the SDK initiates an LRO and this succeeds but then the polling fails, we return an error to the customer and now the customer doesn't know (since we put multiple operations into a single method) what to do: Did initiating the operation fail and so it never got started? Or, did it get started and now there is a problem with knowing its state? The error recovery for these 2 scenarios is VERY different and a customer would have to write the proper code to deal with them separately/correctly. Having a wrapper function makes this much harder. |
Can we add a new
Synchronized LRO:
Usage:
The generic type is a problem for now. But if this way could work, it should be some more elegant implementation. |
Your sample codes shows how to detect the error but not how to properly recover from the error. |
@JeffreyRichter I think in Chenjie's code if errors.As(err, &pollingErr) {
poller := pollingErr.Poller
_ = poller
log.Fatalf("Inner error: %+v", errors.Unwrap(err))
} else {
log.Fatalf("Other error: %+v", err)
} If the error is a polling error, developers can get that poller from the error and try poll until done again |
Yes. Here is the comparison:
Sync:
|
@jhendrixMSFT To answer your concern about the execution time increasement if we provide a synchronized method for LRO, I list the LRO execution time distribution as follows. Most operations can be done in 20 seconds. Regarding we also provide asynchronized Some statistics related to total time for LRO based on CLI telemetry data:
|
For mgmt. plane SDK, we want to add an API to create poller and poll final result simultaneously. It is an addition for current create poller API (
BeginCreateOrUpdate
). The possible name for the API is the same with the rest operation name (CreateOrUpdate
). The reason is in mgmt. scenario, user always emphasis on theresource
result regardless the operation is LRO or not. The problem is duplicity and may involve confusion. Since this should be a non-breaking feature, we may gather more user feedback first.The text was updated successfully, but these errors were encountered: