t8y2/dbx · info

TDengine operation was cancelled

Error message

TDengine operation was cancelled

What it means

cancellable races a TDengine operation against a CancellationToken and the timeout. When the token fires before the operation completes, the driver aborts the await and returns 'TDengine operation was cancelled'. It is the driver's uniform cancellation signal, not a connector fault.

Source

Thrown at agents/drivers/tdengine/src/driver.rs:811

}

async fn cancellable<T, F>(token: &CancellationToken, timeout_secs: u64, future: F) -> Result<T>
where
    F: Future<Output = taos::RawResult<T>>,
{
    tokio::pin!(future);
    let operation = async {
        if timeout_secs == 0 {
            future.await.map_err(anyhow::Error::from)
        } else {
            timeout(Duration::from_secs(timeout_secs), future)
                .await
                .map_err(|_| anyhow!("TDengine operation timed out after {timeout_secs} seconds"))?
                .map_err(anyhow::Error::from)
        }
    };
    tokio::select! {
        _ = token.cancelled() => bail!("TDengine operation was cancelled"),
        result = operation => result,
    }
}

fn effective_database<'a>(requested: &'a str, current: &'a str) -> Result<&'a str> {
    let requested = requested.trim();
    if !requested.is_empty() {
        return validate_database_name(requested);
    }
    let current = current.trim();
    if current.is_empty() {
        bail!("TDengine database is required");
    }
    validate_database_name(current)
}

fn validate_database_name(value: &str) -> Result<&str> {
    let value = value.trim();

View on GitHub (pinned to c0390bff16)

Solutions

  1. Verify the cancellation was intended (shutdown/timeout) — this error usually means an upstream caller cancelled, so propagate it as cancelled, not retryable
  2. If it fires unexpectedly, audit shared tokens: ensure long queries get their own token not tied to short request lifecycles
  3. Retry with a fresh token if the operation must complete despite the earlier cancellation

Example fix

// before
let token = shared_request_token.clone();
driver.execute_query(&conn, sql, &token, 600).await?;
// after (don't tie long queries to short-lived request tokens)
let token = CancellationToken::new();
driver.execute_query(&conn, sql, &token, 600).await?;
Defensive patterns

Strategy: try-catch

Validate before calling

if token.is_cancelled() { return Err(anyhow!("already cancelled")); } // check before starting long ops

Try / catch

match driver.execute_query(&conn, sql, &token, timeout).await {
    Err(e) if e.to_string().contains("was cancelled") => {/* expected cancellation: log and return 499-style */},
    other => other,
}

Prevention

When it happens

Trigger: The caller's CancellationToken is cancelled while any wrapped operation is in flight — execute_statements, use_database, start_cursor, next_raw_row, query_scalar_string — e.g. a request timeout/shutdown triggers token.cancel().

Common situations: HTTP request aborted by the client, agent shutdown mid-query, or an outer timeout layer cancelling the shared token while a slow query runs.

Related errors


AI-assisted analysis of t8y2/dbx@c0390bff16 (2026-09-05). Data as JSON: /api/errors/136c66e483587435. Report an issue: GitHub.