apache/beam · warning

capacity must be a positive integer, got

Error message

capacity must be a positive integer, got %v

What it means

SideInputCache.Init(cap) prepares the side-input cache and its ID-to-token map. It returns this error for negative capacities; cap == 0 legitimately disables the cache, and positive values enable it. The message text says "must be a positive integer" but the guard checks cap < 0, so the actual invalid case is a negative value. Callers should only pass 0 (disabled) or a positive size.

Solutions

  1. Pass a positive integer capacity to enable caching, or 0 to explicitly disable it; never a negative value.
  2. If the value comes from config/env/flag, validate it is >= 0 before calling Init.
  3. Fix any sentinel usage: use 0 for disabled rather than -1.
  4. If this fires in stock harness startup, check the beam_go_sdk container/harness options for a corrupted cache-size option.
  5. Note the guard checks cap < 0 while the message says positive — zero is accepted as disabled; don't rely on the message text for the exact boundary.

Example fix

// before
var cacheSize int = -1 // "unlimited" sentinel
cache.Init(cacheSize)
// after
cacheSize := 0 // 0 disables the cache explicitly; use >0 to enable
if cacheSize < 0 {
    return fmt.Errorf("invalid state cache capacity %d", cacheSize)
}
if err := cache.Init(cacheSize); err != nil {
    return err
}
Defensive patterns

Strategy: validation

Validate before calling

func validCacheCapacity(n int) bool {
    return n >= 0 // 0 disables the cache; positive enables it; negative is invalid
}

Try / catch

if err := cache.Init(capacity); err != nil {
    if strings.Contains(err.Error(), "capacity must be a positive integer") {
        return fmt.Errorf("bad state cache config: %v", err)
    }
    return err
}

Prevention

When it happens

Trigger: Calling Init with a negative capacity, e.g. a cache size parsed from an env var or flag with a sign/format problem, or a caller passing -1 as an "unlimited" sentinel.

Common situations: Setting the harness cache size via environment/flags where a value like "-1" leaks through parsing; custom harness wiring passes a negative sentinel expecting unlimited; unit-test configs exercising bad-input cases (TestInit_Bad).

Understand the failure class

Background: "Must be a positive integer", "Invalid value", "Unsupported": the invalid-argument-value error family, when a library rejects the value you pass — this error's family across 35 libraries.

Related errors


AI-assisted analysis of apache/beam@12126d8942 (2026-09-13). Data as JSON: /api/errors/3d48b730366c3d5e. Report an issue: GitHub.

Appendix: source

Thrown at sdks/go/pkg/beam/core/runtime/harness/statecache/statecache.go:77

	enabled     bool
	mu          sync.Mutex
	cache       map[cacheKey]exec.ReStream
	idsToTokens map[string]token
	validTokens map[cacheToken]int8 // Maps tokens to active bundle counts
	metrics     CacheMetrics
}

// CacheMetrics stores metrics for the cache across a pipeline run.
type CacheMetrics struct {
	Hits, Misses, Evictions, InUseEvictions, ReStreamErrors int64
}

// Init makes the cache map and the map of IDs to cache tokens for the
// SideInputCache. Should only be called once. Returns an error for
// non-positive capacities.
func (c *SideInputCache) Init(cap int) error {
	if cap < 0 {
		return errors.Errorf("capacity must be a positive integer, got %v", cap)
	}
	c.mu.Lock()
	defer c.mu.Unlock()
	if cap == 0 {
		c.enabled = false
		return nil
	}
	c.cache = make(map[cacheKey]exec.ReStream, cap)
	c.idsToTokens = make(map[string]token)
	c.validTokens = make(map[cacheToken]int8)
	c.capacity = cap
	c.metrics = CacheMetrics{}
	c.enabled = true
	return nil
}

// SetValidTokens clears the list of valid tokens then sets new ones, also updating the mapping of
// transform and side input IDs to cache tokens in the process. Should be called at the start of every

View on GitHub (pinned to 12126d8942)