nautechsystems/nautilus_trader · error · anyhow::Error

GTD LIMIT requires expire_time

Error message

GTD LIMIT requires expire_time

What it means

This error is raised by `build_order_configuration` when a LIMIT order uses `TimeInForce::Gtd` (good-til-date) but no `expire_time` is provided. Coinbase's `LimitGtd` payload requires an `end_time`, so the adapter fails fast rather than submitting an order without an expiry. It indicates the order was marked GTD but the expiration timestamp was never set.

Source

Thrown at crates/adapters/coinbase/src/http/client.rs:1663

                    )
                }
            }
        }
        OrderType::Limit => {
            let limit_price =
                price.ok_or_else(|| anyhow::anyhow!("LIMIT order requires a price"))?;

            match time_in_force {
                TimeInForce::Gtc => Ok(OrderConfiguration::LimitGtc(LimitGtc {
                    limit_limit_gtc: LimitGtcParams {
                        base_size: qty,
                        limit_price,
                        post_only,
                    },
                })),
                TimeInForce::Gtd => {
                    let expire = expire_time
                        .ok_or_else(|| anyhow::anyhow!("GTD LIMIT requires expire_time"))?;
                    Ok(OrderConfiguration::LimitGtd(LimitGtd {
                        limit_limit_gtd: LimitGtdParams {
                            base_size: qty,
                            limit_price,
                            end_time: format_rfc3339_from_nanos(expire)?,
                            post_only,
                        },
                    }))
                }
                TimeInForce::Fok => Ok(OrderConfiguration::LimitFok(LimitFok {
                    limit_limit_fok: LimitFokParams {
                        base_size: qty,
                        limit_price,
                    },
                })),
                _ => anyhow::bail!("Unsupported TIF {time_in_force} for LIMIT on Coinbase"),
            }
        }

View on GitHub (pinned to 18893faf8b)

Solutions

  1. Set a valid `expire_time` (UnixNanos) when constructing the GTD LIMIT order.
  2. Fall back to TimeInForce::Gtc when no expiry is needed or available.
  3. Validate at the strategy/order-factory level that GTD orders always carry expire_time.
  4. Compute the expiry from a policy (e.g. session end or now + N hours) instead of leaving it unset.

Example fix

// before
let order = factory.limit(instrument_id, Buy, qty, price, TimeInForce::Gtd); // no expire_time
// after
let expire = factory.ts_now() + Duration::from_secs(8 * 3600).as_nanos() as u64;
let order = factory.limit_gtd(instrument_id, Buy, qty, price, expire);
Defensive patterns

Strategy: validation

Validate before calling

fn validate_gtd(tif: TimeInForce, expire_time: Option<UnixNanos>) -> Result<(), String> {
    match (tif, expire_time) {
        (TimeInForce::Gtd, None) => Err("GTD LIMIT requires expire_time".into()),
        _ => Ok(()),
    }
}

Try / catch

let tif = if expire_time.is_some() { TimeInForce::Gtd } else { TimeInForce::Gtc };
match build_order_configuration(OrderType::Limit, side, qty, price, None, tif, expire_time, post_only, false, false) {
    Ok(config) => submit(config),
    Err(e) if e.to_string().contains("expire_time") => { tracing::error!("GTD order without expiry"); Err(e) }
    Err(e) => return Err(e),
}

Prevention

When it happens

Trigger: Submitting a LIMIT order with time_in_force=Gtd and expire_time=None — e.g. a strategy selecting GTD without computing/passing the expiry timestamp (UnixNanos), or a default TIF of GTD applied without expiry configuration.

Common situations: Strategy configs where GTD is the default TIF but expiry is optional; end-of-session expiry logic that fails to set expire_time; porting GTD orders from venues where the exchange assigns a default expiry.

Understand the failure class

Background: "missing required argument" and "the following required arguments were not provided": what required-argument errors mean and how to fix them — this error's family across 20 libraries.

Related errors


AI-assisted analysis of nautechsystems/nautilus_trader@18893faf8b (2026-09-08). Data as JSON: /api/errors/79ee378dadd89a56. Report an issue: GitHub.