Skip to content

Commit

Permalink
Add function to poll async operations
Browse files Browse the repository at this point in the history
This will be called, for example, when we create a new
resource. It will wait until the resource has been
created and then return the URI of the newly created resource.
  • Loading branch information
stuart-mclaren-hpe committed Aug 21, 2024
1 parent 4cd9cb3 commit e37d870
Showing 1 changed file with 105 additions and 0 deletions.
105 changes: 105 additions & 0 deletions internal/poll/operation.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,105 @@
package poll

import (
"context"
"time"

"github.com/HewlettPackard/hpegl-pcbe-terraform-resources/internal/client"
"github.com/HewlettPackard/hpegl-pcbe-terraform-resources/internal/sdk/async/dataservices"
"github.com/hashicorp/terraform-plugin-framework/diag"
)

// AsyncOperation polls an asynchronous operation until it completes.
// It returns the URI of the source resource of the operation.
func AsyncOperation(
ctx context.Context,
client client.PCBeClient,
OperationID string,
diagsP *diag.Diagnostics,
) *string {
maxPolls := int(client.Config.MaxPolls)
pollWaitTime := time.Duration(client.Config.PollInterval) * time.Second

asyncClient, err := client.NewAsyncClient(ctx)
if err != nil {
(*diagsP).AddError(
"error polling async operation "+OperationID,
err.Error(),
)

return nil
}

var opResp dataservices.V1beta1AsyncOperationsItemAsyncOperationsGetResponseable
arc := dataservices.
V1beta1AsyncOperationsAsyncOperationsItemRequestBuilderGetRequestConfiguration{}

for count := 1; ; count++ {

opResp, err = asyncClient.DataServices().
V1beta1().
AsyncOperations().
ById(OperationID).
Get(ctx, &arc)
if err != nil {
(*diagsP).AddError(
"error polling async operation "+OperationID,
err.Error(),
)

return nil
}

if opResp == nil {
msg := "nil op response"
(*diagsP).AddError(
"error polling async operation "+OperationID,
msg,
)

return nil
}

opRespState := opResp.GetState()
if opRespState == nil {
msg := "operation has nil state"
(*diagsP).AddError(
"error polling async operation "+OperationID,
msg,
)

return nil
}

// TODO: (API) Use enum not string for state when FF-28181 is fixed
if *opRespState == "FAILED" {
msg := "operation state FAILED"

(*diagsP).AddError(
"error polling async operation "+OperationID,
msg,
)

return nil
}

// TODO: (API) Use enum not string for state when FF-28181 is fixed
if *opRespState == "SUCCEEDED" {
break
}

if count == maxPolls {
msg := "max polls exceeded"
(*diagsP).AddError(
"error polling async operation "+OperationID,
msg,
)

return nil
}

time.Sleep(pollWaitTime)
}

return opResp.GetSourceResourceUri()
}

0 comments on commit e37d870

Please sign in to comment.