pola-rs/polars · error

activate one of {{'dtype-date', 'dtype-datetime', dtype-time

Error message

activate one of {{'dtype-date', 'dtype-datetime', dtype-time'}} features

What it means

infer_field_schema() converts date/time-looking CSV fields to Date/Datetime/Time dtypes, but only when the polars-time crate is compiled in - enabled via the dtype-date, dtype-datetime or dtype-time cargo features. In a build with none of them, the cfg(not(feature = "polars-time")) arm panics as soon as try_parse_dates is on and a quoted value reaches this branch (this is the quoted-field branch at line 330). Python builds always ship these features; only custom Rust builds can hit it.

Source

Thrown at crates/polars-io/src/csv/read/schema_inference.rs:353

            #[cfg(feature = "polars-time")]
            {
                match date_infer::infer_pattern_single(&string[1..string.len() - 1]) {
                    Some(pattern_with_offset) => match pattern_with_offset {
                        Pattern::DatetimeYMD | Pattern::DatetimeDMY => {
                            DataType::Datetime(TimeUnit::Microseconds, None)
                        },
                        Pattern::DateYMD | Pattern::DateDMY => DataType::Date,
                        Pattern::DatetimeYMDZ => {
                            DataType::Datetime(TimeUnit::Microseconds, Some(TimeZone::UTC))
                        },
                        Pattern::Time => DataType::Time,
                    },
                    None => DataType::String,
                }
            }
            #[cfg(not(feature = "polars-time"))]
            {
                panic!("activate one of {{'dtype-date', 'dtype-datetime', dtype-time'}} features")
            }
        } else {
            DataType::String
        }
    }
    // match regex in a particular order
    else if BOOLEAN_RE.is_match(string) {
        DataType::Boolean
    } else if !decimal_comma && FLOAT_RE.is_match(string)
        || decimal_comma && FLOAT_RE_DECIMAL.is_match(string)
    {
        DataType::Float64
    } else if INTEGER_RE.is_match(string) {
        if string.parse::<i64>().is_ok() {
            DataType::Int64
        } else {
            #[cfg(feature = "dtype-i128")]
            {

View on GitHub (pinned to 5d8ebabf11)

Solutions

  1. Add the features in Cargo.toml: polars-io = { version = "...", default-features = false, features = ["dtype-date", "dtype-datetime", "dtype-time"] } (or enable polars-time)
  2. If you depend on the umbrella polars crate, enable the same-named features there - they are additive and flow down
  3. Workaround: pass an explicit schema typing those columns as String, or set try_parse_dates=false, so inference never enters the temporal branch

Example fix

# before
polars-io = { version = "0.4", default-features = false }

# after
polars-io = { version = "0.4", default-features = false, features = [
  "dtype-date", "dtype-datetime", "dtype-time",
] }
Defensive patterns

Strategy: validation

Validate before calling

use polars_io::prelude::*;
use std::io::Cursor;

fn csv_temporal_inference_available() -> bool {
    // If the polars-time feature is off, date-like inference panics.
    // Probe once, cheaply, at startup:
    std::panic::catch_unwind(|| {
        let src = Cursor::new(b"d\n2024-01-31\n");
        CsvReader::new(src).with_try_parse_dates(true).finish()
    })
    .is_ok()
}
// if false -> fail startup with 'rebuild polars-io with dtype-date/dtype-datetime/dtype-time'

Try / catch

The panic is deterministic (missing compile-time feature): catch_unwind(AssertUnwindSafe(|| reader.finish())) can only downgrade it to an error message; the durable fix is Cargo features, not catching.

Prevention

When it happens

Trigger: read_csv with try_parse_dates=true (or any code path calling infer_field_schema) on a file whose quoted values look temporal (e.g. "\"2024-01-31\""), in a crate built with polars-io default-features=false and none of the dtype-date/dtype-datetime/dtype-time features.

Common situations: Slimming a Rust binary by trimming polars features; losing feature unification from a transitive dependency after an upgrade; porting working code from the python wheel (features always on) to a Rust service.

Related errors


AI-assisted analysis of pola-rs/polars@5d8ebabf11 (2026-08-19). Data as JSON: /api/errors/b02597f7cb284b08. Report an issue: GitHub.