hashicorp/nomad · error

error parsing HTTPReadTimeout: %w

Error message

error parsing HTTPReadTimeout: %w

What it means

`ArtifactConfigFromAgent` converts the client agent's public artifact config into an internal readonly copy. It parses HTTPReadTimeout with time.ParseDuration and, on failure, wraps the parse error as "error parsing HTTPReadTimeout: %w". This is a startup-time configuration validation error: the supplied string is not a valid Go duration (e.g. missing unit).

Source

Thrown at client/config/artifact.go:40

	GitTimeout time.Duration
	HgTimeout  time.Duration
	S3Timeout  time.Duration

	DecompressionLimitFileCount int
	DecompressionLimitSize      int64

	DisableArtifactInspection     bool
	DisableFilesystemIsolation    bool
	FilesystemIsolationExtraPaths []string
	SetEnvironmentVariables       string
}

// ArtifactConfigFromAgent creates a new internal readonly copy of the client
// agent's ArtifactConfig. The config should have already been validated.
func ArtifactConfigFromAgent(c *config.ArtifactConfig) (*ArtifactConfig, error) {
	httpReadTimeout, err := time.ParseDuration(*c.HTTPReadTimeout)
	if err != nil {
		return nil, fmt.Errorf("error parsing HTTPReadTimeout: %w", err)
	}

	httpMaxSize, err := humanize.ParseBytes(*c.HTTPMaxSize)
	if err != nil {
		return nil, fmt.Errorf("error parsing HTTPMaxSize: %w", err)
	}

	gcsTimeout, err := time.ParseDuration(*c.GCSTimeout)
	if err != nil {
		return nil, fmt.Errorf("error parsing GCSTimeout: %w", err)
	}

	gitTimeout, err := time.ParseDuration(*c.GitTimeout)
	if err != nil {
		return nil, fmt.Errorf("error parsing GitTimeout: %w", err)
	}

	hgTimeout, err := time.ParseDuration(*c.HgTimeout)

View on GitHub (pinned to 482b49bf1a)

Solutions

  1. Set http_read_timeout to a valid Go duration string including the unit, e.g. "30m" or "1h"
  2. Validate the rendered config with `nomad agent -config ... -verify` (or run nomad config validate) before deploy
  3. Fix any templating/env interpolation that yields empty or malformed values

Example fix

// nomad client config
// before
client {
  artifact {
    http_read_timeout = "30" // missing unit
  }
}
// after
client {
  artifact {
    http_read_timeout = "30m"
  }
}
Defensive patterns

Strategy: validation

Validate before calling

if _, err := time.ParseDuration(cfg.Artifact.HTTPReadTimeout); err != nil {
    log.Fatalf("invalid http_read_timeout %q: %v", cfg.Artifact.HTTPReadTimeout, err)
}

Try / catch

cfg, err := clientconfig.ArtifactConfigFromAgent(agentCfg.Artifact)
if err != nil {
    if strings.Contains(err.Error(), "error parsing HTTPReadTimeout") {
        return fmt.Errorf("fix client.artifact.http_read_timeout to a Go duration like 30m: %w", err)
    }
    return err
}

Prevention

When it happens

Trigger: Starting a Nomad client with client.artifact.http_read_timeout set to an invalid duration string such as "30", "30s4m2" or "ten seconds"; config values injected via environment variables or templating that produce malformed durations.

Common situations: Operators setting a bare number assuming seconds (Go durations require units like 30s); config management templates rendering empty strings; copy-pasted config using non-Go duration syntax like 5m30 (valid) vs 5:30 (invalid).

Understand the failure class

Related errors


AI-assisted analysis of hashicorp/nomad@482b49bf1a (2026-09-04). Data as JSON: /api/errors/012d9051410d156a. Report an issue: GitHub.