juicedata/juicefs · error

Failed to create Azure blob client with token credential: %v

Error message

Failed to create Azure blob client with token credential: %v

What it means

Thrown when azblob.NewClient(serviceURL, tokenCred, azblobOptions()) rejects the assembled service URL or options, after credential creation and endpoint discovery succeeded. Indicates a malformed final service URL.

Source

Thrown at pkg/object/azure.go:364

			}
			return &wasb{container: client.ServiceClient().NewContainerClient(containerName), azblobCli: client, cName: containerName, useTokenAuth: true}, nil
		}

		tokenCred, err := createAzureCredential()
		if err != nil {
			return nil, fmt.Errorf("Failed to create Azure credential (managed identity/Azure CLI): %v", err)
		}
		if domain == "" {
			if domain, err = autoWasbEndpoint(accountName, uri.Scheme, func(serviceURL string) (*azblob.Client, error) {
				return azblob.NewClient(serviceURL, tokenCred, nil)
			}); err != nil {
				return nil, fmt.Errorf("Unable to get endpoint of container %s: %s", containerName, err)
			}
		}
		serviceURL := fmt.Sprintf("%s://%s.%s", uri.Scheme, accountName, domain)
		client, err := azblob.NewClient(serviceURL, tokenCred, azblobOptions())
		if err != nil {
			return nil, fmt.Errorf("Failed to create Azure blob client with token credential: %v", err)
		}
		return &wasb{container: client.ServiceClient().NewContainerClient(containerName), azblobCli: client, cName: containerName, useTokenAuth: true}, nil
	}

	// Priority 3: Shared key authentication
	credential, err := azblob.NewSharedKeyCredential(accountName, accountKey)
	if err != nil {
		return nil, err
	}
	domain := domainFromHost(hostParts)
	if domain == "" {
		if domain, err = autoWasbEndpoint(accountName, uri.Scheme, func(serviceURL string) (*azblob.Client, error) {
			return azblob.NewClientWithSharedKeyCredential(serviceURL, credential, nil)
		}); err != nil {
			return nil, fmt.Errorf("Unable to get endpoint of container %s: %w", containerName, err)
		}
	}
	client, err := azblob.NewClientWithSharedKeyCredential(fmt.Sprintf("%s://%s.%s", uri.Scheme, accountName, domain), credential, azblobOptions())

View on GitHub (pinned to c9a67b23e8)

Solutions

  1. Ensure the account name is non-empty and contains only valid characters.
  2. Confirm the endpoint scheme is https (or http for emulators).
  3. Use an explicit full domain in the endpoint instead of relying on discovery.
  4. Log/print the constructed serviceURL to verify its shape before calling NewClient.

Example fix

// before
azblob:///  (empty account)
// after
azblob://myaccount.blob.core.windows.net
Defensive patterns

Strategy: validation

Validate before calling

if accountName == "" { return errors.New("account name is required") }
serviceURL := fmt.Sprintf("%s://%s.%s", scheme, accountName, domain)
if _, err := url.Parse(serviceURL); err != nil { return fmt.Errorf("bad service URL %q: %w", serviceURL, err) }

Try / catch

client, err := azblob.NewClient(serviceURL, tokenCred, opts)
if err != nil {
    return fmt.Errorf("invalid service URL %q: %w", serviceURL, err)
}

Prevention

When it happens

Trigger: newWasb token-auth path where fmt.Sprintf("%s://%s.%s", scheme, accountName, domain) produces a URL the SDK cannot parse — typically an empty account name or domain.

Common situations: Empty account name in the endpoint config; scheme other than http/https; auto-discovered domain empty due to a probe that returned no usable value.

Understand the failure class

Background: "Invalid URL" / "URL cannot be empty": fix the malformed or missing URL behind request-construction failures — this error's family across 50 libraries.

Related errors


AI-assisted analysis of juicedata/juicefs@c9a67b23e8 (2026-09-06). Data as JSON: /api/errors/5cb0226675d72de5. Report an issue: GitHub.