Skip to content

Locy Use Case: Infrastructure Blast Radius (Rust)

Compute transitive downstream impact from a failing upstream service.

This notebook uses schema-first mode and mirrors the Python flow using the Rust API (uni_db).

How To Read This Notebook

  • Define schema first, then load data.
  • Keep Locy rules declarative and focused.
  • Read output rows together with materialization stats.

1) Setup

Initialize an in-memory database and import DataType for schema definitions.

use uni_db::{DataType, Uni, Result};

let db = Uni::in_memory().build().await?;

Define labels, typed properties, and edge types before inserting graph facts.

db.schema()
    .label("Service")
        .property("name", DataType::String)
    .edge_type("CALLS", &["Service"], &["Service"])
    .apply()
    .await?;

println!("Schema created");

3) Seed Graph Data

Insert the minimal graph needed for the scenario.

let session = db.session();
let tx = session.tx().await?;
tx.execute("CREATE (:Service {name: 'api'})").await?;
tx.execute("CREATE (:Service {name: 'gateway'})").await?;
tx.execute("CREATE (:Service {name: 'worker'})").await?;
tx.execute("CREATE (:Service {name: 'db'})").await?;
tx.execute("CREATE (:Service {name: 'cache'})").await?;
tx.execute("MATCH (a:Service {name:'api'}), (g:Service {name:'gateway'}) CREATE (a)-[:CALLS]->(g)").await?;
tx.execute("MATCH (g:Service {name:'gateway'}), (w:Service {name:'worker'}) CREATE (g)-[:CALLS]->(w)").await?;
tx.execute("MATCH (w:Service {name:'worker'}), (d:Service {name:'db'}) CREATE (w)-[:CALLS]->(d)").await?;
tx.execute("MATCH (w:Service {name:'worker'}), (c:Service {name:'cache'}) CREATE (w)-[:CALLS]->(c)").await?;
tx.commit().await?;
println!("Seeded graph data");

4) Locy Program

Rules derive relations, then QUERY ... WHERE ... RETURN ... projects the final answer.

let program = r#"CREATE RULE impacts AS\nMATCH (a:Service)-[:CALLS]->(b:Service)\nYIELD KEY a, KEY b\n\nCREATE RULE impacts AS\nMATCH (a:Service)-[:CALLS]->(mid:Service)\nWHERE mid IS impacts TO b\nYIELD KEY a, KEY b\n\nQUERY impacts WHERE a.name = 'api' RETURN b.name AS impacted_service"#;

5) Evaluate

Evaluate the Locy program and inspect stats/rows.

let session = db.session();
let result = session.locy(program).await?;
println!("Derived relations: {:?}", result.derived.keys().collect::<Vec<_>>());
println!("Iterations: {}", result.stats().total_iterations);
println!("Queries executed: {}", result.stats().queries_executed);
for (name, rows) in &result.derived {
    println!("{}: {} row(s)", name, rows.len());
}

if let Some(rows) = result.rows() {
    println!("Rows: {:?}", rows);
}

6) What To Expect

Use these checks to validate output after evaluation: - For api, impacted services should include gateway, worker, db, and cache. - Rows should represent transitive reachability, not only direct neighbors. - This pattern is useful for outage simulation and dependency triage.

Notes

  • Rust notebooks are included for API parity and learning.
  • In this docs build, Rust notebooks are rendered without execution.