Durable workflows.
Compiled to native.

Run on bare metal, embedded devices or cloud.

native compilation

JSON workflows compile directly to native binaries. No interpreter overhead.

🔄

durable checkpoints

Snapshot execution state. Resume from any checkpoint. Survive crashes and restarts.

☁️

run anywhere

Deploy on dedicated servers, cloud VMs, or edge. Same runtime, any environment.

🔧

deterministic replay

Same inputs, same outputs. Debug and test with confidence.

main.rs
use runtara_sdk::{RuntaraSdk, durable};
use serde::{Deserialize, Serialize};

#[derive(Debug, Clone, Serialize, Deserialize)]
pub struct Order {
    pub id: String,
    pub customer_name: String,
    pub total: f64,
}

/// Fetch an order - first arg is idempotency key
#[durable]
pub async fn get_order(key: &str, order_id: &str) -> Result<Order, AppError> {
    tokio::time::sleep(Duration::from_millis(100)).await;
    Ok(Order {
        id: order_id.to_string(),
        customer_name: format!("Customer for ", order_id),
        total: 99.99,
    })
}

/// Process payment - idempotent via the key
#[durable]
pub async fn process_payment(key: &str, amount: f64) -> Result<String, AppError> {
    Ok(format!("txn-", Uuid::new_v4()))
}

#[tokio::main]
async fn main() -> Result<(), Box<dyn Error>> {
    RuntaraSdk::localhost("example-1", "demo")?
        .init(None).await?;

    // First call - executes and caches
    let order = get_order("order-123", "123").await?;

    // Second call with same key - returns cached
    let order2 = get_order("order-123", "123").await?;

    // Payment
    let txn = process_payment("pay-123", 99.99).await?;

    Ok(())
}
50x
faster execution
~1ms
per step
0
interpreter overhead