quickwit-oss/tantivy · error

dictionary missing for str accessor

Error message

dictionary missing for str accessor

What it means

precompute_term_ord needs the term dictionary of a str column to compute term ordinals for composite aggregation buckets, and it .expect()s that the optional StrColumn is present. When str_dict_column is None, the process panics with "dictionary missing for str accessor". This means the accessor was built for a field that turned out to have no string dictionary column, violating the assumption made when constructing it.

Source

Thrown at src/aggregation/bucket/composite/accessors.rs:455

            .downcast_arc::<CompactSpaceU64Accessor>()
            .map_err(|_| {
                TantivyError::AggregationError(crate::aggregation::AggregationError::InternalError(
                    "type mismatch: could not downcast to CompactSpaceU64Accessor".to_string(),
                ))
            })?;
        let ip_u128 = key.to_bits();
        let ip_next_compact = compact_space_accessor.u128_to_next_compact(ip_u128);
        Ok(ip_next_compact.into())
    }

    fn precompute_term_ord(
        str_dict_column: &Option<StrColumn>,
        key: &str,
        field: &str,
    ) -> crate::Result<Self> {
        let dict = str_dict_column
            .as_ref()
            .expect("dictionary missing for str accessor")
            .dictionary();
        let next_ord = dict.term_ord_or_next(key).map_err(|_| {
            TantivyError::InvalidArgument(format!(
                "failed to lookup after_key '{}' for field '{}'",
                key, field
            ))
        })?;
        Ok(next_ord.into())
    }

    /// Projects the after key into the column space of the given accessor.
    ///
    /// The computed after key will not take care of skipping entire columns
    /// when the after key type is ordered after the accessor's type, that
    /// should be performed earlier.
    pub fn precompute(
        composite_accessor: &CompositeAccessor,
        source_after_key: &CompositeIntermediateKey,

View on GitHub (pinned to b5d8deb80c)

Solutions

  1. Verify the field exists in the schema as a str/keyword column with a dictionary and correct any field-name typos.
  2. Guard the code: return a TantivyError (e.g. InvalidArgument "field has no dictionary") instead of expect when str_dict_column is None.
  3. Re-index the data so all segments include the str dictionary for the field.
  4. Filter out segments/fields lacking a dictionary before precompute_term_ord is called.

Example fix

// before
let dict = str_dict_column.as_ref().expect("dictionary missing for str accessor").dictionary();
// after
let dict = str_dict_column.as_ref()
    .ok_or_else(|| TantivyError::InvalidArgument(format!("field '{}' has no str dictionary", field)))?
    .dictionary();
Defensive patterns

Strategy: validation

Validate before calling

// Ensure the field has a str dictionary column before precompute
if accessor.str_dict_column().is_none() {
    return Err(TantivyError::InvalidArgument(format!(
        "field '{}' has no str dictionary; cannot precompute term ords", field
    )));
}

Type guard

fn has_str_dictionary(str_dict_column: &Option<StrColumn>) -> bool {
    str_dict_column.is_some()
}

Prevention

When it happens

Trigger: Running the composite aggregation precompute on a field whose dictionary column is absent: field missing from the segment, field is not a str/keyword column (numeric or text-only), or the segment was built without dictionary for that field.

Common situations: Aggregating on a field not indexed as keyword/str; querying segments written before the field existed; typo in field name leading to fallback columns without dictionaries; mixed-type field across segments.

Related errors


AI-assisted analysis of quickwit-oss/tantivy@b5d8deb80c (2026-09-05). Data as JSON: /api/errors/72de50ec15718a17. Report an issue: GitHub.