influxdata/influxdb · error · InvalidKeyError

key cannot be empty

Error message

{key_type} key cannot be empty

What it means

LineBuilder._validate_key enforces that tag keys and field keys are non-empty and free of spaces, commas, and equals signs, since those characters are line-protocol delimiters and would corrupt the generated point. The first check raises InvalidKeyError with '{key_type} key cannot be empty' when an empty string is passed as a tag or field key.

Solutions

  1. Check key length before calling the setter and skip/error on empty keys.
  2. Fix the source of the empty name (bad split, missing dict entry, blank config value).
  3. Provide a default key name when the dynamic key is unavailable.

Example fix

# before
for k, v in tags.items():
    lb.tag(k, v)
# after
for k, v in tags.items():
    if not k:
        continue
    lb.tag(k, v)
Defensive patterns

Strategy: validation

Validate before calling

def safe_tag(lb, key: str, value: str):
    if not isinstance(key, str) or not key:
        raise ValueError("tag key must be a non-empty string")
    lb.tag(key, value)

Type guard

def is_valid_key(k) -> bool:
    return isinstance(k, str) and len(k) > 0 and not any(c in k for c in " ,=")

Try / catch

try:
    lb.tag(key, value)
except InvalidKeyError as e:
    log.warning(f"skipping invalid key: {e}")

Prevention

When it happens

Trigger: Calling lb.tag("", "v") or any field setter (uint64_field/int64_field/float64_field/string_field/bool_field) with an empty key string — typically when the key comes from a dict lookup, split result, or variable that ends up as ''.

Common situations: Dynamic tag/field names built from parsed input where a segment is missing (e.g. 'cpu,=val'.split(',') behavior, dict.get returning ''), or configuration entries with blank names.

Understand the failure class

Background: "must not be empty", "cannot be empty" — required-field validation errors across open-source libraries — this error's family across 41 libraries.

Related errors


AI-assisted analysis of influxdata/influxdb@06200ef96b (2026-09-19). Data as JSON: /api/errors/f2fdb97be1c957e6. Report an issue: GitHub.

Appendix: source

Thrown at influxdb3_py_api/src/line_builder/line_builder.py:41

class InvalidLineError(InfluxDBError):
    """Raised when a line protocol string is invalid"""

    pass


class LineBuilder:
    def __init__(self, measurement: str):
        if " " in measurement:
            raise InvalidMeasurementError("Measurement name cannot contain spaces")
        self.measurement = measurement
        self.tags: OrderedDict[str, str] = OrderedDict()
        self.fields: OrderedDict[str, str] = OrderedDict()
        self._timestamp_ns: Optional[int] = None

    def _validate_key(self, key: str, key_type: str) -> None:
        """Validate that a key does not contain spaces, commas, or equals signs."""
        if not key:
            raise InvalidKeyError(f"{key_type} key cannot be empty")
        if " " in key:
            raise InvalidKeyError(f"{key_type} key '{key}' cannot contain spaces")
        if "," in key:
            raise InvalidKeyError(f"{key_type} key '{key}' cannot contain commas")
        if "=" in key:
            raise InvalidKeyError(f"{key_type} key '{key}' cannot contain equals signs")

    def _escape_measurement(self, value: str) -> str:
        """Escape characters in measurement names according to line protocol."""
        return value.replace(",", "\\,").replace(" ", "\\ ")

    def _escape_tag_value(self, value: str) -> str:
        """Escape characters in tag values according to line protocol."""
        return (
            value.replace("\\", "\\\\")
            .replace(",", "\\,")
            .replace("=", "\\=")
            .replace(" ", "\\ ")

View on GitHub (pinned to 06200ef96b)