influxdata/influxdb · error · Error

Invalid InfluxQL metadata

Error message

Invalid InfluxQL metadata: {0}

What it means

Error::InvalidMetadata wraps a serde_json::Error produced when deserializing InfluxQlMetadata from the Arrow schema metadata map. The metadata key exists but its JSON payload cannot be parsed into the expected struct (via #[from] serde_json::Error), so the formatter reports 'Invalid InfluxQL metadata: {0}'.

Solutions

  1. Log the raw metadata string and the inner serde_json error to see which field/shape mismatched
  2. Align client and server versions so InfluxQlMetadata serialization matches on both sides
  3. Fix the metadata JSON in test fixtures to match the InfluxQlMetadata struct (correct field names and types)
  4. Catch this variant and fall back to a plain formatter (csv/json) if you only need raw rows, not line protocol

Example fix

// before
// metadata: {"measurement": "cpu"} // missing required fields
let out = formatter.format(&batches)?;
// after
// metadata: {"measurement": "cpu", "tag_keys": ["host"], "field_keys": ["usage"]}
let out = formatter.format(&batches)?;
Defensive patterns

Strategy: try-catch

Validate before calling

fn metadata_is_valid_json(batches: &[RecordBatch], key: &str) -> bool {
    batches.first()
        .and_then(|b| b.schema().metadata().get(key))
        .map(|v| serde_json::from_str::<serde_json::Value>(v).is_ok())
        .unwrap_or(false)
}

Type guard

fn is_invalid_metadata(e: &influxql_format::Error) -> bool {
    matches!(e, influxql_format::Error::InvalidMetadata(_))
}

Try / catch

match formatter.format(&batches) {
    Err(influxql_format::Error::InvalidMetadata(src)) => {
        eprintln!("metadata JSON parse failed: {src}; falling back to csv");
        csv_formatter.format(&batches)?;
    }
    other => other?,
}

Prevention

When it happens

Trigger: Formatting batches whose schema metadata contains an InfluxQlMetadata value that is not valid JSON or does not match the InfluxQlMetadata struct fields — e.g., payload produced by an incompatible server version or manually written test metadata.

Common situations: Client and server version skew (metadata JSON schema changed between IOx releases); hand-crafting the metadata entry with wrong field names/types; metadata string corrupted by an intermediary proxy rewriting headers/annotations.

Understand the failure class

Background: "failed to unmarshal" / json.Unmarshal errors: why parsing a response into a Go struct fails and how to fix it — this error's family across 23 libraries.

Related errors


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

Appendix: source

Thrown at core/influxdb_iox_client/src/format/influxql.rs:24

use comfy_table::{Cell, Table};
use generated_types::influxdata::iox::querier::v1::InfluxQlMetadata;
use std::io::Write;
use std::iter;
use thiserror::Error;

/// Error type for results formatting
#[derive(Debug, Error)]
pub enum Error {
    /// Arrow error.
    #[error("Arrow error: {}", .0)]
    Arrow(ArrowError),

    /// [`InfluxQlMetadata`] not found in Arrow schema metadata.
    #[error("Missing InfluxQL metadata")]
    MissingMetadata,

    /// Error deserializing [`InfluxQlMetadata`] from Arrow schema metadata.
    #[error("Invalid InfluxQL metadata: {0}")]
    InvalidMetadata(#[from] serde_json::Error),

    /// Error writing formatted output.
    #[error("Error writing output: {0}")]
    Write(#[from] std::io::Error),
}
type Result<T, E = Error> = std::result::Result<T, E>;

/// Options for controlling how table borders are rendered.
#[derive(Debug, Default, Clone, Copy)]
pub enum TableBorders {
    /// Use ASCII characters.
    #[default]
    Ascii,
    /// Use UNICODE box-drawing characters.
    Unicode,
    /// Do not render borders.
    None,

View on GitHub (pinned to 06200ef96b)