influxdata/influxdb · error · PluginError

schedule duration cannot be greater than 1 year

Error message

schedule duration cannot be greater than 1 year

What it means

This error is thrown when a trigger is created with an `Every { duration }` schedule whose interval exceeds one year. The check exists to prevent arithmetic overflow when computing the next trigger time in milliseconds. The trigger specification is rejected at construction time via `TriggerSpecificationDefinition::try_new`, so the trigger is never registered.

Solutions

  1. Reduce the EVERY interval to 1 year or less (e.g. `EVERY 365d`).
  2. Use a `cron` schedule expression instead for very long intervals — cron schedules don't have this one-year cap.
  3. If sub-second precision isn't needed and the goal is a one-shot job, use a cron expression that fires on the desired date instead of a huge EVERY duration.

Example fix

// before
CREATE TRIGGER "long" ON db PROCESSING ENGINE PLUGIN my_plugin AT EVERY 2 years
// after
CREATE TRIGGER "long" ON db PROCESSING ENGINE PLUGIN my_plugin AT cron '0 0 1 1 *'
Defensive patterns

Strategy: validation

Validate before calling

// Rust: before creating the trigger
let max = parse_duration("1 year").unwrap();
assert!(requested_duration <= max, "EVERY duration must be <= 1 year; use cron for longer");

Prevention

When it happens

Trigger: Creating a trigger with `CREATE TRIGGER ... EVERY <duration>` where the parsed duration is greater than `parse_duration("1 year")`, e.g. `EVERY 2 years` or `EVERY 400d`.

Common situations: Misconfigured cron replacements where a developer wants a long-lived trigger and assumes arbitrary intervals are allowed; using duration strings like '2y' in the EVERY clause; copy-pasted configs from other schedulers with unlimited intervals.

Understand the failure class

Background: "value must be between 0 and 1" / "out of range" / "must not be negative" errors: fixing range-validation failures across open-source libraries — this error's family across 42 libraries.

Related errors


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

Appendix: source

Thrown at influxdb3_processing_engine/src/plugins.rs:185

        time_provider: Arc<dyn TimeProvider>,
    ) -> Result<Self, PluginError> {
        match trigger_spec {
            TriggerSpecificationDefinition::AllTablesWalWrite
            | TriggerSpecificationDefinition::SingleTableWalWrite { .. } => {
                Err(anyhow!("shouldn't have table trigger for scheduled plugin").into())
            }
            TriggerSpecificationDefinition::RequestPath { .. } => {
                Err(anyhow!("shouldn't have request path trigger for scheduled plugin").into())
            }
            TriggerSpecificationDefinition::Schedule { schedule } => {
                let schedule = CronSchedule::from_str(schedule.as_str())
                    .context("cron schedule should be parsable")?;
                Ok(Self::new_cron(schedule, time_provider))
            }
            TriggerSpecificationDefinition::Every { duration } => {
                // check that duration isn't longer than a year, so we avoid overflows.
                if *duration > parse_duration("1 year").unwrap() {
                    return Err(anyhow!("schedule duration cannot be greater than 1 year").into());
                }
                Ok(Self::new_every(
                    Duration::from_std(*duration)
                        .context("should be able to convert durations. ")?,
                    time_provider,
                ))
            }
        }
    }

    fn new_cron(cron_schedule: CronSchedule, time_provider: Arc<dyn TimeProvider>) -> Self {
        let mut schedule = Box::new(cron_schedule.after_owned(time_provider.now().date_time()));
        let next_trigger_time = schedule.next();
        Self {
            schedule: Schedule::Cron(schedule),
            next_trigger_time,
        }
    }

View on GitHub (pinned to 06200ef96b)