kubernetes/kops · error

waiting for disk create/update completion: %w

Error message

waiting for disk create/update completion: %w

What it means

After BeginCreateOrUpdate accepts the request, CreateOrUpdate polls the returned future with PollUntilDone until the ARM long-running operation finishes. If polling fails (operation error, context cancellation, or transient HTTP failure mid-poll), the error is wrapped as "waiting for disk create/update completion: %w". This means the request was accepted but the disk never reached a final successful state within the call.

Source

Thrown at upup/pkg/fi/cloudup/azure/disk.go:49

	CreateOrUpdate(ctx context.Context, resourceGroupName, diskName string, parameters compute.Disk) (*compute.Disk, error)
	List(ctx context.Context, resourceGroupName string) ([]*compute.Disk, error)
	Delete(ctx context.Context, resourceGroupName, diskname string) error
}

type disksClientImpl struct {
	c *compute.DisksClient
}

var _ DisksClient = (*disksClientImpl)(nil)

func (c *disksClientImpl) CreateOrUpdate(ctx context.Context, resourceGroupName, diskName string, parameters compute.Disk) (*compute.Disk, error) {
	future, err := c.c.BeginCreateOrUpdate(ctx, resourceGroupName, diskName, parameters, nil)
	if err != nil {
		return nil, fmt.Errorf("creating/updating disk: %w", err)
	}
	resp, err := future.PollUntilDone(ctx, nil)
	if err != nil {
		return nil, fmt.Errorf("waiting for disk create/update completion: %w", err)
	}
	return &resp.Disk, err
}

func (c *disksClientImpl) List(ctx context.Context, resourceGroupName string) ([]*compute.Disk, error) {
	if resourceGroupName == "" {
		return nil, nil
	}

	var l []*compute.Disk
	pager := c.c.NewListByResourceGroupPager(resourceGroupName, nil)
	for pager.More() {
		resp, err := pager.NextPage(ctx)
		if err != nil {
			var respErr *azcore.ResponseError
			if errors.As(err, &respErr) && respErr.ErrorCode == "ResourceGroupNotFound" {
				return nil, nil
			}

View on GitHub (pinned to 4c8573c808)

Solutions

  1. Unwrap to check for context.DeadlineExceeded/Canceled: if so, re-check the disk's actual state via DisksClient.List or the ARM portal before retrying, since the operation may still complete.
  2. Increase the context timeout passed to CreateOrUpdate (disk creation can take several minutes).
  3. Inspect the wrapped *azcore.ResponseError for provisioning failure details (ErrorCode) and fix the underlying cause (SKU/region/quota).
  4. Handle 429 by backing off and retrying the poll or the whole operation.

Example fix

// before
ctx, cancel := context.WithTimeout(ctx, 30*time.Second)
// after
diskCtx, cancel := context.WithTimeout(context.Background(), 15*time.Minute)
_, err := disks.CreateOrUpdate(diskCtx, rg, name, params)
Defensive patterns

Strategy: retry

Validate before calling

if ctx.Err() != nil {
    return fmt.Errorf("context already done before disk create/update: %w", ctx.Err())
}
// ensure generous deadline for LROs
ctx, cancel := context.WithTimeout(ctx, 15*time.Minute)
defer cancel()

Type guard

func isContextError(err error) bool {
    return errors.Is(err, context.DeadlineExceeded) || errors.Is(err, context.Canceled)
}

Try / catch

if err != nil {
    if errors.Is(err, context.DeadlineExceeded) {
        // do NOT immediately recreate: verify the disk's actual state first
        existing, listErr := disks.List(ctx, rg)
        if listErr == nil && findDisk(existing, diskName) != nil {
            return nil // operation actually completed
        }
    }
    return fmt.Errorf("disk LRO failed: %w", err)
}

Prevention

When it happens

Trigger: Calling DisksClient.CreateOrUpdate where the accepted LRO subsequently fails or hangs: context deadline/timeout exceeded during PollUntilDone, ARM returns a failed provisioning state (e.g. disk size/SKU not supported in region), 429 throttling during polling, or the operation is cancelled upstream.

Common situations: Short context timeouts on slow Azure regions where disk creation takes minutes; region/SKU combination unavailable (e.g. Premium_ZRS not offered); subscription quota hit while the operation is in flight; node provisioning interrupted so the ctx passed in is cancelled.

Related errors


AI-assisted analysis of kubernetes/kops@4c8573c808 (2026-09-05). Data as JSON: /api/errors/811dd7769af1a318. Report an issue: GitHub.