//! Osiris Engine Example //! //! This example demonstrates how to: //! 1. Create an Osiris Rhai engine with all registered functions //! 2. Execute Rhai scripts using the actual Osiris API //! 3. Test context creation, save, get, list, delete operations //! //! Run with: cargo run --example engine -p runner-osiris use rhai::{Dynamic, Map}; // Import the actual engine creation function mod engine_impl { include!("../src/engine.rs"); } use engine_impl::create_osiris_engine; #[tokio::main] async fn main() -> Result<(), Box> { println!("šŸš€ Osiris Engine Example\n"); println!("==========================================\n"); // Create the engine with all Osiris functions registered let mut engine = create_osiris_engine()?; // Set up context tags (simulating what the runner does) let mut tag_map = Map::new(); let signatories: rhai::Array = vec![ Dynamic::from("pk1".to_string()), Dynamic::from("pk2".to_string()), ]; tag_map.insert("SIGNATORIES".into(), Dynamic::from(signatories)); tag_map.insert("CALLER_ID".into(), "test-caller".to_string().into()); tag_map.insert("CONTEXT_ID".into(), "test-context".to_string().into()); engine.set_default_tag(Dynamic::from(tag_map)); // Test 1: Simple Rhai script println!("šŸ“ Test 1: Simple Rhai Script"); let script = r#" let x = 10; let y = 20; x + y "#; match engine.eval::(script) { Ok(result) => println!(" āœ“ Result: {}\n", result), Err(e) => println!(" āœ— Error: {}\n", e), } // Test 2: Get context (Osiris function) println!("šŸ“ Test 2: Get Context"); let context_script = r#" // Get context with participants (must be signatories) let ctx = get_context(["pk1", "pk2"]); ctx.context_id() "#; match engine.eval::(context_script) { Ok(result) => println!(" āœ“ Context ID: {}\n", result), Err(e) => println!(" āœ— Error: {}\n", e), } // Test 3: Create a Note and save it println!("šŸ“ Test 3: Create and Save a Note"); let note_script = r#" let ctx = get_context(["pk1"]); // Use the builder-style API let my_note = note("test-note-123") .title("Test Note") .content("This is a test note"); ctx.save(my_note); "Note saved successfully" "#; match engine.eval::(note_script) { Ok(result) => println!(" āœ“ {}\n", result), Err(e) => println!(" āœ— Error: {}\n", e), } // Test 4: Get from collection println!("šŸ“ Test 4: Get from Collection"); let get_script = r#" let ctx = get_context(["pk1"]); // Try to get a note (will fail if doesn't exist, but shows the API works) ctx.get("notes", "test-note-123") "#; match engine.eval::(get_script) { Ok(result) => println!(" āœ“ Result: {:?}\n", result), Err(e) => println!(" ⚠ Error (expected if note doesn't exist): {}\n", e), } // Test 5: List from collection println!("šŸ“ Test 5: List from Collection"); let list_script = r#" let ctx = get_context(["pk1"]); // List all notes in the context ctx.list("notes") "#; match engine.eval::(list_script) { Ok(result) => println!(" āœ“ Result: {:?}\n", result), Err(e) => println!(" ⚠ Error: {}\n", e), } // Test 6: Delete from collection println!("šŸ“ Test 6: Delete from Collection"); let delete_script = r#" let ctx = get_context(["pk1"]); // Try to delete a note ctx.delete("notes", "test-note-123") "#; match engine.eval::(delete_script) { Ok(result) => println!(" āœ“ Result: {:?}\n", result), Err(e) => println!(" ⚠ Error (expected if note doesn't exist): {}\n", e), } // Test 7: Create an Event println!("šŸ“ Test 7: Create and Save an Event"); let event_script = r#" let ctx = get_context(["pk1"]); // event() takes (namespace, title) in the module version let my_event = event("test-event-123", "Test Event") .description("This is a test event"); ctx.save(my_event); "Event saved successfully" "#; match engine.eval::(event_script) { Ok(result) => println!(" āœ“ {}\n", result), Err(e) => println!(" āœ— Error: {}\n", e), } // Test 8: Create a User (HeroLedger) println!("šŸ“ Test 8: Create and Save a User"); let user_script = r#" let ctx = get_context(["pk1"]); let my_user = new_user() .username("testuser") .add_email("test@example.com") .pubkey("pk1"); ctx.save(my_user); "User saved successfully" "#; match engine.eval::(user_script) { Ok(result) => println!(" āœ“ {}\n", result), Err(e) => println!(" āœ— Error: {}\n", e), } // Test 9: Create a Group (HeroLedger) println!("šŸ“ Test 9: Create and Save a Group"); let group_script = r#" let ctx = get_context(["pk1"]); let my_group = new_group() .name("Test Group") .description("A test group"); ctx.save(my_group); "Group saved successfully" "#; match engine.eval::(group_script) { Ok(result) => println!(" āœ“ {}\n", result), Err(e) => println!(" āœ— Error: {}\n", e), } // Test 10: List users println!("šŸ“ Test 10: List Users from Collection"); let list_users_script = r#" let ctx = get_context(["pk1"]); ctx.list("users") "#; match engine.eval::(list_users_script) { Ok(result) => println!(" āœ“ Users: {:?}\n", result), Err(e) => println!(" ⚠ Error: {}\n", e), } println!("=========================================="); println!("šŸŽ‰ All tests completed!\n"); println!("šŸ“š Available Object Types:"); println!(" - Note: note(id).title(...).content(...)"); println!(" - Event: event(id, title).description(...)"); println!(" - User: new_user().username(...).add_email(...).pubkey(...)"); println!(" - Group: new_group().name(...).description(...)"); println!(" - Account: new_account()..."); println!(" - And many more: KycSession, FlowTemplate, FlowInstance, Contract, etc."); println!("\nšŸ“– Available Operations:"); println!(" - ctx.save(object) - Save an object"); println!(" - ctx.get(collection, id) - Get an object by ID"); println!(" - ctx.list(collection) - List all objects in collection"); println!(" - ctx.delete(collection, id) - Delete an object"); Ok(()) }