[{"data":1,"prerenderedAt":-1},["ShallowReactive",2],{"skill:01M6JVCAPQCCP58F1N7ESBKJQ5":3,"skill-same:01M6JVCAPQCCP58F1N7ESBKJQ5":62},{"skillNo":4,"name":5,"nameZh":6,"description":7,"descriptionZh":6,"repositoryFullName":8,"ownerLogin":9,"ownerAvatarUrl":10,"ownerAccountNo":11,"ownerDisplayName":12,"repositoryNo":13,"starsCount":14,"licenseSpdxId":15,"licenseFileUrl":6,"sourceHtmlUrl":16,"categories":17,"keywords":18,"publishedAt":32,"linkOnly":33,"markdownContent":34,"markdownBody":35,"frontMatter":36,"refName":38,"commitSha":39,"skillDirectory":40,"forksCount":41,"repositoryHtmlUrl":42,"repositoryHomepageUrl":43,"ownerHtmlUrl":44,"ownerBlogUrl":45,"ownerDescription":46,"updatedAt":47,"install":48,"resources":61},"01M6JVCAPQCCP58F1N7ESBKJQ5","rust-patterns",null,"Idiomatic Rust patterns, ownership, error handling, traits, concurrency, and best practices for building safe, performant applications.","hashgraph-online\u002Fawesome-codex-plugins","hashgraph-online","https:\u002F\u002Favatars.githubusercontent.com\u002Fu\u002F160371962?v=4","01M6CNB6NRJVNNGN14TR01Q6D3","HOL (Hashgraph Online)","01M6JT1HSKKG9V68KQAQGBA7XP",1559,"Apache-2.0","https:\u002F\u002Fgithub.com\u002Fhashgraph-online\u002Fawesome-codex-plugins\u002Fblob\u002Fmain\u002Fplugins\u002FColin4k1024\u002Ftsp\u002Fskills\u002Frust-patterns\u002FSKILL.md",[],[19,20,21,22,23,24,25,26,27,28,29,30,31],"rust","rust patterns","patterns","safe","error handling","best practices","concurrency","applications","error","traits","ownership","for","idiomatic","2026-11-10 10:12:30",false,"---\nname: rust-patterns\ndescription: Idiomatic Rust patterns, ownership, error handling, traits, concurrency, and best practices for building safe, performant applications.\norigin: ECC\n---\n\n# Rust Development Patterns\n\nIdiomatic Rust patterns and best practices for building safe, performant, and maintainable applications.\n\n## When to Use\n\n- Writing new Rust code\n- Reviewing Rust code\n- Refactoring existing Rust code\n- Designing crate structure and module layout\n\n## How It Works\n\nThis skill enforces idiomatic Rust conventions across six key areas: ownership and borrowing to prevent data races at compile time, `Result`\u002F`?` error propagation with `thiserror` for libraries and `anyhow` for applications, enums and exhaustive pattern matching to make illegal states unrepresentable, traits and generics for zero-cost abstraction, safe concurrency via `Arc\u003CMutex\u003CT>>`, channels, and async\u002Fawait, and minimal `pub` surfaces organized by domain.\n\n## Core Principles\n\n### 1. Ownership and Borrowing\n\nRust's ownership system prevents data races and memory bugs at compile time.\n\n```rust\n\u002F\u002F Good: Pass references when you don't need ownership\nfn process(data: &[u8]) -> usize {\n    data.len()\n}\n\n\u002F\u002F Good: Take ownership only when you need to store or consume\nfn store(data: Vec\u003Cu8>) -> Record {\n    Record { payload: data }\n}\n\n\u002F\u002F Bad: Cloning unnecessarily to avoid borrow checker\nfn process_bad(data: &Vec\u003Cu8>) -> usize {\n    let cloned = data.clone(); \u002F\u002F Wasteful — just borrow\n    cloned.len()\n}\n```\n\n### Use `Cow` for Flexible Ownership\n\n```rust\nuse std::borrow::Cow;\n\nfn normalize(input: &str) -> Cow\u003C'_, str> {\n    if input.contains(' ') {\n        Cow::Owned(input.replace(' ', \"_\"))\n    } else {\n        Cow::Borrowed(input) \u002F\u002F Zero-cost when no mutation needed\n    }\n}\n```\n\n## Error Handling\n\n### Use `Result` and `?` — Never `unwrap()` in Production\n\n```rust\n\u002F\u002F Good: Propagate errors with context\nuse anyhow::{Context, Result};\n\nfn load_config(path: &str) -> Result\u003CConfig> {\n    let content = std::fs::read_to_string(path)\n        .with_context(|| format!(\"failed to read config from {path}\"))?;\n    let config: Config = toml::from_str(&content)\n        .with_context(|| format!(\"failed to parse config from {path}\"))?;\n    Ok(config)\n}\n\n\u002F\u002F Bad: Panics on error\nfn load_config_bad(path: &str) -> Config {\n    let content = std::fs::read_to_string(path).unwrap(); \u002F\u002F Panics!\n    toml::from_str(&content).unwrap()\n}\n```\n\n### Library Errors with `thiserror`, Application Errors with `anyhow`\n\n```rust\n\u002F\u002F Library code: structured, typed errors\nuse thiserror::Error;\n\n#[derive(Debug, Error)]\npub enum StorageError {\n    #[error(\"record not found: {id}\")]\n    NotFound { id: String },\n    #[error(\"connection failed\")]\n    Connection(#[from] std::io::Error),\n    #[error(\"invalid data: {0}\")]\n    InvalidData(String),\n}\n\n\u002F\u002F Application code: flexible error handling\nuse anyhow::{bail, Result};\n\nfn run() -> Result\u003C()> {\n    let config = load_config(\"app.toml\")?;\n    if config.workers == 0 {\n        bail!(\"worker count must be > 0\");\n    }\n    Ok(())\n}\n```\n\n### `Option` Combinators Over Nested Matching\n\n```rust\n\u002F\u002F Good: Combinator chain\nfn find_user_email(users: &[User], id: u64) -> Option\u003CString> {\n    users.iter()\n        .find(|u| u.id == id)\n        .map(|u| u.email.clone())\n}\n\n\u002F\u002F Bad: Deeply nested matching\nfn find_user_email_bad(users: &[User], id: u64) -> Option\u003CString> {\n    match users.iter().find(|u| u.id == id) {\n        Some(user) => match &user.email {\n            email => Some(email.clone()),\n        },\n        None => None,\n    }\n}\n```\n\n## Enums and Pattern Matching\n\n### Model States as Enums\n\n```rust\n\u002F\u002F Good: Impossible states are unrepresentable\nenum ConnectionState {\n    Disconnected,\n    Connecting { attempt: u32 },\n    Connected { session_id: String },\n    Failed { reason: String, retries: u32 },\n}\n\nfn handle(state: &ConnectionState) {\n    match state {\n        ConnectionState::Disconnected => connect(),\n        ConnectionState::Connecting { attempt } if *attempt > 3 => abort(),\n        ConnectionState::Connecting { .. } => wait(),\n        ConnectionState::Connected { session_id } => use_session(session_id),\n        ConnectionState::Failed { retries, .. } if *retries \u003C 5 => retry(),\n        ConnectionState::Failed { reason, .. } => log_failure(reason),\n    }\n}\n```\n\n### Exhaustive Matching — No Catch-All for Business Logic\n\n```rust\n\u002F\u002F Good: Handle every variant explicitly\nmatch command {\n    Command::Start => start_service(),\n    Command::Stop => stop_service(),\n    Command::Restart => restart_service(),\n    \u002F\u002F Adding a new variant forces handling here\n}\n\n\u002F\u002F Bad: Wildcard hides new variants\nmatch command {\n    Command::Start => start_service(),\n    _ => {} \u002F\u002F Silently ignores Stop, Restart, and future variants\n}\n```\n\n## Traits and Generics\n\n### Accept Generics, Return Concrete Types\n\n```rust\n\u002F\u002F Good: Generic input, concrete output\nfn read_all(reader: &mut impl Read) -> std::io::Result\u003CVec\u003Cu8>> {\n    let mut buf = Vec::new();\n    reader.read_to_end(&mut buf)?;\n    Ok(buf)\n}\n\n\u002F\u002F Good: Trait bounds for multiple constraints\nfn process\u003CT: Display + Send + 'static>(item: T) -> String {\n    format!(\"processed: {item}\")\n}\n```\n\n### Trait Objects for Dynamic Dispatch\n\n```rust\n\u002F\u002F Use when you need heterogeneous collections or plugin systems\ntrait Handler: Send + Sync {\n    fn handle(&self, request: &Request) -> Response;\n}\n\nstruct Router {\n    handlers: Vec\u003CBox\u003Cdyn Handler>>,\n}\n\n\u002F\u002F Use generics when you need performance (monomorphization)\nfn fast_process\u003CH: Handler>(handler: &H, request: &Request) -> Response {\n    handler.handle(request)\n}\n```\n\n### Newtype Pattern for Type Safety\n\n```rust\n\u002F\u002F Good: Distinct types prevent mixing up arguments\nstruct UserId(u64);\nstruct OrderId(u64);\n\nfn get_order(user: UserId, order: OrderId) -> Result\u003COrder> {\n    \u002F\u002F Can't accidentally swap user and order IDs\n    todo!()\n}\n\n\u002F\u002F Bad: Easy to swap arguments\nfn get_order_bad(user_id: u64, order_id: u64) -> Result\u003COrder> {\n    todo!()\n}\n```\n\n## Structs and Data Modeling\n\n### Builder Pattern for Complex Construction\n\n```rust\nstruct ServerConfig {\n    host: String,\n    port: u16,\n    max_connections: usize,\n}\n\nimpl ServerConfig {\n    fn builder(host: impl Into\u003CString>, port: u16) -> ServerConfigBuilder {\n        ServerConfigBuilder { host: host.into(), port, max_connections: 100 }\n    }\n}\n\nstruct ServerConfigBuilder { host: String, port: u16, max_connections: usize }\n\nimpl ServerConfigBuilder {\n    fn max_connections(mut self, n: usize) -> Self { self.max_connections = n; self }\n    fn build(self) -> ServerConfig {\n        ServerConfig { host: self.host, port: self.port, max_connections: self.max_connections }\n    }\n}\n\n\u002F\u002F Usage: ServerConfig::builder(\"localhost\", 8080).max_connections(200).build()\n```\n\n## Iterators and Closures\n\n### Prefer Iterator Chains Over Manual Loops\n\n```rust\n\u002F\u002F Good: Declarative, lazy, composable\nlet active_emails: Vec\u003CString> = users.iter()\n    .filter(|u| u.is_active)\n    .map(|u| u.email.clone())\n    .collect();\n\n\u002F\u002F Bad: Imperative accumulation\nlet mut active_emails = Vec::new();\nfor user in &users {\n    if user.is_active {\n        active_emails.push(user.email.clone());\n    }\n}\n```\n\n### Use `collect()` with Type Annotation\n\n```rust\n\u002F\u002F Collect into different types\nlet names: Vec\u003C_> = items.iter().map(|i| &i.name).collect();\nlet lookup: HashMap\u003C_, _> = items.iter().map(|i| (i.id, i)).collect();\nlet combined: String = parts.iter().copied().collect();\n\n\u002F\u002F Collect Results — short-circuits on first error\nlet parsed: Result\u003CVec\u003Ci32>, _> = strings.iter().map(|s| s.parse()).collect();\n```\n\n## Concurrency\n\n### `Arc\u003CMutex\u003CT>>` for Shared Mutable State\n\n```rust\nuse std::sync::{Arc, Mutex};\n\nlet counter = Arc::new(Mutex::new(0));\nlet handles: Vec\u003C_> = (0..10).map(|_| {\n    let counter = Arc::clone(&counter);\n    std::thread::spawn(move || {\n        let mut num = counter.lock().expect(\"mutex poisoned\");\n        *num += 1;\n    })\n}).collect();\n\nfor handle in handles {\n    handle.join().expect(\"worker thread panicked\");\n}\n```\n\n### Channels for Message Passing\n\n```rust\nuse std::sync::mpsc;\n\nlet (tx, rx) = mpsc::sync_channel(16); \u002F\u002F Bounded channel with backpressure\n\nfor i in 0..5 {\n    let tx = tx.clone();\n    std::thread::spawn(move || {\n        tx.send(format!(\"message {i}\")).expect(\"receiver disconnected\");\n    });\n}\ndrop(tx); \u002F\u002F Close sender so rx iterator terminates\n\nfor msg in rx {\n    println!(\"{msg}\");\n}\n```\n\n### Async with Tokio\n\n```rust\nuse tokio::time::Duration;\n\nasync fn fetch_with_timeout(url: &str) -> Result\u003CString> {\n    let response = tokio::time::timeout(\n        Duration::from_secs(5),\n        reqwest::get(url),\n    )\n    .await\n    .context(\"request timed out\")?\n    .context(\"request failed\")?;\n\n    response.text().await.context(\"failed to read body\")\n}\n\n\u002F\u002F Spawn concurrent tasks\nasync fn fetch_all(urls: Vec\u003CString>) -> Vec\u003CResult\u003CString>> {\n    let handles: Vec\u003C_> = urls.into_iter()\n        .map(|url| tokio::spawn(async move {\n            fetch_with_timeout(&url).await\n        }))\n        .collect();\n\n    let mut results = Vec::with_capacity(handles.len());\n    for handle in handles {\n        results.push(handle.await.unwrap_or_else(|e| panic!(\"spawned task panicked: {e}\")));\n    }\n    results\n}\n```\n\n## Unsafe Code\n\n### When Unsafe Is Acceptable\n\n```rust\n\u002F\u002F Acceptable: FFI boundary with documented invariants (Rust 2024+)\n\u002F\u002F\u002F # Safety\n\u002F\u002F\u002F `ptr` must be a valid, aligned pointer to an initialized `Widget`.\nunsafe fn widget_from_raw\u003C'a>(ptr: *const Widget) -> &'a Widget {\n    \u002F\u002F SAFETY: caller guarantees ptr is valid and aligned\n    unsafe { &*ptr }\n}\n\n\u002F\u002F Acceptable: Performance-critical path with proof of correctness\n\u002F\u002F SAFETY: index is always \u003C len due to the loop bound\nunsafe { slice.get_unchecked(index) }\n```\n\n### When Unsafe Is NOT Acceptable\n\n```rust\n\u002F\u002F Bad: Using unsafe to bypass borrow checker\n\u002F\u002F Bad: Using unsafe for convenience\n\u002F\u002F Bad: Using unsafe without a Safety comment\n\u002F\u002F Bad: Transmuting between unrelated types\n```\n\n## Module System and Crate Structure\n\n### Organize by Domain, Not by Type\n\n```text\nmy_app\u002F\n├── src\u002F\n│   ├── main.rs\n│   ├── lib.rs\n│   ├── auth\u002F          # Domain module\n│   │   ├── mod.rs\n│   │   ├── token.rs\n│   │   └── middleware.rs\n│   ├── orders\u002F        # Domain module\n│   │   ├── mod.rs\n│   │   ├── model.rs\n│   │   └── service.rs\n│   └── db\u002F            # Infrastructure\n│       ├── mod.rs\n│       └── pool.rs\n├── tests\u002F             # Integration tests\n├── benches\u002F           # Benchmarks\n└── Cargo.toml\n```\n\n### Visibility — Expose Minimally\n\n```rust\n\u002F\u002F Good: pub(crate) for internal sharing\npub(crate) fn validate_input(input: &str) -> bool {\n    !input.is_empty()\n}\n\n\u002F\u002F Good: Re-export public API from lib.rs\npub mod auth;\npub use auth::AuthMiddleware;\n\n\u002F\u002F Bad: Making everything pub\npub fn internal_helper() {} \u002F\u002F Should be pub(crate) or private\n```\n\n## Tooling Integration\n\n### Essential Commands\n\n```bash\n# Build and check\ncargo build\ncargo check              # Fast type checking without codegen\ncargo clippy             # Lints and suggestions\ncargo fmt                # Format code\n\n# Testing\ncargo test\ncargo test -- --nocapture    # Show println output\ncargo test --lib             # Unit tests only\ncargo test --test integration # Integration tests only\n\n# Dependencies\ncargo audit              # Security audit\ncargo tree               # Dependency tree\ncargo update             # Update dependencies\n\n# Performance\ncargo bench              # Run benchmarks\n```\n\n## Quick Reference: Rust Idioms\n\n| Idiom | Description |\n|-------|-------------|\n| Borrow, don't clone | Pass `&T` instead of cloning unless ownership is needed |\n| Make illegal states unrepresentable | Use enums to model valid states only |\n| `?` over `unwrap()` | Propagate errors, never panic in library\u002Fproduction code |\n| Parse, don't validate | Convert unstructured data to typed structs at the boundary |\n| Newtype for type safety | Wrap primitives in newtypes to prevent argument swaps |\n| Prefer iterators over loops | Declarative chains are clearer and often faster |\n| `#[must_use]` on Results | Ensure callers handle return values |\n| `Cow` for flexible ownership | Avoid allocations when borrowing suffices |\n| Exhaustive matching | No wildcard `_` for business-critical enums |\n| Minimal `pub` surface | Use `pub(crate)` for internal APIs |\n\n## Anti-Patterns to Avoid\n\n```rust\n\u002F\u002F Bad: .unwrap() in production code\nlet value = map.get(\"key\").unwrap();\n\n\u002F\u002F Bad: .clone() to satisfy borrow checker without understanding why\nlet data = expensive_data.clone();\nprocess(&original, &data);\n\n\u002F\u002F Bad: Using String when &str suffices\nfn greet(name: String) { \u002F* should be &str *\u002F }\n\n\u002F\u002F Bad: Box\u003Cdyn Error> in libraries (use thiserror instead)\nfn parse(input: &str) -> Result\u003CData, Box\u003Cdyn std::error::Error>> { todo!() }\n\n\u002F\u002F Bad: Ignoring must_use warnings\nlet _ = validate(input); \u002F\u002F Silently discarding a Result\n\n\u002F\u002F Bad: Blocking in async context\nasync fn bad_async() {\n    std::thread::sleep(Duration::from_secs(1)); \u002F\u002F Blocks the executor!\n    \u002F\u002F Use: tokio::time::sleep(Duration::from_secs(1)).await;\n}\n```\n\n**Remember**: If it compiles, it's probably correct — but only if you avoid `unwrap()`, minimize `unsafe`, and let the type system work for you.\n","# Rust Development Patterns\n\nIdiomatic Rust patterns and best practices for building safe, performant, and maintainable applications.\n\n## When to Use\n\n- Writing new Rust code\n- Reviewing Rust code\n- Refactoring existing Rust code\n- Designing crate structure and module layout\n\n## How It Works\n\nThis skill enforces idiomatic Rust conventions across six key areas: ownership and borrowing to prevent data races at compile time, `Result`\u002F`?` error propagation with `thiserror` for libraries and `anyhow` for applications, enums and exhaustive pattern matching to make illegal states unrepresentable, traits and generics for zero-cost abstraction, safe concurrency via `Arc\u003CMutex\u003CT>>`, channels, and async\u002Fawait, and minimal `pub` surfaces organized by domain.\n\n## Core Principles\n\n### 1. Ownership and Borrowing\n\nRust's ownership system prevents data races and memory bugs at compile time.\n\n```rust\n\u002F\u002F Good: Pass references when you don't need ownership\nfn process(data: &[u8]) -> usize {\n    data.len()\n}\n\n\u002F\u002F Good: Take ownership only when you need to store or consume\nfn store(data: Vec\u003Cu8>) -> Record {\n    Record { payload: data }\n}\n\n\u002F\u002F Bad: Cloning unnecessarily to avoid borrow checker\nfn process_bad(data: &Vec\u003Cu8>) -> usize {\n    let cloned = data.clone(); \u002F\u002F Wasteful — just borrow\n    cloned.len()\n}\n```\n\n### Use `Cow` for Flexible Ownership\n\n```rust\nuse std::borrow::Cow;\n\nfn normalize(input: &str) -> Cow\u003C'_, str> {\n    if input.contains(' ') {\n        Cow::Owned(input.replace(' ', \"_\"))\n    } else {\n        Cow::Borrowed(input) \u002F\u002F Zero-cost when no mutation needed\n    }\n}\n```\n\n## Error Handling\n\n### Use `Result` and `?` — Never `unwrap()` in Production\n\n```rust\n\u002F\u002F Good: Propagate errors with context\nuse anyhow::{Context, Result};\n\nfn load_config(path: &str) -> Result\u003CConfig> {\n    let content = std::fs::read_to_string(path)\n        .with_context(|| format!(\"failed to read config from {path}\"))?;\n    let config: Config = toml::from_str(&content)\n        .with_context(|| format!(\"failed to parse config from {path}\"))?;\n    Ok(config)\n}\n\n\u002F\u002F Bad: Panics on error\nfn load_config_bad(path: &str) -> Config {\n    let content = std::fs::read_to_string(path).unwrap(); \u002F\u002F Panics!\n    toml::from_str(&content).unwrap()\n}\n```\n\n### Library Errors with `thiserror`, Application Errors with `anyhow`\n\n```rust\n\u002F\u002F Library code: structured, typed errors\nuse thiserror::Error;\n\n#[derive(Debug, Error)]\npub enum StorageError {\n    #[error(\"record not found: {id}\")]\n    NotFound { id: String },\n    #[error(\"connection failed\")]\n    Connection(#[from] std::io::Error),\n    #[error(\"invalid data: {0}\")]\n    InvalidData(String),\n}\n\n\u002F\u002F Application code: flexible error handling\nuse anyhow::{bail, Result};\n\nfn run() -> Result\u003C()> {\n    let config = load_config(\"app.toml\")?;\n    if config.workers == 0 {\n        bail!(\"worker count must be > 0\");\n    }\n    Ok(())\n}\n```\n\n### `Option` Combinators Over Nested Matching\n\n```rust\n\u002F\u002F Good: Combinator chain\nfn find_user_email(users: &[User], id: u64) -> Option\u003CString> {\n    users.iter()\n        .find(|u| u.id == id)\n        .map(|u| u.email.clone())\n}\n\n\u002F\u002F Bad: Deeply nested matching\nfn find_user_email_bad(users: &[User], id: u64) -> Option\u003CString> {\n    match users.iter().find(|u| u.id == id) {\n        Some(user) => match &user.email {\n            email => Some(email.clone()),\n        },\n        None => None,\n    }\n}\n```\n\n## Enums and Pattern Matching\n\n### Model States as Enums\n\n```rust\n\u002F\u002F Good: Impossible states are unrepresentable\nenum ConnectionState {\n    Disconnected,\n    Connecting { attempt: u32 },\n    Connected { session_id: String },\n    Failed { reason: String, retries: u32 },\n}\n\nfn handle(state: &ConnectionState) {\n    match state {\n        ConnectionState::Disconnected => connect(),\n        ConnectionState::Connecting { attempt } if *attempt > 3 => abort(),\n        ConnectionState::Connecting { .. } => wait(),\n        ConnectionState::Connected { session_id } => use_session(session_id),\n        ConnectionState::Failed { retries, .. } if *retries \u003C 5 => retry(),\n        ConnectionState::Failed { reason, .. } => log_failure(reason),\n    }\n}\n```\n\n### Exhaustive Matching — No Catch-All for Business Logic\n\n```rust\n\u002F\u002F Good: Handle every variant explicitly\nmatch command {\n    Command::Start => start_service(),\n    Command::Stop => stop_service(),\n    Command::Restart => restart_service(),\n    \u002F\u002F Adding a new variant forces handling here\n}\n\n\u002F\u002F Bad: Wildcard hides new variants\nmatch command {\n    Command::Start => start_service(),\n    _ => {} \u002F\u002F Silently ignores Stop, Restart, and future variants\n}\n```\n\n## Traits and Generics\n\n### Accept Generics, Return Concrete Types\n\n```rust\n\u002F\u002F Good: Generic input, concrete output\nfn read_all(reader: &mut impl Read) -> std::io::Result\u003CVec\u003Cu8>> {\n    let mut buf = Vec::new();\n    reader.read_to_end(&mut buf)?;\n    Ok(buf)\n}\n\n\u002F\u002F Good: Trait bounds for multiple constraints\nfn process\u003CT: Display + Send + 'static>(item: T) -> String {\n    format!(\"processed: {item}\")\n}\n```\n\n### Trait Objects for Dynamic Dispatch\n\n```rust\n\u002F\u002F Use when you need heterogeneous collections or plugin systems\ntrait Handler: Send + Sync {\n    fn handle(&self, request: &Request) -> Response;\n}\n\nstruct Router {\n    handlers: Vec\u003CBox\u003Cdyn Handler>>,\n}\n\n\u002F\u002F Use generics when you need performance (monomorphization)\nfn fast_process\u003CH: Handler>(handler: &H, request: &Request) -> Response {\n    handler.handle(request)\n}\n```\n\n### Newtype Pattern for Type Safety\n\n```rust\n\u002F\u002F Good: Distinct types prevent mixing up arguments\nstruct UserId(u64);\nstruct OrderId(u64);\n\nfn get_order(user: UserId, order: OrderId) -> Result\u003COrder> {\n    \u002F\u002F Can't accidentally swap user and order IDs\n    todo!()\n}\n\n\u002F\u002F Bad: Easy to swap arguments\nfn get_order_bad(user_id: u64, order_id: u64) -> Result\u003COrder> {\n    todo!()\n}\n```\n\n## Structs and Data Modeling\n\n### Builder Pattern for Complex Construction\n\n```rust\nstruct ServerConfig {\n    host: String,\n    port: u16,\n    max_connections: usize,\n}\n\nimpl ServerConfig {\n    fn builder(host: impl Into\u003CString>, port: u16) -> ServerConfigBuilder {\n        ServerConfigBuilder { host: host.into(), port, max_connections: 100 }\n    }\n}\n\nstruct ServerConfigBuilder { host: String, port: u16, max_connections: usize }\n\nimpl ServerConfigBuilder {\n    fn max_connections(mut self, n: usize) -> Self { self.max_connections = n; self }\n    fn build(self) -> ServerConfig {\n        ServerConfig { host: self.host, port: self.port, max_connections: self.max_connections }\n    }\n}\n\n\u002F\u002F Usage: ServerConfig::builder(\"localhost\", 8080).max_connections(200).build()\n```\n\n## Iterators and Closures\n\n### Prefer Iterator Chains Over Manual Loops\n\n```rust\n\u002F\u002F Good: Declarative, lazy, composable\nlet active_emails: Vec\u003CString> = users.iter()\n    .filter(|u| u.is_active)\n    .map(|u| u.email.clone())\n    .collect();\n\n\u002F\u002F Bad: Imperative accumulation\nlet mut active_emails = Vec::new();\nfor user in &users {\n    if user.is_active {\n        active_emails.push(user.email.clone());\n    }\n}\n```\n\n### Use `collect()` with Type Annotation\n\n```rust\n\u002F\u002F Collect into different types\nlet names: Vec\u003C_> = items.iter().map(|i| &i.name).collect();\nlet lookup: HashMap\u003C_, _> = items.iter().map(|i| (i.id, i)).collect();\nlet combined: String = parts.iter().copied().collect();\n\n\u002F\u002F Collect Results — short-circuits on first error\nlet parsed: Result\u003CVec\u003Ci32>, _> = strings.iter().map(|s| s.parse()).collect();\n```\n\n## Concurrency\n\n### `Arc\u003CMutex\u003CT>>` for Shared Mutable State\n\n```rust\nuse std::sync::{Arc, Mutex};\n\nlet counter = Arc::new(Mutex::new(0));\nlet handles: Vec\u003C_> = (0..10).map(|_| {\n    let counter = Arc::clone(&counter);\n    std::thread::spawn(move || {\n        let mut num = counter.lock().expect(\"mutex poisoned\");\n        *num += 1;\n    })\n}).collect();\n\nfor handle in handles {\n    handle.join().expect(\"worker thread panicked\");\n}\n```\n\n### Channels for Message Passing\n\n```rust\nuse std::sync::mpsc;\n\nlet (tx, rx) = mpsc::sync_channel(16); \u002F\u002F Bounded channel with backpressure\n\nfor i in 0..5 {\n    let tx = tx.clone();\n    std::thread::spawn(move || {\n        tx.send(format!(\"message {i}\")).expect(\"receiver disconnected\");\n    });\n}\ndrop(tx); \u002F\u002F Close sender so rx iterator terminates\n\nfor msg in rx {\n    println!(\"{msg}\");\n}\n```\n\n### Async with Tokio\n\n```rust\nuse tokio::time::Duration;\n\nasync fn fetch_with_timeout(url: &str) -> Result\u003CString> {\n    let response = tokio::time::timeout(\n        Duration::from_secs(5),\n        reqwest::get(url),\n    )\n    .await\n    .context(\"request timed out\")?\n    .context(\"request failed\")?;\n\n    response.text().await.context(\"failed to read body\")\n}\n\n\u002F\u002F Spawn concurrent tasks\nasync fn fetch_all(urls: Vec\u003CString>) -> Vec\u003CResult\u003CString>> {\n    let handles: Vec\u003C_> = urls.into_iter()\n        .map(|url| tokio::spawn(async move {\n            fetch_with_timeout(&url).await\n        }))\n        .collect();\n\n    let mut results = Vec::with_capacity(handles.len());\n    for handle in handles {\n        results.push(handle.await.unwrap_or_else(|e| panic!(\"spawned task panicked: {e}\")));\n    }\n    results\n}\n```\n\n## Unsafe Code\n\n### When Unsafe Is Acceptable\n\n```rust\n\u002F\u002F Acceptable: FFI boundary with documented invariants (Rust 2024+)\n\u002F\u002F\u002F # Safety\n\u002F\u002F\u002F `ptr` must be a valid, aligned pointer to an initialized `Widget`.\nunsafe fn widget_from_raw\u003C'a>(ptr: *const Widget) -> &'a Widget {\n    \u002F\u002F SAFETY: caller guarantees ptr is valid and aligned\n    unsafe { &*ptr }\n}\n\n\u002F\u002F Acceptable: Performance-critical path with proof of correctness\n\u002F\u002F SAFETY: index is always \u003C len due to the loop bound\nunsafe { slice.get_unchecked(index) }\n```\n\n### When Unsafe Is NOT Acceptable\n\n```rust\n\u002F\u002F Bad: Using unsafe to bypass borrow checker\n\u002F\u002F Bad: Using unsafe for convenience\n\u002F\u002F Bad: Using unsafe without a Safety comment\n\u002F\u002F Bad: Transmuting between unrelated types\n```\n\n## Module System and Crate Structure\n\n### Organize by Domain, Not by Type\n\n```text\nmy_app\u002F\n├── src\u002F\n│   ├── main.rs\n│   ├── lib.rs\n│   ├── auth\u002F          # Domain module\n│   │   ├── mod.rs\n│   │   ├── token.rs\n│   │   └── middleware.rs\n│   ├── orders\u002F        # Domain module\n│   │   ├── mod.rs\n│   │   ├── model.rs\n│   │   └── service.rs\n│   └── db\u002F            # Infrastructure\n│       ├── mod.rs\n│       └── pool.rs\n├── tests\u002F             # Integration tests\n├── benches\u002F           # Benchmarks\n└── Cargo.toml\n```\n\n### Visibility — Expose Minimally\n\n```rust\n\u002F\u002F Good: pub(crate) for internal sharing\npub(crate) fn validate_input(input: &str) -> bool {\n    !input.is_empty()\n}\n\n\u002F\u002F Good: Re-export public API from lib.rs\npub mod auth;\npub use auth::AuthMiddleware;\n\n\u002F\u002F Bad: Making everything pub\npub fn internal_helper() {} \u002F\u002F Should be pub(crate) or private\n```\n\n## Tooling Integration\n\n### Essential Commands\n\n```bash\n# Build and check\ncargo build\ncargo check              # Fast type checking without codegen\ncargo clippy             # Lints and suggestions\ncargo fmt                # Format code\n\n# Testing\ncargo test\ncargo test -- --nocapture    # Show println output\ncargo test --lib             # Unit tests only\ncargo test --test integration # Integration tests only\n\n# Dependencies\ncargo audit              # Security audit\ncargo tree               # Dependency tree\ncargo update             # Update dependencies\n\n# Performance\ncargo bench              # Run benchmarks\n```\n\n## Quick Reference: Rust Idioms\n\n| Idiom | Description |\n|-------|-------------|\n| Borrow, don't clone | Pass `&T` instead of cloning unless ownership is needed |\n| Make illegal states unrepresentable | Use enums to model valid states only |\n| `?` over `unwrap()` | Propagate errors, never panic in library\u002Fproduction code |\n| Parse, don't validate | Convert unstructured data to typed structs at the boundary |\n| Newtype for type safety | Wrap primitives in newtypes to prevent argument swaps |\n| Prefer iterators over loops | Declarative chains are clearer and often faster |\n| `#[must_use]` on Results | Ensure callers handle return values |\n| `Cow` for flexible ownership | Avoid allocations when borrowing suffices |\n| Exhaustive matching | No wildcard `_` for business-critical enums |\n| Minimal `pub` surface | Use `pub(crate)` for internal APIs |\n\n## Anti-Patterns to Avoid\n\n```rust\n\u002F\u002F Bad: .unwrap() in production code\nlet value = map.get(\"key\").unwrap();\n\n\u002F\u002F Bad: .clone() to satisfy borrow checker without understanding why\nlet data = expensive_data.clone();\nprocess(&original, &data);\n\n\u002F\u002F Bad: Using String when &str suffices\nfn greet(name: String) { \u002F* should be &str *\u002F }\n\n\u002F\u002F Bad: Box\u003Cdyn Error> in libraries (use thiserror instead)\nfn parse(input: &str) -> Result\u003CData, Box\u003Cdyn std::error::Error>> { todo!() }\n\n\u002F\u002F Bad: Ignoring must_use warnings\nlet _ = validate(input); \u002F\u002F Silently discarding a Result\n\n\u002F\u002F Bad: Blocking in async context\nasync fn bad_async() {\n    std::thread::sleep(Duration::from_secs(1)); \u002F\u002F Blocks the executor!\n    \u002F\u002F Use: tokio::time::sleep(Duration::from_secs(1)).await;\n}\n```\n\n**Remember**: If it compiles, it's probably correct — but only if you avoid `unwrap()`, minimize `unsafe`, and let the type system work for you.\n",{"name":5,"origin":37,"description":7},"ECC","main","b0f0a87593c578a7898eccaf1b363f7f87c1f99b","plugins\u002FColin4k1024\u002Ftsp\u002Fskills\u002Frust-patterns",474,"https:\u002F\u002Fgithub.com\u002Fhashgraph-online\u002Fawesome-codex-plugins","https:\u002F\u002Fhol.org\u002Fplugins\u002Fbest-codex-plugins","https:\u002F\u002Fgithub.com\u002Fhashgraph-online","https:\u002F\u002Fhol.org","Open-source standards and developer tools for interoperable AI agents: discovery, identity, communication, payments, privacy and security.","2026-11-11 14:40:14",{"source":8,"skillName":5,"commands":49,"prompt":59,"zipAvailable":60},[50,53,56],{"tool":51,"command":52},"npx","npx skills add hashgraph-online\u002Fawesome-codex-plugins --skill rust-patterns",{"tool":54,"command":55},"bunx","bunx skills add hashgraph-online\u002Fawesome-codex-plugins --skill rust-patterns",{"tool":57,"command":58},"pnpm","pnpm dlx skills add hashgraph-online\u002Fawesome-codex-plugins --skill rust-patterns","安装技能，技能地址：https:\u002F\u002Fgithub.com\u002Fhashgraph-online\u002Fawesome-codex-plugins\u002Fblob\u002Fmain\u002Fplugins\u002FColin4k1024\u002Ftsp\u002Fskills\u002Frust-patterns\u002FSKILL.md",true,[],[63,71,78,85,111,136],{"skillNo":64,"name":65,"nameZh":6,"description":66,"descriptionZh":6,"repositoryFullName":8,"ownerLogin":9,"ownerAvatarUrl":10,"ownerAccountNo":11,"ownerDisplayName":12,"repositoryNo":13,"starsCount":14,"licenseSpdxId":15,"licenseFileUrl":6,"sourceHtmlUrl":67,"categories":68,"keywords":69,"publishedAt":70},"01M746ZWACVKMZ1BJXJZHYJSSX","migrate-to-e2e","Moves an existing Playwright, Cypress, Selenium, Appium, Detox, Maestro, or TesterArmy suite to e2e one slice at a time, with the old suite running beside the new one until each ported test is proven. Keeps a MIGRATION.md progress file so any later session resumes where the last stopped. Optionally plants a defect to show both suites catch it. Use for \u002Fmigrate-to-e2e, \"migrate our tests to e2e\", \"port these Maestro flows\", \"move our TesterArmy tests\", or when a project has an e2e config and an older suite still running.","https:\u002F\u002Fgithub.com\u002Fhashgraph-online\u002Fawesome-codex-plugins\u002Fblob\u002Fmain\u002Fplugins\u002Ftester-army\u002Fe2e\u002Fskills\u002Fmigrate-to-e2e\u002FSKILL.md",[],[],"2026-11-11 15:11:14",{"skillNo":72,"name":73,"nameZh":6,"description":74,"descriptionZh":6,"repositoryFullName":8,"ownerLogin":9,"ownerAvatarUrl":10,"ownerAccountNo":11,"ownerDisplayName":12,"repositoryNo":13,"starsCount":14,"licenseSpdxId":15,"licenseFileUrl":6,"sourceHtmlUrl":75,"categories":76,"keywords":77,"publishedAt":70},"01M746ZPTAX1Q0FBKAB1CYND7E","e2e","Writes, runs, and debugs end-to-end tests for web and mobile apps with e2e, the agentic test runner, which mixes agent.act goals with exact locator assertions on a Playwright browser or an iOS or Android device. Also drives a project's running app live over the e2e MCP server to look at a screen, check a UI change, take a screenshot or record a video, and try a locator; and runs bug bashes, parallel e2e explore runs with each bug proven by a repro test. Use when a project depends on e2e or has an e2e.config.ts, when asked for end-to-end, browser, mobile, or agentic UI tests, to check a change in the running app, to QA or bug bash an app or branch, or when an e2e run fails.","https:\u002F\u002Fgithub.com\u002Fhashgraph-online\u002Fawesome-codex-plugins\u002Fblob\u002Fmain\u002Fplugins\u002Ftester-army\u002Fe2e\u002Fskills\u002Fe2e\u002FSKILL.md",[],[],{"skillNo":79,"name":80,"nameZh":6,"description":81,"descriptionZh":6,"repositoryFullName":8,"ownerLogin":9,"ownerAvatarUrl":10,"ownerAccountNo":11,"ownerDisplayName":12,"repositoryNo":13,"starsCount":14,"licenseSpdxId":15,"licenseFileUrl":6,"sourceHtmlUrl":82,"categories":83,"keywords":84,"publishedAt":70},"01M746ZJN784HVHMDP9MQGCSGG","create-verification-skill","Generate a project-local verify-\u003Capp> skill on top of e2e, so any coding agent can launch the app, check it is worth driving, exercise a feature the way a user does, keep evidence, and bug bash it. Writes the skill, a feature map with one explore charter per feature, and proves it once. Use for \u002Fcreate-verification-skill, \"make a verification skill for this repo\", or when a project has no scripted way to prove UI behavior.","https:\u002F\u002Fgithub.com\u002Fhashgraph-online\u002Fawesome-codex-plugins\u002Fblob\u002Fmain\u002Fplugins\u002Ftester-army\u002Fe2e\u002Fskills\u002Fcreate-verification-skill\u002FSKILL.md",[],[],{"skillNo":86,"name":87,"nameZh":6,"description":88,"descriptionZh":6,"repositoryFullName":8,"ownerLogin":9,"ownerAvatarUrl":10,"ownerAccountNo":11,"ownerDisplayName":12,"repositoryNo":13,"starsCount":14,"licenseSpdxId":15,"licenseFileUrl":6,"sourceHtmlUrl":89,"categories":90,"keywords":91,"publishedAt":32},"01M716A6ETNB9B1SQ3GXZC75VR","deja-search","deja-vu memory — search the user's past AI coding sessions with the deja CLI. Holds what they already settled and never wrote into the repo (naming rules, banned or already-tried tools, required checks before merge, preferred values, who owns what). Use before your first edit in a task, before you call a change done or ready to merge, before you recommend a tool, library, design or reviewer, before re-debugging an error that may already be solved, when they say 'didn't we fix this before', 'what did we decide about X' or 'I already have that', and before telling them something on this machine does not exist.","https:\u002F\u002Fgithub.com\u002Fhashgraph-online\u002Fawesome-codex-plugins\u002Fblob\u002Fmain\u002Fplugins\u002Fvshulcz\u002Fdeja-vu\u002Fskills\u002Fdeja-search\u002FSKILL.md",[],[92,93,94,27,95,96,97,98,99,100,101,102,103,104,105,106,107,108,109,110],"search","deja search","never","ready","memory","re","decide","fix","design","debugging","when","you","done","reviewer","io","change","cli","merge","past",{"skillNo":112,"name":113,"nameZh":6,"description":114,"descriptionZh":6,"repositoryFullName":8,"ownerLogin":9,"ownerAvatarUrl":10,"ownerAccountNo":11,"ownerDisplayName":12,"repositoryNo":13,"starsCount":14,"licenseSpdxId":15,"licenseFileUrl":6,"sourceHtmlUrl":115,"categories":116,"keywords":117,"publishedAt":32},"01M716A3J2W5SENSE9VGMXB375","deja-reflect","End-of-session reflection and memory curation with deja-vu. Review what was decided, what commands broke and what repaired them, and record durable project rules or decisions with deja remember so the next session starts with them.","https:\u002F\u002Fgithub.com\u002Fhashgraph-online\u002Fawesome-codex-plugins\u002Fblob\u002Fmain\u002Fplugins\u002Fvshulcz\u002Fdeja-vu\u002Fskills\u002Fdeja-reflect\u002FSKILL.md",[],[118,119,120,106,121,122,123,124,125,126,127,128,129,130,96,131,132,133,134,135],"deja reflect","reflect","review","with","record","github","next","https","node","Rules","decisions","brew","remember","project rules","project","session","end","reflection",{"skillNo":137,"name":138,"nameZh":6,"description":139,"descriptionZh":6,"repositoryFullName":8,"ownerLogin":9,"ownerAvatarUrl":10,"ownerAccountNo":11,"ownerDisplayName":12,"repositoryNo":13,"starsCount":14,"licenseSpdxId":15,"licenseFileUrl":6,"sourceHtmlUrl":140,"categories":141,"keywords":153,"publishedAt":32},"01M715T3RR4BAYSR57HPPTJ0PF","revid","Make, edit, export and post AI videos with Revid (revid.ai) through the Revid MCP server. Use whenever the user wants a short-form or long-form video made (from an idea, a script, a URL, an article, a PDF, a tweet, a product page, their own clips, or a song), wants to find what is going viral on TikTok, YouTube, Instagram or X before making something, wants to edit or re-export an existing Revid project, generate a standalone AI image or clip, make a series episode, or publish and schedule a finished video to connected social accounts. Covers setup (hosted MCP with OAuth, or an API key), the 36 tools, credits, polling and the rules for publishing. Routes to the more specific revid-* skills when one fits.","https:\u002F\u002Fgithub.com\u002Fhashgraph-online\u002Fawesome-codex-plugins\u002Fblob\u002Fmain\u002Fplugins\u002Ftmakersas\u002Frevid-skills\u002Fskills\u002Frevid\u002FSKILL.md",[142,147,150],{"categoryNo":143,"categoryName":144,"taxonomyType":145,"taxonomyTypeDesc":146},"01JBSEEDCAT000000000000016","图像与多媒体","SCENARIO","使用场景",{"categoryNo":148,"categoryName":149,"taxonomyType":145,"taxonomyTypeDesc":146},"01JBSEEDCAT000000000000023","Skill与智能体开发",{"categoryNo":151,"categoryName":152,"taxonomyType":145,"taxonomyTypeDesc":146},"01JBSEEDCAT000000000000010","后端与接口",[138,154,155,156,157,158,159,132,160,97,161,162,163,164,102,165,166,167,168,169],"URL","Video","short-form","standalone","PDF","viral","tiktok","short","social","MCP","song","image","mcp server","schedule","api","publish"]