headroomlabs-ai/headroom · error · ValueError

cache_max_size must be positive, got {self.cache_max_size}

Error message

cache_max_size must be positive, got {self.cache_max_size}

What it means

ValueError raised in MemoryConfig.__post_init__ when cache_max_size < 1. The memory system keeps an in-memory result/entry cache bounded by this size; a zero or negative bound is invalid (and would silently disable caching, which the config forbids), so it fails at construction.

Source

Thrown at headroom/memory/config.py:151

    def __post_init__(self) -> None:
        """Validate configuration after initialization."""
        if self.vector_dimension < 1:
            raise ValueError(f"vector_dimension must be positive, got {self.vector_dimension}")

        if self.hnsw_ef_construction < 1:
            raise ValueError(
                f"hnsw_ef_construction must be positive, got {self.hnsw_ef_construction}"
            )

        if self.hnsw_m < 1:
            raise ValueError(f"hnsw_m must be positive, got {self.hnsw_m}")

        if self.hnsw_ef_search < 1:
            raise ValueError(f"hnsw_ef_search must be positive, got {self.hnsw_ef_search}")

        if self.cache_max_size < 1:
            raise ValueError(f"cache_max_size must be positive, got {self.cache_max_size}")

        if self.embedder_backend == EmbedderBackend.OPENAI and not self.openai_api_key:
            raise ValueError("openai_api_key is required when using OpenAI embedder backend")

        # Ensure db_path is a Path object
        if isinstance(self.db_path, str):
            self.db_path = Path(self.db_path)

View on GitHub (pinned to 322425c43b)

Solutions

  1. Use cache_max_size=1 as the smallest legal cache if you want it effectively off, or a realistic bound like 1000
  2. To disable caching entirely, set cache_enabled=False instead of zeroing the size
  3. Validate derived size computations (e.g. int(mem * ratio)) with a floor of 1

Example fix

# before
cfg = MemoryConfig(cache_max_size=0)  # ValueError: cache_max_size must be positive

# after
cfg = MemoryConfig(cache_enabled=False)  # actually disable caching
cfg = MemoryConfig(cache_max_size=1000)  # or size it properly
Defensive patterns

Strategy: validation

Validate before calling

# want caching off? use the enabled flag, not size 0
if not want_cache:
    cfg = MemoryConfig(cache_enabled=False)
else:
    size = max(1, int(cache_size))  # floor at 1
    cfg = MemoryConfig(cache_enabled=True, cache_max_size=size)

Type guard

def is_valid_cache_size(v) -> bool:
    return isinstance(v, int) and not isinstance(v, bool) and v >= 1

Try / catch

try:
    cfg = MemoryConfig(cache_max_size=size)
except ValueError:
    cfg = MemoryConfig(cache_max_size=1000)

Prevention

When it happens

Trigger: MemoryConfig(cache_max_size=0) — frequently an intentional attempt to disable the cache that the config rejects; or a negative value from arithmetic on another setting.

Common situations: Trying to turn caching off for benchmarking by setting size 0; configs where '0' is the sentinel for 'unset'; cache sizing derived from machine specs producing 0 on tiny instances.

Related errors


AI-assisted analysis of headroomlabs-ai/headroom@322425c43b (2026-08-15). Data as JSON: /api/errors/40ccbf8eb90b7c95. Report an issue: GitHub.