gastownhall/beads · error

key cannot be only whitespace

Error message

key cannot be only whitespace

What it means

validateKVKey trims the key; if only whitespace remains (spaces, tabs, newlines) the key is functionally meaningless in the store, so the CLI rejects it. This catches keys that pass a naive `key == ""` check but are still unusable.

Source

Thrown at cmd/bd/kv.go:25

	"strings"

	"github.com/spf13/cobra"

	"github.com/steveyegge/beads/internal/metrics"
	"github.com/steveyegge/beads/internal/storage/kvkeys"
)

// kvPrefix is prepended to all user keys to separate them from internal config
const kvPrefix = kvkeys.Prefix

// validateKVKey checks if a key is valid for the KV store.
// Returns an error if the key is invalid.
func validateKVKey(key string) error {
	if key == "" {
		return fmt.Errorf("key cannot be empty")
	}
	if strings.TrimSpace(key) == "" {
		return fmt.Errorf("key cannot be only whitespace")
	}
	// Prevent keys that would create nested kv.kv.* prefixes
	if strings.HasPrefix(key, kvPrefix) {
		return fmt.Errorf("key cannot start with 'kv.' (would create nested prefix)")
	}
	// Reserve the persistent-memory namespace: a generic memory.* key would
	// store to kv.memory.*, indistinguishable from a `bd remember` memory, and
	// the merge resolver auto-resolves kv.memory.* conflicts with --theirs
	// (GH#2474). Without this guard a user's deliberate kv value could be
	// silently overridden by a remote on pull. Keep the namespace owned by
	// bd remember / bd forget.
	if strings.HasPrefix(key, kvkeys.MemoryPrefix) {
		return fmt.Errorf("key cannot start with %q (reserved for persistent memories; use 'bd remember' / 'bd forget')", kvkeys.MemoryPrefix)
	}
	// Prevent keys that look like internal config
	if strings.HasPrefix(key, "sync.") || strings.HasPrefix(key, "conflict.") ||
		strings.HasPrefix(key, "federation.") || strings.HasPrefix(key, "jira.") ||
		strings.HasPrefix(key, "linear.") || strings.HasPrefix(key, "export.") ||

View on GitHub (pinned to 71377f2769)

Solutions

  1. Trim the key before passing it: bd kv set "$(echo "$KEY" | xargs)" value or similar.
  2. Re-run with a key containing at least one non-whitespace character.
  3. Inspect the key with `printf '%q' "$KEY"` in bash to reveal hidden whitespace.

Example fix

// before
bd kv set "  " "v"   // rejected
// after
bd kv set "settings.timeout" "30"
Defensive patterns

Strategy: validation

Validate before calling

case "$KEY" in *[![:space:]]*) bd kv set "$KEY" "$VALUE";; *) echo "key must contain non-whitespace" >&2; exit 1;; esac

Prevention

When it happens

Trigger: Calling `bd kv set " " value` or any key consisting solely of whitespace characters through the kv set path.

Common situations: Copy-pasting a key with trailing spaces; shell scripts building keys from padded output of another command (`$(...)` results containing newlines).

Related errors


AI-assisted analysis of gastownhall/beads@71377f2769 (2026-08-30). Data as JSON: /api/errors/c91f427756c01f17. Report an issue: GitHub.