# SurrealDB 2.3 Quick Start Guide **Status**: Production Ready ✅ **Version**: SurrealDB 2.3 **Updated**: November 15, 2025 This guide shows how to quickly get started with SurrealDB 2.3 in syntaxis with different deployment contexts. --- ## Quick Install & Run ### Option 1: Embedded In-Memory (Fastest, No Server) ```bash # No installation needed - uses embedded library # Update configs/database.toml: [surrealdb] url = "mem://" # In-memory database namespace = "syntaxis" database = "projects" ``` ```rust use workspace_core::SurrealDatabase; #[tokio::main] async fn main() -> Result<()> { // Create in-memory database let db = SurrealDatabase::new_memory().await?; // Start using database immediately let projects = db.list_projects().await?; println!("Projects: {}", projects.len()); Ok(()) } ``` ### Option 2: Embedded File-Based (Persistent, No Server) ```bash # Update configs/database.toml: [surrealdb] url = "file:///tmp/surrealdb.db" # RocksDB persistent storage namespace = "syntaxis" database = "projects" ``` ```rust let db = SurrealDatabase::new_file("/tmp/surrealdb.db").await?; ``` ### Option 3: Server Mode (Full Features, Requires Setup) #### Install SurrealDB ```bash # macOS brew install surrealdb # Linux/WSL cargo install surreal # Windows choco install surrealdb # Verify surreal version ``` #### Start Server ```bash # Simple in-memory server surreal start --bind 127.0.0.1:8000 memory # File-based with persistence surreal start --bind 127.0.0.1:8000 file:///tmp/surrealdb.db # With authentication surreal start \ --bind 127.0.0.1:8000 \ --username admin \ --password your_password \ file:///tmp/surrealdb.db ``` #### Connect from Application ```rust // Update configs/database.toml: // [surrealdb] // url = "ws://localhost:8000" // username = "admin" // password = "your_password" use workspace_core::SurrealDatabase; #[tokio::main] async fn main() -> Result<()> { let db = SurrealDatabase::new_server( "ws://localhost:8000", "syntaxis", "projects", Some("admin"), Some("your_password"), ).await?; Ok(()) } ``` --- ## Core Operations ### 1. Create a Project ```rust use workspace_core::{SurrealDatabase, DbProject}; use chrono::Utc; use uuid::Uuid; let db = SurrealDatabase::new_memory().await?; let project = DbProject { id: Uuid::new_v4().to_string(), name: "My Project".to_string(), version: "0.1.0".to_string(), description: "A SurrealDB project".to_string(), project_type: "MultiLang".to_string(), current_phase: "Creation".to_string(), created_at: Utc::now().to_rfc3339(), updated_at: Utc::now().to_rfc3339(), }; db.create_project(&project).await?; println!("✓ Project created: {}", project.id); ``` ### 2. Retrieve Projects ```rust // Get all projects let projects = db.list_projects().await?; println!("Total projects: {}", projects.len()); // Get specific project if let Some(project) = db.get_project(&project_id).await? { println!("Project: {} (Phase: {})", project.name, project.current_phase); } else { println!("Project not found"); } // Get projects by phase for project in &projects { if project.current_phase == "Development" { println!(" - {} (in Development)", project.name); } } ``` ### 3. Add Checklist Items ```rust use workspace_core::DbChecklistItem; let item = DbChecklistItem { id: Uuid::new_v4().to_string(), project_id: project.id.clone(), phase: "Creation".to_string(), task_id: "setup-1".to_string(), description: "Initialize project structure".to_string(), completed: false, completed_at: None, created_at: Utc::now().to_rfc3339(), task_type: "Setup".to_string(), task_priority: "High".to_string(), task_due: Some("2025-12-31".to_string()), task_estimation: Some("2d".to_string()), task_deps: "[]".to_string(), // Comma-separated IDs task_note: Some("Remember to test thoroughly".to_string()), task_name: Some("Setup".to_string()), }; db.create_checklist_item(&item).await?; println!("✓ Added checklist item"); ``` ### 4. Track Progress ```rust // Get checklist items for a phase let items = db.get_checklist_items_by_phase(&project_id, "Creation").await?; let completed = items.iter().filter(|i| i.completed).count(); println!("Progress: {}/{}", completed, items.len()); // Get completion percentage let percentage = db.get_completion_percentage(&project_id, "Creation").await?; println!("Phase completion: {:.1}%", percentage); ``` ### 5. Record Phase Transition ```rust use workspace_core::DbPhaseTransition; let transition = DbPhaseTransition { id: Uuid::new_v4().to_string(), project_id: project.id.clone(), from_phase: "Creation".to_string(), to_phase: "Development".to_string(), timestamp: Utc::now().to_rfc3339(), reason: Some("Initial setup complete".to_string()), }; db.record_phase_transition(&transition).await?; println!("✓ Phase transitioned: Creation → Development"); ``` ### 6. Security Assessment ```rust use workspace_core::DbSecurityAssessment; let assessment = DbSecurityAssessment { id: Uuid::new_v4().to_string(), project_id: project.id.clone(), profile: "OWASP".to_string(), risk_level: "Medium".to_string(), passed_rules: 45, failed_rules: 5, critical_issues: 0, assessment_date: Utc::now().to_rfc3339(), }; db.create_security_assessment(&assessment).await?; println!("✓ Security assessment recorded"); ``` --- ## Deployment Modes ### Mode 1: Development (In-Memory) ```bash # Perfect for: Testing, CI/CD, development without server # In Rust: let db = SurrealDatabase::new_memory().await?; # No setup needed! ``` **Pros**: - No server setup - Very fast - Perfect for testing **Cons**: - Data lost on restart - Single process only --- ### Mode 2: Local Development (File-Based) ```bash # For local development with persistence # Start server surreal start --bind 127.0.0.1:8000 file://~/.local/share/surrealdb.db # In configuration [surrealdb] url = "ws://localhost:8000" ``` **Pros**: - Persistent data - Can run alongside multiple processes - Full server features **Cons**: - Requires server running - Single machine only --- ### Mode 3: Docker (Development/Testing) ```bash # Start with Docker Compose docker-compose -f docker-compose.surrealdb.yml up -d # Check if running docker-compose logs surrealdb # Configuration [surrealdb] url = "ws://surrealdb:8000" # Container hostname username = "admin" password = "workspace_password_123" ``` **Pros**: - Isolated environment - Reproducible setup - Matches production **Cons**: - Requires Docker - Slightly more overhead --- ### Mode 4: Kubernetes (Production) ```bash # Deploy to Kubernetes cluster cd k8s && ./deploy.sh # Configuration [surrealdb] url = "ws://surrealdb.workspace:8000" # K8s service DNS username = "admin" password = "${SURREALDB_PASSWORD}" # From k8s secret tls_enabled = true ``` **Pros**: - Production-grade - Scalable - Managed infrastructure **Cons**: - Complex setup - Requires K8s knowledge --- ## Configuration Examples ### Example 1: Local Development **File**: `configs/database.toml` ```toml [database] engine = "surrealdb" [surrealdb] url = "mem://" # In-memory, no server needed namespace = "syntaxis" database = "projects" max_connections = 5 ``` ### Example 2: Docker Development **File**: `configs/database.toml` ```toml [database] engine = "surrealdb" [surrealdb] url = "ws://surrealdb:8000" username = "admin" password = "dev_password" namespace = "syntaxis" database = "projects" max_connections = 10 ``` ### Example 3: Production (Kubernetes) **File**: `configs/database.toml` ```toml [database] engine = "surrealdb" [surrealdb] url = "ws://surrealdb.workspace:8000" username = "admin" password = "${SURREALDB_PASSWORD}" # Environment variable namespace = "syntaxis" database = "projects" max_connections = 20 timeout_secs = 60 tls_enabled = true tls_ca_cert = "/etc/surrealdb/ca.pem" ``` --- ## Testing with SurrealDB ### In-Memory Tests ```rust #[tokio::test] async fn test_project_lifecycle() { // No setup needed - in-memory database let db = SurrealDatabase::new_memory().await.unwrap(); // Create project let project = DbProject { id: "test-1".to_string(), name: "Test Project".to_string(), // ... other fields ... }; let created = db.create_project(&project).await.unwrap(); assert_eq!(created.name, "Test Project"); // Verify retrieval let retrieved = db.get_project("test-1").await.unwrap(); assert!(retrieved.is_some()); } ``` ### Server-Mode Tests ```rust #[tokio::test] async fn test_with_server() { // Requires: surreal start --bind 127.0.0.1:8000 memory let db = SurrealDatabase::new_server( "ws://localhost:8000", "syntaxis", "projects", None, None, ).await.unwrap(); // Run your tests... } ``` ### File-Based Tests ```rust #[tokio::test] async fn test_persistence() { let db_path = "/tmp/test_surrealdb.db"; let db = SurrealDatabase::new_file(db_path).await.unwrap(); // Create data let project = DbProject { /* ... */ }; db.create_project(&project).await.unwrap(); // Reload and verify persistence let db2 = SurrealDatabase::new_file(db_path).await.unwrap(); let retrieved = db2.get_project(&project.id).await.unwrap(); assert!(retrieved.is_some()); } ``` --- ## Switching Between Backends ### SQLite to SurrealDB ```bash # Step 1: Update configuration # configs/database.toml - change engine from "sqlite" to "surrealdb" # Step 2: Start SurrealDB server surreal start --bind 127.0.0.1:8000 file:///data/surrealdb.db # Step 3: Run application with new config RUST_LOG=info cargo run # Step 4: Migration (if needed) # See: SURREALDB_2_3_MIGRATION.md ``` ### Quick Switching Script ```bash #!/bin/bash # Switch between database backends case "$1" in sqlite) echo "Switching to SQLite..." cp configs/database.toml configs/database.toml.backup cp configs/database-default.toml configs/database.toml echo "✓ Using SQLite" ;; surrealdb) echo "Switching to SurrealDB..." cp configs/database.toml configs/database.toml.backup cp configs/database-surrealdb.toml configs/database.toml echo "Starting SurrealDB server..." surreal start --bind 127.0.0.1:8000 memory & echo "✓ Using SurrealDB" ;; *) echo "Usage: $0 {sqlite|surrealdb}" ;; esac ``` --- ## Troubleshooting ### "Connection refused" Error ```bash # Check if SurrealDB is running ps aux | grep surreal # If not, start it surreal start --bind 127.0.0.1:8000 memory # Test connection curl http://localhost:8000/health # Should return: {"status":"ok"} ``` ### "Authentication failed" Error ```rust // Make sure credentials match server startup let db = SurrealDatabase::new_server( "ws://localhost:8000", "syntaxis", "projects", Some("admin"), // Must match --username Some("your_password"), // Must match --password ).await?; ``` ### "Database already in use" Error ```bash # Port 8000 is already in use # Use a different port surreal start --bind 127.0.0.1:8001 memory # Update configuration [surrealdb] url = "ws://localhost:8001" # New port ``` ### Slow Queries ```bash # Enable query logging surreal start --log debug --bind 127.0.0.1:8000 memory # Check output for slow queries in logs ``` --- ## Common Patterns ### Pattern 1: Batch Operations ```rust async fn create_multiple_items( db: &dyn Database, items: Vec, ) -> Result<()> { for item in items { db.create_checklist_item(&item).await?; } Ok(()) } ``` ### Pattern 2: Error Handling ```rust use workspace_core::error::LifecycleError; match db.get_project(&id).await { Ok(Some(project)) => println!("Found: {}", project.name), Ok(None) => println!("Project not found"), Err(LifecycleError::Database(msg)) => eprintln!("DB error: {}", msg), Err(e) => eprintln!("Other error: {}", e), } ``` ### Pattern 3: Configuration-Driven ```rust use workspace_core::DatabaseConfig; let config = DatabaseConfig::load_from_file("configs/database.toml")?; let db = match config.engine.as_str() { "surrealdb" => { let surreal_config = config.surrealdb.ok_or("No SurrealDB config")?; SurrealDatabase::new_server( &surreal_config.url, &surreal_config.namespace, &surreal_config.database, surreal_config.username, surreal_config.password, ).await? } "sqlite" => { // ... SQLite setup ... } _ => return Err("Unknown database engine".into()), }; ``` --- ## Performance Tips ### 1. Use Connection Pooling ```toml [surrealdb] max_connections = 20 # Tune based on load timeout_secs = 60 # Increase for slow networks ``` ### 2. Batch Operations ```rust // Good: Multiple operations for item in items { db.create_checklist_item(&item).await?; } // Could be optimized with batch API (if available) ``` ### 3. Index Critical Fields ```surreql -- In SurrealDB SQL DEFINE INDEX idx_project_phase ON TABLE projects COLUMNS current_phase; DEFINE INDEX idx_item_project ON TABLE checklist_items COLUMNS project_id; ``` --- ## Next Steps 1. **Choose Deployment Mode** - Development: `mem://` (in-memory, fastest) - Testing: `file://` (persistent, local) - Production: Server mode with Docker/K8s 2. **Configure Application** - Copy appropriate config template - Update `configs/database.toml` - Set environment variables if needed 3. **Test Connection** - Run: `cargo run -p syntaxis-cli` - Execute: `syntaxis-cli checklist show` - Verify: Data is being stored 4. **Learn More** - [SURREALDB_SETUP_GUIDE.md](SURREALDB_SETUP_GUIDE.md) - Detailed setup - [SURREALDB_2_3_MIGRATION.md](SURREALDB_2_3_MIGRATION.md) - Migration guide - [PERSISTENCE_QUICK_START.md](PERSISTENCE_QUICK_START.md) - Generic DB usage --- ## References - **Official**: https://surrealdb.com/ - **Docs**: https://surrealdb.com/docs - **GitHub**: https://github.com/surrealdb/surrealdb - **Docker**: https://hub.docker.com/r/surrealdb/surrealdb --- **Status**: ✅ Production Ready **Last Updated**: November 15, 2025 **SurrealDB Version**: 2.3