diff --git a/CHANGELOG.md b/CHANGELOG.md index ad89e06..dcbfa2c 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -7,6 +7,36 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0 ## [Unreleased] +### Added - Workflow Engine Hardening (Persistence · Saga · Cedar) + +#### `vapora-workflow-engine` — three new hardening layers + +- **`persistence.rs`**: `SurrealWorkflowStore` — crash-recoverable `WorkflowInstance` state in SurrealDB + - `save()` upserts on every state-mutating operation; serializes via `serde_json::Value` (surrealdb v3 `SurrealValue` requirement) + - `load_active()` on startup restores all non-terminal instances to the in-memory `DashMap` + - `delete()` removes terminal instances after completion +- **`saga.rs`**: `SagaCompensator` — reverse-order rollback dispatch via `SwarmCoordinator` + - Iterates executed stages in reverse; skips stages without `compensation_agents` in `StageConfig` + - Dispatches `{ type: "compensation", stage_name, workflow_id, original_context, artifacts_to_undo }` payload + - Best-effort: errors are logged and never propagated +- **`auth.rs`**: `CedarAuthorizer` — per-stage Cedar policy enforcement + - `load_from_dir(path)` reads all `*.cedar` files and compiles a single `PolicySet` + - Called before each `SwarmCoordinator::assign_task()`; deny returns `WorkflowError::Unauthorized` + - Disabled when `EngineConfig.cedar_policy_dir` is `None` +- **`config.rs`**: `StageConfig` gains `compensation_agents: Option>`; `EngineConfig` gains `cedar_policy_dir: Option` +- **`instance.rs`**: `WorkflowInstance::mark_current_task_failed()` — isolates the `current_stage_mut()` borrow to avoid NLL conflicts and clippy `excessive_nesting` in `on_task_failed()` +- **`migrations/009_workflow_state.surql`**: SCHEMAFULL `workflow_instances` table; indexes on `template_name` and `created_at` +- New deps: `surrealdb = { workspace = true }`, `cedar-policy = "4.9"` +- Tests: 31 pass (5 new — `auth` × 3, `saga` × 2); 0 clippy warnings + +#### `vapora-knowledge-graph` — surrealdb v3 compatibility fixes + +- All `response.take(0)` call sites updated from custom `#[derive(Deserialize)]` structs to `Vec` intermediary pattern + - Affected: `find_similar_executions`, `get_agent_success_rate`, `get_task_distribution`, `cleanup_old_executions`, `get_execution_count`, `get_executions_for_task_type`, `get_agent_executions`, `get_task_type_analytics`, `get_dashboard_metrics`, `get_cost_report`, `get_rlm_executions_by_doc`, `find_similar_rlm_tasks`, `get_rlm_execution_count`, `cleanup_old_rlm_executions` +- Root cause: `surrealdb` v3 changed `take()` bound from `T: DeserializeOwned` to `T: SurrealValue`; `serde_json::Value` satisfies this; custom structs do not + +--- + ### Fixed - `distro.just` build and installation - `distro::install`: now builds all 5 server binaries in one `cargo build --release` pass diff --git a/Cargo.lock b/Cargo.lock index e159e9a..e88d8b0 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -43,7 +43,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "d122413f284cf2d62fb1b7db97e02edb8cda96d769b16e443a4f6195e35662b0" dependencies = [ "crypto-common", - "generic-array", + "generic-array 0.14.9", ] [[package]] @@ -83,6 +83,21 @@ dependencies = [ "tokio", ] +[[package]] +name = "affinitypool" +version = "0.4.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7a58b64a64aecad4ba7f2ccf0f79115f5d2d184b1e55307f78c20be07adc6633" +dependencies = [ + "crossbeam", + "libc", + "num_cpus", + "parking_lot", + "thiserror 2.0.18", + "tokio", + "winapi", +] + [[package]] name = "ahash" version = "0.4.8" @@ -107,7 +122,6 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "5a15f179cd60c4584b8a8c596927aadc462e27f2ca70c04e0071964a73ba7a75" dependencies = [ "cfg-if", - "const-random", "getrandom 0.3.4", "once_cell", "serde", @@ -130,7 +144,7 @@ version = "0.4.3" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "ee4508988c62edf04abd8d92897fca0c2995d907ce1dfeaf369dac3716a40685" dependencies = [ - "as-slice", + "as-slice 0.2.1", ] [[package]] @@ -314,9 +328,12 @@ checksum = "c3d036a3c4ab069c7b410a2ce876bd74808d2d0888a82667669f8e783a898bf1" [[package]] name = "arc-swap" -version = "1.7.1" +version = "1.8.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "69f7f8c3906b62b754cd5326047894316021dcfe5a194c8ea52bdd94934a3457" +checksum = "f9f3647c145568cec02c42054e07bdf9a5a698e15b466fb2341bfc393cd24aa5" +dependencies = [ + "rustversion", +] [[package]] name = "arg_enum_proc_macro" @@ -359,229 +376,24 @@ version = "0.7.6" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "7c02d123df017efcdfbd739ef81735b36c5ba83ec3c59c80a9d7ecc718f92e50" -[[package]] -name = "arrow" -version = "56.2.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6e833808ff2d94ed40d9379848a950d995043c7fb3e81a30b383f4c6033821cc" -dependencies = [ - "arrow-arith", - "arrow-array", - "arrow-buffer", - "arrow-cast", - "arrow-csv", - "arrow-data", - "arrow-ipc", - "arrow-json", - "arrow-ord", - "arrow-row", - "arrow-schema", - "arrow-select", - "arrow-string", -] - -[[package]] -name = "arrow-arith" -version = "56.2.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ad08897b81588f60ba983e3ca39bda2b179bdd84dced378e7df81a5313802ef8" -dependencies = [ - "arrow-array", - "arrow-buffer", - "arrow-data", - "arrow-schema", - "chrono", - "num", -] - -[[package]] -name = "arrow-array" -version = "56.2.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8548ca7c070d8db9ce7aa43f37393e4bfcf3f2d3681df278490772fd1673d08d" -dependencies = [ - "ahash 0.8.12", - "arrow-buffer", - "arrow-data", - "arrow-schema", - "chrono", - "chrono-tz 0.10.4", - "half", - "hashbrown 0.16.1", - "num", -] - -[[package]] -name = "arrow-buffer" -version = "56.2.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e003216336f70446457e280807a73899dd822feaf02087d31febca1363e2fccc" -dependencies = [ - "bytes", - "half", - "num", -] - -[[package]] -name = "arrow-cast" -version = "56.2.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "919418a0681298d3a77d1a315f625916cb5678ad0d74b9c60108eb15fd083023" -dependencies = [ - "arrow-array", - "arrow-buffer", - "arrow-data", - "arrow-schema", - "arrow-select", - "atoi", - "base64 0.22.1", - "chrono", - "comfy-table", - "half", - "lexical-core", - "num", - "ryu", -] - -[[package]] -name = "arrow-csv" -version = "56.2.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "bfa9bf02705b5cf762b6f764c65f04ae9082c7cfc4e96e0c33548ee3f67012eb" -dependencies = [ - "arrow-array", - "arrow-cast", - "arrow-schema", - "chrono", - "csv", - "csv-core", - "regex", -] - -[[package]] -name = "arrow-data" -version = "56.2.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a5c64fff1d142f833d78897a772f2e5b55b36cb3e6320376f0961ab0db7bd6d0" -dependencies = [ - "arrow-buffer", - "arrow-schema", - "half", - "num", -] - -[[package]] -name = "arrow-ipc" -version = "56.2.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1d3594dcddccc7f20fd069bc8e9828ce37220372680ff638c5e00dea427d88f5" -dependencies = [ - "arrow-array", - "arrow-buffer", - "arrow-data", - "arrow-schema", - "arrow-select", - "flatbuffers", - "lz4_flex", - "zstd", -] - -[[package]] -name = "arrow-json" -version = "56.2.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "88cf36502b64a127dc659e3b305f1d993a544eab0d48cce704424e62074dc04b" -dependencies = [ - "arrow-array", - "arrow-buffer", - "arrow-cast", - "arrow-data", - "arrow-schema", - "chrono", - "half", - "indexmap 2.13.0", - "lexical-core", - "memchr", - "num", - "serde", - "serde_json", - "simdutf8", -] - -[[package]] -name = "arrow-ord" -version = "56.2.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3c8f82583eb4f8d84d4ee55fd1cb306720cddead7596edce95b50ee418edf66f" -dependencies = [ - "arrow-array", - "arrow-buffer", - "arrow-data", - "arrow-schema", - "arrow-select", -] - -[[package]] -name = "arrow-row" -version = "56.2.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "9d07ba24522229d9085031df6b94605e0f4b26e099fb7cdeec37abd941a73753" -dependencies = [ - "arrow-array", - "arrow-buffer", - "arrow-data", - "arrow-schema", - "half", -] - -[[package]] -name = "arrow-schema" -version = "56.2.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b3aa9e59c611ebc291c28582077ef25c97f1975383f1479b12f3b9ffee2ffabe" -dependencies = [ - "bitflags 2.10.0", - "serde", - "serde_json", -] - -[[package]] -name = "arrow-select" -version = "56.2.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8c41dbbd1e97bfcaee4fcb30e29105fb2c75e4d82ae4de70b792a5d3f66b2e7a" -dependencies = [ - "ahash 0.8.12", - "arrow-array", - "arrow-buffer", - "arrow-data", - "arrow-schema", - "num", -] - -[[package]] -name = "arrow-string" -version = "56.2.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "53f5183c150fbc619eede22b861ea7c0eebed8eaac0333eaa7f6da5205fd504d" -dependencies = [ - "arrow-array", - "arrow-buffer", - "arrow-data", - "arrow-schema", - "arrow-select", - "memchr", - "num", - "regex", - "regex-syntax", -] - [[package]] name = "as-any" version = "0.3.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "b0f477b951e452a0b6b4a10b53ccd569042d1d01729b519e02074a9c0958a063" +[[package]] +name = "as-slice" +version = "0.1.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "45403b49e3954a4b8428a0ac21a4b7afadccf92bfd96273f1a58cd4812496ae0" +dependencies = [ + "generic-array 0.12.4", + "generic-array 0.13.3", + "generic-array 0.14.9", + "stable_deref_trait", +] + [[package]] name = "as-slice" version = "0.2.1" @@ -637,14 +449,12 @@ version = "0.4.19" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "06575e6a9673580f52661c92107baabffbf41e2141373441cbcdc47cb733003c" dependencies = [ - "brotli 7.0.0", - "bzip2 0.5.2", + "brotli", "flate2", "futures-core", "memchr", "pin-project-lite", "tokio", - "xz2", "zstd", "zstd-safe", ] @@ -679,7 +489,7 @@ dependencies = [ "fnv", "futures-timer", "futures-util", - "http 1.4.0", + "http", "indexmap 2.13.0", "mime", "multer", @@ -773,7 +583,7 @@ dependencies = [ "thiserror 1.0.69", "time", "tokio", - "tokio-rustls 0.26.4", + "tokio-rustls", "tokio-stream", "tokio-util", "tokio-websockets", @@ -788,17 +598,6 @@ version = "0.5.4" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "4288f83726785267c6f2ef073a3d83dc3f9b81464e9f99898240cced85fce35a" -[[package]] -name = "async-recursion" -version = "1.1.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3b43422f69d8ff38f95f1b2bb76517c91589a924d1559a0e935d7c8ce0274c11" -dependencies = [ - "proc-macro2", - "quote", - "syn 2.0.114", -] - [[package]] name = "async-stream" version = "0.3.6" @@ -838,15 +637,6 @@ dependencies = [ "syn 2.0.114", ] -[[package]] -name = "async_cell" -version = "0.2.3" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "447ab28afbb345f5408b120702a44e5529ebf90b1796ec76e9528df8e288e6c2" -dependencies = [ - "loom", -] - [[package]] name = "async_io_stream" version = "0.3.3" @@ -867,6 +657,15 @@ dependencies = [ "num-traits", ] +[[package]] +name = "atomic-polyfill" +version = "1.0.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8cf2bce30dfe09ef0bfaef228b9d414faaf7e563035494d7fe092dba54b300f4" +dependencies = [ + "critical-section", +] + [[package]] name = "atomic-waker" version = "1.1.2" @@ -952,390 +751,29 @@ dependencies = [ "arrayvec 0.7.6", ] -[[package]] -name = "aws-config" -version = "1.8.12" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "96571e6996817bf3d58f6b569e4b9fd2e9d2fcf9f7424eed07b2ce9bb87535e5" -dependencies = [ - "aws-credential-types", - "aws-runtime", - "aws-sdk-sso", - "aws-sdk-ssooidc", - "aws-sdk-sts", - "aws-smithy-async", - "aws-smithy-http", - "aws-smithy-json", - "aws-smithy-runtime", - "aws-smithy-runtime-api", - "aws-smithy-types", - "aws-types", - "bytes", - "fastrand", - "hex", - "http 1.4.0", - "ring", - "time", - "tokio", - "tracing", - "url", - "zeroize", -] - -[[package]] -name = "aws-credential-types" -version = "1.2.11" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3cd362783681b15d136480ad555a099e82ecd8e2d10a841e14dfd0078d67fee3" -dependencies = [ - "aws-smithy-async", - "aws-smithy-runtime-api", - "aws-smithy-types", - "zeroize", -] - [[package]] name = "aws-lc-rs" -version = "1.14.1" +version = "1.16.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "879b6c89592deb404ba4dc0ae6b58ffd1795c78991cbb5b8bc441c48a070440d" +checksum = "d9a7b350e3bb1767102698302bc37256cbd48422809984b98d292c40e2579aa9" dependencies = [ "aws-lc-sys", + "untrusted 0.7.1", "zeroize", ] [[package]] name = "aws-lc-sys" -version = "0.32.3" +version = "0.37.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "107a4e9d9cab9963e04e84bb8dee0e25f2a987f9a8bad5ed054abd439caa8f8c" +checksum = "b092fe214090261288111db7a2b2c2118e5a7f30dc2569f1732c4069a6840549" dependencies = [ - "bindgen 0.72.1", "cc", "cmake", "dunce", "fs_extra", ] -[[package]] -name = "aws-runtime" -version = "1.5.18" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "959dab27ce613e6c9658eb3621064d0e2027e5f2acb65bc526a43577facea557" -dependencies = [ - "aws-credential-types", - "aws-sigv4", - "aws-smithy-async", - "aws-smithy-http", - "aws-smithy-runtime", - "aws-smithy-runtime-api", - "aws-smithy-types", - "aws-types", - "bytes", - "fastrand", - "http 0.2.12", - "http-body 0.4.6", - "percent-encoding", - "pin-project-lite", - "tracing", - "uuid", -] - -[[package]] -name = "aws-sdk-dynamodb" -version = "1.103.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6df2a8b03419775bfaf4f3ebbb65a9772e9e69eed4467a1b33f22226722340fb" -dependencies = [ - "aws-credential-types", - "aws-runtime", - "aws-smithy-async", - "aws-smithy-http", - "aws-smithy-json", - "aws-smithy-observability", - "aws-smithy-runtime", - "aws-smithy-runtime-api", - "aws-smithy-types", - "aws-types", - "bytes", - "fastrand", - "http 0.2.12", - "regex-lite", - "tracing", -] - -[[package]] -name = "aws-sdk-sso" -version = "1.92.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b7d63bd2bdeeb49aa3f9b00c15e18583503b778b2e792fc06284d54e7d5b6566" -dependencies = [ - "aws-credential-types", - "aws-runtime", - "aws-smithy-async", - "aws-smithy-http", - "aws-smithy-json", - "aws-smithy-observability", - "aws-smithy-runtime", - "aws-smithy-runtime-api", - "aws-smithy-types", - "aws-types", - "bytes", - "fastrand", - "http 0.2.12", - "regex-lite", - "tracing", -] - -[[package]] -name = "aws-sdk-ssooidc" -version = "1.94.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "532d93574bf731f311bafb761366f9ece345a0416dbcc273d81d6d1a1205239b" -dependencies = [ - "aws-credential-types", - "aws-runtime", - "aws-smithy-async", - "aws-smithy-http", - "aws-smithy-json", - "aws-smithy-observability", - "aws-smithy-runtime", - "aws-smithy-runtime-api", - "aws-smithy-types", - "aws-types", - "bytes", - "fastrand", - "http 0.2.12", - "regex-lite", - "tracing", -] - -[[package]] -name = "aws-sdk-sts" -version = "1.96.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "357e9a029c7524db6a0099cd77fbd5da165540339e7296cca603531bc783b56c" -dependencies = [ - "aws-credential-types", - "aws-runtime", - "aws-smithy-async", - "aws-smithy-http", - "aws-smithy-json", - "aws-smithy-observability", - "aws-smithy-query", - "aws-smithy-runtime", - "aws-smithy-runtime-api", - "aws-smithy-types", - "aws-smithy-xml", - "aws-types", - "fastrand", - "http 0.2.12", - "regex-lite", - "tracing", -] - -[[package]] -name = "aws-sigv4" -version = "1.3.7" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "69e523e1c4e8e7e8ff219d732988e22bfeae8a1cafdbe6d9eca1546fa080be7c" -dependencies = [ - "aws-credential-types", - "aws-smithy-http", - "aws-smithy-runtime-api", - "aws-smithy-types", - "bytes", - "form_urlencoded", - "hex", - "hmac", - "http 0.2.12", - "http 1.4.0", - "percent-encoding", - "sha2", - "time", - "tracing", -] - -[[package]] -name = "aws-smithy-async" -version = "1.2.7" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "9ee19095c7c4dda59f1697d028ce704c24b2d33c6718790c7f1d5a3015b4107c" -dependencies = [ - "futures-util", - "pin-project-lite", - "tokio", -] - -[[package]] -name = "aws-smithy-http" -version = "0.62.6" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "826141069295752372f8203c17f28e30c464d22899a43a0c9fd9c458d469c88b" -dependencies = [ - "aws-smithy-runtime-api", - "aws-smithy-types", - "bytes", - "bytes-utils", - "futures-core", - "futures-util", - "http 0.2.12", - "http 1.4.0", - "http-body 0.4.6", - "percent-encoding", - "pin-project-lite", - "pin-utils", - "tracing", -] - -[[package]] -name = "aws-smithy-http-client" -version = "1.1.5" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "59e62db736db19c488966c8d787f52e6270be565727236fd5579eaa301e7bc4a" -dependencies = [ - "aws-smithy-async", - "aws-smithy-runtime-api", - "aws-smithy-types", - "h2 0.3.27", - "h2 0.4.12", - "http 0.2.12", - "http 1.4.0", - "http-body 0.4.6", - "hyper 0.14.32", - "hyper 1.8.1", - "hyper-rustls 0.24.2", - "hyper-rustls 0.27.7", - "hyper-util", - "pin-project-lite", - "rustls 0.21.12", - "rustls 0.23.35", - "rustls-native-certs 0.8.3", - "rustls-pki-types", - "tokio", - "tokio-rustls 0.26.4", - "tower", - "tracing", -] - -[[package]] -name = "aws-smithy-json" -version = "0.61.9" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "49fa1213db31ac95288d981476f78d05d9cbb0353d22cdf3472cc05bb02f6551" -dependencies = [ - "aws-smithy-types", -] - -[[package]] -name = "aws-smithy-observability" -version = "0.2.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ef1fcbefc7ece1d70dcce29e490f269695dfca2d2bacdeaf9e5c3f799e4e6a42" -dependencies = [ - "aws-smithy-runtime-api", -] - -[[package]] -name = "aws-smithy-query" -version = "0.60.9" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ae5d689cf437eae90460e944a58b5668530d433b4ff85789e69d2f2a556e057d" -dependencies = [ - "aws-smithy-types", - "urlencoding", -] - -[[package]] -name = "aws-smithy-runtime" -version = "1.9.8" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "bb5b6167fcdf47399024e81ac08e795180c576a20e4d4ce67949f9a88ae37dc1" -dependencies = [ - "aws-smithy-async", - "aws-smithy-http", - "aws-smithy-http-client", - "aws-smithy-observability", - "aws-smithy-runtime-api", - "aws-smithy-types", - "bytes", - "fastrand", - "http 0.2.12", - "http 1.4.0", - "http-body 0.4.6", - "http-body 1.0.1", - "pin-project-lite", - "pin-utils", - "tokio", - "tracing", -] - -[[package]] -name = "aws-smithy-runtime-api" -version = "1.10.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "efce7aaaf59ad53c5412f14fc19b2d5c6ab2c3ec688d272fd31f76ec12f44fb0" -dependencies = [ - "aws-smithy-async", - "aws-smithy-types", - "bytes", - "http 0.2.12", - "http 1.4.0", - "pin-project-lite", - "tokio", - "tracing", - "zeroize", -] - -[[package]] -name = "aws-smithy-types" -version = "1.3.6" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "65f172bcb02424eb94425db8aed1b6d583b5104d4d5ddddf22402c661a320048" -dependencies = [ - "base64-simd", - "bytes", - "bytes-utils", - "futures-core", - "http 0.2.12", - "http 1.4.0", - "http-body 0.4.6", - "http-body 1.0.1", - "http-body-util", - "itoa", - "num-integer", - "pin-project-lite", - "pin-utils", - "ryu", - "serde", - "time", - "tokio", - "tokio-util", -] - -[[package]] -name = "aws-smithy-xml" -version = "0.60.13" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "11b2f670422ff42bf7065031e72b45bc52a3508bd089f743ea90731ca2b6ea57" -dependencies = [ - "xmlparser", -] - -[[package]] -name = "aws-types" -version = "1.3.11" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1d980627d2dd7bfc32a3c025685a033eeab8d365cc840c631ef59d1b8f428164" -dependencies = [ - "aws-credential-types", - "aws-smithy-async", - "aws-smithy-runtime-api", - "aws-smithy-types", - "rustc_version", - "tracing", -] - [[package]] name = "axum" version = "0.8.8" @@ -1348,10 +786,10 @@ dependencies = [ "bytes", "form_urlencoded", "futures-util", - "http 1.4.0", - "http-body 1.0.1", + "http", + "http-body", "http-body-util", - "hyper 1.8.1", + "hyper", "hyper-util", "itoa", "matchit", @@ -1382,8 +820,8 @@ checksum = "59446ce19cd142f8833f856eb31f3eb097812d1479ab224f54d72428ca21ea22" dependencies = [ "bytes", "futures-core", - "http 1.4.0", - "http-body 1.0.1", + "http", + "http-body", "http-body-util", "mime", "pin-project-lite", @@ -1414,15 +852,15 @@ dependencies = [ "bytes", "either", "fs-err", - "http 1.4.0", - "http-body 1.0.1", - "hyper 1.8.1", + "http", + "http-body", + "hyper", "hyper-util", "pin-project-lite", - "rustls 0.23.35", + "rustls", "rustls-pki-types", "tokio", - "tokio-rustls 0.26.4", + "tokio-rustls", "tower-service", ] @@ -1438,9 +876,9 @@ dependencies = [ "bytesize", "cookie", "expect-json", - "http 1.4.0", + "http", "http-body-util", - "hyper 1.8.1", + "hyper", "hyper-util", "mime", "pretty_assertions", @@ -1455,17 +893,6 @@ dependencies = [ "url", ] -[[package]] -name = "backon" -version = "1.6.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "cffb0e931875b666fc4fcb20fee52e9bbd1ef836fd9e9e04ec21555f9f85f7ef" -dependencies = [ - "fastrand", - "gloo-timers", - "tokio", -] - [[package]] name = "base16" version = "0.2.1" @@ -1496,16 +923,6 @@ version = "0.22.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "72b3254f16251a8381aa12e40e3c4d2f0199f8c6508fbecb9d91f575e0fbb8c6" -[[package]] -name = "base64-simd" -version = "0.8.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "339abbe78e73178762e23bea9dfd08e697eb3f3301cd4be981c0f78ba5859195" -dependencies = [ - "outref", - "vsimd", -] - [[package]] name = "base64ct" version = "1.8.0" @@ -1526,22 +943,16 @@ dependencies = [ ] [[package]] -name = "beef" -version = "0.5.2" +name = "bcrypt" +version = "0.18.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3a8241f3ebb85c056b509d4327ad0358fbbba6ffb340bf388f26350aeda225b1" - -[[package]] -name = "bigdecimal" -version = "0.4.10" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4d6867f1565b3aad85681f1015055b087fcfd840d6aeee6eee7f2da317603695" +checksum = "9a0f5948f30df5f43ac29d310b7476793be97c50787e6ef4a63d960a0d0be827" dependencies = [ - "autocfg", - "libm", - "num-bigint", - "num-integer", - "num-traits", + "base64 0.22.1", + "blowfish", + "getrandom 0.3.4", + "subtle", + "zeroize", ] [[package]] @@ -1553,6 +964,26 @@ dependencies = [ "serde", ] +[[package]] +name = "bincode" +version = "2.0.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "36eaf5d7b090263e8150820482d5d93cd964a81e4019913c972f4edcc6edb740" +dependencies = [ + "bincode_derive", + "serde", + "unty", +] + +[[package]] +name = "bincode_derive" +version = "2.0.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bf95709a440f45e986983918d0e8a1f30a9b1df04918fc828670606804ac3c09" +dependencies = [ + "virtue", +] + [[package]] name = "bindgen" version = "0.71.1" @@ -1583,8 +1014,6 @@ dependencies = [ "cexpr", "clang-sys", "itertools 0.13.0", - "log", - "prettyplease", "proc-macro2", "quote", "regex", @@ -1685,15 +1114,16 @@ dependencies = [ [[package]] name = "blake3" -version = "1.8.2" +version = "1.8.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3888aaa89e4b2a40fca9848e400f6a658a5a3978de7be858e209cafa8be9a4a0" +checksum = "2468ef7d57b3fb7e16b576e8377cdbde2320c60e1491e961d11da40fc4f02a2d" dependencies = [ "arrayref", "arrayvec 0.7.6", "cc", "cfg-if", "constant_time_eq", + "cpufeatures", ] [[package]] @@ -1702,16 +1132,7 @@ version = "0.10.4" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "3078c7629b62d3f0439517fa394996acacc5cbc91c5a20d8c658e77abd503a71" dependencies = [ - "generic-array", -] - -[[package]] -name = "block-padding" -version = "0.3.3" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a8894febbff9f758034a5b8e12d87918f56dfc64a8e1fe757d65e29041538d93" -dependencies = [ - "generic-array", + "generic-array 0.14.9", ] [[package]] @@ -1724,6 +1145,12 @@ dependencies = [ "cipher", ] +[[package]] +name = "bnum" +version = "0.12.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f781dba93de3a5ef6dc5b17c9958b208f6f3f021623b360fb605ea51ce443f10" + [[package]] name = "bollard" version = "0.18.1" @@ -1736,9 +1163,9 @@ dependencies = [ "futures-core", "futures-util", "hex", - "http 1.4.0", + "http", "http-body-util", - "hyper 1.8.1", + "hyper", "hyper-named-pipe", "hyper-util", "hyperlocal", @@ -1816,6 +1243,12 @@ dependencies = [ "syn 2.0.114", ] +[[package]] +name = "boxcar" +version = "0.2.14" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "36f64beae40a84da1b4b26ff2761a5b895c12adc41dc25aaee1c4f2bbfe97a6e" + [[package]] name = "brotli" version = "7.0.0" @@ -1824,18 +1257,7 @@ checksum = "cc97b8f16f944bba54f0433f07e30be199b6dc2bd25937444bbad560bcea29bd" dependencies = [ "alloc-no-stdlib", "alloc-stdlib", - "brotli-decompressor 4.0.3", -] - -[[package]] -name = "brotli" -version = "8.0.2" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4bd8b9603c7aa97359dbd97ecf258968c95f3adddd6db2f7e7a5bef101c84560" -dependencies = [ - "alloc-no-stdlib", - "alloc-stdlib", - "brotli-decompressor 5.0.0", + "brotli-decompressor", ] [[package]] @@ -1848,16 +1270,6 @@ dependencies = [ "alloc-stdlib", ] -[[package]] -name = "brotli-decompressor" -version = "5.0.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "874bb8112abecc98cbd6d81ea4fa7e94fb9449648c93cc89aa40c81c24d7de03" -dependencies = [ - "alloc-no-stdlib", - "alloc-stdlib", -] - [[package]] name = "bstr" version = "1.12.1" @@ -1938,40 +1350,12 @@ dependencies = [ "serde", ] -[[package]] -name = "bytes-utils" -version = "0.1.4" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7dafe3a8757b027e2be6e4e5601ed563c55989fcf1546e933c66c8eb3a058d35" -dependencies = [ - "bytes", - "either", -] - [[package]] name = "bytesize" version = "2.3.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "6bd91ee7b2422bcb158d90ef4d14f75ef67f340943fc4149891dcce8f8b972a3" -[[package]] -name = "bzip2" -version = "0.5.2" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "49ecfb22d906f800d4fe833b6282cf4dc1c298f5057ca0b5445e5c209735ca47" -dependencies = [ - "bzip2-sys", -] - -[[package]] -name = "bzip2" -version = "0.6.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f3a53fac24f34a81bc9954b5d6cfce0c21e18ec6959f44f56e8e90e4bb7c346c" -dependencies = [ - "libbz2-rs-sys", -] - [[package]] name = "bzip2-sys" version = "0.1.13+1.0.8" @@ -2081,15 +1465,6 @@ dependencies = [ "rustversion", ] -[[package]] -name = "cbc" -version = "0.1.2" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "26b52a9543ae338f279b96b0b9fed9c8093744685043739079ce85cd58f289a6" -dependencies = [ - "cipher", -] - [[package]] name = "cc" version = "1.2.45" @@ -2121,11 +1496,11 @@ dependencies = [ [[package]] name = "cedar-policy" -version = "4.8.1" +version = "4.9.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6a9bb2659528c9901c2ef23ca1a3d6915aed8ee81d1a32c468b26fb541b27b24" +checksum = "c55625387d203085efb7dca8eb594188d586c99f97a83cf577d60bc588b1c705" dependencies = [ - "cedar-policy-core 4.8.1", + "cedar-policy-core 4.9.0", "cedar-policy-formatter", "itertools 0.14.0", "linked-hash-map", @@ -2164,9 +1539,9 @@ dependencies = [ [[package]] name = "cedar-policy-core" -version = "4.8.1" +version = "4.9.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "890556d1962b99fc37fdff92279c20c3f1aedce8ec0f0f3c47835f0a00a7d125" +checksum = "c2ac16501266418b913a4ee73d1d14542d479c73baf7fccea2542996a2a82fe2" dependencies = [ "chrono", "educe", @@ -2180,7 +1555,7 @@ dependencies = [ "nonempty", "ref-cast", "regex", - "rustc_lexer", + "rustc-literal-escaper", "serde", "serde_json", "serde_with", @@ -2192,11 +1567,11 @@ dependencies = [ [[package]] name = "cedar-policy-formatter" -version = "4.8.1" +version = "4.9.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "fc9e0957a377f88787a348b6155414d656833e1f3bd592cb7e9aae1656ba0384" +checksum = "99f4b40c3d8a88264578fd9ef17b43ef35ec36e1283ae22930542dff8a6b80ae" dependencies = [ - "cedar-policy-core 4.8.1", + "cedar-policy-core 4.9.0", "itertools 0.14.0", "logos", "miette 7.6.0", @@ -2281,9 +1656,9 @@ dependencies = [ [[package]] name = "chrono" -version = "0.4.42" +version = "0.4.43" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "145052bdd345b87320e369255277e3fb5152762ad123a901ef5c262dd38fe8d2" +checksum = "fac4744fb15ae8337dc853fee7fb3f4e48c0fbaa23d0afe49c447b4fab126118" dependencies = [ "iana-time-zone", "js-sys", @@ -2304,16 +1679,6 @@ dependencies = [ "phf 0.11.3", ] -[[package]] -name = "chrono-tz" -version = "0.10.4" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a6139a8597ed92cf816dfb33f5dd6cf0bb93a6adc938f11039f371bc5bcd26c3" -dependencies = [ - "chrono", - "phf 0.12.1", -] - [[package]] name = "chrono-tz-build" version = "0.3.0" @@ -2480,17 +1845,6 @@ dependencies = [ "memchr", ] -[[package]] -name = "comfy-table" -version = "7.1.2" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e0d05af1e006a2407bedef5af410552494ce5be9090444dbbcb57258c1af3d56" -dependencies = [ - "strum", - "strum_macros", - "unicode-width 0.2.2", -] - [[package]] name = "compact_str" version = "0.9.0" @@ -2580,26 +1934,6 @@ version = "0.9.6" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "c2459377285ad874054d797f3ccebf984978aa39129f6eafde5cdc8315b612f8" -[[package]] -name = "const-random" -version = "0.1.18" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "87e00182fe74b066627d63b85fd550ac2998d4b0bd86bfed477a0ae4c7c71359" -dependencies = [ - "const-random-macro", -] - -[[package]] -name = "const-random-macro" -version = "0.1.16" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f9d839f2a20b0aee515dc581a6172f2321f96cab76c1a38a4c584a194955390e" -dependencies = [ - "getrandom 0.2.16", - "once_cell", - "tiny-keccak", -] - [[package]] name = "const-str" version = "0.7.1" @@ -2634,9 +1968,9 @@ checksum = "f67855af358fcb20fac58f9d714c94e2b228fe5694c1c9b4ead4a366343eda1b" [[package]] name = "constant_time_eq" -version = "0.3.1" +version = "0.4.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7c74b8349d32d297c9134b8c88677813a227df8f779daa29bfc29c183fe3dca6" +checksum = "3d52eff69cd5e647efe296129160853a42795992097e8af39800e1060caeea9b" [[package]] name = "convert_case" @@ -2851,15 +2185,6 @@ version = "2.4.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "19d374276b40fb8bbdee95aef7c7fa6b5316ec764510eb64b8dd0e2ed0d7e7f5" -[[package]] -name = "crc32c" -version = "0.6.8" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3a47af21622d091a8f0fb295b88bc886ac74efcc613efc19f5d0b21de5c89e47" -dependencies = [ - "rustc_version", -] - [[package]] name = "crc32fast" version = "1.5.0" @@ -2905,6 +2230,25 @@ dependencies = [ "itertools 0.13.0", ] +[[package]] +name = "critical-section" +version = "1.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "790eea4361631c5e7d22598ecd5723ff611904e3344ce8720784c93e3d83d40b" + +[[package]] +name = "crossbeam" +version = "0.8.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1137cd7e7fc0fb5d3c5a8678be38ec56e819125d8d7907411fe24ccb943faca8" +dependencies = [ + "crossbeam-channel", + "crossbeam-deque", + "crossbeam-epoch", + "crossbeam-queue", + "crossbeam-utils", +] + [[package]] name = "crossbeam-channel" version = "0.5.15" @@ -2942,6 +2286,16 @@ dependencies = [ "crossbeam-utils", ] +[[package]] +name = "crossbeam-skiplist" +version = "0.1.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "df29de440c58ca2cc6e587ec3d22347551a32435fbde9d2bff64e78a9ffa151b" +dependencies = [ + "crossbeam-epoch", + "crossbeam-utils", +] + [[package]] name = "crossbeam-utils" version = "0.8.21" @@ -2987,7 +2341,7 @@ version = "0.5.5" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "0dc92fb57ca44df6db8059111ab3af99a63d5d0f8375d9972e319a379c6bab76" dependencies = [ - "generic-array", + "generic-array 0.14.9", "rand_core 0.6.4", "subtle", "zeroize", @@ -2999,7 +2353,7 @@ version = "0.1.6" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "1bfb12502f3fc46cca1bb51ac28df9d618d813cdc3d2f25b9fe775a34af26bb3" dependencies = [ - "generic-array", + "generic-array 0.14.9", "rand_core 0.6.4", "typenum", ] @@ -3037,27 +2391,6 @@ dependencies = [ "memchr", ] -[[package]] -name = "csv" -version = "1.4.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "52cd9d68cf7efc6ddfaaee42e7288d3a99d613d4b50f76ce9827ae0c6e14f938" -dependencies = [ - "csv-core", - "itoa", - "ryu", - "serde_core", -] - -[[package]] -name = "csv-core" -version = "0.1.13" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "704a3c26996a80471189265814dbc2c257598b96b8a7feae2d31ace646bb9782" -dependencies = [ - "memchr", -] - [[package]] name = "ctr" version = "0.9.2" @@ -3212,649 +2545,6 @@ version = "2.9.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "2a2330da5de22e8a3cb63252ce2abb30116bf5265e89c0e01bc17015ce30a476" -[[package]] -name = "datafusion" -version = "50.3.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2af15bb3c6ffa33011ef579f6b0bcbe7c26584688bd6c994f548e44df67f011a" -dependencies = [ - "arrow", - "arrow-ipc", - "arrow-schema", - "async-trait", - "bytes", - "bzip2 0.6.1", - "chrono", - "datafusion-catalog", - "datafusion-catalog-listing", - "datafusion-common", - "datafusion-common-runtime", - "datafusion-datasource", - "datafusion-datasource-csv", - "datafusion-datasource-json", - "datafusion-datasource-parquet", - "datafusion-execution", - "datafusion-expr", - "datafusion-expr-common", - "datafusion-functions", - "datafusion-functions-aggregate", - "datafusion-functions-nested", - "datafusion-functions-table", - "datafusion-functions-window", - "datafusion-optimizer", - "datafusion-physical-expr", - "datafusion-physical-expr-adapter", - "datafusion-physical-expr-common", - "datafusion-physical-optimizer", - "datafusion-physical-plan", - "datafusion-session", - "datafusion-sql", - "flate2", - "futures", - "itertools 0.14.0", - "log", - "object_store", - "parking_lot", - "parquet", - "rand 0.9.2", - "regex", - "sqlparser", - "tempfile", - "tokio", - "url", - "uuid", - "xz2", - "zstd", -] - -[[package]] -name = "datafusion-catalog" -version = "50.3.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "187622262ad8f7d16d3be9202b4c1e0116f1c9aa387e5074245538b755261621" -dependencies = [ - "arrow", - "async-trait", - "dashmap 6.1.0", - "datafusion-common", - "datafusion-common-runtime", - "datafusion-datasource", - "datafusion-execution", - "datafusion-expr", - "datafusion-physical-expr", - "datafusion-physical-plan", - "datafusion-session", - "datafusion-sql", - "futures", - "itertools 0.14.0", - "log", - "object_store", - "parking_lot", - "tokio", -] - -[[package]] -name = "datafusion-catalog-listing" -version = "50.3.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "9657314f0a32efd0382b9a46fdeb2d233273ece64baa68a7c45f5a192daf0f83" -dependencies = [ - "arrow", - "async-trait", - "datafusion-catalog", - "datafusion-common", - "datafusion-datasource", - "datafusion-execution", - "datafusion-expr", - "datafusion-physical-expr", - "datafusion-physical-expr-common", - "datafusion-physical-plan", - "datafusion-session", - "futures", - "log", - "object_store", - "tokio", -] - -[[package]] -name = "datafusion-common" -version = "50.3.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "5a83760d9a13122d025fbdb1d5d5aaf93dd9ada5e90ea229add92aa30898b2d1" -dependencies = [ - "ahash 0.8.12", - "arrow", - "arrow-ipc", - "base64 0.22.1", - "chrono", - "half", - "hashbrown 0.14.5", - "indexmap 2.13.0", - "libc", - "log", - "object_store", - "parquet", - "paste", - "recursive", - "sqlparser", - "tokio", - "web-time", -] - -[[package]] -name = "datafusion-common-runtime" -version = "50.3.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "5b6234a6c7173fe5db1c6c35c01a12b2aa0f803a3007feee53483218817f8b1e" -dependencies = [ - "futures", - "log", - "tokio", -] - -[[package]] -name = "datafusion-datasource" -version = "50.3.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7256c9cb27a78709dd42d0c80f0178494637209cac6e29d5c93edd09b6721b86" -dependencies = [ - "arrow", - "async-compression", - "async-trait", - "bytes", - "bzip2 0.6.1", - "chrono", - "datafusion-common", - "datafusion-common-runtime", - "datafusion-execution", - "datafusion-expr", - "datafusion-physical-expr", - "datafusion-physical-expr-adapter", - "datafusion-physical-expr-common", - "datafusion-physical-plan", - "datafusion-session", - "flate2", - "futures", - "glob", - "itertools 0.14.0", - "log", - "object_store", - "parquet", - "rand 0.9.2", - "tempfile", - "tokio", - "tokio-util", - "url", - "xz2", - "zstd", -] - -[[package]] -name = "datafusion-datasource-csv" -version = "50.3.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "64533a90f78e1684bfb113d200b540f18f268134622d7c96bbebc91354d04825" -dependencies = [ - "arrow", - "async-trait", - "bytes", - "datafusion-catalog", - "datafusion-common", - "datafusion-common-runtime", - "datafusion-datasource", - "datafusion-execution", - "datafusion-expr", - "datafusion-physical-expr", - "datafusion-physical-expr-common", - "datafusion-physical-plan", - "datafusion-session", - "futures", - "object_store", - "regex", - "tokio", -] - -[[package]] -name = "datafusion-datasource-json" -version = "50.3.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8d7ebeb12c77df0aacad26f21b0d033aeede423a64b2b352f53048a75bf1d6e6" -dependencies = [ - "arrow", - "async-trait", - "bytes", - "datafusion-catalog", - "datafusion-common", - "datafusion-common-runtime", - "datafusion-datasource", - "datafusion-execution", - "datafusion-expr", - "datafusion-physical-expr", - "datafusion-physical-expr-common", - "datafusion-physical-plan", - "datafusion-session", - "futures", - "object_store", - "serde_json", - "tokio", -] - -[[package]] -name = "datafusion-datasource-parquet" -version = "50.3.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "09e783c4c7d7faa1199af2df4761c68530634521b176a8d1331ddbc5a5c75133" -dependencies = [ - "arrow", - "async-trait", - "bytes", - "datafusion-catalog", - "datafusion-common", - "datafusion-common-runtime", - "datafusion-datasource", - "datafusion-execution", - "datafusion-expr", - "datafusion-functions-aggregate", - "datafusion-physical-expr", - "datafusion-physical-expr-adapter", - "datafusion-physical-expr-common", - "datafusion-physical-optimizer", - "datafusion-physical-plan", - "datafusion-pruning", - "datafusion-session", - "futures", - "itertools 0.14.0", - "log", - "object_store", - "parking_lot", - "parquet", - "rand 0.9.2", - "tokio", -] - -[[package]] -name = "datafusion-doc" -version = "50.3.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "99ee6b1d9a80d13f9deb2291f45c07044b8e62fb540dbde2453a18be17a36429" - -[[package]] -name = "datafusion-execution" -version = "50.3.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a4cec0a57653bec7b933fb248d3ffa3fa3ab3bd33bd140dc917f714ac036f531" -dependencies = [ - "arrow", - "async-trait", - "dashmap 6.1.0", - "datafusion-common", - "datafusion-expr", - "futures", - "log", - "object_store", - "parking_lot", - "rand 0.9.2", - "tempfile", - "url", -] - -[[package]] -name = "datafusion-expr" -version = "50.3.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ef76910bdca909722586389156d0aa4da4020e1631994d50fadd8ad4b1aa05fe" -dependencies = [ - "arrow", - "async-trait", - "chrono", - "datafusion-common", - "datafusion-doc", - "datafusion-expr-common", - "datafusion-functions-aggregate-common", - "datafusion-functions-window-common", - "datafusion-physical-expr-common", - "indexmap 2.13.0", - "paste", - "recursive", - "serde_json", - "sqlparser", -] - -[[package]] -name = "datafusion-expr-common" -version = "50.3.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6d155ccbda29591ca71a1344dd6bed26c65a4438072b400df9db59447f590bb6" -dependencies = [ - "arrow", - "datafusion-common", - "indexmap 2.13.0", - "itertools 0.14.0", - "paste", -] - -[[package]] -name = "datafusion-functions" -version = "50.3.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7de2782136bd6014670fd84fe3b0ca3b3e4106c96403c3ae05c0598577139977" -dependencies = [ - "arrow", - "arrow-buffer", - "base64 0.22.1", - "blake2", - "blake3", - "chrono", - "datafusion-common", - "datafusion-doc", - "datafusion-execution", - "datafusion-expr", - "datafusion-expr-common", - "datafusion-macros", - "hex", - "itertools 0.14.0", - "log", - "md-5", - "rand 0.9.2", - "regex", - "sha2", - "unicode-segmentation", - "uuid", -] - -[[package]] -name = "datafusion-functions-aggregate" -version = "50.3.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "07331fc13603a9da97b74fd8a273f4238222943dffdbbed1c4c6f862a30105bf" -dependencies = [ - "ahash 0.8.12", - "arrow", - "datafusion-common", - "datafusion-doc", - "datafusion-execution", - "datafusion-expr", - "datafusion-functions-aggregate-common", - "datafusion-macros", - "datafusion-physical-expr", - "datafusion-physical-expr-common", - "half", - "log", - "paste", -] - -[[package]] -name = "datafusion-functions-aggregate-common" -version = "50.3.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b5951e572a8610b89968a09b5420515a121fbc305c0258651f318dc07c97ab17" -dependencies = [ - "ahash 0.8.12", - "arrow", - "datafusion-common", - "datafusion-expr-common", - "datafusion-physical-expr-common", -] - -[[package]] -name = "datafusion-functions-nested" -version = "50.3.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "fdacca9302c3d8fc03f3e94f338767e786a88a33f5ebad6ffc0e7b50364b9ea3" -dependencies = [ - "arrow", - "arrow-ord", - "datafusion-common", - "datafusion-doc", - "datafusion-execution", - "datafusion-expr", - "datafusion-functions", - "datafusion-functions-aggregate", - "datafusion-functions-aggregate-common", - "datafusion-macros", - "datafusion-physical-expr-common", - "itertools 0.14.0", - "log", - "paste", -] - -[[package]] -name = "datafusion-functions-table" -version = "50.3.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8c37ff8a99434fbbad604a7e0669717c58c7c4f14c472d45067c4b016621d981" -dependencies = [ - "arrow", - "async-trait", - "datafusion-catalog", - "datafusion-common", - "datafusion-expr", - "datafusion-physical-plan", - "parking_lot", - "paste", -] - -[[package]] -name = "datafusion-functions-window" -version = "50.3.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "48e2aea7c79c926cffabb13dc27309d4eaeb130f4a21c8ba91cdd241c813652b" -dependencies = [ - "arrow", - "datafusion-common", - "datafusion-doc", - "datafusion-expr", - "datafusion-functions-window-common", - "datafusion-macros", - "datafusion-physical-expr", - "datafusion-physical-expr-common", - "log", - "paste", -] - -[[package]] -name = "datafusion-functions-window-common" -version = "50.3.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "0fead257ab5fd2ffc3b40fda64da307e20de0040fe43d49197241d9de82a487f" -dependencies = [ - "datafusion-common", - "datafusion-physical-expr-common", -] - -[[package]] -name = "datafusion-macros" -version = "50.3.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ec6f637bce95efac05cdfb9b6c19579ed4aa5f6b94d951cfa5bb054b7bb4f730" -dependencies = [ - "datafusion-expr", - "quote", - "syn 2.0.114", -] - -[[package]] -name = "datafusion-optimizer" -version = "50.3.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c6583ef666ae000a613a837e69e456681a9faa96347bf3877661e9e89e141d8a" -dependencies = [ - "arrow", - "chrono", - "datafusion-common", - "datafusion-expr", - "datafusion-expr-common", - "datafusion-physical-expr", - "indexmap 2.13.0", - "itertools 0.14.0", - "log", - "recursive", - "regex", - "regex-syntax", -] - -[[package]] -name = "datafusion-physical-expr" -version = "50.3.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c8668103361a272cbbe3a61f72eca60c9b7c706e87cc3565bcf21e2b277b84f6" -dependencies = [ - "ahash 0.8.12", - "arrow", - "datafusion-common", - "datafusion-expr", - "datafusion-expr-common", - "datafusion-functions-aggregate-common", - "datafusion-physical-expr-common", - "half", - "hashbrown 0.14.5", - "indexmap 2.13.0", - "itertools 0.14.0", - "log", - "parking_lot", - "paste", - "petgraph 0.8.3", -] - -[[package]] -name = "datafusion-physical-expr-adapter" -version = "50.3.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "815acced725d30601b397e39958e0e55630e0a10d66ef7769c14ae6597298bb0" -dependencies = [ - "arrow", - "datafusion-common", - "datafusion-expr", - "datafusion-functions", - "datafusion-physical-expr", - "datafusion-physical-expr-common", - "itertools 0.14.0", -] - -[[package]] -name = "datafusion-physical-expr-common" -version = "50.3.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6652fe7b5bf87e85ed175f571745305565da2c0b599d98e697bcbedc7baa47c3" -dependencies = [ - "ahash 0.8.12", - "arrow", - "datafusion-common", - "datafusion-expr-common", - "hashbrown 0.14.5", - "itertools 0.14.0", -] - -[[package]] -name = "datafusion-physical-optimizer" -version = "50.3.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "49b7d623eb6162a3332b564a0907ba00895c505d101b99af78345f1acf929b5c" -dependencies = [ - "arrow", - "datafusion-common", - "datafusion-execution", - "datafusion-expr", - "datafusion-expr-common", - "datafusion-physical-expr", - "datafusion-physical-expr-common", - "datafusion-physical-plan", - "datafusion-pruning", - "itertools 0.14.0", - "log", - "recursive", -] - -[[package]] -name = "datafusion-physical-plan" -version = "50.3.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e2f7f778a1a838dec124efb96eae6144237d546945587557c9e6936b3414558c" -dependencies = [ - "ahash 0.8.12", - "arrow", - "arrow-ord", - "arrow-schema", - "async-trait", - "chrono", - "datafusion-common", - "datafusion-common-runtime", - "datafusion-execution", - "datafusion-expr", - "datafusion-functions-aggregate-common", - "datafusion-functions-window-common", - "datafusion-physical-expr", - "datafusion-physical-expr-common", - "futures", - "half", - "hashbrown 0.14.5", - "indexmap 2.13.0", - "itertools 0.14.0", - "log", - "parking_lot", - "pin-project-lite", - "tokio", -] - -[[package]] -name = "datafusion-pruning" -version = "50.3.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "cd1e59e2ca14fe3c30f141600b10ad8815e2856caa59ebbd0e3e07cd3d127a65" -dependencies = [ - "arrow", - "arrow-schema", - "datafusion-common", - "datafusion-datasource", - "datafusion-expr-common", - "datafusion-physical-expr", - "datafusion-physical-expr-common", - "datafusion-physical-plan", - "itertools 0.14.0", - "log", -] - -[[package]] -name = "datafusion-session" -version = "50.3.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "21ef8e2745583619bd7a49474e8f45fbe98ebb31a133f27802217125a7b3d58d" -dependencies = [ - "arrow", - "async-trait", - "dashmap 6.1.0", - "datafusion-common", - "datafusion-common-runtime", - "datafusion-execution", - "datafusion-expr", - "datafusion-physical-expr", - "datafusion-physical-plan", - "datafusion-sql", - "futures", - "itertools 0.14.0", - "log", - "object_store", - "parking_lot", - "tokio", -] - -[[package]] -name = "datafusion-sql" -version = "50.3.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "89abd9868770386fede29e5a4b14f49c0bf48d652c3b9d7a8a0332329b87d50b" -dependencies = [ - "arrow", - "bigdecimal", - "datafusion-common", - "datafusion-expr", - "indexmap 2.13.0", - "log", - "recursive", - "regex", - "sqlparser", -] - [[package]] name = "deadpool" version = "0.12.3" @@ -3882,26 +2572,6 @@ dependencies = [ "uuid", ] -[[package]] -name = "deepsize" -version = "0.2.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1cdb987ec36f6bf7bfbea3f928b75590b736fc42af8e54d97592481351b2b96c" -dependencies = [ - "deepsize_derive", -] - -[[package]] -name = "deepsize_derive" -version = "0.1.2" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "990101d41f3bc8c1a45641024377ee284ecc338e5ecf3ea0f0e236d897c72796" -dependencies = [ - "proc-macro2", - "quote", - "syn 1.0.109", -] - [[package]] name = "der" version = "0.7.10" @@ -4106,15 +2776,6 @@ dependencies = [ "syn 2.0.114", ] -[[package]] -name = "dlv-list" -version = "0.5.2" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "442039f5147480ba31067cb00ada1adae6892028e40e45fc5de7b7df6dcc1b5f" -dependencies = [ - "const-random", -] - [[package]] name = "dmp" version = "0.2.3" @@ -4293,7 +2954,7 @@ dependencies = [ "crypto-bigint", "digest", "ff", - "generic-array", + "generic-array 0.14.9", "group", "hkdf", "pem-rfc7468", @@ -4355,6 +3016,12 @@ version = "0.1.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "c34f04666d835ff5d62e058c3995147c06f42fe86ff053337632bca83e42702d" +[[package]] +name = "endian-type" +version = "0.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "869b0adbda23651a9c5c0c3d270aac9fcb52e8622a8f2b17e57802d7791962f2" + [[package]] name = "enum-ordinalize" version = "4.3.2" @@ -4445,12 +3112,6 @@ dependencies = [ "windows-sys 0.48.0", ] -[[package]] -name = "ethnum" -version = "1.5.2" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ca81e6b4777c89fd810c25a4be2b1bd93ea034fbe58e6a75216a34c6b82c539b" - [[package]] name = "event-listener" version = "5.4.1" @@ -4546,12 +3207,6 @@ version = "0.3.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "2acce4a10f12dc2fb14a218589d4f1f62ef011b2d0cc4b3cb1bba8e94da14649" -[[package]] -name = "fast-float2" -version = "0.2.3" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f8eb564c5c7423d25c886fb561d1e4ee69f72354d16918afa32c08811f6b6a55" - [[package]] name = "fastdivide" version = "0.4.2" @@ -4560,9 +3215,9 @@ checksum = "9afc2bd4d5a73106dd53d10d73d3401c2f32730ba2c0b93ddb888a8983680471" [[package]] name = "fastembed" -version = "5.8.1" +version = "5.11.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "59a3f841f27a44bcc32214f8df75cc9b6cea55dbbebbfe546735690eab5bb2d2" +checksum = "b4339d45a80579ab8305616a501eacdbf18fb0f7def7fa6e4c0b75941416d5b0" dependencies = [ "anyhow", "hf-hub", @@ -4575,6 +3230,17 @@ dependencies = [ "tokenizers", ] +[[package]] +name = "fastnum" +version = "0.7.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4089ab2dfd45d8ddc92febb5ca80644389d5ebb954f40231274a3f18341762e2" +dependencies = [ + "bnum", + "num-integer", + "num-traits", +] + [[package]] name = "fastrand" version = "2.3.0" @@ -4663,6 +3329,7 @@ checksum = "35f6839d7b3b98adde531effaf34f0c2badc6f4735d26fe74709d8e513a96ef3" dependencies = [ "bitflags 2.10.0", "rustc_version", + "serde", ] [[package]] @@ -4672,7 +3339,6 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "bfe33edd8e85a12a67454e37f8c75e730830d83e313556ab9ebf9ee7fbeb3bfb" dependencies = [ "crc32fast", - "libz-rs-sys", "miniz_oxide", ] @@ -4807,6 +3473,16 @@ dependencies = [ "windows-sys 0.59.0", ] +[[package]] +name = "fs2" +version = "0.4.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9564fc758e15025b46aa6643b1b77d047d1a56a1aea6e01002ac0c7026876213" +dependencies = [ + "libc", + "winapi", +] + [[package]] name = "fs4" version = "0.8.4" @@ -4842,24 +3518,11 @@ dependencies = [ "libc", ] -[[package]] -name = "fsst" -version = "1.0.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "5ffdff7a2d68d22afc0657eddde3e946371ce7cfe730a3f78a5ed44ea5b1cb2e" -dependencies = [ - "arrow-array", - "rand 0.9.2", -] - [[package]] name = "fst" version = "0.4.7" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "7ab85b9b05e3978cc9a9cf8fea7f01b494e1a09ed3037e16ba39edc7a29eb61a" -dependencies = [ - "utf8-ranges", -] [[package]] name = "funty" @@ -5029,18 +3692,21 @@ dependencies = [ ] [[package]] -name = "generator" -version = "0.8.8" +name = "generic-array" +version = "0.12.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "52f04ae4152da20c76fe800fa48659201d5cf627c5149ca0b707b69d7eef6cf9" +checksum = "ffdf9f34f1447443d37393cc6c2b8313aebddcd96906caf34e54c68d8e57d7bd" dependencies = [ - "cc", - "cfg-if", - "libc", - "log", - "rustversion", - "windows-link 0.2.1", - "windows-result 0.4.1", + "typenum", +] + +[[package]] +name = "generic-array" +version = "0.13.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f797e67af32588215eaaab8327027ee8e71b9dd0b2b26996aedf20c030fce309" +dependencies = [ + "typenum", ] [[package]] @@ -5067,7 +3733,7 @@ dependencies = [ "log", "num-traits", "robust", - "rstar", + "rstar 0.12.2", "serde", "spade", ] @@ -5086,95 +3752,49 @@ dependencies = [ "log", "num-traits", "robust", - "rstar", + "rstar 0.12.2", + "serde", "spade", ] [[package]] -name = "geo-traits" -version = "0.3.0" +name = "geo" +version = "0.32.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2e7c353d12a704ccfab1ba8bfb1a7fe6cb18b665bf89d37f4f7890edcd260206" +checksum = "3f3901269ec6d4f6068d3f09e5f02f995bd076398dcd1dfec407cd230b02d11b" dependencies = [ + "earcutr", + "float_next_after", "geo-types", + "geographiclib-rs", + "i_overlay", + "log", + "num-traits", + "rand 0.8.5", + "robust", + "rstar 0.12.2", + "serde", + "sif-itree", + "spade", ] [[package]] name = "geo-types" -version = "0.7.17" +version = "0.7.18" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "75a4dcd69d35b2c87a7c83bce9af69fd65c9d68d3833a0ded568983928f3fc99" +checksum = "24f8647af4005fa11da47cd56252c6ef030be8fa97bdbf355e7dfb6348f0a82c" dependencies = [ "approx 0.5.1", "num-traits", "rayon", - "rstar", + "rstar 0.10.0", + "rstar 0.11.0", + "rstar 0.12.2", + "rstar 0.8.4", + "rstar 0.9.3", "serde", ] -[[package]] -name = "geoarrow-array" -version = "0.6.2" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7d1884b17253d8572e88833c282fcbb442365e4ae5f9052ced2831608253436c" -dependencies = [ - "arrow-array", - "arrow-buffer", - "arrow-schema", - "geo-traits", - "geoarrow-schema", - "num-traits", - "wkb", - "wkt", -] - -[[package]] -name = "geoarrow-expr-geo" -version = "0.6.2" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a67d3b543bc3ebeffdc204b67d69b8f9fcd33d76269ddd4a4618df99f053a934" -dependencies = [ - "arrow-array", - "arrow-buffer", - "geo 0.31.0", - "geo-traits", - "geoarrow-array", - "geoarrow-schema", -] - -[[package]] -name = "geoarrow-schema" -version = "0.6.2" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "02f1b18b1c9a44ecd72be02e53d6e63bbccfdc8d1765206226af227327e2be6e" -dependencies = [ - "arrow-schema", - "geo-traits", - "serde", - "serde_json", - "thiserror 1.0.69", -] - -[[package]] -name = "geodatafusion" -version = "0.1.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "83d676b8d8b5f391ab4270ba31e9b599ee2c3d780405a38e272a0a7565ea189c" -dependencies = [ - "arrow-arith", - "arrow-array", - "arrow-schema", - "datafusion", - "geo 0.31.0", - "geo-traits", - "geoarrow-array", - "geoarrow-expr-geo", - "geoarrow-schema", - "geohash", - "thiserror 1.0.69", - "wkt", -] - [[package]] name = "geographiclib-rs" version = "0.2.5" @@ -5184,16 +3804,6 @@ dependencies = [ "libm", ] -[[package]] -name = "geohash" -version = "0.13.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "0fb94b1a65401d6cbf22958a9040aa364812c26674f841bee538b12c135db1e6" -dependencies = [ - "geo-types", - "libm", -] - [[package]] name = "getopts" version = "0.2.24" @@ -5321,7 +3931,7 @@ dependencies = [ "futures-core", "futures-sink", "gloo-utils 0.2.0", - "http 1.4.0", + "http", "js-sys", "pin-project", "serde", @@ -5387,25 +3997,6 @@ version = "1.3.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "17e2ac29387b1aa07a1e448f7bb4f35b500787971e965b02842b900afa5c8f6f" -[[package]] -name = "h2" -version = "0.3.27" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "0beca50380b1fc32983fc1cb4587bfa4bb9e78fc259aad4a0032d2080309222d" -dependencies = [ - "bytes", - "fnv", - "futures-core", - "futures-sink", - "futures-util", - "http 0.2.12", - "indexmap 2.13.0", - "slab", - "tokio", - "tokio-util", - "tracing", -] - [[package]] name = "h2" version = "0.4.12" @@ -5417,7 +4008,7 @@ dependencies = [ "fnv", "futures-core", "futures-sink", - "http 1.4.0", + "http", "indexmap 2.13.0", "slab", "tokio", @@ -5433,10 +4024,27 @@ checksum = "6ea2d84b969582b4b1864a92dc5d27cd2b77b622a8d79306834f1be5ba20d84b" dependencies = [ "cfg-if", "crunchy", - "num-traits", "zerocopy", ] +[[package]] +name = "hash32" +version = "0.1.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d4041af86e63ac4298ce40e5cca669066e75b6f1aa3390fe2561ffa5e1d9f4cc" +dependencies = [ + "byteorder", +] + +[[package]] +name = "hash32" +version = "0.2.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b0c35f58762feb77d74ebe43bdbc3210f09be9fe6742234d573bacc26ed92b67" +dependencies = [ + "byteorder", +] + [[package]] name = "hash32" version = "0.3.1" @@ -5508,13 +4116,62 @@ dependencies = [ "hashbrown 0.15.5", ] +[[package]] +name = "headers" +version = "0.4.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b3314d5adb5d94bcdf56771f2e50dbbc80bb4bdf88967526706205ac9eff24eb" +dependencies = [ + "base64 0.22.1", + "bytes", + "headers-core", + "http", + "httpdate", + "mime", + "sha1", +] + +[[package]] +name = "headers-core" +version = "0.3.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "54b4a22553d4242c49fddb9ba998a99962b5cc6f22cb5a3482bec22522403ce4" +dependencies = [ + "http", +] + +[[package]] +name = "heapless" +version = "0.6.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "634bd4d29cbf24424d0a4bfcbf80c6960129dc24424752a7d1d1390607023422" +dependencies = [ + "as-slice 0.1.5", + "generic-array 0.14.9", + "hash32 0.1.1", + "stable_deref_trait", +] + +[[package]] +name = "heapless" +version = "0.7.17" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "cdc6457c0eb62c71aac4bc17216026d8410337c4126773b9c5daba343f17964f" +dependencies = [ + "atomic-polyfill", + "hash32 0.2.1", + "rustc_version", + "spin", + "stable_deref_trait", +] + [[package]] name = "heapless" version = "0.8.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "0bfb9eb618601c89945a70e254898da93b13be0388091d42117462b265bb3fad" dependencies = [ - "hash32", + "hash32 0.3.1", "stable_deref_trait", ] @@ -5543,7 +4200,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "629d8f3bbeda9d148036d6b0de0a3ab947abd08ce90626327fc3547a49d59d97" dependencies = [ "dirs 6.0.0", - "http 1.4.0", + "http", "indicatif", "libc", "log", @@ -5616,17 +4273,6 @@ version = "0.3.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "e9025058dae765dee5070ec375f591e2ba14638c63feff74f13805a72e523163" -[[package]] -name = "http" -version = "0.2.12" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "601cbb57e577e2f5ef5be8e7b83f0f63994f25aa94d673e54a92d5c516d101f1" -dependencies = [ - "bytes", - "fnv", - "itoa", -] - [[package]] name = "http" version = "1.4.0" @@ -5637,17 +4283,6 @@ dependencies = [ "itoa", ] -[[package]] -name = "http-body" -version = "0.4.6" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7ceab25649e9960c0311ea418d17bee82c0dcec1bd053b5f9a66e265a693bed2" -dependencies = [ - "bytes", - "http 0.2.12", - "pin-project-lite", -] - [[package]] name = "http-body" version = "1.0.1" @@ -5655,7 +4290,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "1efedce1fb8e6913f23e0c92de8e62cd5b772a67e7b3946df930a62566c93184" dependencies = [ "bytes", - "http 1.4.0", + "http", ] [[package]] @@ -5666,8 +4301,8 @@ checksum = "b021d93e26becf5dc7e1b75b1bed1fd93124b374ceb73f43d4d4eafec896a64a" dependencies = [ "bytes", "futures-core", - "http 1.4.0", - "http-body 1.0.1", + "http", + "http-body", "pin-project-lite", ] @@ -5730,30 +4365,6 @@ dependencies = [ "wasm-bindgen", ] -[[package]] -name = "hyper" -version = "0.14.32" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "41dfc780fdec9373c01bae43289ea34c972e40ee3c9f6b3c8801a35f35586ce7" -dependencies = [ - "bytes", - "futures-channel", - "futures-core", - "futures-util", - "h2 0.3.27", - "http 0.2.12", - "http-body 0.4.6", - "httparse", - "httpdate", - "itoa", - "pin-project-lite", - "socket2 0.5.10", - "tokio", - "tower-service", - "tracing", - "want", -] - [[package]] name = "hyper" version = "1.8.1" @@ -5764,9 +4375,9 @@ dependencies = [ "bytes", "futures-channel", "futures-core", - "h2 0.4.12", - "http 1.4.0", - "http-body 1.0.1", + "h2", + "http", + "http-body", "httparse", "httpdate", "itoa", @@ -5784,7 +4395,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "73b7d8abf35697b81a825e386fc151e0d503e8cb5fcb93cc8669c376dfd6f278" dependencies = [ "hex", - "hyper 1.8.1", + "hyper", "hyper-util", "pin-project-lite", "tokio", @@ -5792,39 +4403,36 @@ dependencies = [ "winapi", ] -[[package]] -name = "hyper-rustls" -version = "0.24.2" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ec3efd23720e2049821a693cbc7e65ea87c72f1c58ff2f9522ff332b1491e590" -dependencies = [ - "futures-util", - "http 0.2.12", - "hyper 0.14.32", - "log", - "rustls 0.21.12", - "tokio", - "tokio-rustls 0.24.1", -] - [[package]] name = "hyper-rustls" version = "0.27.7" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "e3c93eb611681b207e1fe55d5a71ecf91572ec8a6705cdb6857f7d8d5242cf58" dependencies = [ - "http 1.4.0", - "hyper 1.8.1", + "http", + "hyper", "hyper-util", - "rustls 0.23.35", - "rustls-native-certs 0.8.3", + "rustls", "rustls-pki-types", "tokio", - "tokio-rustls 0.26.4", + "tokio-rustls", "tower-service", "webpki-roots 1.0.4", ] +[[package]] +name = "hyper-timeout" +version = "0.5.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2b90d566bffbce6a75bd8b09a05aa8c2cb1fabb6cb348f8840c9e4c90a0d83b0" +dependencies = [ + "hyper", + "hyper-util", + "pin-project-lite", + "tokio", + "tower-service", +] + [[package]] name = "hyper-tls" version = "0.6.0" @@ -5833,7 +4441,7 @@ checksum = "70206fc6890eaca9fde8a0bf71caa2ddfc9fe045ac9e5c70df101a7dbde866e0" dependencies = [ "bytes", "http-body-util", - "hyper 1.8.1", + "hyper", "hyper-util", "native-tls", "tokio", @@ -5852,14 +4460,14 @@ dependencies = [ "futures-channel", "futures-core", "futures-util", - "http 1.4.0", - "http-body 1.0.1", - "hyper 1.8.1", + "http", + "http-body", + "hyper", "ipnet", "libc", "percent-encoding", "pin-project-lite", - "socket2 0.6.1", + "socket2", "system-configuration", "tokio", "tower-service", @@ -5875,7 +4483,7 @@ checksum = "986c5ce3b994526b3cd75578e62554abd09f0899d6206de48b3e96ab34ccc8c7" dependencies = [ "hex", "http-body-util", - "hyper 1.8.1", + "hyper", "hyper-util", "pin-project-lite", "tokio", @@ -6190,8 +4798,7 @@ version = "0.1.4" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "879f10e63c20629ecabbb64a8010319738c66a5cd0c29b02d63d272b03751d01" dependencies = [ - "block-padding", - "generic-array", + "generic-array 0.14.9", ] [[package]] @@ -6241,6 +4848,12 @@ version = "3.0.4" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "8bb03732005da905c88227371639bf1ad885cc712789c011c31c5fb3ab3ccf02" +[[package]] +name = "integer-encoding" +version = "4.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "14c00403deb17c3221a1fe4fb571b9ed0370b3dcd116553c77fa294a3d918699" + [[package]] name = "interpolate_name" version = "0.2.4" @@ -6395,47 +5008,6 @@ dependencies = [ "cc", ] -[[package]] -name = "jiff" -version = "0.2.18" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e67e8da4c49d6d9909fe03361f9b620f58898859f5c7aded68351e85e71ecf50" -dependencies = [ - "jiff-static", - "jiff-tzdb-platform", - "log", - "portable-atomic", - "portable-atomic-util", - "serde_core", - "windows-sys 0.61.2", -] - -[[package]] -name = "jiff-static" -version = "0.2.18" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e0c84ee7f197eca9a86c6fd6cb771e55eb991632f15f2bc3ca6ec838929e6e78" -dependencies = [ - "proc-macro2", - "quote", - "syn 2.0.114", -] - -[[package]] -name = "jiff-tzdb" -version = "0.1.5" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "68971ebff725b9e2ca27a601c5eb38a4c5d64422c4cbab0c535f248087eda5c2" - -[[package]] -name = "jiff-tzdb-platform" -version = "0.1.3" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "875a5a69ac2bab1a891711cf5eccbec1ce0341ea805560dcd90b7a2e925132e8" -dependencies = [ - "jiff-tzdb", -] - [[package]] name = "jni" version = "0.21.1" @@ -6478,26 +5050,6 @@ dependencies = [ "wasm-bindgen", ] -[[package]] -name = "jsonb" -version = "0.5.5" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2a901f06163d352fbe41c3c2ff5e08b75330a003cc941e988fb501022f5421e6" -dependencies = [ - "byteorder", - "ethnum", - "fast-float2", - "itoa", - "jiff", - "nom 8.0.0", - "num-traits", - "ordered-float 5.1.0", - "rand 0.9.2", - "ryu", - "serde", - "serde_json", -] - [[package]] name = "jsonwebtoken" version = "9.3.1" @@ -6519,6 +5071,7 @@ version = "10.3.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "0529410abe238729a60b108898784df8984c87f6054c9c4fcacc47e4803c1ce1" dependencies = [ + "aws-lc-rs", "base64 0.22.1", "ed25519-dalek", "getrandom 0.2.16", @@ -6628,568 +5181,6 @@ dependencies = [ "rustversion", ] -[[package]] -name = "lance" -version = "1.0.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e8c439decbc304e180748e34bb6d3df729069a222e83e74e2185c38f107136e9" -dependencies = [ - "arrow", - "arrow-arith", - "arrow-array", - "arrow-buffer", - "arrow-ipc", - "arrow-ord", - "arrow-row", - "arrow-schema", - "arrow-select", - "async-recursion", - "async-trait", - "async_cell", - "aws-credential-types", - "aws-sdk-dynamodb", - "byteorder", - "bytes", - "chrono", - "dashmap 6.1.0", - "datafusion", - "datafusion-expr", - "datafusion-functions", - "datafusion-physical-expr", - "datafusion-physical-plan", - "deepsize", - "either", - "futures", - "half", - "humantime", - "itertools 0.13.0", - "lance-arrow", - "lance-core", - "lance-datafusion", - "lance-encoding", - "lance-file", - "lance-geo", - "lance-index", - "lance-io", - "lance-linalg", - "lance-namespace", - "lance-table", - "log", - "moka", - "object_store", - "permutation", - "pin-project", - "prost", - "prost-types", - "rand 0.9.2", - "roaring", - "semver", - "serde", - "serde_json", - "snafu", - "tantivy 0.24.2", - "tokio", - "tokio-stream", - "tracing", - "url", - "uuid", -] - -[[package]] -name = "lance-arrow" -version = "1.0.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f4ee5508b225456d3d56998eaeef0d8fbce5ea93856df47b12a94d2e74153210" -dependencies = [ - "arrow-array", - "arrow-buffer", - "arrow-cast", - "arrow-data", - "arrow-schema", - "arrow-select", - "bytes", - "getrandom 0.2.16", - "half", - "jsonb", - "num-traits", - "rand 0.9.2", -] - -[[package]] -name = "lance-bitpacking" -version = "1.0.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d1c065fb3bd4a8cc4f78428443e990d4921aa08f707b676753db740e0b402a21" -dependencies = [ - "arrayref", - "paste", - "seq-macro", -] - -[[package]] -name = "lance-core" -version = "1.0.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e8856abad92e624b75cd57a04703f6441948a239463bdf973f2ac1924b0bcdbe" -dependencies = [ - "arrow-array", - "arrow-buffer", - "arrow-schema", - "async-trait", - "byteorder", - "bytes", - "chrono", - "datafusion-common", - "datafusion-sql", - "deepsize", - "futures", - "lance-arrow", - "libc", - "log", - "mock_instant", - "moka", - "num_cpus", - "object_store", - "pin-project", - "prost", - "rand 0.9.2", - "roaring", - "serde_json", - "snafu", - "tempfile", - "tokio", - "tokio-stream", - "tokio-util", - "tracing", - "url", -] - -[[package]] -name = "lance-datafusion" -version = "1.0.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4c8835308044cef5467d7751be87fcbefc2db01c22370726a8704bd62991693f" -dependencies = [ - "arrow", - "arrow-array", - "arrow-buffer", - "arrow-ord", - "arrow-schema", - "arrow-select", - "async-trait", - "chrono", - "datafusion", - "datafusion-common", - "datafusion-functions", - "datafusion-physical-expr", - "futures", - "jsonb", - "lance-arrow", - "lance-core", - "lance-datagen", - "lance-geo", - "log", - "pin-project", - "prost", - "snafu", - "tokio", - "tracing", -] - -[[package]] -name = "lance-datagen" -version = "1.0.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "612de1e888bb36f6bf51196a6eb9574587fdf256b1759a4c50e643e00d5f96d0" -dependencies = [ - "arrow", - "arrow-array", - "arrow-cast", - "arrow-schema", - "chrono", - "futures", - "half", - "hex", - "rand 0.9.2", - "rand_xoshiro", - "random_word", -] - -[[package]] -name = "lance-encoding" -version = "1.0.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2b456b29b135d3c7192602e516ccade38b5483986e121895fa43cf1fdb38bf60" -dependencies = [ - "arrow-arith", - "arrow-array", - "arrow-buffer", - "arrow-cast", - "arrow-data", - "arrow-schema", - "arrow-select", - "bytemuck", - "byteorder", - "bytes", - "fsst", - "futures", - "hex", - "hyperloglogplus", - "itertools 0.13.0", - "lance-arrow", - "lance-bitpacking", - "lance-core", - "log", - "lz4", - "num-traits", - "prost", - "prost-build", - "prost-types", - "rand 0.9.2", - "snafu", - "strum", - "tokio", - "tracing", - "xxhash-rust", - "zstd", -] - -[[package]] -name = "lance-file" -version = "1.0.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ab1538d14d5bb3735b4222b3f5aff83cfa59cc6ef7cdd3dd9139e4c77193c80b" -dependencies = [ - "arrow-arith", - "arrow-array", - "arrow-buffer", - "arrow-data", - "arrow-schema", - "arrow-select", - "async-recursion", - "async-trait", - "byteorder", - "bytes", - "datafusion-common", - "deepsize", - "futures", - "lance-arrow", - "lance-core", - "lance-encoding", - "lance-io", - "log", - "num-traits", - "object_store", - "prost", - "prost-build", - "prost-types", - "snafu", - "tokio", - "tracing", -] - -[[package]] -name = "lance-geo" -version = "1.0.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a5a69a2f3b55703d9c240ad7c5ffa2c755db69e9cf8aa05efe274a212910472d" -dependencies = [ - "datafusion", - "geo-types", - "geoarrow-array", - "geoarrow-schema", - "geodatafusion", -] - -[[package]] -name = "lance-index" -version = "1.0.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "0ea84613df6fa6b9168a1f056ba4f9cb73b90a1b452814c6fd4b3529bcdbfc78" -dependencies = [ - "arrow", - "arrow-arith", - "arrow-array", - "arrow-ord", - "arrow-schema", - "arrow-select", - "async-channel", - "async-recursion", - "async-trait", - "bitpacking", - "bitvec", - "bytes", - "crossbeam-queue", - "datafusion", - "datafusion-common", - "datafusion-expr", - "datafusion-physical-expr", - "datafusion-sql", - "deepsize", - "dirs 6.0.0", - "fst", - "futures", - "half", - "itertools 0.13.0", - "jsonb", - "lance-arrow", - "lance-core", - "lance-datafusion", - "lance-datagen", - "lance-encoding", - "lance-file", - "lance-io", - "lance-linalg", - "lance-table", - "libm", - "log", - "ndarray 0.16.1", - "num-traits", - "object_store", - "prost", - "prost-build", - "prost-types", - "rand 0.9.2", - "rand_distr 0.5.1", - "rayon", - "roaring", - "serde", - "serde_json", - "snafu", - "tantivy 0.24.2", - "tempfile", - "tokio", - "tracing", - "twox-hash", - "uuid", -] - -[[package]] -name = "lance-io" -version = "1.0.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6b3fc4c1d941fceef40a0edbd664dbef108acfc5d559bb9e7f588d0c733cbc35" -dependencies = [ - "arrow", - "arrow-arith", - "arrow-array", - "arrow-buffer", - "arrow-cast", - "arrow-data", - "arrow-schema", - "arrow-select", - "async-recursion", - "async-trait", - "aws-config", - "aws-credential-types", - "byteorder", - "bytes", - "chrono", - "deepsize", - "futures", - "lance-arrow", - "lance-core", - "lance-namespace", - "log", - "object_store", - "object_store_opendal", - "opendal", - "path_abs", - "pin-project", - "prost", - "rand 0.9.2", - "serde", - "shellexpand 3.1.1", - "snafu", - "tokio", - "tracing", - "url", -] - -[[package]] -name = "lance-linalg" -version = "1.0.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b62ffbc5ce367fbf700a69de3fe0612ee1a11191a64a632888610b6bacfa0f63" -dependencies = [ - "arrow-array", - "arrow-buffer", - "arrow-schema", - "cc", - "deepsize", - "half", - "lance-arrow", - "lance-core", - "num-traits", - "rand 0.9.2", -] - -[[package]] -name = "lance-namespace" -version = "1.0.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "791bbcd868ee758123a34e07d320a1fb99379432b5ecc0e78d6b4686e999b629" -dependencies = [ - "arrow", - "async-trait", - "bytes", - "lance-core", - "lance-namespace-reqwest-client", - "snafu", -] - -[[package]] -name = "lance-namespace-impls" -version = "1.0.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ee713505576f6b1988a491f77c7ca8b0cf7090a393598e63c85079fa70a53ebf" -dependencies = [ - "arrow", - "arrow-ipc", - "arrow-schema", - "async-trait", - "bytes", - "futures", - "lance", - "lance-core", - "lance-index", - "lance-io", - "lance-namespace", - "log", - "object_store", - "rand 0.9.2", - "serde_json", - "snafu", - "tokio", - "url", -] - -[[package]] -name = "lance-namespace-reqwest-client" -version = "0.0.18" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3ea349999bcda4eea53fc05d334b3775ec314761e6a706555c777d7a29b18d19" -dependencies = [ - "reqwest 0.12.24", - "serde", - "serde_json", - "serde_repr", - "url", -] - -[[package]] -name = "lance-table" -version = "1.0.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6fdb2d56bfa4d1511c765fa0cc00fdaa37e5d2d1cd2f57b3c6355d9072177052" -dependencies = [ - "arrow", - "arrow-array", - "arrow-buffer", - "arrow-ipc", - "arrow-schema", - "async-trait", - "aws-credential-types", - "aws-sdk-dynamodb", - "byteorder", - "bytes", - "chrono", - "deepsize", - "futures", - "lance-arrow", - "lance-core", - "lance-file", - "lance-io", - "log", - "object_store", - "prost", - "prost-build", - "prost-types", - "rand 0.9.2", - "rangemap", - "roaring", - "semver", - "serde", - "serde_json", - "snafu", - "tokio", - "tracing", - "url", - "uuid", -] - -[[package]] -name = "lance-testing" -version = "1.0.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d8ccb1a4a9284435c6a8c02c8c06e7e041bece0d7f722152159353cf55dc51e3" -dependencies = [ - "arrow-array", - "arrow-schema", - "lance-arrow", - "num-traits", - "rand 0.9.2", -] - -[[package]] -name = "lancedb" -version = "0.23.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "9217d7d3a1f4e088bdedaad9b4fa79045b077e07f961f1cd3ec6f90850c425f2" -dependencies = [ - "ahash 0.8.12", - "arrow", - "arrow-array", - "arrow-cast", - "arrow-data", - "arrow-ipc", - "arrow-ord", - "arrow-schema", - "arrow-select", - "async-trait", - "bytes", - "chrono", - "datafusion", - "datafusion-catalog", - "datafusion-common", - "datafusion-execution", - "datafusion-expr", - "datafusion-physical-plan", - "futures", - "half", - "lance", - "lance-arrow", - "lance-core", - "lance-datafusion", - "lance-datagen", - "lance-encoding", - "lance-file", - "lance-index", - "lance-io", - "lance-linalg", - "lance-namespace", - "lance-namespace-impls", - "lance-table", - "lance-testing", - "lazy_static", - "log", - "moka", - "num-traits", - "object_store", - "pin-project", - "rand 0.9.2", - "regex", - "semver", - "serde", - "serde_json", - "serde_with", - "snafu", - "tempfile", - "tokio", - "url", - "uuid", -] - [[package]] name = "lazy_static" version = "1.5.0" @@ -7403,63 +5394,6 @@ version = "0.2.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "0c2cdeb66e45e9f36bfad5bbdb4d2384e70936afbee843c6f6543f0c551ebb25" -[[package]] -name = "lexical-core" -version = "1.0.6" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7d8d125a277f807e55a77304455eb7b1cb52f2b18c143b60e766c120bd64a594" -dependencies = [ - "lexical-parse-float", - "lexical-parse-integer", - "lexical-util", - "lexical-write-float", - "lexical-write-integer", -] - -[[package]] -name = "lexical-parse-float" -version = "1.0.6" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "52a9f232fbd6f550bc0137dcb5f99ab674071ac2d690ac69704593cb4abbea56" -dependencies = [ - "lexical-parse-integer", - "lexical-util", -] - -[[package]] -name = "lexical-parse-integer" -version = "1.0.6" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "9a7a039f8fb9c19c996cd7b2fcce303c1b2874fe1aca544edc85c4a5f8489b34" -dependencies = [ - "lexical-util", -] - -[[package]] -name = "lexical-util" -version = "1.0.7" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2604dd126bb14f13fb5d1bd6a66155079cb9fa655b37f875b3a742c705dbed17" - -[[package]] -name = "lexical-write-float" -version = "1.0.6" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "50c438c87c013188d415fbabbb1dceb44249ab81664efbd31b14ae55dabb6361" -dependencies = [ - "lexical-util", - "lexical-write-integer", -] - -[[package]] -name = "lexical-write-integer" -version = "1.0.6" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "409851a618475d2d5796377cad353802345cba92c867d9fbcde9cf4eac4e14df" -dependencies = [ - "lexical-util", -] - [[package]] name = "lexicmp" version = "0.1.0" @@ -7470,10 +5404,13 @@ dependencies = [ ] [[package]] -name = "libbz2-rs-sys" -version = "0.2.2" +name = "lexicmp" +version = "0.2.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2c4a545a15244c7d945065b5d392b2d2d7f21526fba56ce51467b06ed445e8f7" +checksum = "0e8f89da8fd95c4eb6274e914694bea90c7826523b26f2a2fd863d44b9d42c43" +dependencies = [ + "deunicode", +] [[package]] name = "libc" @@ -7530,12 +5467,14 @@ dependencies = [ ] [[package]] -name = "libz-rs-sys" -version = "0.5.5" +name = "libz-sys" +version = "1.1.23" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c10501e7805cee23da17c7790e59df2870c0d4043ec6d03f67d31e2b53e77415" +checksum = "15d118bbf3771060e7311cc7bb0545b01d08a8b4a7de949198dec1fa0ca1c0f7" dependencies = [ - "zlib-rs", + "cc", + "pkg-config", + "vcpkg", ] [[package]] @@ -7615,51 +5554,36 @@ checksum = "5e5032e24019045c762d3c0f28f5b6b8bbf38563a65908389bf7978758920897" [[package]] name = "logos" -version = "0.15.1" +version = "0.16.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ff472f899b4ec2d99161c51f60ff7075eeb3097069a36050d8037a6325eb8154" +checksum = "eb2c55a318a87600ea870ff8c2012148b44bf18b74fad48d0f835c38c7d07c5f" dependencies = [ "logos-derive", ] [[package]] name = "logos-codegen" -version = "0.15.1" +version = "0.16.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "192a3a2b90b0c05b27a0b2c43eecdb7c415e29243acc3f89cc8247a5b693045c" +checksum = "58b3ffaa284e1350d017a57d04ada118c4583cf260c8fb01e0fe28a2e9cf8970" dependencies = [ - "beef", "fnv", - "lazy_static", "proc-macro2", "quote", + "regex-automata", "regex-syntax", - "rustc_version", "syn 2.0.114", ] [[package]] name = "logos-derive" -version = "0.15.1" +version = "0.16.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "605d9697bcd5ef3a42d38efc51541aa3d6a4a25f7ab6d1ed0da5ac632a26b470" +checksum = "52d3a9855747c17eaf4383823f135220716ab49bea5fbea7dd42cc9a92f8aa31" dependencies = [ "logos-codegen", ] -[[package]] -name = "loom" -version = "0.7.2" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "419e0dc8046cb947daa77eb95ae174acfbddb7673b4151f56d1eed8e93fbfaca" -dependencies = [ - "cfg-if", - "generator", - "scoped-tls", - "tracing", - "tracing-subscriber", -] - [[package]] name = "loop9" version = "0.1.5" @@ -7708,6 +5632,12 @@ name = "lz4_flex" version = "0.11.5" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "08ab2867e3eeeca90e844d1940eab391c9dc5228783db2ed999acbc0a9ed375a" + +[[package]] +name = "lz4_flex" +version = "0.12.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ab6473172471198271ff72e9379150e9dfd70d8e533e0752a27e515b48dd375e" dependencies = [ "twox-hash", ] @@ -7718,17 +5648,6 @@ version = "0.15.7" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "1670343e58806300d87950e3401e820b519b9384281bbabfb15e3636689ffd69" -[[package]] -name = "lzma-sys" -version = "0.1.20" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "5fda04ab3764e6cde78b9974eec4f779acaba7c4e84b36eca3cf77c581b85d27" -dependencies = [ - "cc", - "libc", - "pkg-config", -] - [[package]] name = "mac" version = "0.1.1" @@ -7833,10 +5752,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "a06de3016e9fae57a36fd14dba131fccf49f74b40b7fbdb472f96e361ec71a08" dependencies = [ "autocfg", - "num_cpus", - "once_cell", "rawpointer", - "thread-tree", ] [[package]] @@ -8014,12 +5930,6 @@ dependencies = [ "windows-sys 0.61.2", ] -[[package]] -name = "mock_instant" -version = "0.6.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "dce6dd36094cac388f119d2e9dc82dc730ef91c32a6222170d630e5414b956e6" - [[package]] name = "mockall" version = "0.14.0" @@ -8056,10 +5966,10 @@ dependencies = [ "bytes", "colored", "futures-core", - "http 1.4.0", - "http-body 1.0.1", + "http", + "http-body", "http-body-util", - "hyper 1.8.1", + "hyper", "hyper-util", "log", "pin-project-lite", @@ -8132,7 +6042,7 @@ dependencies = [ "bytes", "encoding_rs", "futures-util", - "http 1.4.0", + "http", "httparse", "memchr", "mime", @@ -8140,12 +6050,6 @@ dependencies = [ "version_check", ] -[[package]] -name = "multimap" -version = "0.10.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1d87ecb2933e8aeadb3e3a02b828fed80a7528047e68b4f424523a0981a3a084" - [[package]] name = "murmurhash32" version = "0.3.1" @@ -8192,21 +6096,6 @@ dependencies = [ "rawpointer", ] -[[package]] -name = "ndarray" -version = "0.16.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "882ed72dce9365842bf196bdeedf5055305f11fc8c03dee7bb0194a6cad34841" -dependencies = [ - "matrixmultiply", - "num-complex", - "num-integer", - "num-traits", - "portable-atomic", - "portable-atomic-util", - "rawpointer", -] - [[package]] name = "ndarray" version = "0.17.2" @@ -8237,6 +6126,21 @@ dependencies = [ "rand 0.8.5", ] +[[package]] +name = "ndarray-stats" +version = "0.7.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9b6e54a8b65764f71827a90ca1d56965ec0c67f069f996477bd493402a901d1f" +dependencies = [ + "indexmap 2.13.0", + "itertools 0.13.0", + "ndarray 0.17.2", + "noisy_float", + "num-integer", + "num-traits", + "rand 0.8.5", +] + [[package]] name = "new_debug_unreachable" version = "1.0.6" @@ -8484,34 +6388,31 @@ dependencies = [ "libc", ] -[[package]] -name = "num_enum" -version = "0.7.5" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b1207a7e20ad57b847bbddc6776b968420d38292bbfe2089accff5e19e82454c" -dependencies = [ - "num_enum_derive", - "rustversion", -] - -[[package]] -name = "num_enum_derive" -version = "0.7.5" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ff32365de1b6743cb203b710788263c44a03de03802daf96092f2da4fe6ba4d7" -dependencies = [ - "proc-macro-crate", - "proc-macro2", - "quote", - "syn 2.0.114", -] - [[package]] name = "number_prefix" version = "0.4.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "830b246a0e5f20af87141b25c173cd1b609bd7779a4617d6ec582abaf90870f3" +[[package]] +name = "objc2-core-foundation" +version = "0.3.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2a180dd8642fa45cdb7dd721cd4c11b1cadd4929ce112ebd8b9f5803cc79d536" +dependencies = [ + "bitflags 2.10.0", +] + +[[package]] +name = "objc2-io-kit" +version = "0.3.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "33fafba39597d6dc1fb709123dfa8289d39406734be322956a69f0931c73bb15" +dependencies = [ + "libc", + "objc2-core-foundation", +] + [[package]] name = "object" version = "0.32.2" @@ -8540,28 +6441,14 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "4c1be0c6c22ec0817cdc77d3842f721a17fd30ab6965001415b5402a74e6b740" dependencies = [ "async-trait", - "base64 0.22.1", "bytes", "chrono", - "form_urlencoded", "futures", - "http 1.4.0", - "http-body-util", - "httparse", + "http", "humantime", - "hyper 1.8.1", "itertools 0.14.0", - "md-5", "parking_lot", "percent-encoding", - "quick-xml 0.38.4", - "rand 0.9.2", - "reqwest 0.12.24", - "ring", - "rustls-pemfile", - "serde", - "serde_json", - "serde_urlencoded", "thiserror 2.0.18", "tokio", "tracing", @@ -8572,19 +6459,27 @@ dependencies = [ ] [[package]] -name = "object_store_opendal" -version = "0.55.0" +name = "object_store" +version = "0.13.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "113ab0769e972eee585e57407b98de08bda5354fa28e8ba4d89038d6cb6a8991" +checksum = "c2858065e55c148d294a9f3aae3b0fa9458edadb41a108397094566f4e3c0dfb" dependencies = [ "async-trait", "bytes", "chrono", "futures", - "object_store", - "opendal", - "pin-project", + "http", + "humantime", + "itertools 0.14.0", + "parking_lot", + "percent-encoding", + "thiserror 2.0.18", "tokio", + "tracing", + "url", + "walkdir", + "wasm-bindgen-futures", + "web-time", ] [[package]] @@ -8649,36 +6544,6 @@ version = "0.3.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "c08d65885ee38876c4f86fa503fb49d7b507c2b62552df7c70b2fce627e06381" -[[package]] -name = "opendal" -version = "0.55.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d075ab8a203a6ab4bc1bce0a4b9fe486a72bf8b939037f4b78d95386384bc80a" -dependencies = [ - "anyhow", - "backon", - "base64 0.22.1", - "bytes", - "crc32c", - "futures", - "getrandom 0.2.16", - "http 1.4.0", - "http-body 1.0.1", - "jiff", - "log", - "md-5", - "percent-encoding", - "quick-xml 0.38.4", - "reqsign", - "reqwest 0.12.24", - "serde", - "serde_json", - "sha2", - "tokio", - "url", - "uuid", -] - [[package]] name = "openssl" version = "0.10.75" @@ -8889,16 +6754,6 @@ dependencies = [ "num-traits", ] -[[package]] -name = "ordered-multimap" -version = "0.7.3" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "49203cdcae0030493bad186b28da2fa25645fa276a51b6fec8010d281e02ef79" -dependencies = [ - "dlv-list", - "hashbrown 0.14.5", -] - [[package]] name = "ort" version = "2.0.0-rc.11" @@ -8923,12 +6778,6 @@ dependencies = [ "ureq 3.1.4", ] -[[package]] -name = "outref" -version = "0.5.2" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1a80800c0488c3a21695ea981a54918fbb37abf04f4d0720c453632255e2ff0e" - [[package]] name = "ownedbytes" version = "0.7.0" @@ -8981,6 +6830,16 @@ dependencies = [ "winapi", ] +[[package]] +name = "papaya" +version = "0.2.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f92dd0b07c53a0a0c764db2ace8c541dc47320dad97c2200c2a637ab9dd2328f" +dependencies = [ + "equivalent", + "seize", +] + [[package]] name = "parking" version = "2.2.1" @@ -9010,43 +6869,6 @@ dependencies = [ "windows-link 0.2.1", ] -[[package]] -name = "parquet" -version = "56.2.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f0dbd48ad52d7dccf8ea1b90a3ddbfaea4f69878dd7683e51c507d4bc52b5b27" -dependencies = [ - "ahash 0.8.12", - "arrow-array", - "arrow-buffer", - "arrow-cast", - "arrow-data", - "arrow-ipc", - "arrow-schema", - "arrow-select", - "base64 0.22.1", - "brotli 8.0.2", - "bytes", - "chrono", - "flate2", - "futures", - "half", - "hashbrown 0.16.1", - "lz4_flex", - "num", - "num-bigint", - "object_store", - "paste", - "ring", - "seq-macro", - "simdutf8", - "snap", - "thrift", - "tokio", - "twox-hash", - "zstd", -] - [[package]] name = "parse-zoneinfo" version = "0.3.1" @@ -9085,18 +6907,6 @@ version = "1.0.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "17359afc20d7ab31fdb42bb844c8b3bb1dabd7dcf7e68428492da7f16966fcef" -[[package]] -name = "path_abs" -version = "0.5.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "05ef02f6342ac01d8a93b65f96db53fe68a92a15f41144f97fb00a9e669633c3" -dependencies = [ - "serde", - "serde_derive", - "std_prelude", - "stfu8", -] - [[package]] name = "pathdiff" version = "0.2.3" @@ -9115,6 +6925,12 @@ dependencies = [ "sha2", ] +[[package]] +name = "pdqselect" +version = "0.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4ec91767ecc0a0bbe558ce8c9da33c068066c57ecc8bb8477ef8c1ad3ef77c27" + [[package]] name = "pem" version = "3.0.6" @@ -9140,12 +6956,6 @@ version = "2.3.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "9b4f627cb1b25917193a259e49bdad08f671f8d9708acfd5fe0a8c1455d87220" -[[package]] -name = "permutation" -version = "0.4.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "df202b0b0f5b8e389955afd5f27b007b00fb948162953f1db9c70d2c7e3157d7" - [[package]] name = "pest" version = "2.8.3" @@ -9237,17 +7047,19 @@ version = "0.11.3" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "1fd6780a80ae0c52cc120a26a1a42c1ae51b247a253e4e06113d23d2c2edd078" dependencies = [ - "phf_macros", + "phf_macros 0.11.3", "phf_shared 0.11.3", ] [[package]] name = "phf" -version = "0.12.1" +version = "0.13.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "913273894cec178f401a31ec4b656318d95473527be05c0752cc41cdc32be8b7" +checksum = "c1562dc717473dbaa4c1f85a36410e03c047b2e7df7f45ee938fbef64ae7fadf" dependencies = [ - "phf_shared 0.12.1", + "phf_macros 0.13.1", + "phf_shared 0.13.1", + "serde", ] [[package]] @@ -9256,7 +7068,7 @@ version = "0.11.3" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "aef8048c789fa5e851558d709946d6d79a8ff88c0440c587967f8e94bfb1216a" dependencies = [ - "phf_generator", + "phf_generator 0.11.3", "phf_shared 0.11.3", ] @@ -9270,13 +7082,23 @@ dependencies = [ "rand 0.8.5", ] +[[package]] +name = "phf_generator" +version = "0.13.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "135ace3a761e564ec88c03a77317a7c6b80bb7f7135ef2544dbe054243b89737" +dependencies = [ + "fastrand", + "phf_shared 0.13.1", +] + [[package]] name = "phf_macros" version = "0.11.3" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "f84ac04429c13a7ff43785d75ad27569f2951ce0ffd30a3321230db2fc727216" dependencies = [ - "phf_generator", + "phf_generator 0.11.3", "phf_shared 0.11.3", "proc-macro2", "quote", @@ -9284,6 +7106,20 @@ dependencies = [ "unicase", ] +[[package]] +name = "phf_macros" +version = "0.13.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "812f032b54b1e759ccd5f8b6677695d5268c588701effba24601f6932f8269ef" +dependencies = [ + "phf_generator 0.13.1", + "phf_shared 0.13.1", + "proc-macro2", + "quote", + "syn 2.0.114", + "unicase", +] + [[package]] name = "phf_shared" version = "0.11.3" @@ -9296,11 +7132,12 @@ dependencies = [ [[package]] name = "phf_shared" -version = "0.12.1" +version = "0.13.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "06005508882fb681fd97892ecff4b7fd0fee13ef1aa569f8695dae7ab9099981" +checksum = "e57fef6bc5981e38c2ce2d63bfa546861309f875b8a75f092d1d54ae2d64f266" dependencies = [ "siphasher", + "unicase", ] [[package]] @@ -9352,21 +7189,6 @@ dependencies = [ "spki", ] -[[package]] -name = "pkcs5" -version = "0.7.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e847e2c91a18bfa887dd028ec33f2fe6f25db77db3619024764914affe8b69a6" -dependencies = [ - "aes", - "cbc", - "der", - "pbkdf2", - "scrypt", - "sha2", - "spki", -] - [[package]] name = "pkcs8" version = "0.10.2" @@ -9374,8 +7196,6 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "f950b2377845cebe5cf8b5165cb3cc1a5e0fa5cfa3e1f7f55707d8fd82e0a7b7" dependencies = [ "der", - "pkcs5", - "rand_core 0.6.4", "spki", ] @@ -9691,39 +7511,19 @@ dependencies = [ [[package]] name = "prost" -version = "0.13.5" +version = "0.14.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2796faa41db3ec313a31f7624d9286acf277b52de526150b7e69f3debf891ee5" +checksum = "d2ea70524a2f82d518bce41317d0fae74151505651af45faf1ffbd6fd33f0568" dependencies = [ "bytes", "prost-derive", ] -[[package]] -name = "prost-build" -version = "0.13.5" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "be769465445e8c1474e9c5dac2018218498557af32d9ed057325ec9a41ae81bf" -dependencies = [ - "heck", - "itertools 0.14.0", - "log", - "multimap", - "once_cell", - "petgraph 0.7.1", - "prettyplease", - "prost", - "prost-types", - "regex", - "syn 2.0.114", - "tempfile", -] - [[package]] name = "prost-derive" -version = "0.13.5" +version = "0.14.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8a56d757972c98b346a9b766e3f02746cde6dd1cd1d1d563472929fdd74bec4d" +checksum = "27c6023962132f4b30eb4c172c91ce92d933da334c59c23cddee82358ddafb0b" dependencies = [ "anyhow", "itertools 0.14.0", @@ -9734,9 +7534,9 @@ dependencies = [ [[package]] name = "prost-types" -version = "0.13.5" +version = "0.14.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "52c2c1bf36ddb1a1c396b3601a3cec27c2462e45f07c386894ec3ccf5332bd16" +checksum = "8991c4cbdb8bc5b11f0b074ffe286c30e523de90fee5ba8132f1399f23cb3dd7" dependencies = [ "prost", ] @@ -9857,26 +7657,6 @@ version = "2.0.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "a993555f31e5a609f617c12db6250dedcac1b0a85076912c436e6fc9b2c8e6a3" -[[package]] -name = "quick-xml" -version = "0.37.5" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "331e97a1af0bf59823e6eadffe373d7b27f485be8748f71471c662c1f269b7fb" -dependencies = [ - "memchr", - "serde", -] - -[[package]] -name = "quick-xml" -version = "0.38.4" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b66c2058c55a409d601666cffe35f04333cf1013010882cec174a7467cd4e21c" -dependencies = [ - "memchr", - "serde", -] - [[package]] name = "quick_cache" version = "0.5.2" @@ -9913,8 +7693,8 @@ dependencies = [ "quinn-proto", "quinn-udp", "rustc-hash 2.1.1", - "rustls 0.23.35", - "socket2 0.6.1", + "rustls", + "socket2", "thiserror 2.0.18", "tokio", "tracing", @@ -9934,7 +7714,7 @@ dependencies = [ "rand 0.9.2", "ring", "rustc-hash 2.1.1", - "rustls 0.23.35", + "rustls", "rustls-pki-types", "slab", "thiserror 2.0.18", @@ -9952,7 +7732,7 @@ dependencies = [ "cfg_aliases", "libc", "once_cell", - "socket2 0.6.1", + "socket2", "tracing", "windows-sys 0.60.2", ] @@ -10006,7 +7786,18 @@ version = "0.2.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "c069c179fcdc6a2fe24d8d18305cf085fdbd4f922c041943e203685d6a1c58fd" dependencies = [ - "endian-type", + "endian-type 0.1.2", + "nibble_vec", + "serde", +] + +[[package]] +name = "radix_trie" +version = "0.3.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3b4431027dcd37fc2a73ef740b5f233aa805897935b8bce0195e41bbf9a3289a" +dependencies = [ + "endian-type 0.2.0", "nibble_vec", "serde", ] @@ -10080,16 +7871,6 @@ dependencies = [ "rand 0.8.5", ] -[[package]] -name = "rand_distr" -version = "0.5.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6a8615d50dcf34fa31f7ab52692afec947c4dd0ab803cc87cb3b0b4570ff7463" -dependencies = [ - "num-traits", - "rand 0.9.2", -] - [[package]] name = "rand_xorshift" version = "0.4.0" @@ -10099,34 +7880,6 @@ dependencies = [ "rand_core 0.9.3", ] -[[package]] -name = "rand_xoshiro" -version = "0.7.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f703f4665700daf5512dcca5f43afa6af89f09db47fb56be587f80636bda2d41" -dependencies = [ - "rand_core 0.9.3", -] - -[[package]] -name = "random_word" -version = "0.5.2" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e47a395bdb55442b883c89062d6bcff25dc90fa5f8369af81e0ac6d49d78cf81" -dependencies = [ - "ahash 0.8.12", - "brotli 8.0.2", - "paste", - "rand 0.9.2", - "unicase", -] - -[[package]] -name = "rangemap" -version = "1.7.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "973443cf09a9c8656b574a866ab68dfa19f0867d0340648c7d2f6a71b8a8ea68" - [[package]] name = "rav1e" version = "0.8.1" @@ -10274,26 +8027,6 @@ version = "0.4.3" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "bbc4a4ea2a66a41a1152c4b3d86e8954dc087bdf33af35446e6e176db4e73c8c" -[[package]] -name = "recursive" -version = "0.1.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "0786a43debb760f491b1bc0269fe5e84155353c67482b9e60d0cfb596054b43e" -dependencies = [ - "recursive-proc-macro-impl", - "stacker", -] - -[[package]] -name = "recursive-proc-macro-impl" -version = "0.1.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "76009fbe0614077fc1a2ce255e3a1881a2e3a3527097d5dc6d8212c585e7e38b" -dependencies = [ - "quote", - "syn 2.0.114", -] - [[package]] name = "redox_syscall" version = "0.5.18" @@ -10381,18 +8114,18 @@ dependencies = [ "regex-syntax", ] -[[package]] -name = "regex-lite" -version = "0.1.8" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8d942b98df5e658f56f20d592c7f868833fe38115e65c33003d8cd224b0155da" - [[package]] name = "regex-syntax" version = "0.8.8" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "7a2d987857b319362043e95f5353c0535c1f58eec5336fdfcf626430af7def58" +[[package]] +name = "relative-path" +version = "1.9.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ba39f3699c378cd8970968dcbff9c43159ea4cfbd88d43c00b22f2ef10a435d2" + [[package]] name = "rend" version = "0.4.2" @@ -10402,38 +8135,6 @@ dependencies = [ "bytecheck", ] -[[package]] -name = "reqsign" -version = "0.16.5" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "43451dbf3590a7590684c25fb8d12ecdcc90ed3ac123433e500447c7d77ed701" -dependencies = [ - "anyhow", - "async-trait", - "base64 0.22.1", - "chrono", - "form_urlencoded", - "getrandom 0.2.16", - "hex", - "hmac", - "home", - "http 1.4.0", - "jsonwebtoken 9.3.1", - "log", - "once_cell", - "percent-encoding", - "quick-xml 0.37.5", - "rand 0.8.5", - "reqwest 0.12.24", - "rsa", - "rust-ini", - "serde", - "serde_json", - "sha1", - "sha2", - "tokio", -] - [[package]] name = "reqwasm" version = "0.5.0" @@ -10449,18 +8150,17 @@ version = "0.12.24" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "9d0946410b9f7b082a427e4ef5c8ff541a88b357bc6c637c40db3a68ac70a36f" dependencies = [ - "async-compression", "base64 0.22.1", "bytes", "encoding_rs", "futures-core", "futures-util", - "h2 0.4.12", - "http 1.4.0", - "http-body 1.0.1", + "h2", + "http", + "http-body", "http-body-util", - "hyper 1.8.1", - "hyper-rustls 0.27.7", + "hyper", + "hyper-rustls", "hyper-tls", "hyper-util", "js-sys", @@ -10471,8 +8171,7 @@ dependencies = [ "percent-encoding", "pin-project-lite", "quinn", - "rustls 0.23.35", - "rustls-native-certs 0.8.3", + "rustls", "rustls-pki-types", "serde", "serde_json", @@ -10480,7 +8179,7 @@ dependencies = [ "sync_wrapper", "tokio", "tokio-native-tls", - "tokio-rustls 0.26.4", + "tokio-rustls", "tokio-util", "tower", "tower-http", @@ -10504,27 +8203,28 @@ dependencies = [ "encoding_rs", "futures-core", "futures-util", - "h2 0.4.12", - "http 1.4.0", - "http-body 1.0.1", + "h2", + "http", + "http-body", "http-body-util", - "hyper 1.8.1", - "hyper-rustls 0.27.7", + "hyper", + "hyper-rustls", "hyper-util", "js-sys", "log", "mime", + "mime_guess", "percent-encoding", "pin-project-lite", "quinn", - "rustls 0.23.35", + "rustls", "rustls-pki-types", "rustls-platform-verifier", "serde", "serde_json", "sync_wrapper", "tokio", - "tokio-rustls 0.26.4", + "tokio-rustls", "tokio-util", "tower", "tower-http", @@ -10564,7 +8264,23 @@ dependencies = [ "geo 0.28.0", "regex", "revision-derive 0.11.0", - "roaring", + "roaring 0.10.12", + "rust_decimal", + "uuid", +] + +[[package]] +name = "revision" +version = "0.17.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "11c3c8ec8b2be254beb5f8acdd80cdd57b7b5d40988c2ec3d0b7cdb6f7c2829b" +dependencies = [ + "bytes", + "chrono", + "geo 0.31.0", + "regex", + "revision-derive 0.17.0", + "roaring 0.11.3", "rust_decimal", "uuid", ] @@ -10591,6 +8307,17 @@ dependencies = [ "syn 2.0.114", ] +[[package]] +name = "revision-derive" +version = "0.17.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "76be63634a8b1809e663bc0b975d78f6883c0fadbcce9c52e19b9e421f423357" +dependencies = [ + "proc-macro2", + "quote", + "syn 2.0.114", +] + [[package]] name = "rfc6979" version = "0.4.0" @@ -10622,7 +8349,7 @@ dependencies = [ "futures", "futures-timer", "glob", - "http 1.4.0", + "http", "mime", "mime_guess", "nanoid", @@ -10649,15 +8376,15 @@ dependencies = [ "cfg-if", "getrandom 0.2.16", "libc", - "untrusted", + "untrusted 0.9.0", "windows-sys 0.52.0", ] [[package]] name = "rkyv" -version = "0.7.45" +version = "0.7.46" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "9008cd6385b9e161d8229e1f6549dd23c3d022f132a2ea37ac3a10ac4935779b" +checksum = "2297bf9c81a3f0dc96bc9521370b88f054168c29826a75e89c55ff196e7ed6a1" dependencies = [ "bitvec", "bytecheck", @@ -10673,9 +8400,9 @@ dependencies = [ [[package]] name = "rkyv_derive" -version = "0.7.45" +version = "0.7.46" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "503d1d27590a2b0a3a4ca4c94755aa2875657196ecbf401a42eff41d7de532c0" +checksum = "84d7b42d4b8d06048d3ac8db0eb31bcb942cbeb709f0b5f2b2ebde398d3038f5" dependencies = [ "proc-macro2", "quote", @@ -10724,6 +8451,17 @@ dependencies = [ "serde", ] +[[package]] +name = "roaring" +version = "0.11.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8ba9ce64a8f45d7fc86358410bb1a82e8c987504c0d4900e9141d69a9f26c885" +dependencies = [ + "bytemuck", + "byteorder", + "serde", +] + [[package]] name = "robust" version = "1.2.0" @@ -10755,24 +8493,102 @@ dependencies = [ "pkcs1", "pkcs8", "rand_core 0.6.4", - "sha2", "signature", "spki", "subtle", "zeroize", ] +[[package]] +name = "rstar" +version = "0.8.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3a45c0e8804d37e4d97e55c6f258bc9ad9c5ee7b07437009dd152d764949a27c" +dependencies = [ + "heapless 0.6.1", + "num-traits", + "pdqselect", + "serde", + "smallvec", +] + +[[package]] +name = "rstar" +version = "0.9.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b40f1bfe5acdab44bc63e6699c28b74f75ec43afb59f3eda01e145aff86a25fa" +dependencies = [ + "heapless 0.7.17", + "num-traits", + "serde", + "smallvec", +] + +[[package]] +name = "rstar" +version = "0.10.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1f39465655a1e3d8ae79c6d9e007f4953bfc5d55297602df9dc38f9ae9f1359a" +dependencies = [ + "heapless 0.7.17", + "num-traits", + "serde", + "smallvec", +] + +[[package]] +name = "rstar" +version = "0.11.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "73111312eb7a2287d229f06c00ff35b51ddee180f017ab6dec1f69d62ac098d6" +dependencies = [ + "heapless 0.7.17", + "num-traits", + "serde", + "smallvec", +] + [[package]] name = "rstar" version = "0.12.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "421400d13ccfd26dfa5858199c30a5d76f9c54e0dba7575273025b43c5175dbb" dependencies = [ - "heapless", + "heapless 0.8.0", "num-traits", + "serde", "smallvec", ] +[[package]] +name = "rstest" +version = "0.26.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f5a3193c063baaa2a95a33f03035c8a72b83d97a54916055ba22d35ed3839d49" +dependencies = [ + "futures-timer", + "futures-util", + "rstest_macros", +] + +[[package]] +name = "rstest_macros" +version = "0.26.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9c845311f0ff7951c5506121a9ad75aec44d083c31583b2ea5a30bcb0b0abba0" +dependencies = [ + "cfg-if", + "glob", + "proc-macro-crate", + "proc-macro2", + "quote", + "regex", + "relative-path", + "rustc_version", + "syn 2.0.114", + "unicode-ident", +] + [[package]] name = "rstml" version = "0.12.1" @@ -10798,16 +8614,6 @@ dependencies = [ "windows-sys 0.52.0", ] -[[package]] -name = "rust-ini" -version = "0.21.3" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "796e8d2b6696392a43bea58116b667fb4c29727dc5abd27d6acf338bb4f688c7" -dependencies = [ - "cfg-if", - "ordered-multimap", -] - [[package]] name = "rust-multipart-rfc7578_2" version = "0.8.0" @@ -10817,7 +8623,7 @@ dependencies = [ "bytes", "futures-core", "futures-util", - "http 1.4.0", + "http", "mime", "rand 0.9.2", "thiserror 2.0.18", @@ -10835,9 +8641,9 @@ dependencies = [ [[package]] name = "rust_decimal" -version = "1.39.0" +version = "1.40.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "35affe401787a9bd846712274d97654355d21b2a2c092a3139aabe31e9022282" +checksum = "61f703d19852dbf87cbc513643fa81428361eb6940f1ac14fd58155d295a3eb0" dependencies = [ "arrayvec 0.7.6", "borsh", @@ -10867,6 +8673,12 @@ version = "2.1.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "357703d41365b4b27c590e3ed91eabb1b663f07c4c084095e60cbed4362dff0d" +[[package]] +name = "rustc-literal-escaper" +version = "0.0.7" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8be87abb9e40db7466e0681dc8ecd9dcfd40360cb10b4c8fe24a7c4c3669b198" + [[package]] name = "rustc_lexer" version = "0.1.0" @@ -10923,21 +8735,9 @@ dependencies = [ [[package]] name = "rustls" -version = "0.21.12" +version = "0.23.36" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3f56a14d1f48b391359b22f731fd4bd7e43c97f3c50eee276f3aa09c94784d3e" -dependencies = [ - "log", - "ring", - "rustls-webpki 0.101.7", - "sct", -] - -[[package]] -name = "rustls" -version = "0.23.35" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "533f54bc6a7d4f647e46ad909549eda97bf5afc1585190ef692b4286b198bd8f" +checksum = "c665f33d38cea657d9614f766881e4d510e0eda4239891eea56b4cadcf01801b" dependencies = [ "aws-lc-rs", "log", @@ -10985,9 +8785,9 @@ dependencies = [ [[package]] name = "rustls-pki-types" -version = "1.13.0" +version = "1.14.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "94182ad936a0c91c324cd46c6511b9510ed16af436d7b5bab34beab0afd55f7a" +checksum = "be040f8b0a225e40375822a563fa9524378b9d63112f53e19ffff34df5d33fdd" dependencies = [ "web-time", "zeroize", @@ -11004,7 +8804,7 @@ dependencies = [ "jni", "log", "once_cell", - "rustls 0.23.35", + "rustls", "rustls-native-certs 0.8.3", "rustls-platform-verifier-android", "rustls-webpki 0.103.8", @@ -11020,16 +8820,6 @@ version = "0.1.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "f87165f0995f63a9fbeea62b64d10b4d9d8e78ec6d7d51fb2125fda7bb36788f" -[[package]] -name = "rustls-webpki" -version = "0.101.7" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8b6275d1ee7a1cd780b64aca7726599a1dbc893b1e64144529e55c3c2f745765" -dependencies = [ - "ring", - "untrusted", -] - [[package]] name = "rustls-webpki" version = "0.102.8" @@ -11037,7 +8827,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "64ca1bc8749bd4cf37b5ce386cc146580777b4e8572c7b97baf22c83f444bee9" dependencies = [ "rustls-pki-types", - "untrusted", + "untrusted 0.9.0", ] [[package]] @@ -11049,7 +8839,7 @@ dependencies = [ "aws-lc-rs", "ring", "rustls-pki-types", - "untrusted", + "untrusted 0.9.0", ] [[package]] @@ -11151,12 +8941,6 @@ dependencies = [ "syn 2.0.114", ] -[[package]] -name = "scoped-tls" -version = "1.0.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e1cf6437eb19a8f4a6cc0f7dca544973b0b78843adbfeb3683d1a94a0024a294" - [[package]] name = "scopeguard" version = "1.2.0" @@ -11175,16 +8959,6 @@ dependencies = [ "sha2", ] -[[package]] -name = "sct" -version = "0.7.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "da046153aa2352493d6cb7da4b6e5c0c057d8a1d0a9aa8560baffdd945acd414" -dependencies = [ - "ring", - "untrusted", -] - [[package]] name = "seahash" version = "4.1.0" @@ -11199,7 +8973,7 @@ checksum = "d3e97a565f76233a6003f9f5c54be1d9c5bdfa3eccfb189469f11ec4901c47dc" dependencies = [ "base16ct", "der", - "generic-array", + "generic-array 0.14.9", "pkcs8", "subtle", "zeroize", @@ -11211,33 +8985,34 @@ version = "0.1.0" dependencies = [ "aes-gcm", "anyhow", + "async-nats", "async-trait", "axum", "axum-server", "base64 0.22.1", - "cedar-policy 4.8.1", + "cedar-policy 4.9.0", "chacha20poly1305", "chrono", "clap", "hex", "hkdf", - "hyper 1.8.1", + "hyper", "hyper-util", "openssl", "oqs", "rand 0.9.2", "regex", "reqwest 0.13.1", - "rustls 0.23.35", + "rustls", "rustls-pemfile", "serde", "serde_json", "sha2", "sharks", - "surrealdb", + "surrealdb 3.0.0", "thiserror 2.0.18", "tokio", - "tokio-rustls 0.26.4", + "tokio-rustls", "toml 0.9.8", "tower", "tower-http", @@ -11282,6 +9057,16 @@ dependencies = [ "libc", ] +[[package]] +name = "seize" +version = "0.5.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5b55fb86dfd3a2f5f76ea78310a88f96c4ea21a3031f8d212443d56123fd0521" +dependencies = [ + "libc", + "windows-sys 0.61.2", +] + [[package]] name = "self_cell" version = "1.2.2" @@ -11307,12 +9092,6 @@ dependencies = [ "futures-core", ] -[[package]] -name = "seq-macro" -version = "0.3.6" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1bc711410fbe7399f390ca1c3b60ad0f53f80e95c5eb935e52268a0e2cd49acc" - [[package]] name = "serde" version = "1.0.228" @@ -11472,9 +9251,9 @@ dependencies = [ [[package]] name = "serde_with" -version = "3.15.1" +version = "3.16.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "aa66c845eee442168b2c8134fec70ac50dc20e760769c8ba0ad1319ca1959b04" +checksum = "4fa237f2807440d238e0364a218270b98f767a00d3dada77b1c53ae88940e2e7" dependencies = [ "base64 0.22.1", "chrono", @@ -11491,9 +9270,9 @@ dependencies = [ [[package]] name = "serde_with_macros" -version = "3.15.1" +version = "3.16.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b91a903660542fced4e99881aa481bdbaec1634568ee02e0b8bd57c64cb38955" +checksum = "52a8e3ca0ca629121f70ab50f95249e5a6f925cc0f6ffe8256c45b728875706c" dependencies = [ "darling 0.21.3", "proc-macro2", @@ -11527,7 +9306,7 @@ dependencies = [ "dashmap 6.1.0", "futures", "gloo-net 0.6.0", - "http 1.4.0", + "http", "js-sys", "pin-project-lite", "rustc_version", @@ -11639,21 +9418,18 @@ dependencies = [ "dirs 4.0.0", ] -[[package]] -name = "shellexpand" -version = "3.1.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8b1fdf65dd6331831494dd616b30351c38e96e45921a27745cf98490458b90bb" -dependencies = [ - "dirs 6.0.0", -] - [[package]] name = "shlex" version = "1.3.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "0fda2ff0d084019ba4d7c6f371c95d8fd75ce3524c3cb8fb653a3023f6323e64" +[[package]] +name = "sif-itree" +version = "0.4.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "142099cd6db3c4fab61e5133c62ff80b26674391e195860791fda0b1be3e5080" + [[package]] name = "signal-hook" version = "0.3.18" @@ -11828,43 +9604,12 @@ dependencies = [ "serde_core", ] -[[package]] -name = "snafu" -version = "0.8.9" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6e84b3f4eacbf3a1ce05eac6763b4d629d60cbc94d632e4092c54ade71f1e1a2" -dependencies = [ - "snafu-derive", -] - -[[package]] -name = "snafu-derive" -version = "0.8.9" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c1c97747dbf44bb1ca44a561ece23508e99cb592e862f22222dcf42f51d1e451" -dependencies = [ - "heck", - "proc-macro2", - "quote", - "syn 2.0.114", -] - [[package]] name = "snap" version = "1.1.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "1b6b67fb9a61334225b5b790716f609cd58395f895b3fe8b328786812a40bc3b" -[[package]] -name = "socket2" -version = "0.5.10" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e22376abed350d73dd1cd119b57ffccad95b4e585a7cda43e286245ce23c0678" -dependencies = [ - "libc", - "windows-sys 0.52.0", -] - [[package]] name = "socket2" version = "0.6.1" @@ -11935,28 +9680,6 @@ version = "0.3.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "3b9b39299b249ad65f3b7e96443bad61c02ca5cd3589f46cb6d610a0fd6c0d6a" -[[package]] -name = "sqlparser" -version = "0.58.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ec4b661c54b1e4b603b37873a18c59920e4c51ea8ea2cf527d925424dbd4437c" -dependencies = [ - "log", - "recursive", - "sqlparser_derive", -] - -[[package]] -name = "sqlparser_derive" -version = "0.3.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "da5fc6819faabb412da764b99d3b713bb55083c11e7e0c00144d386cd6a1939c" -dependencies = [ - "proc-macro2", - "quote", - "syn 2.0.114", -] - [[package]] name = "sqlx" version = "0.8.6" @@ -11994,7 +9717,7 @@ dependencies = [ "memchr", "once_cell", "percent-encoding", - "rustls 0.23.35", + "rustls", "serde", "serde_json", "sha2", @@ -12066,7 +9789,7 @@ dependencies = [ "futures-core", "futures-io", "futures-util", - "generic-array", + "generic-array 0.14.9", "hex", "hkdf", "hmac", @@ -12186,18 +9909,6 @@ version = "1.1.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "d7beae5182595e9a8b683fa98c4317f956c9a2dec3b9716990d20023cc60c766" -[[package]] -name = "std_prelude" -version = "0.2.12" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8207e78455ffdf55661170876f88daf85356e4edd54e0a3dbc79586ca1e50cbe" - -[[package]] -name = "stfu8" -version = "0.2.7" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e51f1e89f093f99e7432c491c382b88a6860a5adbe6bf02574bf0a08efff1978" - [[package]] name = "storekey" version = "0.5.0" @@ -12210,20 +9921,41 @@ dependencies = [ "thiserror 1.0.69", ] +[[package]] +name = "storekey" +version = "0.11.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bd9a94571bde7369ecaac47cec2e6844642d99166bd452fbd8def74b5b917b2f" +dependencies = [ + "bytes", + "storekey-derive", + "uuid", +] + +[[package]] +name = "storekey-derive" +version = "0.11.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6079d53242246522ec982de613c5c952cc7b1380ef2f8622fcdab9bfe73c0098" +dependencies = [ + "proc-macro2", + "quote", + "syn 2.0.114", +] + [[package]] name = "stratum-embeddings" version = "0.1.0" dependencies = [ - "arrow", "async-trait", "fastembed", "futures", "humantime-serde", - "lancedb", "moka", "reqwest 0.13.1", "serde", "serde_json", + "surrealdb 3.0.0", "thiserror 2.0.18", "tokio", "tracing", @@ -12249,7 +9981,7 @@ version = "0.5.4" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "c711928715f1fe0fe509c53b43e993a9a557babc2d0a3567d0a3006f1ac931a0" dependencies = [ - "phf_generator", + "phf_generator 0.11.3", "phf_shared 0.11.3", "proc-macro2", "quote", @@ -12308,7 +10040,7 @@ checksum = "62b7720b39ce2985efbfa10858b7397ffd95655a9bab6d9dfaa03622bbdc3bc2" dependencies = [ "arrayvec 0.7.6", "async-channel", - "bincode", + "bincode 1.3.3", "chrono", "dmp", "futures", @@ -12322,13 +10054,13 @@ dependencies = [ "revision 0.11.0", "ring", "rust_decimal", - "rustls 0.23.35", + "rustls", "rustls-pki-types", "semver", "serde", "serde-content", "serde_json", - "surrealdb-core", + "surrealdb-core 2.6.0", "thiserror 1.0.69", "tokio", "tokio-tungstenite 0.23.1", @@ -12338,10 +10070,47 @@ dependencies = [ "url", "uuid", "wasm-bindgen-futures", - "wasmtimer", + "wasmtimer 0.2.1", "ws_stream_wasm", ] +[[package]] +name = "surrealdb" +version = "3.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2150ced737a7dd6b1ba97b9c3579282c9a18263f88a73700103de0e32f442666" +dependencies = [ + "anyhow", + "async-channel", + "boxcar", + "chrono", + "futures", + "getrandom 0.3.4", + "indexmap 2.13.0", + "js-sys", + "path-clean", + "reqwest 0.13.1", + "ring", + "rustls", + "rustls-pki-types", + "semver", + "serde", + "serde_json", + "surrealdb-core 3.0.0", + "surrealdb-types", + "tokio", + "tokio-tungstenite 0.28.0", + "tokio-tungstenite-wasm", + "tokio-util", + "tracing", + "url", + "uuid", + "wasm-bindgen", + "wasm-bindgen-futures", + "wasmtimer 0.4.3", + "web-sys", +] + [[package]] name = "surrealdb-core" version = "2.6.0" @@ -12349,7 +10118,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "c48e42c81713be2f9b3dae64328999eafe8b8060dd584059445a908748b39787" dependencies = [ "addr", - "affinitypool", + "affinitypool 0.3.1", "ahash 0.8.12", "ammonia", "any_ascii", @@ -12358,8 +10127,8 @@ dependencies = [ "async-executor", "async-graphql", "base64 0.21.7", - "bcrypt", - "bincode", + "bcrypt 0.15.1", + "bincode 1.3.3", "blake3", "bytes", "castaway", @@ -12378,25 +10147,25 @@ dependencies = [ "getrandom 0.3.4", "hashbrown 0.14.5", "hex", - "http 1.4.0", + "http", "ipnet", "jsonwebtoken 9.3.1", - "lexicmp", + "lexicmp 0.1.0", "linfa-linalg", "md-5", "nanoid", "ndarray 0.15.6", - "ndarray-stats", + "ndarray-stats 0.5.1", "num-traits", "num_cpus", - "object_store", + "object_store 0.12.4", "parking_lot", "pbkdf2", "pharos", "phf 0.11.3", "pin-project-lite", "quick_cache 0.5.2", - "radix_trie", + "radix_trie 0.2.1", "rand 0.8.5", "rayon", "reblessive", @@ -12404,7 +10173,7 @@ dependencies = [ "revision 0.11.0", "ring", "rmpv", - "roaring", + "roaring 0.10.12", "rust-stemmers", "rust_decimal", "scrypt", @@ -12415,11 +10184,11 @@ dependencies = [ "sha1", "sha2", "snap", - "storekey", + "storekey 0.5.0", "strsim", "subtle", - "surrealkv", - "sysinfo", + "surrealkv 0.9.3", + "sysinfo 0.33.1", "tempfile", "thiserror 1.0.69", "tokio", @@ -12431,10 +10200,188 @@ dependencies = [ "uuid", "vart 0.8.1", "wasm-bindgen-futures", - "wasmtimer", + "wasmtimer 0.2.1", "ws_stream_wasm", ] +[[package]] +name = "surrealdb-core" +version = "3.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "225816a998dff5f898b72925494487877dd42fdef9985799433801e5ea8113c8" +dependencies = [ + "addr", + "affinitypool 0.4.0", + "ahash 0.8.12", + "ammonia", + "anyhow", + "argon2", + "async-channel", + "async-stream", + "async-trait", + "base64 0.22.1", + "bcrypt 0.18.0", + "blake3", + "bytes", + "chrono", + "ciborium", + "dashmap 6.1.0", + "deunicode", + "dmp", + "ext-sort", + "fastnum", + "fst", + "futures", + "fuzzy-matcher", + "geo 0.32.0", + "geo-types", + "getrandom 0.3.4", + "headers", + "hex", + "http", + "humantime", + "ipnet", + "jsonwebtoken 10.3.0", + "lexicmp 0.2.0", + "md-5", + "mime", + "ndarray 0.17.2", + "ndarray-stats 0.7.0", + "num-traits", + "num_cpus", + "object_store 0.13.1", + "parking_lot", + "path-clean", + "pbkdf2", + "phf 0.13.1", + "pin-project-lite", + "quick_cache 0.6.18", + "radix_trie 0.3.0", + "rand 0.8.5", + "rayon", + "reblessive", + "regex", + "revision 0.17.0", + "ring", + "roaring 0.11.3", + "rust-stemmers", + "rust_decimal", + "scrypt", + "semver", + "serde", + "serde_json", + "sha1", + "sha2", + "storekey 0.11.0", + "strsim", + "subtle", + "surrealdb-protocol", + "surrealdb-rocksdb", + "surrealdb-types", + "surrealkv 0.20.2", + "surrealmx", + "sysinfo 0.37.2", + "tempfile", + "thiserror 2.0.18", + "tokio", + "tokio-util", + "tracing", + "trice", + "ulid", + "unicase", + "url", + "uuid", + "vart 0.9.3", + "wasm-bindgen-futures", + "wasmtimer 0.4.3", +] + +[[package]] +name = "surrealdb-librocksdb-sys" +version = "0.17.3+10.6.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "db194f1cf601bb6f2d0f4cbf0931bc3e5a602bac41ef2e9a87eccdfb28b7fed2" +dependencies = [ + "bindgen 0.72.1", + "bzip2-sys", + "cc", + "libc", + "libz-sys", + "lz4-sys", + "zstd-sys", +] + +[[package]] +name = "surrealdb-protocol" +version = "0.8.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "eb37698e0493bcfac3229ecb6ec6894a3ad705a3a2087b1562eeb881b3db19d4" +dependencies = [ + "anyhow", + "async-trait", + "bytes", + "chrono", + "flatbuffers", + "futures", + "geo 0.32.0", + "prost", + "prost-types", + "rust_decimal", + "semver", + "serde", + "serde_json", + "tonic", + "tonic-prost", + "uuid", +] + +[[package]] +name = "surrealdb-rocksdb" +version = "0.24.0-surreal.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "057727f56d48825ddbe45e4e7401cda6e99d864fbc004e7474b4689a5e72c86d" +dependencies = [ + "libc", + "surrealdb-librocksdb-sys", +] + +[[package]] +name = "surrealdb-types" +version = "3.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "72231b6b94c1dbd6e2453c50266c679eb621701cd01cb8f8fc32923d3ce0a217" +dependencies = [ + "anyhow", + "bytes", + "chrono", + "flatbuffers", + "geo 0.32.0", + "hex", + "http", + "papaya", + "rand 0.8.5", + "regex", + "rstest", + "rust_decimal", + "serde", + "serde_json", + "surrealdb-protocol", + "surrealdb-types-derive", + "ulid", + "uuid", +] + +[[package]] +name = "surrealdb-types-derive" +version = "3.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ef7818b988bb8a8d424751ba5c0fe6aabf3e41dc26fbc8a922803c1615ae641b" +dependencies = [ + "proc-macro2", + "quote", + "syn 2.0.114", +] + [[package]] name = "surrealkv" version = "0.9.3" @@ -12454,6 +10401,55 @@ dependencies = [ "vart 0.9.3", ] +[[package]] +name = "surrealkv" +version = "0.20.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a6c1dd97851edc773c24afb282d6a17eb1bc798fafac53ea0d2951458854d472" +dependencies = [ + "arc-swap", + "async-trait", + "byteorder", + "bytes", + "chrono", + "crc32fast", + "crossbeam-skiplist", + "fs2", + "getrandom 0.3.4", + "guardian", + "integer-encoding 4.1.0", + "log", + "lz4_flex 0.12.0", + "parking_lot", + "quick_cache 0.6.18", + "rand 0.9.2", + "scopeguard", + "sha2", + "snap", + "tokio", +] + +[[package]] +name = "surrealmx" +version = "0.17.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "703077c9f8bdce4053dce39c5f5ef71b79b8fffe1e59dbd629b455340586814e" +dependencies = [ + "arc-swap", + "bincode 2.0.1", + "bytes", + "crossbeam-deque", + "crossbeam-queue", + "crossbeam-skiplist", + "lz4", + "papaya", + "parking_lot", + "serde", + "smallvec", + "thiserror 2.0.18", + "tracing", +] + [[package]] name = "syn" version = "1.0.109" @@ -12528,7 +10524,21 @@ dependencies = [ "memchr", "ntapi", "rayon", - "windows", + "windows 0.57.0", +] + +[[package]] +name = "sysinfo" +version = "0.37.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "16607d5caffd1c07ce073528f9ed972d88db15dd44023fa57142963be3feb11f" +dependencies = [ + "libc", + "memchr", + "ntapi", + "objc2-core-foundation", + "objc2-io-kit", + "windows 0.61.3", ] [[package]] @@ -12631,7 +10641,7 @@ dependencies = [ "levenshtein_automata", "log", "lru", - "lz4_flex", + "lz4_flex 0.11.5", "measure_time 0.8.3", "memmap2", "num_cpus", @@ -12659,58 +10669,6 @@ dependencies = [ "winapi", ] -[[package]] -name = "tantivy" -version = "0.24.2" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "64a966cb0e76e311f09cf18507c9af192f15d34886ee43d7ba7c7e3803660c43" -dependencies = [ - "aho-corasick", - "arc-swap", - "base64 0.22.1", - "bitpacking", - "bon", - "byteorder", - "census", - "crc32fast", - "crossbeam-channel", - "downcast-rs 2.0.2", - "fastdivide", - "fnv", - "fs4 0.8.4", - "htmlescape", - "hyperloglogplus", - "itertools 0.14.0", - "levenshtein_automata", - "log", - "lru", - "lz4_flex", - "measure_time 0.9.0", - "memmap2", - "once_cell", - "oneshot", - "rayon", - "regex", - "rust-stemmers", - "rustc-hash 2.1.1", - "serde", - "serde_json", - "sketches-ddsketch 0.3.0", - "smallvec", - "tantivy-bitpacker 0.8.0", - "tantivy-columnar 0.5.0", - "tantivy-common 0.9.0", - "tantivy-fst", - "tantivy-query-grammar 0.24.0", - "tantivy-stacker 0.5.0", - "tantivy-tokenizer-api 0.5.0", - "tempfile", - "thiserror 2.0.18", - "time", - "uuid", - "winapi", -] - [[package]] name = "tantivy" version = "0.25.0" @@ -12736,7 +10694,7 @@ dependencies = [ "levenshtein_automata", "log", "lru", - "lz4_flex", + "lz4_flex 0.11.5", "measure_time 0.9.0", "memmap2", "once_cell", @@ -12772,15 +10730,6 @@ dependencies = [ "bitpacking", ] -[[package]] -name = "tantivy-bitpacker" -version = "0.8.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1adc286a39e089ae9938935cd488d7d34f14502544a36607effd2239ff0e2494" -dependencies = [ - "bitpacking", -] - [[package]] name = "tantivy-bitpacker" version = "0.9.0" @@ -12806,22 +10755,6 @@ dependencies = [ "tantivy-stacker 0.3.0", ] -[[package]] -name = "tantivy-columnar" -version = "0.5.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6300428e0c104c4f7db6f95b466a6f5c1b9aece094ec57cdd365337908dc7344" -dependencies = [ - "downcast-rs 2.0.2", - "fastdivide", - "itertools 0.14.0", - "serde", - "tantivy-bitpacker 0.8.0", - "tantivy-common 0.9.0", - "tantivy-sstable 0.5.0", - "tantivy-stacker 0.5.0", -] - [[package]] name = "tantivy-columnar" version = "0.6.0" @@ -12851,19 +10784,6 @@ dependencies = [ "time", ] -[[package]] -name = "tantivy-common" -version = "0.9.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e91b6ea6090ce03dc72c27d0619e77185d26cc3b20775966c346c6d4f7e99d7f" -dependencies = [ - "async-trait", - "byteorder", - "ownedbytes 0.9.0", - "serde", - "time", -] - [[package]] name = "tantivy-common" version = "0.10.0" @@ -12897,17 +10817,6 @@ dependencies = [ "nom 7.1.3", ] -[[package]] -name = "tantivy-query-grammar" -version = "0.24.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e810cdeeebca57fc3f7bfec5f85fdbea9031b2ac9b990eb5ff49b371d52bbe6a" -dependencies = [ - "nom 7.1.3", - "serde", - "serde_json", -] - [[package]] name = "tantivy-query-grammar" version = "0.25.0" @@ -12931,20 +10840,6 @@ dependencies = [ "zstd", ] -[[package]] -name = "tantivy-sstable" -version = "0.5.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "709f22c08a4c90e1b36711c1c6cad5ae21b20b093e535b69b18783dd2cb99416" -dependencies = [ - "futures-util", - "itertools 0.14.0", - "tantivy-bitpacker 0.8.0", - "tantivy-common 0.9.0", - "tantivy-fst", - "zstd", -] - [[package]] name = "tantivy-sstable" version = "0.6.0" @@ -12966,21 +10861,10 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "c56d6ff5591fc332739b3ce7035b57995a3ce29a93ffd6012660e0949c956ea8" dependencies = [ "murmurhash32", - "rand_distr 0.4.3", + "rand_distr", "tantivy-common 0.7.0", ] -[[package]] -name = "tantivy-stacker" -version = "0.5.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2bcdebb267671311d1e8891fd9d1301803fdb8ad21ba22e0a30d0cab49ba59c1" -dependencies = [ - "murmurhash32", - "rand_distr 0.4.3", - "tantivy-common 0.9.0", -] - [[package]] name = "tantivy-stacker" version = "0.6.0" @@ -12988,7 +10872,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "23d38a379411169f0b3002c9cba61cdfe315f757e9d4f239c00c282497a0749d" dependencies = [ "murmurhash32", - "rand_distr 0.4.3", + "rand_distr", "tantivy-common 0.10.0", ] @@ -13001,15 +10885,6 @@ dependencies = [ "serde", ] -[[package]] -name = "tantivy-tokenizer-api" -version = "0.5.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "dfa942fcee81e213e09715bbce8734ae2180070b97b33839a795ba1de201547d" -dependencies = [ - "serde", -] - [[package]] name = "tantivy-tokenizer-api" version = "0.6.0" @@ -13062,7 +10937,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "e8004bca281f2d32df3bacd59bc67b312cb4c70cea46cbd79dbe8ac5ed206722" dependencies = [ "chrono", - "chrono-tz 0.9.0", + "chrono-tz", "globwalk", "humansize", "lazy_static", @@ -13152,15 +11027,6 @@ dependencies = [ "syn 2.0.114", ] -[[package]] -name = "thread-tree" -version = "0.3.3" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ffbd370cb847953a25954d9f63e14824a36113f8c72eecf6eccef5dc4b45d630" -dependencies = [ - "crossbeam-channel", -] - [[package]] name = "thread_local" version = "1.1.9" @@ -13186,7 +11052,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "7e54bc85fc7faa8bc175c4bab5b92ba8d9a3ce893d0e9f42cc455c8ab16a9e09" dependencies = [ "byteorder", - "integer-encoding", + "integer-encoding 3.0.4", "log", "ordered-float 2.10.1", "threadpool", @@ -13336,7 +11202,7 @@ dependencies = [ "parking_lot", "pin-project-lite", "signal-hook-registry", - "socket2 0.6.1", + "socket2", "tokio-macros", "windows-sys 0.61.2", ] @@ -13362,23 +11228,13 @@ dependencies = [ "tokio", ] -[[package]] -name = "tokio-rustls" -version = "0.24.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c28327cf380ac148141087fbfb9de9d7bd4e84ab5d2c28fbc911d753de8a7081" -dependencies = [ - "rustls 0.21.12", - "tokio", -] - [[package]] name = "tokio-rustls" version = "0.26.4" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "1729aa945f29d91ba541258c8df89027d5792d85a8841fb65e8bf0f4ede4ef61" dependencies = [ - "rustls 0.23.35", + "rustls", "tokio", ] @@ -13401,10 +11257,10 @@ checksum = "c6989540ced10490aaf14e6bad2e3d33728a2813310a0c71d1574304c49631cd" dependencies = [ "futures-util", "log", - "rustls 0.23.35", + "rustls", "rustls-pki-types", "tokio", - "tokio-rustls 0.26.4", + "tokio-rustls", "tungstenite 0.23.0", "webpki-roots 0.26.11", ] @@ -13417,15 +11273,38 @@ checksum = "d25a406cddcc431a75d3d9afc6a7c0f7428d4891dd973e4d54c56b46127bf857" dependencies = [ "futures-util", "log", + "rustls", + "rustls-pki-types", "tokio", + "tokio-rustls", "tungstenite 0.28.0", + "webpki-roots 0.26.11", +] + +[[package]] +name = "tokio-tungstenite-wasm" +version = "0.8.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ccecee909c02b8863f9bda87253127eb4da0e7e1342330b2583fbc4d1795c2f8" +dependencies = [ + "bytes", + "futures-channel", + "futures-util", + "http", + "httparse", + "js-sys", + "thiserror 2.0.18", + "tokio", + "tokio-tungstenite 0.28.0", + "wasm-bindgen", + "web-sys", ] [[package]] name = "tokio-util" -version = "0.7.17" +version = "0.7.18" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2efa149fe76073d6e8fd97ef4f4eca7b67f599660115591483572e406e165594" +checksum = "9ae9cec805b01e8fc3fd2fe289f89149a9b66dd16786abd8b19cfa7b48cb0098" dependencies = [ "bytes", "futures-core", @@ -13445,13 +11324,13 @@ dependencies = [ "bytes", "futures-core", "futures-sink", - "http 1.4.0", + "http", "httparse", "rand 0.8.5", "ring", "rustls-pki-types", "tokio", - "tokio-rustls 0.26.4", + "tokio-rustls", "tokio-util", "webpki-roots 0.26.11", ] @@ -13548,6 +11427,46 @@ version = "1.0.4" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "df8b2b54733674ad286d16267dcfc7a71ed5c776e4ac7aa3c3e2561f7c637bf2" +[[package]] +name = "tonic" +version = "0.14.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "fec7c61a0695dc1887c1b53952990f3ad2e3a31453e1f49f10e75424943a93ec" +dependencies = [ + "async-trait", + "axum", + "base64 0.22.1", + "bytes", + "h2", + "http", + "http-body", + "http-body-util", + "hyper", + "hyper-timeout", + "hyper-util", + "percent-encoding", + "pin-project", + "socket2", + "sync_wrapper", + "tokio", + "tokio-stream", + "tower", + "tower-layer", + "tower-service", + "tracing", +] + +[[package]] +name = "tonic-prost" +version = "0.14.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a55376a0bbaa4975a3f10d009ad763d8f4108f067c7c2e74f3001fb49778d309" +dependencies = [ + "bytes", + "prost", + "tonic", +] + [[package]] name = "tower" version = "0.5.3" @@ -13556,9 +11475,12 @@ checksum = "ebe5ef63511595f1344e2d5cfa636d973292adc0eec1f0ad45fae9f0851ab1d4" dependencies = [ "futures-core", "futures-util", + "indexmap 2.13.0", "pin-project-lite", + "slab", "sync_wrapper", "tokio", + "tokio-util", "tower-layer", "tower-service", "tracing", @@ -13573,7 +11495,7 @@ dependencies = [ "axum-core", "cookie", "futures-util", - "http 1.4.0", + "http", "parking_lot", "pin-project-lite", "tower-layer", @@ -13591,8 +11513,8 @@ dependencies = [ "bytes", "futures-core", "futures-util", - "http 1.4.0", - "http-body 1.0.1", + "http", + "http-body", "http-body-util", "http-range-header", "httpdate", @@ -13628,7 +11550,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "518dca34b74a17cadfcee06e616a09d2bd0c3984eff1769e1e76d58df978fc78" dependencies = [ "async-trait", - "http 1.4.0", + "http", "time", "tokio", "tower-cookies", @@ -13649,7 +11571,7 @@ dependencies = [ "axum-core", "base64 0.22.1", "futures", - "http 1.4.0", + "http", "parking_lot", "rand 0.9.2", "serde", @@ -13785,10 +11707,10 @@ dependencies = [ "chrono", "clap", "futures", - "generic-array", + "generic-array 0.14.9", "glob", "hex", - "http 1.4.0", + "http", "ignore", "notify", "proptest", @@ -13844,11 +11766,11 @@ dependencies = [ "byteorder", "bytes", "data-encoding", - "http 1.4.0", + "http", "httparse", "log", "rand 0.8.5", - "rustls 0.23.35", + "rustls", "rustls-pki-types", "sha1", "thiserror 1.0.69", @@ -13864,12 +11786,15 @@ checksum = "8628dcc84e5a09eb3d8423d6cb682965dea9133204e8fb3efee74c2a0c259442" dependencies = [ "bytes", "data-encoding", - "http 1.4.0", + "http", "httparse", "log", "rand 0.9.2", + "rustls", + "rustls-pki-types", "sha1", "thiserror 2.0.18", + "url", "utf-8", ] @@ -13878,9 +11803,6 @@ name = "twox-hash" version = "2.1.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "9ea3136b675547379c4bd395ca6b938e5ad3c3d20fad76e7fe85f9e0d011419c" -dependencies = [ - "rand 0.9.2", -] [[package]] name = "type-map" @@ -13954,7 +11876,7 @@ dependencies = [ "serde", "serde_json", "serde_yaml", - "surrealdb", + "surrealdb 2.6.0", "thiserror 2.0.18", "tokio", "toml 0.9.8", @@ -13972,7 +11894,7 @@ version = "0.1.0" dependencies = [ "anyhow", "async-trait", - "bincode", + "bincode 1.3.3", "chrono", "dialoguer", "dirs 6.0.0", @@ -14076,9 +11998,9 @@ dependencies = [ [[package]] name = "unicase" -version = "2.8.1" +version = "2.9.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "75b844d17643ee918803943289730bec8aac480150456169e647ed0b576ba539" +checksum = "dbc4bc3a9f746d862c45cb89d705aa10f187bb96c76001afab07a0d35ce60142" [[package]] name = "unicode-bidi" @@ -14178,12 +12100,24 @@ version = "0.2.11" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "673aac59facbab8a9007c7f6108d11f63b603f7cabff99fabf650fea5c32b861" +[[package]] +name = "untrusted" +version = "0.7.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a156c684c91ea7d62626509bce3cb4e1d9ed5c4d978f7b4352658f96a4c26b4a" + [[package]] name = "untrusted" version = "0.9.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "8ecb6da28b8a351d773b68d5825ac39017e680750f980f3a1a85cd8dd28a47c1" +[[package]] +name = "unty" +version = "0.0.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6d49784317cd0d1ee7ec5c716dd598ec5b4483ea832a2dced265471cc0f690ae" + [[package]] name = "ureq" version = "2.12.1" @@ -14195,7 +12129,7 @@ dependencies = [ "log", "native-tls", "once_cell", - "rustls 0.23.35", + "rustls", "rustls-pki-types", "serde", "serde_json", @@ -14229,7 +12163,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "d81f9efa9df032be5934a46a068815a10a042b494b6a58cb0a1a97bb5467ed6f" dependencies = [ "base64 0.22.1", - "http 1.4.0", + "http", "httparse", "log", ] @@ -14327,7 +12261,7 @@ dependencies = [ "reqwest 0.13.1", "serde", "serde_json", - "surrealdb", + "surrealdb 3.0.0", "thiserror 2.0.18", "tokio", "tower", @@ -14371,7 +12305,7 @@ dependencies = [ "secretumvault", "serde", "serde_json", - "surrealdb", + "surrealdb 3.0.0", "tempfile", "thiserror 2.0.18", "tokio", @@ -14397,7 +12331,7 @@ dependencies = [ "parking_lot", "serde", "serde_json", - "surrealdb", + "surrealdb 3.0.0", "thiserror 2.0.18", "tokio", "tokio-stream", @@ -14419,21 +12353,21 @@ dependencies = [ "clap", "dotenv", "futures", - "http 1.4.0", + "http", "jsonwebtoken 10.3.0", "lazy_static", "mockall", "once_cell", "prometheus", "regex", - "rustls 0.23.35", + "rustls", "rustls-pemfile", "secretumvault", "serde", "serde_json", "serde_yaml", "sqlx", - "surrealdb", + "surrealdb 3.0.0", "tempfile", "thiserror 2.0.18", "tokio", @@ -14515,7 +12449,7 @@ dependencies = [ "rayon", "serde", "serde_json", - "surrealdb", + "surrealdb 3.0.0", "thiserror 2.0.18", "tokio", "tracing", @@ -14607,7 +12541,7 @@ dependencies = [ "prometheus", "serde", "serde_json", - "surrealdb", + "surrealdb 3.0.0", "tantivy 0.22.1", "tempfile", "thiserror 2.0.18", @@ -14630,7 +12564,7 @@ dependencies = [ "regex", "serde", "serde_json", - "surrealdb", + "surrealdb 3.0.0", "thiserror 2.0.18", "tokio", "toml 0.9.8", @@ -14707,6 +12641,7 @@ dependencies = [ "anyhow", "async-nats", "async-trait", + "cedar-policy 4.9.0", "chrono", "dashmap 6.1.0", "futures", @@ -14714,6 +12649,8 @@ dependencies = [ "prometheus", "serde", "serde_json", + "surrealdb 3.0.0", + "tempfile", "thiserror 2.0.18", "tokio", "toml 0.9.8", @@ -14765,10 +12702,10 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "0b928f33d975fc6ad9f86c8f283853ad26bdd5b10b7f1542aa2fa15e2289105a" [[package]] -name = "vsimd" -version = "0.8.0" +name = "virtue" +version = "0.0.18" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "5c3082ca00d5a5ef149bb8b555a72ae84c9c59f7250f013ac822ac2e49b19c64" +checksum = "051eb1abcf10076295e815102942cc58f9d5e3b4560e46e53c21e8ff6f3af7b1" [[package]] name = "wait-timeout" @@ -15296,6 +13233,19 @@ dependencies = [ "wasm-bindgen", ] +[[package]] +name = "wasmtimer" +version = "0.4.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1c598d6b99ea013e35844697fc4670d08339d5cda15588f193c6beedd12f644b" +dependencies = [ + "futures", + "js-sys", + "parking_lot", + "pin-utils", + "wasm-bindgen", +] + [[package]] name = "wast" version = "35.0.2" @@ -15427,7 +13377,7 @@ dependencies = [ "heck", "proc-macro2", "quote", - "shellexpand 2.1.2", + "shellexpand", "syn 2.0.114", "witx", ] @@ -15502,6 +13452,28 @@ dependencies = [ "windows-targets 0.52.6", ] +[[package]] +name = "windows" +version = "0.61.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9babd3a767a4c1aef6900409f85f5d53ce2544ccdfaa86dad48c91782c6d6893" +dependencies = [ + "windows-collections", + "windows-core 0.61.2", + "windows-future", + "windows-link 0.1.3", + "windows-numerics", +] + +[[package]] +name = "windows-collections" +version = "0.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3beeceb5e5cfd9eb1d76b381630e82c4241ccd0d27f1a39ed41b2760b255c5e8" +dependencies = [ + "windows-core 0.61.2", +] + [[package]] name = "windows-core" version = "0.57.0" @@ -15514,6 +13486,19 @@ dependencies = [ "windows-targets 0.52.6", ] +[[package]] +name = "windows-core" +version = "0.61.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c0fdd3ddb90610c7638aa2b3a3ab2904fb9e5cdbecc643ddb3647212781c4ae3" +dependencies = [ + "windows-implement 0.60.2", + "windows-interface 0.59.3", + "windows-link 0.1.3", + "windows-result 0.3.4", + "windows-strings 0.4.2", +] + [[package]] name = "windows-core" version = "0.62.2" @@ -15527,6 +13512,17 @@ dependencies = [ "windows-strings 0.5.1", ] +[[package]] +name = "windows-future" +version = "0.2.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "fc6a41e98427b19fe4b73c550f060b59fa592d7d686537eebf9385621bfbad8e" +dependencies = [ + "windows-core 0.61.2", + "windows-link 0.1.3", + "windows-threading", +] + [[package]] name = "windows-implement" version = "0.57.0" @@ -15583,6 +13579,16 @@ version = "0.2.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "f0805222e57f7521d6a62e36fa9163bc891acd422f971defe97d64e70d0a4fe5" +[[package]] +name = "windows-numerics" +version = "0.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9150af68066c4c5c07ddc0ce30421554771e528bde427614c61038bc2c92c2b1" +dependencies = [ + "windows-core 0.61.2", + "windows-link 0.1.3", +] + [[package]] name = "windows-registry" version = "0.5.3" @@ -15756,6 +13762,15 @@ dependencies = [ "windows_x86_64_msvc 0.53.1", ] +[[package]] +name = "windows-threading" +version = "0.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b66463ad2e0ea3bbf808b7f1d371311c80e115c0b71d60efc142cafbcfb057a6" +dependencies = [ + "windows-link 0.1.3", +] + [[package]] name = "windows_aarch64_gnullvm" version = "0.42.2" @@ -15965,9 +13980,9 @@ dependencies = [ "base64 0.22.1", "deadpool", "futures", - "http 1.4.0", + "http", "http-body-util", - "hyper 1.8.1", + "hyper", "hyper-util", "log", "once_cell", @@ -16014,31 +14029,6 @@ dependencies = [ "wast 35.0.2", ] -[[package]] -name = "wkb" -version = "0.9.2" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a120b336c7ad17749026d50427c23d838ecb50cd64aaea6254b5030152f890a9" -dependencies = [ - "byteorder", - "geo-traits", - "num_enum", - "thiserror 1.0.69", -] - -[[package]] -name = "wkt" -version = "0.14.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "efb2b923ccc882312e559ffaa832a055ba9d1ac0cc8e86b3e25453247e4b81d7" -dependencies = [ - "geo-traits", - "geo-types", - "log", - "num-traits", - "thiserror 1.0.69", -] - [[package]] name = "writeable" version = "0.6.2" @@ -16073,27 +14063,12 @@ dependencies = [ "tap", ] -[[package]] -name = "xmlparser" -version = "0.13.6" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "66fee0b777b0f5ac1c69bb06d361268faafa61cd4682ae064a171c16c433e9e4" - [[package]] name = "xxhash-rust" version = "0.8.15" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "fdd20c5420375476fbd4394763288da7eb0cc0b8c11deed431a91562af7335d3" -[[package]] -name = "xz2" -version = "0.1.7" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "388c44dc09d76f1536602ead6d325eb532f5c122f17782bd57fb47baeeb767e2" -dependencies = [ - "lzma-sys", -] - [[package]] name = "y4m" version = "0.8.0" @@ -16224,12 +14199,6 @@ dependencies = [ "syn 2.0.114", ] -[[package]] -name = "zlib-rs" -version = "0.5.5" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "40990edd51aae2c2b6907af74ffb635029d5788228222c4bb811e9351c0caad3" - [[package]] name = "zmij" version = "1.0.19" diff --git a/Cargo.toml b/Cargo.toml index 840c792..49c8a9d 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -53,6 +53,12 @@ vapora-rlm = { path = "crates/vapora-rlm" } secretumvault = { path = "../secretumvault", default-features = true } # ["openssl", "filesystem", "server", "surrealdb-storage", "pqc", "cli", "cedar"] +# Stratumiops — shared graph, state and embedding primitives +stratum-graph = { path = "../stratumiops/crates/stratum-graph" } +stratum-state = { path = "../stratumiops/crates/stratum-state", features = ["mem-store"] } +stratum-embeddings = { path = "../stratumiops/crates/stratum-embeddings", features = ["openai-provider", "ollama-provider", "fastembed-provider", "huggingface-provider", "memory-cache", "persistent-cache", "surrealdb-store"] } +stratum-llm = { path = "../stratumiops/crates/stratum-llm", features = ["anthropic", "openai", "ollama"] } + # Leptos ecosystem (CSR-only for frontend) leptos = { version = "0.8.15" } leptos_router = { version = "0.8.11" } @@ -139,19 +145,25 @@ time = { version = "0.3", features = ["serde"] } # Database sqlx = { version = "0.8.6", features = ["runtime-tokio-rustls", "postgres", "sqlite", "chrono", "uuid", "migrate"] } -# Note: SurrealDB will be added when available in workspace -surrealdb = "2.6" +surrealdb = { version = "3", features = ["protocol-ws", "rustls"] } # Message Queue -# Note: async-nats will be added when available in workspace async-nats = "0.46" # LLM Agent Framework & RAG rig-core = "0.30" -# Embeddings: Use provider APIs (Claude, OpenAI, Gemini, Ollama) instead of fastembed -# - rig-core integrates with all major providers -# - Routing through vapora-llm-router for optimal provider selection -# - Phase 3: Implement embedding service using provider APIs + +# Stratum embedding/llm workspace dep requirements (all referenced with workspace=true in crate Cargo.tomls) +fastembed = "5.11" +moka = { version = "0.12", features = ["future"] } +xxhash-rust = { version = "0.8", features = ["xxh3"] } +humantime-serde = "1.1" +sled = "0.34" +lancedb = "0.26" +# Arrow 56.x pinned: lancedb 0.26 uses Arrow 56 internally; DO NOT upgrade until lancedb supports Arrow 57 +arrow = "=56" +dirs = "6.0" +which = "8.0" # Cryptography aes-gcm = { version = "0.10" } diff --git a/crates/vapora-a2a/src/main.rs b/crates/vapora-a2a/src/main.rs index 50253da..cfe745e 100644 --- a/crates/vapora-a2a/src/main.rs +++ b/crates/vapora-a2a/src/main.rs @@ -56,8 +56,8 @@ async fn main() -> Result<(), Box> { surrealdb::Surreal::new::(surreal_url.as_str()).await?; db.signin(surrealdb::opt::auth::Root { - username: "root", - password: "root", + username: "root".to_string(), + password: "root".to_string(), }) .await?; diff --git a/crates/vapora-a2a/src/server.rs b/crates/vapora-a2a/src/server.rs index 9cdd07b..53c5daf 100644 --- a/crates/vapora-a2a/src/server.rs +++ b/crates/vapora-a2a/src/server.rs @@ -136,8 +136,8 @@ mod tests { .unwrap(); db.signin(surrealdb::opt::auth::Root { - username: "root", - password: "root", + username: "root".to_string(), + password: "root".to_string(), }) .await .unwrap(); diff --git a/crates/vapora-a2a/src/task_manager.rs b/crates/vapora-a2a/src/task_manager.rs index c3ddba2..24a7cd5 100644 --- a/crates/vapora-a2a/src/task_manager.rs +++ b/crates/vapora-a2a/src/task_manager.rs @@ -271,8 +271,8 @@ mod tests { .unwrap(); db.signin(surrealdb::opt::auth::Root { - username: "root", - password: "root", + username: "root".to_string(), + password: "root".to_string(), }) .await .unwrap(); diff --git a/crates/vapora-a2a/tests/integration_test.rs b/crates/vapora-a2a/tests/integration_test.rs index 19df622..999ec2e 100644 --- a/crates/vapora-a2a/tests/integration_test.rs +++ b/crates/vapora-a2a/tests/integration_test.rs @@ -25,8 +25,8 @@ async fn setup_test_db() -> Surreal { .expect("Failed to connect to SurrealDB"); db.signin(Root { - username: "root", - password: "root", + username: "root".to_string(), + password: "root".to_string(), }) .await .expect("Failed to sign in"); diff --git a/crates/vapora-backend/src/api/workflow_orchestrator.rs b/crates/vapora-backend/src/api/workflow_orchestrator.rs index 10cfae1..2b1ebd3 100644 --- a/crates/vapora-backend/src/api/workflow_orchestrator.rs +++ b/crates/vapora-backend/src/api/workflow_orchestrator.rs @@ -288,6 +288,7 @@ mod tests { parallel: false, max_parallel: None, approval_required: false, + compensation_agents: None, }], }; diff --git a/crates/vapora-backend/src/main.rs b/crates/vapora-backend/src/main.rs index 098c28d..6ef3bc6 100644 --- a/crates/vapora-backend/src/main.rs +++ b/crates/vapora-backend/src/main.rs @@ -76,8 +76,8 @@ async fn main() -> Result<()> { // Sign in to database db.signin(surrealdb::opt::auth::Root { - username: "root", - password: "root", + username: "root".to_string(), + password: "root".to_string(), }) .await?; diff --git a/crates/vapora-backend/src/services/agent_service.rs b/crates/vapora-backend/src/services/agent_service.rs index 873d0ff..72de088 100644 --- a/crates/vapora-backend/src/services/agent_service.rs +++ b/crates/vapora-backend/src/services/agent_service.rs @@ -1,5 +1,3 @@ -// Agent service - Registry and management for the 12 agent roles - use chrono::Utc; use surrealdb::engine::remote::ws::Client; use surrealdb::Surreal; @@ -20,10 +18,8 @@ impl AgentService { /// Register a new agent pub async fn register_agent(&self, mut agent: Agent) -> Result { - // Set creation timestamp agent.created_at = Utc::now(); - // Check if agent with this role already exists let existing = self.get_agent_by_role(&agent.role).await; if existing.is_ok() { return Err(VaporaError::InvalidInput(format!( @@ -32,16 +28,10 @@ impl AgentService { ))); } - // Create agent in database - let created: Option = self - .db - .create("agents") - .content(agent) - .await? - .into_iter() - .next(); - - created.ok_or_else(|| VaporaError::DatabaseError("Failed to register agent".to_string())) + let json = serde_json::to_value(&agent)?; + let raw: Option = self.db.create("agents").content(json).await?; + raw.and_then(|v| serde_json::from_value(v).ok()) + .ok_or_else(|| VaporaError::DatabaseError("Failed to register agent".to_string())) } /// List all agents @@ -51,8 +41,11 @@ impl AgentService { .query("SELECT * FROM agents ORDER BY role ASC") .await?; - let agents: Vec = response.take(0)?; - Ok(agents) + let raw: Vec = response.take(0)?; + Ok(raw + .into_iter() + .filter_map(|v| serde_json::from_value(v).ok()) + .collect()) } /// List agents by status @@ -71,15 +64,18 @@ impl AgentService { .bind(("status", status_str.to_string())) .await?; - let agents: Vec = response.take(0)?; - Ok(agents) + let raw: Vec = response.take(0)?; + Ok(raw + .into_iter() + .filter_map(|v| serde_json::from_value(v).ok()) + .collect()) } /// Get an agent by ID pub async fn get_agent(&self, id: &str) -> Result { - let agent: Option = self.db.select(("agents", id)).await?; - - agent.ok_or_else(|| VaporaError::NotFound(format!("Agent with id '{}' not found", id))) + let raw: Option = self.db.select(("agents", id)).await?; + raw.and_then(|v| serde_json::from_value(v).ok()) + .ok_or_else(|| VaporaError::NotFound(format!("Agent with id '{}' not found", id))) } /// Get an agent by role @@ -105,43 +101,34 @@ impl AgentService { .bind(("role", role_str.to_string())) .await?; - let agents: Vec = response.take(0)?; - - agents - .into_iter() - .next() + let raw: Vec = response.take(0)?; + raw.into_iter() + .find_map(|v| serde_json::from_value(v).ok()) .ok_or_else(|| VaporaError::NotFound(format!("Agent with role '{:?}' not found", role))) } /// Update an agent pub async fn update_agent(&self, id: &str, mut updates: Agent) -> Result { - // Verify agent exists let existing = self.get_agent(id).await?; - - // Preserve certain fields updates.id = existing.id; updates.created_at = existing.created_at; - // Update in database - let updated: Option = self.db.update(("agents", id)).content(updates).await?; - - updated.ok_or_else(|| VaporaError::DatabaseError("Failed to update agent".to_string())) + let json = serde_json::to_value(&updates)?; + let raw: Option = self.db.update(("agents", id)).content(json).await?; + raw.and_then(|v| serde_json::from_value(v).ok()) + .ok_or_else(|| VaporaError::DatabaseError("Failed to update agent".to_string())) } /// Update agent status pub async fn update_agent_status(&self, id: &str, status: AgentStatus) -> Result { - // Verify agent exists self.get_agent(id).await?; - let updated: Option = self + let raw: Option = self .db .update(("agents", id)) - .merge(serde_json::json!({ - "status": status - })) + .merge(serde_json::json!({ "status": status })) .await?; - - updated + raw.and_then(|v| serde_json::from_value(v).ok()) .ok_or_else(|| VaporaError::DatabaseError("Failed to update agent status".to_string())) } @@ -149,19 +136,16 @@ impl AgentService { pub async fn add_capability(&self, id: &str, capability: String) -> Result { let mut agent = self.get_agent(id).await?; - // Add capability if not already present if !agent.capabilities.contains(&capability) { agent.capabilities.push(capability); - let updated: Option = self + let raw: Option = self .db .update(("agents", id)) - .merge(serde_json::json!({ - "capabilities": agent.capabilities - })) + .merge(serde_json::json!({ "capabilities": agent.capabilities })) .await?; - - return updated + return raw + .and_then(|v| serde_json::from_value(v).ok()) .ok_or_else(|| VaporaError::DatabaseError("Failed to add capability".to_string())); } @@ -171,38 +155,31 @@ impl AgentService { /// Remove capability from an agent pub async fn remove_capability(&self, id: &str, capability: &str) -> Result { let mut agent = self.get_agent(id).await?; - - // Remove capability agent.capabilities.retain(|c| c != capability); - let updated: Option = self + let raw: Option = self .db .update(("agents", id)) - .merge(serde_json::json!({ - "capabilities": agent.capabilities - })) + .merge(serde_json::json!({ "capabilities": agent.capabilities })) .await?; - - updated.ok_or_else(|| VaporaError::DatabaseError("Failed to remove capability".to_string())) + raw.and_then(|v| serde_json::from_value(v).ok()) + .ok_or_else(|| VaporaError::DatabaseError("Failed to remove capability".to_string())) } /// Add skill to an agent pub async fn add_skill(&self, id: &str, skill: String) -> Result { let mut agent = self.get_agent(id).await?; - // Add skill if not already present if !agent.skills.contains(&skill) { agent.skills.push(skill); - let updated: Option = self + let raw: Option = self .db .update(("agents", id)) - .merge(serde_json::json!({ - "skills": agent.skills - })) + .merge(serde_json::json!({ "skills": agent.skills })) .await?; - - return updated + return raw + .and_then(|v| serde_json::from_value(v).ok()) .ok_or_else(|| VaporaError::DatabaseError("Failed to add skill".to_string())); } @@ -211,30 +188,29 @@ impl AgentService { /// Deregister an agent pub async fn deregister_agent(&self, id: &str) -> Result<()> { - // Verify agent exists self.get_agent(id).await?; - - // Delete from database - let _: Option = self.db.delete(("agents", id)).await?; - + let _: Option = self.db.delete(("agents", id)).await?; Ok(()) } - /// Get agent health status (checks if agent is active and responding) + /// Get agent health status pub async fn check_agent_health(&self, id: &str) -> Result { let agent = self.get_agent(id).await?; Ok(agent.status == AgentStatus::Active) } - /// Get agents available for task assignment (active agents with capacity) + /// Get agents available for task assignment pub async fn get_available_agents(&self) -> Result> { let mut response = self .db .query("SELECT * FROM agents WHERE status = 'active' ORDER BY role ASC") .await?; - let agents: Vec = response.take(0)?; - Ok(agents) + let raw: Vec = response.take(0)?; + Ok(raw + .into_iter() + .filter_map(|v| serde_json::from_value(v).ok()) + .collect()) } } @@ -243,13 +219,6 @@ mod tests { #[allow(unused_imports)] use super::*; - // Note: These are placeholder tests. Real tests require a running SurrealDB - // instance or mocking. For Phase 1, we'll add integration tests that use a - // test database. - #[test] - fn test_agent_service_creation() { - // This test just verifies the service can be created - // Real database tests will be in integration tests - } + fn test_agent_service_creation() {} } diff --git a/crates/vapora-backend/src/services/project_service.rs b/crates/vapora-backend/src/services/project_service.rs index de9526f..afd7ae1 100644 --- a/crates/vapora-backend/src/services/project_service.rs +++ b/crates/vapora-backend/src/services/project_service.rs @@ -1,5 +1,3 @@ -// Project service - CRUD operations for projects - use chrono::Utc; use surrealdb::engine::remote::ws::Client; use surrealdb::Surreal; @@ -20,21 +18,14 @@ impl ProjectService { /// Create a new project pub async fn create_project(&self, mut project: Project) -> Result { - // Set timestamps let now = Utc::now(); project.created_at = now; project.updated_at = now; - // Create project in database - let created: Option = self - .db - .create("projects") - .content(project) - .await? - .into_iter() - .next(); - - created.ok_or_else(|| VaporaError::DatabaseError("Failed to create project".to_string())) + let json = serde_json::to_value(&project)?; + let raw: Option = self.db.create("projects").content(json).await?; + raw.and_then(|v| serde_json::from_value(v).ok()) + .ok_or_else(|| VaporaError::DatabaseError("Failed to create project".to_string())) } /// List all projects for a tenant @@ -45,8 +36,11 @@ impl ProjectService { .bind(("tenant_id", tenant_id.to_string())) .await?; - let projects: Vec = response.take(0)?; - Ok(projects) + let raw: Vec = response.take(0)?; + Ok(raw + .into_iter() + .filter_map(|v| serde_json::from_value(v).ok()) + .collect()) } /// List projects by status for a tenant @@ -72,18 +66,20 @@ impl ProjectService { .bind(("status", status_str.to_string())) .await?; - let projects: Vec = response.take(0)?; - Ok(projects) + let raw: Vec = response.take(0)?; + Ok(raw + .into_iter() + .filter_map(|v| serde_json::from_value(v).ok()) + .collect()) } /// Get a project by ID pub async fn get_project(&self, id: &str, tenant_id: &str) -> Result { - let project: Option = self.db.select(("projects", id)).await?; - - let project = project + let raw: Option = self.db.select(("projects", id)).await?; + let project: Project = raw + .and_then(|v| serde_json::from_value(v).ok()) .ok_or_else(|| VaporaError::NotFound(format!("Project with id '{}' not found", id)))?; - // Verify tenant ownership if project.tenant_id != tenant_id { return Err(VaporaError::Unauthorized( "Project does not belong to this tenant".to_string(), @@ -100,29 +96,22 @@ impl ProjectService { tenant_id: &str, mut updates: Project, ) -> Result { - // Verify project exists and belongs to tenant let existing = self.get_project(id, tenant_id).await?; - - // Preserve certain fields updates.id = existing.id; updates.tenant_id = existing.tenant_id; updates.created_at = existing.created_at; updates.updated_at = Utc::now(); - // Update in database - let updated: Option = self.db.update(("projects", id)).content(updates).await?; - - updated.ok_or_else(|| VaporaError::DatabaseError("Failed to update project".to_string())) + let json = serde_json::to_value(&updates)?; + let raw: Option = self.db.update(("projects", id)).content(json).await?; + raw.and_then(|v| serde_json::from_value(v).ok()) + .ok_or_else(|| VaporaError::DatabaseError("Failed to update project".to_string())) } /// Delete a project pub async fn delete_project(&self, id: &str, tenant_id: &str) -> Result<()> { - // Verify project exists and belongs to tenant self.get_project(id, tenant_id).await?; - - // Delete from database - let _: Option = self.db.delete(("projects", id)).await?; - + let _: Option = self.db.delete(("projects", id)).await?; Ok(()) } @@ -130,12 +119,11 @@ impl ProjectService { pub async fn add_feature(&self, id: &str, tenant_id: &str, feature: String) -> Result { let mut project = self.get_project(id, tenant_id).await?; - // Add feature if not already present if !project.features.contains(&feature) { project.features.push(feature); project.updated_at = Utc::now(); - let updated: Option = self + let raw: Option = self .db .update(("projects", id)) .merge(serde_json::json!({ @@ -143,8 +131,8 @@ impl ProjectService { "updated_at": project.updated_at })) .await?; - - return updated + return raw + .and_then(|v| serde_json::from_value(v).ok()) .ok_or_else(|| VaporaError::DatabaseError("Failed to add feature".to_string())); } @@ -159,12 +147,10 @@ impl ProjectService { feature: &str, ) -> Result { let mut project = self.get_project(id, tenant_id).await?; - - // Remove feature project.features.retain(|f| f != feature); project.updated_at = Utc::now(); - let updated: Option = self + let raw: Option = self .db .update(("projects", id)) .merge(serde_json::json!({ @@ -172,17 +158,17 @@ impl ProjectService { "updated_at": project.updated_at })) .await?; - - updated.ok_or_else(|| VaporaError::DatabaseError("Failed to remove feature".to_string())) + raw.and_then(|v| serde_json::from_value(v).ok()) + .ok_or_else(|| VaporaError::DatabaseError("Failed to remove feature".to_string())) } - /// Archive a project (set status to archived) + /// Archive a project pub async fn archive_project(&self, id: &str, tenant_id: &str) -> Result { let mut project = self.get_project(id, tenant_id).await?; project.status = ProjectStatus::Archived; project.updated_at = Utc::now(); - let updated: Option = self + let raw: Option = self .db .update(("projects", id)) .merge(serde_json::json!({ @@ -190,8 +176,8 @@ impl ProjectService { "updated_at": project.updated_at })) .await?; - - updated.ok_or_else(|| VaporaError::DatabaseError("Failed to archive project".to_string())) + raw.and_then(|v| serde_json::from_value(v).ok()) + .ok_or_else(|| VaporaError::DatabaseError("Failed to archive project".to_string())) } } @@ -200,13 +186,6 @@ mod tests { #[allow(unused_imports)] use super::*; - // Note: These are placeholder tests. Real tests require a running SurrealDB - // instance or mocking. For Phase 1, we'll add integration tests that use a - // test database. - #[test] - fn test_project_service_creation() { - // This test just verifies the service can be created - // Real database tests will be in integration tests - } + fn test_project_service_creation() {} } diff --git a/crates/vapora-backend/src/services/proposal_service.rs b/crates/vapora-backend/src/services/proposal_service.rs index ad0795f..e9d9527 100644 --- a/crates/vapora-backend/src/services/proposal_service.rs +++ b/crates/vapora-backend/src/services/proposal_service.rs @@ -1,5 +1,3 @@ -// Proposal service - CRUD operations for approval gate proposals - use chrono::Utc; use surrealdb::engine::remote::ws::Client; use surrealdb::Surreal; @@ -20,18 +18,12 @@ impl ProposalService { /// Create a new proposal pub async fn create_proposal(&self, mut proposal: Proposal) -> Result { - let now = Utc::now(); - proposal.created_at = now; + proposal.created_at = Utc::now(); - let created: Option = self - .db - .create("proposals") - .content(proposal) - .await? - .into_iter() - .next(); - - created.ok_or_else(|| VaporaError::DatabaseError("Failed to create proposal".to_string())) + let json = serde_json::to_value(&proposal)?; + let raw: Option = self.db.create("proposals").content(json).await?; + raw.and_then(|v| serde_json::from_value(v).ok()) + .ok_or_else(|| VaporaError::DatabaseError("Failed to create proposal".to_string())) } /// Get proposal by ID @@ -43,10 +35,9 @@ impl ProposalService { .bind(("tenant_id", tenant_id.to_string())) .await?; - let proposals: Vec = response.take(0)?; - proposals - .into_iter() - .next() + let raw: Vec = response.take(0)?; + raw.into_iter() + .find_map(|v| serde_json::from_value(v).ok()) .ok_or_else(|| VaporaError::NotFound(format!("Proposal not found: {}", id))) } @@ -57,7 +48,7 @@ impl ProposalService { tenant_id: &str, status: Option, ) -> Result> { - let query = if let Some(ref _s) = status { + let query = if status.is_some() { "SELECT * FROM proposals WHERE project_id = $project_id AND tenant_id = $tenant_id AND \ status = $status ORDER BY created_at DESC" .to_string() @@ -78,8 +69,11 @@ impl ProposalService { } let mut response = response.await?; - let proposals: Vec = response.take(0)?; - Ok(proposals) + let raw: Vec = response.take(0)?; + Ok(raw + .into_iter() + .filter_map(|v| serde_json::from_value(v).ok()) + .collect()) } /// List proposals by task ID @@ -99,51 +93,42 @@ impl ProposalService { .bind(("tenant_id", tenant_id.to_string())) .await?; - let proposals: Vec = response.take(0)?; - Ok(proposals) + let raw: Vec = response.take(0)?; + Ok(raw + .into_iter() + .filter_map(|v| serde_json::from_value(v).ok()) + .collect()) } /// Submit proposal for approval pub async fn submit_proposal(&self, id: &str, tenant_id: &str) -> Result { - let now = Utc::now(); - let mut proposal = self.get_proposal(id, tenant_id).await?; proposal.status = ProposalStatus::Proposed; - proposal.submitted_at = Some(now); - + proposal.submitted_at = Some(Utc::now()); self.update_proposal(id, tenant_id, proposal).await } /// Approve proposal pub async fn approve_proposal(&self, id: &str, tenant_id: &str) -> Result { - let now = Utc::now(); - let mut proposal = self.get_proposal(id, tenant_id).await?; proposal.status = ProposalStatus::Approved; - proposal.reviewed_at = Some(now); - + proposal.reviewed_at = Some(Utc::now()); self.update_proposal(id, tenant_id, proposal).await } /// Reject proposal pub async fn reject_proposal(&self, id: &str, tenant_id: &str) -> Result { - let now = Utc::now(); - let mut proposal = self.get_proposal(id, tenant_id).await?; proposal.status = ProposalStatus::Rejected; - proposal.reviewed_at = Some(now); - + proposal.reviewed_at = Some(Utc::now()); self.update_proposal(id, tenant_id, proposal).await } /// Mark proposal as executed pub async fn mark_executed(&self, id: &str, tenant_id: &str) -> Result { - let now = Utc::now(); - let mut proposal = self.get_proposal(id, tenant_id).await?; proposal.status = ProposalStatus::Executed; - proposal.executed_at = Some(now); - + proposal.executed_at = Some(Utc::now()); self.update_proposal(id, tenant_id, proposal).await } @@ -154,20 +139,19 @@ impl ProposalService { tenant_id: &str, proposal: Proposal, ) -> Result { - // Verify ownership self.get_proposal(id, tenant_id).await?; - let updated: Option = self.db.update(("proposals", id)).content(proposal).await?; - - updated.ok_or_else(|| VaporaError::DatabaseError("Failed to update proposal".to_string())) + let json = serde_json::to_value(&proposal)?; + let raw: Option = + self.db.update(("proposals", id)).content(json).await?; + raw.and_then(|v| serde_json::from_value(v).ok()) + .ok_or_else(|| VaporaError::DatabaseError("Failed to update proposal".to_string())) } /// Delete proposal pub async fn delete_proposal(&self, id: &str, tenant_id: &str) -> Result<()> { - // Verify ownership self.get_proposal(id, tenant_id).await?; - - let _: Option<()> = self.db.delete(("proposals", id)).await?; + let _: Option = self.db.delete(("proposals", id)).await?; Ok(()) } @@ -180,15 +164,11 @@ impl ProposalService { review.proposal_id = proposal_id.to_string(); review.created_at = Utc::now(); - let created: Option = self - .db - .create("proposal_reviews") - .content(review.clone()) - .await? - .into_iter() - .next(); - - created.ok_or_else(|| VaporaError::DatabaseError("Failed to create review".to_string())) + let json = serde_json::to_value(&review)?; + let raw: Option = + self.db.create("proposal_reviews").content(json).await?; + raw.and_then(|v| serde_json::from_value(v).ok()) + .ok_or_else(|| VaporaError::DatabaseError("Failed to create review".to_string())) } /// List reviews for proposal @@ -202,8 +182,11 @@ impl ProposalService { .bind(("proposal_id", proposal_id.to_string())) .await?; - let reviews: Vec = response.take(0)?; - Ok(reviews) + let raw: Vec = response.take(0)?; + Ok(raw + .into_iter() + .filter_map(|v| serde_json::from_value(v).ok()) + .collect()) } /// Get proposals pending approval with risk level @@ -227,12 +210,13 @@ impl ProposalService { .bind(("risk_level", risk_str)) .await?; - let proposals: Vec = response.take(0)?; - Ok(proposals) + let raw: Vec = response.take(0)?; + Ok(raw + .into_iter() + .filter_map(|v| serde_json::from_value(v).ok()) + .collect()) } - // Helper functions for serialization - fn status_to_string(status: &ProposalStatus) -> String { match status { ProposalStatus::Proposed => "proposed", diff --git a/crates/vapora-backend/src/services/task_service.rs b/crates/vapora-backend/src/services/task_service.rs index 9ce6c86..7f53904 100644 --- a/crates/vapora-backend/src/services/task_service.rs +++ b/crates/vapora-backend/src/services/task_service.rs @@ -1,5 +1,3 @@ -// Task service - CRUD operations and Kanban management for tasks - use chrono::Utc; use surrealdb::engine::remote::ws::Client; use surrealdb::Surreal; @@ -20,12 +18,10 @@ impl TaskService { /// Create a new task pub async fn create_task(&self, mut task: Task) -> Result { - // Set timestamps let now = Utc::now(); task.created_at = now; task.updated_at = now; - // If task_order is not set, get the max order for this project/status and add 1 if task.task_order == 0 { let max_order = self .get_max_task_order(&task.project_id, &task.status) @@ -33,16 +29,10 @@ impl TaskService { task.task_order = max_order + 1; } - // Create task in database - let created: Option = self - .db - .create("tasks") - .content(task) - .await? - .into_iter() - .next(); - - created.ok_or_else(|| VaporaError::DatabaseError("Failed to create task".to_string())) + let json = serde_json::to_value(&task)?; + let raw: Option = self.db.create("tasks").content(json).await?; + raw.and_then(|v| serde_json::from_value(v).ok()) + .ok_or_else(|| VaporaError::DatabaseError("Failed to create task".to_string())) } /// List all tasks for a project @@ -57,8 +47,11 @@ impl TaskService { .bind(("tenant_id", tenant_id.to_string())) .await?; - let tasks: Vec = response.take(0)?; - Ok(tasks) + let raw: Vec = response.take(0)?; + Ok(raw + .into_iter() + .filter_map(|v| serde_json::from_value(v).ok()) + .collect()) } /// List tasks by status (for Kanban columns) @@ -86,8 +79,11 @@ impl TaskService { .bind(("status", status_str.to_string())) .await?; - let tasks: Vec = response.take(0)?; - Ok(tasks) + let raw: Vec = response.take(0)?; + Ok(raw + .into_iter() + .filter_map(|v| serde_json::from_value(v).ok()) + .collect()) } /// List tasks by assignee @@ -108,18 +104,20 @@ impl TaskService { .bind(("assignee", assignee.to_string())) .await?; - let tasks: Vec = response.take(0)?; - Ok(tasks) + let raw: Vec = response.take(0)?; + Ok(raw + .into_iter() + .filter_map(|v| serde_json::from_value(v).ok()) + .collect()) } /// Get a task by ID pub async fn get_task(&self, id: &str, tenant_id: &str) -> Result { - let task: Option = self.db.select(("tasks", id)).await?; + let raw: Option = self.db.select(("tasks", id)).await?; + let task: Task = raw + .and_then(|v| serde_json::from_value(v).ok()) + .ok_or_else(|| VaporaError::NotFound(format!("Task with id '{}' not found", id)))?; - let task = - task.ok_or_else(|| VaporaError::NotFound(format!("Task with id '{}' not found", id)))?; - - // Verify tenant ownership if task.tenant_id != tenant_id { return Err(VaporaError::Unauthorized( "Task does not belong to this tenant".to_string(), @@ -131,19 +129,16 @@ impl TaskService { /// Update a task pub async fn update_task(&self, id: &str, tenant_id: &str, mut updates: Task) -> Result { - // Verify task exists and belongs to tenant let existing = self.get_task(id, tenant_id).await?; - - // Preserve certain fields updates.id = existing.id; updates.tenant_id = existing.tenant_id; updates.created_at = existing.created_at; updates.updated_at = Utc::now(); - // Update in database - let updated: Option = self.db.update(("tasks", id)).content(updates).await?; - - updated.ok_or_else(|| VaporaError::DatabaseError("Failed to update task".to_string())) + let json = serde_json::to_value(&updates)?; + let raw: Option = self.db.update(("tasks", id)).content(json).await?; + raw.and_then(|v| serde_json::from_value(v).ok()) + .ok_or_else(|| VaporaError::DatabaseError("Failed to update task".to_string())) } /// Update task status (for Kanban column changes) @@ -154,11 +149,9 @@ impl TaskService { status: TaskStatus, ) -> Result { let task = self.get_task(id, tenant_id).await?; - - // Get max order for new status let max_order = self.get_max_task_order(&task.project_id, &status).await?; - let updated: Option = self + let raw: Option = self .db .update(("tasks", id)) .merge(serde_json::json!({ @@ -167,8 +160,7 @@ impl TaskService { "updated_at": Utc::now() })) .await?; - - updated + raw.and_then(|v| serde_json::from_value(v).ok()) .ok_or_else(|| VaporaError::DatabaseError("Failed to update task status".to_string())) } @@ -182,7 +174,6 @@ impl TaskService { ) -> Result { let mut task = self.get_task(id, tenant_id).await?; - // Update status if provided if let Some(status) = new_status { task.status = status; } @@ -190,7 +181,7 @@ impl TaskService { task.task_order = new_order; task.updated_at = Utc::now(); - let updated: Option = self + let raw: Option = self .db .update(("tasks", id)) .merge(serde_json::json!({ @@ -199,8 +190,8 @@ impl TaskService { "updated_at": task.updated_at })) .await?; - - updated.ok_or_else(|| VaporaError::DatabaseError("Failed to reorder task".to_string())) + raw.and_then(|v| serde_json::from_value(v).ok()) + .ok_or_else(|| VaporaError::DatabaseError("Failed to reorder task".to_string())) } /// Assign task to agent/user @@ -209,7 +200,7 @@ impl TaskService { task.assignee = assignee; task.updated_at = Utc::now(); - let updated: Option = self + let raw: Option = self .db .update(("tasks", id)) .merge(serde_json::json!({ @@ -217,8 +208,8 @@ impl TaskService { "updated_at": task.updated_at })) .await?; - - updated.ok_or_else(|| VaporaError::DatabaseError("Failed to assign task".to_string())) + raw.and_then(|v| serde_json::from_value(v).ok()) + .ok_or_else(|| VaporaError::DatabaseError("Failed to assign task".to_string())) } /// Update task priority @@ -232,7 +223,7 @@ impl TaskService { task.priority = priority; task.updated_at = Utc::now(); - let updated: Option = self + let raw: Option = self .db .update(("tasks", id)) .merge(serde_json::json!({ @@ -240,18 +231,14 @@ impl TaskService { "updated_at": task.updated_at })) .await?; - - updated.ok_or_else(|| VaporaError::DatabaseError("Failed to update priority".to_string())) + raw.and_then(|v| serde_json::from_value(v).ok()) + .ok_or_else(|| VaporaError::DatabaseError("Failed to update priority".to_string())) } /// Delete a task pub async fn delete_task(&self, id: &str, tenant_id: &str) -> Result<()> { - // Verify task exists and belongs to tenant self.get_task(id, tenant_id).await?; - - // Delete from database - let _: Option = self.db.delete(("tasks", id)).await?; - + let _: Option = self.db.delete(("tasks", id)).await?; Ok(()) } @@ -274,8 +261,11 @@ impl TaskService { .bind(("status", status_str.to_string())) .await?; - let orders: Vec = response.take(0)?; - Ok(orders.first().copied().unwrap_or(0)) + let raw: Vec = response.take(0)?; + Ok(raw + .into_iter() + .find_map(|v| v.as_i64().map(|n| n as i32)) + .unwrap_or(0)) } } @@ -284,13 +274,6 @@ mod tests { #[allow(unused_imports)] use super::*; - // Note: These are placeholder tests. Real tests require a running SurrealDB - // instance or mocking. For Phase 1, we'll add integration tests that use a - // test database. - #[test] - fn test_task_service_creation() { - // This test just verifies the service can be created - // Real database tests will be in integration tests - } + fn test_task_service_creation() {} } diff --git a/crates/vapora-backend/tests/rlm_api_test.rs b/crates/vapora-backend/tests/rlm_api_test.rs index df6da53..51a2031 100644 --- a/crates/vapora-backend/tests/rlm_api_test.rs +++ b/crates/vapora-backend/tests/rlm_api_test.rs @@ -24,8 +24,8 @@ async fn setup_test_app() -> Router { .expect("Failed to connect to SurrealDB"); db.signin(Root { - username: "root", - password: "root", + username: "root".to_string(), + password: "root".to_string(), }) .await .expect("Failed to sign in"); diff --git a/crates/vapora-frontend/dist/index.html b/crates/vapora-frontend/dist/index.html new file mode 100644 index 0000000..2707f9b --- /dev/null +++ b/crates/vapora-frontend/dist/index.html @@ -0,0 +1,74 @@ + + + + + + VAPORA - Multi-Agent Development Platform + + + + + + + +
+
Loading VAPORA...
+
+ + + diff --git a/crates/vapora-frontend/dist/vapora-frontend-4e82c70edbf89867.js b/crates/vapora-frontend/dist/vapora-frontend-4e82c70edbf89867.js new file mode 100644 index 0000000..3d47340 --- /dev/null +++ b/crates/vapora-frontend/dist/vapora-frontend-4e82c70edbf89867.js @@ -0,0 +1,451 @@ +export class IntoUnderlyingByteSource { + __destroy_into_raw() { + const ptr = this.__wbg_ptr; + this.__wbg_ptr = 0; + IntoUnderlyingByteSourceFinalization.unregister(this); + return ptr; + } + free() { + const ptr = this.__destroy_into_raw(); + wasm.__wbg_intounderlyingbytesource_free(ptr, 0); + } + /** + * @returns {number} + */ + get autoAllocateChunkSize() { + const ret = wasm.intounderlyingbytesource_autoAllocateChunkSize(this.__wbg_ptr); + return ret >>> 0; + } + cancel() { + const ptr = this.__destroy_into_raw(); + wasm.intounderlyingbytesource_cancel(ptr); + } + /** + * @param {ReadableByteStreamController} controller + * @returns {Promise} + */ + pull(controller) { + const ret = wasm.intounderlyingbytesource_pull(this.__wbg_ptr, controller); + return ret; + } + /** + * @param {ReadableByteStreamController} controller + */ + start(controller) { + wasm.intounderlyingbytesource_start(this.__wbg_ptr, controller); + } + /** + * @returns {ReadableStreamType} + */ + get type() { + const ret = wasm.intounderlyingbytesource_type(this.__wbg_ptr); + return __wbindgen_enum_ReadableStreamType[ret]; + } +} +if (Symbol.dispose) IntoUnderlyingByteSource.prototype[Symbol.dispose] = IntoUnderlyingByteSource.prototype.free; + +export class IntoUnderlyingSink { + __destroy_into_raw() { + const ptr = this.__wbg_ptr; + this.__wbg_ptr = 0; + IntoUnderlyingSinkFinalization.unregister(this); + return ptr; + } + free() { + const ptr = this.__destroy_into_raw(); + wasm.__wbg_intounderlyingsink_free(ptr, 0); + } + /** + * @param {any} reason + * @returns {Promise} + */ + abort(reason) { + const ptr = this.__destroy_into_raw(); + const ret = wasm.intounderlyingsink_abort(ptr, reason); + return ret; + } + /** + * @returns {Promise} + */ + close() { + const ptr = this.__destroy_into_raw(); + const ret = wasm.intounderlyingsink_close(ptr); + return ret; + } + /** + * @param {any} chunk + * @returns {Promise} + */ + write(chunk) { + const ret = wasm.intounderlyingsink_write(this.__wbg_ptr, chunk); + return ret; + } +} +if (Symbol.dispose) IntoUnderlyingSink.prototype[Symbol.dispose] = IntoUnderlyingSink.prototype.free; + +export class IntoUnderlyingSource { + __destroy_into_raw() { + const ptr = this.__wbg_ptr; + this.__wbg_ptr = 0; + IntoUnderlyingSourceFinalization.unregister(this); + return ptr; + } + free() { + const ptr = this.__destroy_into_raw(); + wasm.__wbg_intounderlyingsource_free(ptr, 0); + } + cancel() { + const ptr = this.__destroy_into_raw(); + wasm.intounderlyingsource_cancel(ptr); + } + /** + * @param {ReadableStreamDefaultController} controller + * @returns {Promise} + */ + pull(controller) { + const ret = wasm.intounderlyingsource_pull(this.__wbg_ptr, controller); + return ret; + } +} +if (Symbol.dispose) IntoUnderlyingSource.prototype[Symbol.dispose] = IntoUnderlyingSource.prototype.free; + +function __wbg_get_imports() { + const import0 = { + __proto__: null, + __wbg___wbindgen_is_function_0095a73b8b156f76: function(arg0) { + const ret = typeof(arg0) === 'function'; + return ret; + }, + __wbg___wbindgen_is_undefined_9e4d92534c42d778: function(arg0) { + const ret = arg0 === undefined; + return ret; + }, + __wbg___wbindgen_throw_be289d5034ed271b: function(arg0, arg1) { + throw new Error(getStringFromWasm0(arg0, arg1)); + }, + __wbg__wbg_cb_unref_d9b87ff7982e3b21: function(arg0) { + arg0._wbg_cb_unref(); + }, + __wbg_buffer_26d0910f3a5bc899: function(arg0) { + const ret = arg0.buffer; + return ret; + }, + __wbg_byobRequest_80e594e6da4e1af7: function(arg0) { + const ret = arg0.byobRequest; + return isLikeNone(ret) ? 0 : addToExternrefTable0(ret); + }, + __wbg_byteLength_3417f266f4bf562a: function(arg0) { + const ret = arg0.byteLength; + return ret; + }, + __wbg_byteOffset_f88547ca47c86358: function(arg0) { + const ret = arg0.byteOffset; + return ret; + }, + __wbg_call_389efe28435a9388: function() { return handleError(function (arg0, arg1) { + const ret = arg0.call(arg1); + return ret; + }, arguments); }, + __wbg_call_4708e0c13bdc8e95: function() { return handleError(function (arg0, arg1, arg2) { + const ret = arg0.call(arg1, arg2); + return ret; + }, arguments); }, + __wbg_close_06dfa0a815b9d71f: function() { return handleError(function (arg0) { + arg0.close(); + }, arguments); }, + __wbg_close_a79afee31de55b36: function() { return handleError(function (arg0) { + arg0.close(); + }, arguments); }, + __wbg_enqueue_2c63f2044f257c3e: function() { return handleError(function (arg0, arg1) { + arg0.enqueue(arg1); + }, arguments); }, + __wbg_length_32ed9a279acd054c: function(arg0) { + const ret = arg0.length; + return ret; + }, + __wbg_new_72b49615380db768: function(arg0, arg1) { + const ret = new Error(getStringFromWasm0(arg0, arg1)); + return ret; + }, + __wbg_new_b5d9e2fb389fef91: function(arg0, arg1) { + try { + var state0 = {a: arg0, b: arg1}; + var cb0 = (arg0, arg1) => { + const a = state0.a; + state0.a = 0; + try { + return wasm_bindgen__convert__closures_____invoke__h3cd296ad3915ac8d(a, state0.b, arg0, arg1); + } finally { + state0.a = a; + } + }; + const ret = new Promise(cb0); + return ret; + } finally { + state0.a = state0.b = 0; + } + }, + __wbg_new_no_args_1c7c842f08d00ebb: function(arg0, arg1) { + const ret = new Function(getStringFromWasm0(arg0, arg1)); + return ret; + }, + __wbg_new_with_byte_offset_and_length_aa261d9c9da49eb1: function(arg0, arg1, arg2) { + const ret = new Uint8Array(arg0, arg1 >>> 0, arg2 >>> 0); + return ret; + }, + __wbg_queueMicrotask_0aa0a927f78f5d98: function(arg0) { + const ret = arg0.queueMicrotask; + return ret; + }, + __wbg_queueMicrotask_5bb536982f78a56f: function(arg0) { + queueMicrotask(arg0); + }, + __wbg_resolve_002c4b7d9d8f6b64: function(arg0) { + const ret = Promise.resolve(arg0); + return ret; + }, + __wbg_respond_bf6ab10399ca8722: function() { return handleError(function (arg0, arg1) { + arg0.respond(arg1 >>> 0); + }, arguments); }, + __wbg_set_cc56eefd2dd91957: function(arg0, arg1, arg2) { + arg0.set(getArrayU8FromWasm0(arg1, arg2)); + }, + __wbg_static_accessor_GLOBAL_12837167ad935116: function() { + const ret = typeof global === 'undefined' ? null : global; + return isLikeNone(ret) ? 0 : addToExternrefTable0(ret); + }, + __wbg_static_accessor_GLOBAL_THIS_e628e89ab3b1c95f: function() { + const ret = typeof globalThis === 'undefined' ? null : globalThis; + return isLikeNone(ret) ? 0 : addToExternrefTable0(ret); + }, + __wbg_static_accessor_SELF_a621d3dfbb60d0ce: function() { + const ret = typeof self === 'undefined' ? null : self; + return isLikeNone(ret) ? 0 : addToExternrefTable0(ret); + }, + __wbg_static_accessor_WINDOW_f8727f0cf888e0bd: function() { + const ret = typeof window === 'undefined' ? null : window; + return isLikeNone(ret) ? 0 : addToExternrefTable0(ret); + }, + __wbg_then_b9e7b3b5f1a9e1b5: function(arg0, arg1) { + const ret = arg0.then(arg1); + return ret; + }, + __wbg_view_6c32e7184b8606ad: function(arg0) { + const ret = arg0.view; + return isLikeNone(ret) ? 0 : addToExternrefTable0(ret); + }, + __wbindgen_cast_0000000000000001: function(arg0, arg1) { + // Cast intrinsic for `Closure(Closure { dtor_idx: 26, function: Function { arguments: [Externref], shim_idx: 27, ret: Unit, inner_ret: Some(Unit) }, mutable: true }) -> Externref`. + const ret = makeMutClosure(arg0, arg1, wasm.wasm_bindgen__closure__destroy__he857c488161cb29c, wasm_bindgen__convert__closures_____invoke__h34690fc02c54dd49); + return ret; + }, + __wbindgen_init_externref_table: function() { + const table = wasm.__wbindgen_externrefs; + const offset = table.grow(4); + table.set(0, undefined); + table.set(offset + 0, undefined); + table.set(offset + 1, null); + table.set(offset + 2, true); + table.set(offset + 3, false); + }, + }; + return { + __proto__: null, + "./vapora-frontend_bg.js": import0, + }; +} + +function wasm_bindgen__convert__closures_____invoke__h34690fc02c54dd49(arg0, arg1, arg2) { + wasm.wasm_bindgen__convert__closures_____invoke__h34690fc02c54dd49(arg0, arg1, arg2); +} + +function wasm_bindgen__convert__closures_____invoke__h3cd296ad3915ac8d(arg0, arg1, arg2, arg3) { + wasm.wasm_bindgen__convert__closures_____invoke__h3cd296ad3915ac8d(arg0, arg1, arg2, arg3); +} + + +const __wbindgen_enum_ReadableStreamType = ["bytes"]; +const IntoUnderlyingByteSourceFinalization = (typeof FinalizationRegistry === 'undefined') + ? { register: () => {}, unregister: () => {} } + : new FinalizationRegistry(ptr => wasm.__wbg_intounderlyingbytesource_free(ptr >>> 0, 1)); +const IntoUnderlyingSinkFinalization = (typeof FinalizationRegistry === 'undefined') + ? { register: () => {}, unregister: () => {} } + : new FinalizationRegistry(ptr => wasm.__wbg_intounderlyingsink_free(ptr >>> 0, 1)); +const IntoUnderlyingSourceFinalization = (typeof FinalizationRegistry === 'undefined') + ? { register: () => {}, unregister: () => {} } + : new FinalizationRegistry(ptr => wasm.__wbg_intounderlyingsource_free(ptr >>> 0, 1)); + +function addToExternrefTable0(obj) { + const idx = wasm.__externref_table_alloc(); + wasm.__wbindgen_externrefs.set(idx, obj); + return idx; +} + +const CLOSURE_DTORS = (typeof FinalizationRegistry === 'undefined') + ? { register: () => {}, unregister: () => {} } + : new FinalizationRegistry(state => state.dtor(state.a, state.b)); + +function getArrayU8FromWasm0(ptr, len) { + ptr = ptr >>> 0; + return getUint8ArrayMemory0().subarray(ptr / 1, ptr / 1 + len); +} + +function getStringFromWasm0(ptr, len) { + ptr = ptr >>> 0; + return decodeText(ptr, len); +} + +let cachedUint8ArrayMemory0 = null; +function getUint8ArrayMemory0() { + if (cachedUint8ArrayMemory0 === null || cachedUint8ArrayMemory0.byteLength === 0) { + cachedUint8ArrayMemory0 = new Uint8Array(wasm.memory.buffer); + } + return cachedUint8ArrayMemory0; +} + +function handleError(f, args) { + try { + return f.apply(this, args); + } catch (e) { + const idx = addToExternrefTable0(e); + wasm.__wbindgen_exn_store(idx); + } +} + +function isLikeNone(x) { + return x === undefined || x === null; +} + +function makeMutClosure(arg0, arg1, dtor, f) { + const state = { a: arg0, b: arg1, cnt: 1, dtor }; + const real = (...args) => { + + // First up with a closure we increment the internal reference + // count. This ensures that the Rust closure environment won't + // be deallocated while we're invoking it. + state.cnt++; + const a = state.a; + state.a = 0; + try { + return f(a, state.b, ...args); + } finally { + state.a = a; + real._wbg_cb_unref(); + } + }; + real._wbg_cb_unref = () => { + if (--state.cnt === 0) { + state.dtor(state.a, state.b); + state.a = 0; + CLOSURE_DTORS.unregister(state); + } + }; + CLOSURE_DTORS.register(real, state, state); + return real; +} + +let cachedTextDecoder = new TextDecoder('utf-8', { ignoreBOM: true, fatal: true }); +cachedTextDecoder.decode(); +const MAX_SAFARI_DECODE_BYTES = 2146435072; +let numBytesDecoded = 0; +function decodeText(ptr, len) { + numBytesDecoded += len; + if (numBytesDecoded >= MAX_SAFARI_DECODE_BYTES) { + cachedTextDecoder = new TextDecoder('utf-8', { ignoreBOM: true, fatal: true }); + cachedTextDecoder.decode(); + numBytesDecoded = len; + } + return cachedTextDecoder.decode(getUint8ArrayMemory0().subarray(ptr, ptr + len)); +} + +let wasmModule, wasm; +function __wbg_finalize_init(instance, module) { + wasm = instance.exports; + wasmModule = module; + cachedUint8ArrayMemory0 = null; + wasm.__wbindgen_start(); + return wasm; +} + +async function __wbg_load(module, imports) { + if (typeof Response === 'function' && module instanceof Response) { + if (typeof WebAssembly.instantiateStreaming === 'function') { + try { + return await WebAssembly.instantiateStreaming(module, imports); + } catch (e) { + const validResponse = module.ok && expectedResponseType(module.type); + + if (validResponse && module.headers.get('Content-Type') !== 'application/wasm') { + console.warn("`WebAssembly.instantiateStreaming` failed because your server does not serve Wasm with `application/wasm` MIME type. Falling back to `WebAssembly.instantiate` which is slower. Original error:\n", e); + + } else { throw e; } + } + } + + const bytes = await module.arrayBuffer(); + return await WebAssembly.instantiate(bytes, imports); + } else { + const instance = await WebAssembly.instantiate(module, imports); + + if (instance instanceof WebAssembly.Instance) { + return { instance, module }; + } else { + return instance; + } + } + + function expectedResponseType(type) { + switch (type) { + case 'basic': case 'cors': case 'default': return true; + } + return false; + } +} + +function initSync(module) { + if (wasm !== undefined) return wasm; + + + if (module !== undefined) { + if (Object.getPrototypeOf(module) === Object.prototype) { + ({module} = module) + } else { + console.warn('using deprecated parameters for `initSync()`; pass a single object instead') + } + } + + const imports = __wbg_get_imports(); + if (!(module instanceof WebAssembly.Module)) { + module = new WebAssembly.Module(module); + } + const instance = new WebAssembly.Instance(module, imports); + return __wbg_finalize_init(instance, module); +} + +async function __wbg_init(module_or_path) { + if (wasm !== undefined) return wasm; + + + if (module_or_path !== undefined) { + if (Object.getPrototypeOf(module_or_path) === Object.prototype) { + ({module_or_path} = module_or_path) + } else { + console.warn('using deprecated parameters for the initialization function; pass a single object instead') + } + } + + if (module_or_path === undefined) { + module_or_path = new URL('vapora-frontend_bg.wasm', import.meta.url); + } + const imports = __wbg_get_imports(); + + if (typeof module_or_path === 'string' || (typeof Request === 'function' && module_or_path instanceof Request) || (typeof URL === 'function' && module_or_path instanceof URL)) { + module_or_path = fetch(module_or_path); + } + + const { instance, module } = await __wbg_load(await module_or_path, imports); + + return __wbg_finalize_init(instance, module); +} + +export { initSync, __wbg_init as default }; diff --git a/crates/vapora-frontend/dist/vapora-frontend-4e82c70edbf89867_bg.wasm b/crates/vapora-frontend/dist/vapora-frontend-4e82c70edbf89867_bg.wasm new file mode 100644 index 0000000..d284b05 Binary files /dev/null and b/crates/vapora-frontend/dist/vapora-frontend-4e82c70edbf89867_bg.wasm differ diff --git a/crates/vapora-knowledge-graph/src/persistence.rs b/crates/vapora-knowledge-graph/src/persistence.rs index c2e4c6f..b4d447b 100644 --- a/crates/vapora-knowledge-graph/src/persistence.rs +++ b/crates/vapora-knowledge-graph/src/persistence.rs @@ -326,7 +326,11 @@ impl KGPersistence { ); let mut response = self.db.query(&query).await?; - let results: Vec = response.take(0)?; + let raw: Vec = response.take(0)?; + let results = raw + .into_iter() + .filter_map(|v| serde_json::from_value(v).ok()) + .collect(); Ok(results) } @@ -343,13 +347,11 @@ impl KGPersistence { let mut response = self.db.query(&query).await?; - #[derive(Deserialize)] - struct RateResult { - rate: Option, - } - - let result: Vec = response.take(0)?; - Ok(result.first().and_then(|r| r.rate).unwrap_or(0.0)) + let result: Vec = response.take(0)?; + Ok(result + .first() + .and_then(|r| r["rate"].as_f64()) + .unwrap_or(0.0)) } /// Get task type distribution @@ -360,16 +362,14 @@ impl KGPersistence { let mut response = self.db.query(query).await?; - #[derive(Deserialize)] - struct DistResult { - task_type: String, - count: u64, - } - - let results: Vec = response.take(0)?; + let results: Vec = response.take(0)?; Ok(results .into_iter() - .map(|r| (r.task_type, r.count, 0.0)) + .filter_map(|r| { + let task_type = r["task_type"].as_str()?.to_string(); + let count = r["count"].as_u64()?; + Some((task_type, count, 0.0)) + }) .collect()) } @@ -386,15 +386,8 @@ impl KGPersistence { ); let mut response = self.db.query(&query).await?; - - #[derive(Deserialize)] - #[allow(dead_code)] - struct DeleteResult { - deleted: Option, - } - - let _result: Vec = response.take(0)?; - Ok(0) // SurrealDB 2.3 doesn't return delete count easily + let _result: Vec = response.take(0)?; + Ok(0) // SurrealDB doesn't return delete count from DELETE queries } /// Get total execution count @@ -403,15 +396,11 @@ impl KGPersistence { let query = "SELECT count(*) as total FROM kg_executions"; let mut response = self.db.query(query).await?; - - #[derive(Deserialize)] - #[allow(dead_code)] - struct CountResult { - total: u64, - } - - let result: Vec = response.take(0)?; - Ok(result.first().map(|r| r.total).unwrap_or(0)) + let result: Vec = response.take(0)?; + Ok(result + .first() + .and_then(|r| r["total"].as_u64()) + .unwrap_or(0)) } /// Get task-type specific executions for agent (for learning profiles). @@ -435,8 +424,11 @@ impl KGPersistence { ); let mut response = self.db.query(&query).await?; - let results: Vec = response.take(0)?; - Ok(results) + let raw: Vec = response.take(0)?; + Ok(raw + .into_iter() + .filter_map(|v| serde_json::from_value(v).ok()) + .collect()) } /// Get all recent executions for agent across all task types. @@ -457,8 +449,11 @@ impl KGPersistence { ); let mut response = self.db.query(&query).await?; - let results: Vec = response.take(0)?; - Ok(results) + let raw: Vec = response.take(0)?; + Ok(raw + .into_iter() + .filter_map(|v| serde_json::from_value(v).ok()) + .collect()) } /// Record analytics event @@ -541,7 +536,11 @@ impl KGPersistence { ); let mut response = self.db.query(&query).await?; - let executions: Vec = response.take(0)?; + let raw: Vec = response.take(0)?; + let executions: Vec = raw + .into_iter() + .filter_map(|v| serde_json::from_value(v).ok()) + .collect(); // Filter by time period let cutoff = Utc::now() - period.duration(); @@ -573,7 +572,11 @@ impl KGPersistence { // Fetch all recent executions let query = "SELECT * FROM kg_executions ORDER BY executed_at DESC LIMIT 5000"; let mut response = self.db.query(query).await?; - let executions: Vec = response.take(0)?; + let raw: Vec = response.take(0)?; + let executions: Vec = raw + .into_iter() + .filter_map(|v| serde_json::from_value(v).ok()) + .collect(); // Filter by time period let cutoff = Utc::now() - period.duration(); @@ -603,7 +606,11 @@ impl KGPersistence { // Fetch all recent executions let query = "SELECT * FROM kg_executions ORDER BY executed_at DESC LIMIT 5000"; let mut response = self.db.query(query).await?; - let executions: Vec = response.take(0)?; + let raw: Vec = response.take(0)?; + let executions: Vec = raw + .into_iter() + .filter_map(|v| serde_json::from_value(v).ok()) + .collect(); // Filter by time period let cutoff = Utc::now() - period.duration(); @@ -737,8 +744,11 @@ impl KGPersistence { ); let mut response = self.db.query(&query).await?; - let results: Vec = response.take(0)?; - Ok(results) + let raw: Vec = response.take(0)?; + Ok(raw + .into_iter() + .filter_map(|v| serde_json::from_value(v).ok()) + .collect()) } /// Find similar RLM tasks using query embedding similarity @@ -750,17 +760,17 @@ impl KGPersistence { ) -> anyhow::Result> { debug!("Searching for similar RLM tasks (limit: {})", limit); - // SurrealDB vector similarity requires different syntax - // For Phase 7, return recent successful executions - // Full vector similarity implementation deferred to future phase let query = format!( "SELECT * FROM rlm_executions WHERE success = true ORDER BY executed_at DESC LIMIT {}", limit ); let mut response = self.db.query(&query).await?; - let results: Vec = response.take(0)?; - Ok(results) + let raw: Vec = response.take(0)?; + Ok(raw + .into_iter() + .filter_map(|v| serde_json::from_value(v).ok()) + .collect()) } /// Get RLM success rate for a specific document @@ -819,18 +829,13 @@ impl KGPersistence { pub async fn get_rlm_execution_count(&self) -> anyhow::Result { debug!("Fetching RLM execution count"); - // SurrealDB count query syntax let query = "SELECT count() as total FROM rlm_executions GROUP ALL"; let mut response = self.db.query(query).await?; - - #[derive(Deserialize)] - #[allow(dead_code)] - struct CountResult { - total: u64, - } - - let result: Vec = response.take(0)?; - Ok(result.first().map(|r| r.total).unwrap_or(0)) + let result: Vec = response.take(0)?; + Ok(result + .first() + .and_then(|r| r["total"].as_u64()) + .unwrap_or(0)) } /// Cleanup old RLM executions (keep only last N days) @@ -846,15 +851,8 @@ impl KGPersistence { ); let mut response = self.db.query(&query).await?; - - #[derive(Deserialize)] - #[allow(dead_code)] - struct DeleteResult { - deleted: Option, - } - - let _result: Vec = response.take(0)?; - Ok(0) // SurrealDB 2.3 doesn't return delete count easily + let _: Vec = response.take(0)?; + Ok(0) // SurrealDB DELETE doesn't return a count } } diff --git a/crates/vapora-knowledge-graph/tests/rlm_integration.rs b/crates/vapora-knowledge-graph/tests/rlm_integration.rs index 95ffa4f..dbe98e0 100644 --- a/crates/vapora-knowledge-graph/tests/rlm_integration.rs +++ b/crates/vapora-knowledge-graph/tests/rlm_integration.rs @@ -12,8 +12,8 @@ async fn setup_test_db() -> KGPersistence { let db = Surreal::new::("127.0.0.1:8000").await.unwrap(); db.signin(Root { - username: "root", - password: "root", + username: "root".to_string(), + password: "root".to_string(), }) .await .unwrap(); diff --git a/crates/vapora-llm-router/Cargo.toml b/crates/vapora-llm-router/Cargo.toml index a37246a..2b2bd78 100644 --- a/crates/vapora-llm-router/Cargo.toml +++ b/crates/vapora-llm-router/Cargo.toml @@ -15,8 +15,7 @@ crate-type = ["rlib"] vapora-shared = { workspace = true } # Embeddings -# Note: Update STRATUM_EMBEDDINGS_PATH environment variable or adjust path relative to your workspace -stratum-embeddings = { path = "../../../stratumiops/crates/stratum-embeddings", features = ["vapora"] } +stratum-embeddings = { workspace = true } # Secrets management secretumvault = { workspace = true } diff --git a/crates/vapora-rlm/examples/local_ollama.rs b/crates/vapora-rlm/examples/local_ollama.rs index 0a45c8a..518df65 100644 --- a/crates/vapora-rlm/examples/local_ollama.rs +++ b/crates/vapora-rlm/examples/local_ollama.rs @@ -25,8 +25,8 @@ async fn main() -> anyhow::Result<()> { // 1. Setup SurrealDB let db = Surreal::new::("127.0.0.1:8000").await?; db.signin(Root { - username: "root", - password: "root", + username: "root".to_string(), + password: "root".to_string(), }) .await?; db.use_ns("local").use_db("rlm").await?; diff --git a/crates/vapora-rlm/examples/production_setup.rs b/crates/vapora-rlm/examples/production_setup.rs index 77957a3..8471e25 100644 --- a/crates/vapora-rlm/examples/production_setup.rs +++ b/crates/vapora-rlm/examples/production_setup.rs @@ -24,8 +24,8 @@ async fn main() -> anyhow::Result<()> { // 1. Setup SurrealDB let db = Surreal::new::("127.0.0.1:8000").await?; db.signin(Root { - username: "root", - password: "root", + username: "root".to_string(), + password: "root".to_string(), }) .await?; db.use_ns("production").use_db("rlm").await?; diff --git a/crates/vapora-rlm/src/storage/surrealdb.rs b/crates/vapora-rlm/src/storage/surrealdb.rs index 7ee2d4e..ed4b9af 100644 --- a/crates/vapora-rlm/src/storage/surrealdb.rs +++ b/crates/vapora-rlm/src/storage/surrealdb.rs @@ -97,10 +97,14 @@ impl Storage for SurrealDBStorage { RLMError::DatabaseError(Box::new(e)) })?; - let results: Vec = response.take(0).map_err(|e| { + let raw: Vec = response.take(0).map_err(|e| { error!("Failed to parse chunks for doc {}: {}", doc_id, e); RLMError::DatabaseError(Box::new(e)) })?; + let results: Vec = raw + .into_iter() + .filter_map(|v| serde_json::from_value(v).ok()) + .collect(); STORAGE_OPERATIONS .with_label_values(&["get_chunks", "success"]) @@ -125,10 +129,14 @@ impl Storage for SurrealDBStorage { RLMError::DatabaseError(Box::new(e)) })?; - let results: Vec = response.take(0).map_err(|e| { + let raw: Vec = response.take(0).map_err(|e| { error!("Failed to parse chunk {}: {}", chunk_id, e); RLMError::DatabaseError(Box::new(e)) })?; + let results: Vec = raw + .into_iter() + .filter_map(|v| serde_json::from_value(v).ok()) + .collect(); STORAGE_OPERATIONS .with_label_values(&["get_chunk", "success"]) @@ -161,10 +169,14 @@ impl Storage for SurrealDBStorage { RLMError::DatabaseError(Box::new(e)) })?; - let results: Vec = response.take(0).map_err(|e| { + let raw: Vec = response.take(0).map_err(|e| { error!("Failed to parse embedding search results: {}", e); RLMError::DatabaseError(Box::new(e)) })?; + let results: Vec = raw + .into_iter() + .filter_map(|v| serde_json::from_value(v).ok()) + .collect(); STORAGE_OPERATIONS .with_label_values(&["search_embedding", "success"]) @@ -225,10 +237,14 @@ impl Storage for SurrealDBStorage { RLMError::DatabaseError(Box::new(e)) })?; - let results: Vec = response.take(0).map_err(|e| { + let raw: Vec = response.take(0).map_err(|e| { error!("Failed to parse buffer {}: {}", buffer_id, e); RLMError::DatabaseError(Box::new(e)) })?; + let results: Vec = raw + .into_iter() + .filter_map(|v| serde_json::from_value(v).ok()) + .collect(); STORAGE_OPERATIONS .with_label_values(&["get_buffer", "success"]) @@ -332,10 +348,14 @@ impl Storage for SurrealDBStorage { RLMError::DatabaseError(Box::new(e)) })?; - let results: Vec = response.take(0).map_err(|e| { + let raw: Vec = response.take(0).map_err(|e| { error!("Failed to parse executions for doc {}: {}", doc_id, e); RLMError::DatabaseError(Box::new(e)) })?; + let results: Vec = raw + .into_iter() + .filter_map(|v| serde_json::from_value(v).ok()) + .collect(); STORAGE_OPERATIONS .with_label_values(&["get_executions", "success"]) diff --git a/crates/vapora-rlm/tests/e2e_integration.rs b/crates/vapora-rlm/tests/e2e_integration.rs index d654510..67e7d17 100644 --- a/crates/vapora-rlm/tests/e2e_integration.rs +++ b/crates/vapora-rlm/tests/e2e_integration.rs @@ -30,8 +30,8 @@ async fn setup_test_environment() -> ( let db = Surreal::new::("127.0.0.1:8000").await.unwrap(); db.signin(Root { - username: "root", - password: "root", + username: "root".to_string(), + password: "root".to_string(), }) .await .unwrap(); diff --git a/crates/vapora-rlm/tests/e2e_minimal_debug.rs b/crates/vapora-rlm/tests/e2e_minimal_debug.rs index 6daf7f0..fe8e80e 100644 --- a/crates/vapora-rlm/tests/e2e_minimal_debug.rs +++ b/crates/vapora-rlm/tests/e2e_minimal_debug.rs @@ -14,8 +14,8 @@ async fn test_e2e_minimal_trace() { // Setup - exactly like E2E test let db = Surreal::new::("127.0.0.1:8000").await.unwrap(); db.signin(Root { - username: "root", - password: "root", + username: "root".to_string(), + password: "root".to_string(), }) .await .unwrap(); diff --git a/crates/vapora-rlm/tests/engine_bm25_test.rs b/crates/vapora-rlm/tests/engine_bm25_test.rs index 0615e9b..ffa124e 100644 --- a/crates/vapora-rlm/tests/engine_bm25_test.rs +++ b/crates/vapora-rlm/tests/engine_bm25_test.rs @@ -14,8 +14,8 @@ async fn test_engine_bm25_query() { // Setup - same as E2E test let db = Surreal::new::("127.0.0.1:8000").await.unwrap(); db.signin(Root { - username: "root", - password: "root", + username: "root".to_string(), + password: "root".to_string(), }) .await .unwrap(); diff --git a/crates/vapora-rlm/tests/integration_test.rs b/crates/vapora-rlm/tests/integration_test.rs index 3d338a6..aedcea1 100644 --- a/crates/vapora-rlm/tests/integration_test.rs +++ b/crates/vapora-rlm/tests/integration_test.rs @@ -17,8 +17,8 @@ async fn test_storage_chunk_persistence() { .await .expect("Failed to connect to SurrealDB"); db.signin(Root { - username: "root", - password: "root", + username: "root".to_string(), + password: "root".to_string(), }) .await .expect("Failed to sign in"); @@ -79,8 +79,8 @@ async fn test_storage_buffer_operations() { .await .expect("Failed to connect to SurrealDB"); db.signin(Root { - username: "root", - password: "root", + username: "root".to_string(), + password: "root".to_string(), }) .await .expect("Failed to sign in"); @@ -124,8 +124,8 @@ async fn test_storage_execution_history() { .await .expect("Failed to connect to SurrealDB"); db.signin(Root { - username: "root", - password: "root", + username: "root".to_string(), + password: "root".to_string(), }) .await .expect("Failed to sign in"); @@ -177,8 +177,8 @@ async fn test_storage_embedding_search() { .await .expect("Failed to connect to SurrealDB"); db.signin(Root { - username: "root", - password: "root", + username: "root".to_string(), + password: "root".to_string(), }) .await .expect("Failed to sign in"); diff --git a/crates/vapora-rlm/tests/performance_test.rs b/crates/vapora-rlm/tests/performance_test.rs index 54f9942..c5f591e 100644 --- a/crates/vapora-rlm/tests/performance_test.rs +++ b/crates/vapora-rlm/tests/performance_test.rs @@ -17,8 +17,8 @@ use vapora_rlm::RLMEngine; async fn setup_engine() -> Arc> { let db = Surreal::new::("127.0.0.1:8000").await.unwrap(); db.signin(Root { - username: "root", - password: "root", + username: "root".to_string(), + password: "root".to_string(), }) .await .unwrap(); diff --git a/crates/vapora-workflow-engine/Cargo.toml b/crates/vapora-workflow-engine/Cargo.toml index 4be837b..f42f402 100644 --- a/crates/vapora-workflow-engine/Cargo.toml +++ b/crates/vapora-workflow-engine/Cargo.toml @@ -44,7 +44,14 @@ anyhow = { workspace = true } # Metrics prometheus = { workspace = true } +# Persistence +surrealdb = { workspace = true } + +# Authorization +cedar-policy = "4.9" + [dev-dependencies] mockall = { workspace = true } wiremock = { workspace = true } tokio = { workspace = true, features = ["test-util"] } +tempfile = { workspace = true } diff --git a/crates/vapora-workflow-engine/src/auth.rs b/crates/vapora-workflow-engine/src/auth.rs new file mode 100644 index 0000000..4d3935e --- /dev/null +++ b/crates/vapora-workflow-engine/src/auth.rs @@ -0,0 +1,157 @@ +use std::path::Path; + +use cedar_policy::{Authorizer, Context as CedarContext, Entities, PolicySet, Request}; +use tracing::debug; + +use crate::error::{Result, WorkflowError}; + +/// Cedar policy authorizer for per-stage execution control. +/// +/// Loads `.cedar` policy files from a directory and evaluates authorization +/// decisions before each stage dispatch. Authorization is +/// principal/action/resource based: `User::"vapora-orchestrator"`, +/// `Action::"execute-stage"`, `Stage::""`. +pub struct CedarAuthorizer { + policy_set: PolicySet, + authorizer: Authorizer, +} + +impl CedarAuthorizer { + /// Load all `.cedar` policy files from `dir`, combining them into a single + /// policy set. + pub fn load_from_dir(dir: &Path) -> Result { + let entries = std::fs::read_dir(dir).map_err(|e| { + WorkflowError::Internal(format!("reading Cedar policy dir '{}': {e}", dir.display())) + })?; + + let mut combined = String::new(); + + for entry in entries { + let entry = entry + .map_err(|e| WorkflowError::Internal(format!("reading Cedar dir entry: {e}")))?; + let path = entry.path(); + if path.extension().and_then(|e| e.to_str()) != Some("cedar") { + continue; + } + let content = std::fs::read_to_string(&path).map_err(|e| { + WorkflowError::Internal(format!("reading Cedar policy '{}': {e}", path.display())) + })?; + combined.push_str(&content); + combined.push('\n'); + } + + if combined.trim().is_empty() { + return Err(WorkflowError::Internal(format!( + "no .cedar policy files found in '{}'", + dir.display() + ))); + } + + let policy_set: PolicySet = combined + .parse() + .map_err(|e| WorkflowError::Internal(format!("parsing Cedar policies: {e}")))?; + + Ok(Self { + policy_set, + authorizer: Authorizer::new(), + }) + } + + /// Returns `Ok(())` if permitted, `Err(Unauthorized)` if denied. + pub fn authorize(&self, principal: &str, action: &str, resource: &str) -> Result<()> { + let principal_entity: cedar_policy::EntityUid = + format!("User::\"{principal}\"").parse().map_err(|e| { + WorkflowError::Internal(format!("parsing Cedar principal EntityUid: {e}")) + })?; + + let action_entity: cedar_policy::EntityUid = format!("Action::\"{action}\"") + .parse() + .map_err(|e| WorkflowError::Internal(format!("parsing Cedar action EntityUid: {e}")))?; + + let resource_entity: cedar_policy::EntityUid = resource.parse().map_err(|e| { + WorkflowError::Internal(format!( + "parsing Cedar resource EntityUid '{resource}': {e}" + )) + })?; + + let request = Request::new( + principal_entity, + action_entity, + resource_entity, + CedarContext::empty(), + None, + ) + .map_err(|e| WorkflowError::Internal(format!("building Cedar request: {e}")))?; + + let response = + self.authorizer + .is_authorized(&request, &self.policy_set, &Entities::empty()); + + debug!( + "Cedar: {principal} {action} {resource} → {:?}", + response.decision() + ); + + match response.decision() { + cedar_policy::Decision::Allow => Ok(()), + cedar_policy::Decision::Deny => Err(WorkflowError::Unauthorized(format!( + "Cedar denied: principal '{principal}' action '{action}' resource '{resource}'" + ))), + } + } +} + +#[cfg(test)] +mod tests { + use std::io::Write; + + use tempfile::TempDir; + + use super::*; + + fn write_policy(dir: &TempDir, name: &str, content: &str) { + let path = dir.path().join(name); + let mut f = std::fs::File::create(path).unwrap(); + f.write_all(content.as_bytes()).unwrap(); + } + + const PERMIT_ORCHESTRATOR: &str = r#" +permit( + principal == User::"vapora-orchestrator", + action == Action::"execute-stage", + resource == Stage::"deploy" +);"#; + + const FORBID_ALL: &str = r#"forbid(principal, action, resource);"#; + + #[test] + fn test_permit_allows() { + let dir = TempDir::new().unwrap(); + write_policy(&dir, "permit.cedar", PERMIT_ORCHESTRATOR); + + let authz = CedarAuthorizer::load_from_dir(dir.path()).unwrap(); + authz + .authorize("vapora-orchestrator", "execute-stage", "Stage::\"deploy\"") + .unwrap(); + } + + #[test] + fn test_deny_returns_unauthorized() { + let dir = TempDir::new().unwrap(); + write_policy(&dir, "forbid.cedar", FORBID_ALL); + + let authz = CedarAuthorizer::load_from_dir(dir.path()).unwrap(); + let err = authz + .authorize("vapora-orchestrator", "execute-stage", "Stage::\"deploy\"") + .unwrap_err(); + assert!(matches!(err, WorkflowError::Unauthorized(_))); + assert!(err.to_string().contains("Cedar denied")); + } + + #[test] + fn test_empty_dir_fails() { + let dir = TempDir::new().unwrap(); + let result = CedarAuthorizer::load_from_dir(dir.path()); + assert!(result.is_err()); + } +} diff --git a/crates/vapora-workflow-engine/src/config.rs b/crates/vapora-workflow-engine/src/config.rs index 23e4244..4cc3629 100644 --- a/crates/vapora-workflow-engine/src/config.rs +++ b/crates/vapora-workflow-engine/src/config.rs @@ -15,6 +15,8 @@ pub struct EngineConfig { pub max_parallel_tasks: usize, pub workflow_timeout: u64, pub approval_gates_enabled: bool, + #[serde(default)] + pub cedar_policy_dir: Option, } #[derive(Debug, Clone, Deserialize)] @@ -34,6 +36,10 @@ pub struct StageConfig { pub max_parallel: Option, #[serde(default)] pub approval_required: bool, + /// Agent roles that receive a compensation task if this stage needs to be + /// rolled back via Saga. + #[serde(default)] + pub compensation_agents: Option>, } impl WorkflowsConfig { @@ -127,6 +133,7 @@ approval_required = false max_parallel_tasks: 10, workflow_timeout: 3600, approval_gates_enabled: true, + cedar_policy_dir: None, }, workflows: vec![], }; diff --git a/crates/vapora-workflow-engine/src/error.rs b/crates/vapora-workflow-engine/src/error.rs index e53b2b4..9fbccdb 100644 --- a/crates/vapora-workflow-engine/src/error.rs +++ b/crates/vapora-workflow-engine/src/error.rs @@ -41,6 +41,12 @@ pub enum WorkflowError { #[error("Artifact persistence failed: {0}")] ArtifactError(String), + #[error("Database error: {0}")] + DatabaseError(String), + + #[error("Authorization denied: {0}")] + Unauthorized(String), + #[error("Internal error: {0}")] Internal(String), } diff --git a/crates/vapora-workflow-engine/src/instance.rs b/crates/vapora-workflow-engine/src/instance.rs index 5b6a82e..f26b0c6 100644 --- a/crates/vapora-workflow-engine/src/instance.rs +++ b/crates/vapora-workflow-engine/src/instance.rs @@ -171,6 +171,31 @@ impl WorkflowInstance { let _ = stage.transition(StageStatus::Failed(error)); } } + + /// Marks a task as failed in the current stage and optionally transitions + /// the stage to `Failed`. + /// + /// Returns `Some(Ok(stage_name))` when the failure is non-retryable and + /// the stage was transitioned, `None` when retrying or no active stage. + /// Isolates the mutable borrow of `current_stage_mut()` so callers can + /// access other fields of `self` after this returns. + pub fn mark_current_task_failed( + &mut self, + task_id: &str, + error: &str, + can_retry: bool, + ) -> Option> { + let stage = self.current_stage_mut()?; + if let Some(task) = stage.assigned_tasks.get_mut(task_id) { + task.mark_failed(error.to_string()); + } + if can_retry { + return None; + } + let stage_name = stage.name.clone(); + let r = stage.transition(StageStatus::Failed(error.to_string())); + Some(r.map(|()| stage_name)) + } } #[cfg(test)] @@ -190,6 +215,7 @@ mod tests { parallel: false, max_parallel: None, approval_required: false, + compensation_agents: None, }, StageConfig { name: "stage2".to_string(), @@ -197,6 +223,7 @@ mod tests { parallel: false, max_parallel: None, approval_required: false, + compensation_agents: None, }, ], } diff --git a/crates/vapora-workflow-engine/src/lib.rs b/crates/vapora-workflow-engine/src/lib.rs index 2c45f62..abe5eab 100644 --- a/crates/vapora-workflow-engine/src/lib.rs +++ b/crates/vapora-workflow-engine/src/lib.rs @@ -16,58 +16,30 @@ //! - `WorkflowInstance`: State machine tracking individual workflow execution //! - `StageState`: Manages stage execution and task assignment //! - `Artifact`: Data passed between stages -//! -//! # Example -//! -//! ```no_run -//! use vapora_workflow_engine::{WorkflowOrchestrator, config::WorkflowsConfig}; -//! use std::sync::Arc; -//! -//! # async fn example() -> Result<(), Box> { -//! // Initialize dependencies (SwarmCoordinator, KGPersistence, NATS) -//! # let swarm = todo!(); -//! # let kg = todo!(); -//! # let nats = todo!(); -//! -//! // Create orchestrator -//! let orchestrator = Arc::new( -//! WorkflowOrchestrator::new( -//! "config/workflows.toml", -//! swarm, -//! kg, -//! nats, -//! ).await? -//! ); -//! -//! // Start event listener -//! orchestrator.clone().start_event_listener().await?; -//! -//! // Start a workflow -//! let workflow_id = orchestrator.start_workflow( -//! "feature_development", -//! serde_json::json!({ -//! "task": "Add authentication", -//! "requirements": ["OAuth2", "JWT"] -//! }) -//! ).await?; -//! -//! println!("Workflow started: {}", workflow_id); -//! # Ok(()) -//! # } -//! ``` +//! - `SurrealWorkflowStore`: Persistence layer — crash-recoverable via +//! SurrealDB +//! - `SagaCompensator`: Rolls back completed stages on failure (reverse-order +//! dispatch) +//! - `CedarAuthorizer`: Per-stage Cedar policy enforcement pub mod artifact; +pub mod auth; pub mod config; pub mod error; pub mod instance; pub mod metrics; pub mod orchestrator; +pub mod persistence; +pub mod saga; pub mod stage; pub use artifact::{Artifact, ArtifactType}; +pub use auth::CedarAuthorizer; pub use config::{EngineConfig, StageConfig, WorkflowConfig, WorkflowsConfig}; pub use error::{ConfigError, Result, WorkflowError}; pub use instance::{WorkflowInstance, WorkflowStatus}; pub use metrics::WorkflowMetrics; pub use orchestrator::WorkflowOrchestrator; +pub use persistence::SurrealWorkflowStore; +pub use saga::SagaCompensator; pub use stage::{StageState, StageStatus, TaskState, TaskStatus}; diff --git a/crates/vapora-workflow-engine/src/orchestrator.rs b/crates/vapora-workflow-engine/src/orchestrator.rs index e0cfbaa..eaf894c 100644 --- a/crates/vapora-workflow-engine/src/orchestrator.rs +++ b/crates/vapora-workflow-engine/src/orchestrator.rs @@ -4,17 +4,22 @@ use chrono::Utc; use dashmap::DashMap; use futures::StreamExt; use serde_json::Value; +use surrealdb::engine::remote::ws::Client; +use surrealdb::Surreal; use tracing::{debug, error, info, warn}; use vapora_agents::messages::{AgentMessage, TaskCompleted, TaskFailed}; use vapora_knowledge_graph::persistence::KGPersistence; use vapora_swarm::coordinator::SwarmCoordinator; use crate::artifact::{Artifact, ArtifactType}; +use crate::auth::CedarAuthorizer; use crate::config::{StageConfig, WorkflowsConfig}; use crate::error::{Result, WorkflowError}; use crate::instance::{WorkflowInstance, WorkflowStatus}; use crate::metrics::WorkflowMetrics; -use crate::stage::{StageStatus, TaskState}; +use crate::persistence::SurrealWorkflowStore; +use crate::saga::SagaCompensator; +use crate::stage::{StageState, StageStatus, TaskState}; pub struct WorkflowOrchestrator { config: WorkflowsConfig, @@ -24,6 +29,9 @@ pub struct WorkflowOrchestrator { nats: Arc, active_workflows: DashMap, metrics: Arc, + store: Arc, + saga: SagaCompensator, + cedar: Option>, } impl WorkflowOrchestrator { @@ -32,6 +40,7 @@ impl WorkflowOrchestrator { swarm: Arc, kg: Arc, nats: Arc, + db: Surreal, ) -> Result { let config = WorkflowsConfig::load(config_path)?; let metrics = @@ -39,13 +48,50 @@ impl WorkflowOrchestrator { WorkflowError::Internal(format!("Failed to create metrics: {}", e)) })?); + let db = Arc::new(db); + let store = Arc::new(SurrealWorkflowStore::new(db)); + let saga = SagaCompensator::new(swarm.clone()); + + let cedar = config + .engine + .cedar_policy_dir + .as_deref() + .map(|dir| CedarAuthorizer::load_from_dir(std::path::Path::new(dir)).map(Arc::new)) + .transpose() + .map_err(|e| WorkflowError::Internal(format!("Cedar init: {e}")))?; + + if cedar.is_some() { + info!("Cedar authorization enabled for workflow stages"); + } + + // Crash recovery: restore active workflows from DB + let active_workflows = DashMap::new(); + match store.load_active().await { + Ok(instances) => { + let count = instances.len(); + for instance in instances { + active_workflows.insert(instance.id.clone(), instance); + } + if count > 0 { + info!(count = count, "Restored active workflows from DB"); + metrics.active_workflows.add(count as i64); + } + } + Err(e) => { + warn!(error = %e, "Failed to restore active workflows from DB (starting empty)"); + } + } + Ok(Self { config, swarm, kg, nats, - active_workflows: DashMap::new(), + active_workflows, metrics, + store, + saga, + cedar, }) } @@ -66,6 +112,7 @@ impl WorkflowOrchestrator { let instance = WorkflowInstance::new(template, initial_context); let workflow_id = instance.id.clone(); + self.store.save(&instance).await?; self.active_workflows.insert(workflow_id.clone(), instance); self.metrics.active_workflows.inc(); @@ -113,6 +160,12 @@ impl WorkflowOrchestrator { return Ok(()); } + // Cedar authorization check before dispatch + if let Some(cedar) = &self.cedar { + let resource = format!("Stage::\"{}\"", stage_config.name); + cedar.authorize("vapora-orchestrator", "execute-stage", &resource)?; + } + if stage_config.parallel { self.assign_parallel_tasks(workflow_id, &stage_config, context) .await?; @@ -133,6 +186,11 @@ impl WorkflowOrchestrator { } } + // Persist after stage state change + if let Some(instance) = self.active_workflows.get(workflow_id) { + self.store.save(instance.value()).await?; + } + Ok(()) } @@ -302,6 +360,11 @@ impl WorkflowOrchestrator { all_completed }; + // Persist after each state change + if let Some(instance) = self.active_workflows.get(&workflow_id) { + self.store.save(instance.value()).await?; + } + if should_advance { self.advance_to_next_stage(&workflow_id).await?; } @@ -341,6 +404,15 @@ impl WorkflowOrchestrator { ); self.publish_workflow_completed(workflow_id).await?; + + // Remove from DB — terminal state is cleaned up + if let Err(e) = self.store.delete(workflow_id).await { + warn!( + workflow_id = %workflow_id, + error = %e, + "Failed to delete completed workflow from store" + ); + } } Ok(()) @@ -373,19 +445,26 @@ impl WorkflowOrchestrator { } pub async fn cancel_workflow(&self, workflow_id: &str, reason: String) -> Result<()> { - let mut instance = self - .active_workflows - .get_mut(workflow_id) - .ok_or_else(|| WorkflowError::WorkflowNotFound(workflow_id.to_string()))?; + { + let mut instance = self + .active_workflows + .get_mut(workflow_id) + .ok_or_else(|| WorkflowError::WorkflowNotFound(workflow_id.to_string()))?; - instance.cancel(reason.clone()); - self.metrics.active_workflows.dec(); + instance.cancel(reason.clone()); + self.metrics.active_workflows.dec(); - info!( - workflow_id = %workflow_id, - reason = %reason, - "Workflow cancelled" - ); + info!( + workflow_id = %workflow_id, + reason = %reason, + "Workflow cancelled" + ); + } + + // Persist cancelled state, then clean up + if let Some(instance) = self.active_workflows.get(workflow_id) { + self.store.save(instance.value()).await?; + } Ok(()) } @@ -464,27 +543,36 @@ impl WorkflowOrchestrator { async fn on_task_failed(&self, msg: TaskFailed) -> Result<()> { let workflow_id = self.find_workflow_for_task(&msg.task_id)?; - { + // `mark_current_task_failed` encapsulates the mutable stage borrow so + // the DashMap entry can be re-accessed without nesting or borrow + // conflicts. + let compensation_data: Option<(Vec, Value, String)> = { let mut instance = self .active_workflows .get_mut(&workflow_id) .ok_or_else(|| WorkflowError::WorkflowNotFound(workflow_id.clone()))?; - if let Some(stage) = instance.current_stage_mut() { - if let Some(task) = stage.assigned_tasks.get_mut(&msg.task_id) { - task.mark_failed(msg.error.clone()); - } + let stage_result = + instance.mark_current_task_failed(&msg.task_id, &msg.error, msg.can_retry); + + match stage_result { + None => { + if msg.can_retry { + warn!( + workflow_id = %workflow_id, + task_id = %msg.task_id, + retry_count = msg.retry_count, + "Task failed, will retry" + ); + } + None + } + Some(Err(e)) => return Err(e), + Some(Ok(stage_name)) => { + let current_idx = instance.current_stage_idx; + let executed_stages = instance.stages[..current_idx].to_vec(); + let context = instance.initial_context.clone(); - if msg.can_retry { - warn!( - workflow_id = %workflow_id, - task_id = %msg.task_id, - retry_count = msg.retry_count, - "Task failed, will retry" - ); - } else { - let stage_name = stage.name.clone(); - stage.transition(StageStatus::Failed(msg.error.clone()))?; instance.fail(format!("Stage {} failed: {}", stage_name, msg.error)); self.metrics.workflows_failed.inc(); @@ -496,8 +584,22 @@ impl WorkflowOrchestrator { error = %msg.error, "Workflow failed" ); + + Some((executed_stages, context, stage_name)) } } + }; // DashMap lock released here + + if let Some((executed_stages, context, _stage_name)) = compensation_data { + // Saga compensation: dispatch rollback tasks in reverse order (best-effort) + self.saga + .compensate(&workflow_id, &executed_stages, &context) + .await?; + + // Persist the failed state + if let Some(instance) = self.active_workflows.get(&workflow_id) { + self.store.save(instance.value()).await?; + } } Ok(()) diff --git a/crates/vapora-workflow-engine/src/persistence.rs b/crates/vapora-workflow-engine/src/persistence.rs new file mode 100644 index 0000000..c744fa1 --- /dev/null +++ b/crates/vapora-workflow-engine/src/persistence.rs @@ -0,0 +1,97 @@ +use std::sync::Arc; + +use surrealdb::engine::remote::ws::Client; +use surrealdb::Surreal; +use tracing::debug; + +use crate::error::{Result, WorkflowError}; +use crate::instance::WorkflowInstance; + +/// Persists `WorkflowInstance` records to SurrealDB for crash recovery. +/// +/// Uses the injected connection from the backend — does NOT create its own DB +/// connection. Table: `workflow_instances` (created by migration +/// 009_workflow_state.surql). +pub struct SurrealWorkflowStore { + db: Arc>, +} + +impl SurrealWorkflowStore { + pub fn new(db: Arc>) -> Self { + Self { db } + } + + /// Upsert a workflow instance. Called after every state-mutating operation. + pub async fn save(&self, instance: &WorkflowInstance) -> Result<()> { + let json = serde_json::to_value(instance).map_err(|e| { + WorkflowError::DatabaseError(format!("serialize workflow {}: {e}", instance.id)) + })?; + + let _: Option = self + .db + .upsert(("workflow_instances", &*instance.id)) + .content(json) + .await + .map_err(|e| { + WorkflowError::DatabaseError(format!("save workflow {}: {e}", instance.id)) + })?; + + debug!(workflow_id = %instance.id, "Workflow instance persisted"); + Ok(()) + } + + /// Load a single instance by ID. + pub async fn load(&self, id: &str) -> Result> { + let raw: Option = self + .db + .select(("workflow_instances", id)) + .await + .map_err(|e| WorkflowError::DatabaseError(format!("load workflow {id}: {e}")))?; + + raw.map(|v| { + serde_json::from_value(v).map_err(|e| { + WorkflowError::DatabaseError(format!("deserialize workflow {id}: {e}")) + }) + }) + .transpose() + } + + /// Load all non-terminal instances for crash recovery on startup. + /// + /// Fetches all rows and filters in Rust — avoids complex SurrealQL queries + /// against serde-serialized enum variants (e.g. `Failed` serializes as an + /// object). + pub async fn load_active(&self) -> Result> { + let mut response = self + .db + .query("SELECT * FROM workflow_instances") + .await + .map_err(|e| WorkflowError::DatabaseError(format!("load_active query: {e}")))?; + + let raw: Vec = response + .take(0) + .map_err(|e| WorkflowError::DatabaseError(format!("load_active take: {e}")))?; + + let instances: Vec = raw + .into_iter() + .filter_map(|v| serde_json::from_value(v).ok()) + .collect(); + + Ok(instances + .into_iter() + .filter(|i| !i.is_completed() && !i.is_failed() && !i.is_cancelled()) + .collect()) + } + + /// Delete a terminal workflow instance from the store. + pub async fn delete(&self, id: &str) -> Result<()> { + let _: Option = self + .db + .delete(("workflow_instances", id)) + .await + .map_err(|e| WorkflowError::DatabaseError(format!("delete workflow {id}: {e}")))?; + + debug!(workflow_id = %id, "Workflow instance deleted from store"); + Ok(()) + } +} diff --git a/crates/vapora-workflow-engine/src/saga.rs b/crates/vapora-workflow-engine/src/saga.rs new file mode 100644 index 0000000..cebc60e --- /dev/null +++ b/crates/vapora-workflow-engine/src/saga.rs @@ -0,0 +1,175 @@ +use std::sync::Arc; + +use tracing::{error, info}; +use vapora_swarm::coordinator::SwarmCoordinator; + +use crate::error::Result; +use crate::stage::StageState; + +/// Saga compensator that dispatches rollback tasks for completed stages when +/// a downstream stage fails. +/// +/// Iterates executed stages in reverse order, and for each stage that has +/// `compensation_agents` configured, submits a `compensation` task to the +/// `SwarmCoordinator`. Errors are logged but never propagated — compensation +/// is best-effort (consistent with stratum-orchestrator's behaviour). +pub struct SagaCompensator { + swarm: Arc, +} + +impl SagaCompensator { + pub fn new(swarm: Arc) -> Self { + Self { swarm } + } + + /// Dispatch compensation tasks for `executed_stages` in reverse order. + /// + /// `context` is the workflow's `initial_context` — passed to each + /// compensation task so the agent has enough information to undo the work. + pub async fn compensate( + &self, + workflow_id: &str, + executed_stages: &[StageState], + context: &serde_json::Value, + ) -> Result<()> { + for stage in executed_stages.iter().rev() { + let compensation_agents = match &stage.config.compensation_agents { + Some(agents) if !agents.is_empty() => agents.clone(), + _ => continue, + }; + + let task_id = format!("compensate-{}-{}", workflow_id, stage.name); + let task_payload = serde_json::json!({ + "type": "compensation", + "stage_name": stage.name, + "workflow_id": workflow_id, + "original_context": context, + "artifacts_to_undo": stage.artifacts_produced, + }); + + match self + .swarm + .submit_task_for_bidding( + task_id.clone(), + task_payload.to_string(), + compensation_agents, + ) + .await + { + Ok(_) => { + info!( + workflow_id = %workflow_id, + stage = %stage.name, + task_id = %task_id, + "Saga compensation task dispatched" + ); + } + Err(e) => { + error!( + workflow_id = %workflow_id, + stage = %stage.name, + task_id = %task_id, + error = %e, + "Compensation dispatch failed (best-effort, continuing)" + ); + } + } + } + + Ok(()) + } +} + +#[cfg(test)] +mod tests { + use crate::config::StageConfig; + use crate::stage::{StageState, StageStatus, TaskState}; + + fn stage_with_compensation(name: &str, agents: Vec) -> StageState { + let config = StageConfig { + name: name.to_string(), + agents: vec!["developer".to_string()], + parallel: false, + max_parallel: None, + approval_required: false, + compensation_agents: Some(agents), + }; + let mut state = StageState::new(config); + state.status = StageStatus::Completed; + state.artifacts_produced = vec![format!("{name}-artifact")]; + state + } + + fn stage_without_compensation(name: &str) -> StageState { + let config = StageConfig { + name: name.to_string(), + agents: vec!["developer".to_string()], + parallel: false, + max_parallel: None, + approval_required: false, + compensation_agents: None, + }; + let mut state = StageState::new(config); + state.status = StageStatus::Completed; + state + } + + #[test] + fn test_stages_with_no_compensation_agents_are_skipped() { + let stages = vec![ + stage_without_compensation("design"), + stage_without_compensation("review"), + ]; + + // Verify the filter logic: stages without compensation_agents produce no tasks + let compensatable: Vec<&StageState> = stages + .iter() + .rev() + .filter(|s| { + s.config + .compensation_agents + .as_ref() + .map(|a| !a.is_empty()) + .unwrap_or(false) + }) + .collect(); + + assert!(compensatable.is_empty()); + } + + #[test] + fn test_stages_with_compensation_agents_are_included() { + let stages = vec![ + stage_with_compensation("deploy", vec!["ops-agent".to_string()]), + stage_without_compensation("review"), + stage_with_compensation("provision", vec!["infra-agent".to_string()]), + ]; + + let compensatable: Vec<&str> = stages + .iter() + .rev() + .filter(|s| { + s.config + .compensation_agents + .as_ref() + .map(|a| !a.is_empty()) + .unwrap_or(false) + }) + .map(|s| s.name.as_str()) + .collect(); + + // Reverse order: provision first, then deploy + assert_eq!(compensatable, vec!["provision", "deploy"]); + } + + #[test] + fn test_task_state_mark_completed_carries_artifacts() { + let mut task = TaskState::new( + "t1".to_string(), + "agent-1".to_string(), + "ops-agent".to_string(), + ); + task.mark_completed("done".to_string(), vec!["artifact-1".to_string()]); + assert_eq!(task.artifacts, vec!["artifact-1"]); + } +} diff --git a/crates/vapora-workflow-engine/src/stage.rs b/crates/vapora-workflow-engine/src/stage.rs index 25fa3a5..ed71e1e 100644 --- a/crates/vapora-workflow-engine/src/stage.rs +++ b/crates/vapora-workflow-engine/src/stage.rs @@ -154,6 +154,7 @@ mod tests { parallel: false, max_parallel: None, approval_required: false, + compensation_agents: None, } } diff --git a/docs/adrs/0033-stratum-orchestrator-workflow-hardening.md b/docs/adrs/0033-stratum-orchestrator-workflow-hardening.md new file mode 100644 index 0000000..cebaf3d --- /dev/null +++ b/docs/adrs/0033-stratum-orchestrator-workflow-hardening.md @@ -0,0 +1,225 @@ +# ADR-0033: Workflow Engine Hardening — Persistence, Saga Compensation, Cedar Authorization + +**Status**: Implemented +**Date**: 2026-02-21 +**Deciders**: VAPORA Team +**Technical Story**: `vapora-workflow-engine` lost all state on restart, had no rollback mechanism on failure, and applied no per-stage access control. + +--- + +## Decision + +Harden `vapora-workflow-engine` with three independent layers inspired by the stratum-orchestrator project: + +1. **SurrealDB persistence** (`SurrealWorkflowStore`) — crash-recoverable `WorkflowInstance` state +2. **Saga compensation** (`SagaCompensator`) — reverse-order rollback dispatch via `SwarmCoordinator` +3. **Cedar authorization** (`CedarAuthorizer`) — per-stage policy enforcement before task dispatch + +All three are implemented natively inside `vapora-workflow-engine` — stratum-orchestrator is **not** a direct dependency. + +--- + +## Context + +### Gaps Before This ADR + +| Gap | Consequence | +|-----|-------------| +| In-memory `DashMap` only | All running workflows lost on server restart | +| No compensation on failure | Stage 3 failure left Stage 1 and 2 side effects live | +| No authorization check per stage | Any caller could trigger any stage in any workflow | + +### Why Not Import stratum-orchestrator Directly + +The plan initially included: + +```toml +stratum-orchestrator = { path = "../../../stratumiops/crates/stratum-orchestrator" } +``` + +This fails because `stratum-orchestrator → platform-nats → nkeys = { workspace = true }`. The `nkeys` dependency is resolved only inside the `stratumiops` workspace; it is not published to crates.io and has no path resolvable from vapora's workspace root. Cargo errors with `failed to select a version for nkeys`. + +The `CedarAuthorizer` inside stratum-orchestrator is 88 self-contained lines using only `cedar-policy`. Implementing it locally is zero duplication risk and avoids a circular workspace dependency. + +--- + +## Implementation + +### New Modules + +```text +crates/vapora-workflow-engine/src/ +├── auth.rs — CedarAuthorizer: loads .cedar policy files, authorize() +├── persistence.rs — SurrealWorkflowStore: save/load/load_active/delete +└── saga.rs — SagaCompensator: compensate(workflow_id, stages, ctx) +``` + +### New Migration + +```text +migrations/009_workflow_state.surql — SCHEMAFULL workflow_instances table +``` + +### Config Changes + +```toml +[engine] +cedar_policy_dir = "/etc/vapora/cedar" # optional; Cedar disabled if absent + +[[workflows.stages]] +name = "deploy" +agents = ["devops"] +compensation_agents = ["devops"] # receives rollback task if Saga fires +``` + +### Dependency Addition + +```toml +# crates/vapora-workflow-engine/Cargo.toml +surrealdb = { workspace = true } +cedar-policy = "4.9" +``` + +`cedar-policy` enters directly; it was previously only transitive via `secretumvault` (4.8). Cargo resolves the workspace to 4.9 (semver compatible, same major). + +### WorkflowOrchestrator Constructor Change + +```rust +// Before +WorkflowOrchestrator::new(config_path, swarm, kg, nats) + +// After +WorkflowOrchestrator::new(config_path, swarm, kg, nats, db: Surreal) +``` + +`db` is the existing backend connection — the store does not open its own connection. + +--- + +## Data Flow + +```text +start_workflow() + → WorkflowInstance::new() + → store.save() ← persistence + → execute_current_stage() + → cedar.authorize() ← auth (if configured) + → swarm.assign_task() + +on_task_completed() + → task.mark_completed() + → store.save() ← persistence + +on_task_failed(can_retry=false) + → mark_current_task_failed() ← stage transition + → saga.compensate(stages, ctx) ← saga (reverse-order dispatch) + → instance.fail() + → store.save() ← persistence + +startup crash recovery + → store.load_active() ← restores active_workflows DashMap +``` + +--- + +## Saga Compensation Protocol + +Compensation is **best-effort**: errors are logged, never propagated. Stage order is reversed: the last executed stage receives a rollback task first. + +Only stages with `compensation_agents` defined in their `StageConfig` receive a compensation task. Stages without the field are silently skipped. + +Compensation task payload sent to `SwarmCoordinator`: + +```json +{ + "type": "compensation", + "stage_name": "deploy", + "workflow_id": "abc-123", + "original_context": { "…" : "…" }, + "artifacts_to_undo": ["artifact-id-1"] +} +``` + +--- + +## Cedar Authorization + +`CedarAuthorizer::load_from_dir(path)` reads all `*.cedar` files from the directory and compiles them into a single `PolicySet`. Before each stage dispatch: + +```rust +cedar.authorize( + "vapora-orchestrator", // principal + "execute-stage", // action + "Stage::\"architecture\"", // resource +)?; +``` + +A `Deny` decision returns `WorkflowError::Unauthorized`, halting the workflow without dispatching the stage. If `cedar_policy_dir` is not set in `EngineConfig`, Cedar is disabled and all stages proceed without policy checks. + +--- + +## Rationale + +### Why SurrealDB (not Redis / SQLite) + +SurrealDB is already the persistence layer for every other stateful component in vapora. Adding `workflow_instances` as one more table keeps the operational footprint at zero (no new service, no new connection pool). `WorkflowInstance` already implements `Serialize/Deserialize`; the store serializes via `serde_json::Value` to satisfy the `SurrealValue` trait requirement introduced in surrealdb v3. + +### Why Saga Over Two-Phase Commit + +Workflows already span multiple async agent executions over NATS. Two-phase commit across these boundaries would require protocol changes in every agent. Saga achieves eventual consistency via compensating transactions that each agent already understands (a task with `type: "compensation"`). + +### Why Cedar Over RBAC / Custom Middleware + +Cedar policies are already used by the rest of the VAPORA platform (see ADR-0010). Per-stage rules expressed in `.cedar` files are reviewable outside the codebase and hot-swappable without redeployment (restart required to reload, by current design). A custom middleware table would require schema migrations for every policy change. + +--- + +## Consequences + +### Positive + +- Workflows survive server restarts (crash recovery via `load_active()`) +- Non-retryable stage failure triggers best-effort rollback of completed stages +- Per-stage access control via auditable policy files +- Zero new infrastructure (uses existing SurrealDB connection) +- 31/31 existing tests continue to pass; 5 new tests added (auth × 3, saga × 2) + +### Negative + +- `WorkflowOrchestrator::new()` signature change requires callers to pass `Surreal` +- Cedar requires `.cedar` files on disk; missing `cedar_policy_dir` disables auth silently +- Compensation is best-effort — no guarantee of full rollback if compensation agent also fails + +### Mitigations + +| Risk | Mitigation | +|------|------------| +| Saga partial rollback | Metrics track compensation dispatch; dead-letter queue via NATS for retry | +| Cedar files missing | `cedar_policy_dir = None` → no-auth mode; documented explicitly | +| Signature change | Backend already owns `db: Arc>`; passed at construction | + +--- + +## Verification + +```bash +cargo test -p vapora-workflow-engine # 31/31 pass +cargo clippy -p vapora-workflow-engine -- -D warnings # 0 warnings +``` + +New tests: + +- `auth::tests::test_permit_allows` +- `auth::tests::test_deny_returns_unauthorized` +- `auth::tests::test_empty_dir_fails` +- `saga::tests::test_stages_with_compensation_agents_are_included` +- `saga::tests::test_stages_with_no_compensation_agents_are_skipped` + +--- + +## Related ADRs + +- [ADR-0028](./0028-workflow-orchestrator.md) — Workflow Orchestrator (original implementation) +- [ADR-0010](./0010-cedar-authorization.md) — Cedar Authorization +- [ADR-0004](./0004-surrealdb-database.md) — SurrealDB as single persistence layer +- [ADR-0018](./0018-swarm-load-balancing.md) — SwarmCoordinator (Saga dispatch target) diff --git a/docs/adrs/README.md b/docs/adrs/README.md index 03461d0..2dbee85 100644 --- a/docs/adrs/README.md +++ b/docs/adrs/README.md @@ -2,8 +2,8 @@ Documentación de las decisiones arquitectónicas clave del proyecto VAPORA. -**Status**: Complete (32 ADRs documented) -**Last Updated**: 2026-02-17 +**Status**: Complete (33 ADRs documented) +**Last Updated**: 2026-02-21 **Format**: Custom VAPORA (Decision, Rationale, Alternatives, Trade-offs, Implementation, Verification, Consequences) --- @@ -80,6 +80,7 @@ Decisiones únicas que diferencian a VAPORA de otras plataformas de orquestació | [021](./0021-websocket-updates.md) | Real-Time WebSocket Updates | tokio::sync::broadcast para pub/sub eficiente | ✅ Accepted | | [028](./0028-workflow-orchestrator.md) | Workflow Orchestrator para Multi-Agent Pipelines | Short-lived agent contexts + artifact passing para reducir cache tokens 95% | ✅ Accepted | | [029](./0029-rlm-recursive-language-models.md) | Recursive Language Models (RLM) | Custom Rust engine: BM25 + semantic hybrid search + distributed LLM dispatch + WASM/Docker sandbox | ✅ Accepted | +| [033](./0033-stratum-orchestrator-workflow-hardening.md) | Workflow Engine Hardening — Persistence · Saga · Cedar | SurrealDB persistence + Saga best-effort rollback + Cedar per-stage auth; stratum patterns implemented natively (no path dep) | ✅ Implemented | --- diff --git a/docs/guides/workflow-saga-persistence.md b/docs/guides/workflow-saga-persistence.md new file mode 100644 index 0000000..e57d4c2 --- /dev/null +++ b/docs/guides/workflow-saga-persistence.md @@ -0,0 +1,261 @@ +# Workflow Engine: Persistence, Saga Compensation & Cedar Authorization + +How to configure and operate the three hardening layers added in v1.3.0: +crash-recoverable state, Saga-based rollback, and per-stage access control. + +## Prerequisites + +- Running SurrealDB instance (same one used by the backend) +- `vapora-workflow-engine` v1.3.0+ +- Migration `009_workflow_state.surql` applied + +## 1. Apply the Database Migration + +```bash +surreal import \ + --conn ws://localhost:8000 \ + --user root \ + --pass root \ + --ns vapora \ + --db vapora \ + migrations/009_workflow_state.surql +``` + +This creates the `workflow_instances` SCHEMAFULL table with indexes on +`template_name` and `created_at`. + +## 2. Wire the Store into the Orchestrator + +Pass the existing `Surreal` when constructing `WorkflowOrchestrator`: + +```rust +use std::sync::Arc; +use surrealdb::{Surreal, engine::remote::ws::Client}; +use vapora_workflow_engine::WorkflowOrchestrator; + +async fn build_orchestrator( + db: Arc>, + swarm: Arc, + kg: Arc, + nats: Arc, +) -> anyhow::Result> { + let orchestrator = WorkflowOrchestrator::new( + "config/workflows.toml", + swarm, + kg, + nats, + (*db).clone(), // Surreal (not Arc) + ) + .await?; + + Ok(Arc::new(orchestrator)) +} +``` + +On startup the orchestrator calls `store.load_active()` and reinserts any +non-terminal instances from SurrealDB into the in-memory `DashMap`. Workflows +in progress before a crash resume from their last persisted state. + +## 3. Configure Saga Compensation + +Add `compensation_agents` to each stage that should trigger a rollback task +when the workflow fails after that stage has completed: + +```toml +# config/workflows.toml + +[engine] +max_parallel_tasks = 10 +workflow_timeout = 3600 +approval_gates_enabled = true + +[[workflows]] +name = "deploy_pipeline" +trigger = "manual" + +[[workflows.stages]] +name = "provision" +agents = ["devops"] +compensation_agents = ["devops"] # ← Saga: send rollback task to devops + +[[workflows.stages]] +name = "migrate_db" +agents = ["backend"] +compensation_agents = ["backend"] # ← Saga: send DB rollback task to backend + +[[workflows.stages]] +name = "smoke_test" +agents = ["tester"] +# no compensation_agents → skipped in Saga reversal +``` + +### Compensation Task Payload + +When a non-retryable failure occurs at stage N, the `SagaCompensator` iterates +stages `[0..N]` in reverse order. For each stage with `compensation_agents` +defined it dispatches via `SwarmCoordinator`: + +```json +{ + "type": "compensation", + "stage_name": "migrate_db", + "workflow_id": "abc-123", + "original_context": { "…": "…" }, + "artifacts_to_undo": ["artifact-id-1"] +} +``` + +Compensation is **best-effort**: errors are logged but never fail the workflow +state machine. The workflow is already marked `Failed` before Saga fires. + +### Agent Implementation + +Agents receive compensation tasks on the same NATS subjects as regular tasks. +Distinguish by the `"type": "compensation"` field: + +```rust +// In your agent task handler +if task.payload["type"] == "compensation" { + let stage = &task.payload["stage_name"]; + let wf_id = &task.payload["workflow_id"]; + // perform rollback for this stage … + return Ok(()); +} +// normal task handling … +``` + +## 4. Configure Cedar Authorization + +Cedar authorization is **opt-in**: if `cedar_policy_dir` is absent, all stages +execute without policy checks. + +### Enable Cedar + +```toml +[engine] +max_parallel_tasks = 10 +workflow_timeout = 3600 +approval_gates_enabled = true +cedar_policy_dir = "/etc/vapora/cedar" # directory with *.cedar files +``` + +### Write Policies + +Create `.cedar` files in the configured directory. Each file is loaded at +startup and merged into a single `PolicySet`. + +**Allow all stages** (permissive default): + +```cedar +// /etc/vapora/cedar/allow-all.cedar +permit( + principal == "vapora-orchestrator", + action == Action::"execute-stage", + resource +); +``` + +**Restrict deployment stages to approved callers only**: + +```cedar +// /etc/vapora/cedar/restrict-deploy.cedar +forbid( + principal == "vapora-orchestrator", + action == Action::"execute-stage", + resource == Stage::"deployment" +) unless { + context.approved == true +}; +``` + +**Allow only specific stages**: + +```cedar +// /etc/vapora/cedar/workflow-policy.cedar +permit( + principal == "vapora-orchestrator", + action == Action::"execute-stage", + resource in [Stage::"architecture_design", Stage::"implementation", Stage::"testing"] +); + +forbid( + principal == "vapora-orchestrator", + action == Action::"execute-stage", + resource == Stage::"production_deploy" +); +``` + +### Authorization Check + +Before each stage dispatch the engine calls: + +```rust +// principal: "vapora-orchestrator" +// action: "execute-stage" +// resource: Stage::"" +cedar.authorize("vapora-orchestrator", "execute-stage", &stage_name)?; +``` + +A `Deny` decision returns `WorkflowError::Unauthorized` and halts the workflow +immediately. The stage is never dispatched to `SwarmCoordinator`. + +## 5. Crash Recovery Behavior + +| Scenario | Behavior | +|----------|----------| +| Server restart with active workflows | `load_active()` re-populates `DashMap`; event listener resumes NATS subscriptions; in-flight tasks re-dispatch on next `TaskCompleted`/`TaskFailed` event | +| Workflow in `Completed` or `Failed` state | Filtered out by `load_active()`; not reloaded | +| Workflow in `WaitingApproval` | Reloaded; waits for `approve_stage()` call | +| SurrealDB unavailable at startup | `load_active()` returns error; orchestrator fails to start | + +## 6. Observability + +Saga dispatch failures appear in logs with level `warn`: + +```text +WARN vapora_workflow_engine::saga: compensation dispatch failed + workflow_id="abc-123" stage="migrate_db" error="…" +``` + +Cedar denials: + +```text +ERROR vapora_workflow_engine::orchestrator: Cedar authorization denied + workflow_id="abc-123" stage="production_deploy" +``` + +Existing Prometheus metrics track workflow lifecycle: + +```text +vapora_workflows_failed_total # includes Cedar-denied workflows +vapora_active_workflows # drops immediately on denial +``` + +## 7. Full Config Reference + +```toml +[engine] +max_parallel_tasks = 10 +workflow_timeout = 3600 +approval_gates_enabled = true +cedar_policy_dir = "/etc/vapora/cedar" # optional + +[[workflows]] +name = "my_workflow" +trigger = "manual" + +[[workflows.stages]] +name = "stage_a" +agents = ["agent_role"] +parallel = false +max_parallel = 1 +approval_required = false +compensation_agents = ["agent_role"] # optional; omit to skip Saga for this stage +``` + +## Related + +- [ADR-0033: Workflow Engine Hardening](../adrs/0033-stratum-orchestrator-workflow-hardening.md) +- [ADR-0028: Workflow Orchestrator](../adrs/0028-workflow-orchestrator.md) +- [ADR-0010: Cedar Authorization](../adrs/0010-cedar-authorization.md) +- [Workflow Orchestrator Feature Reference](../features/workflow-orchestrator.md) diff --git a/docs/src/SUMMARY.md b/docs/src/SUMMARY.md index 53207e6..820f5d2 100644 --- a/docs/src/SUMMARY.md +++ b/docs/src/SUMMARY.md @@ -62,6 +62,12 @@ - [0025: Multi-Tenancy](../adrs/0025-multi-tenancy.md) - [0026: Shared State](../adrs/0026-shared-state.md) - [0027: Documentation Layers](../adrs/0027-documentation-layers.md) + - [0033: Workflow Engine Hardening](../adrs/0033-stratum-orchestrator-workflow-hardening.md) + +## Guides + +- [Workflow Persistence, Saga & Cedar](../guides/workflow-saga-persistence.md) +- [RLM Usage Guide](../guides/rlm-usage-guide.md) ## Integration Guides @@ -99,8 +105,8 @@ --- -**Documentation Version**: 1.2.0 -**Last Updated**: 2026-01-12 +**Documentation Version**: 1.3.0 +**Last Updated**: 2026-02-21 **Status**: Production Ready For the latest updates, visit: https://github.com/vapora-platform/vapora diff --git a/migrations/009_workflow_state.surql b/migrations/009_workflow_state.surql new file mode 100644 index 0000000..2c3037c --- /dev/null +++ b/migrations/009_workflow_state.surql @@ -0,0 +1,21 @@ +-- Migration 009: Workflow State Persistence +-- Replaces DashMap (in-memory, lost on restart) with durable SurrealDB storage. +-- WorkflowInstance is stored as a JSON document; status is a tagged serde enum. + +DEFINE TABLE workflow_instances SCHEMAFULL; + +DEFINE FIELD id ON TABLE workflow_instances TYPE record; +DEFINE FIELD template_name ON TABLE workflow_instances TYPE string ASSERT $value != NONE; +DEFINE FIELD status ON TABLE workflow_instances FLEXIBLE TYPE any ASSERT $value != NONE; +DEFINE FIELD stages ON TABLE workflow_instances FLEXIBLE TYPE array; +DEFINE FIELD current_stage_idx ON TABLE workflow_instances TYPE int DEFAULT 0; +DEFINE FIELD initial_context ON TABLE workflow_instances FLEXIBLE TYPE object; +DEFINE FIELD accumulated_artifacts ON TABLE workflow_instances FLEXIBLE TYPE object DEFAULT {}; +DEFINE FIELD created_at ON TABLE workflow_instances TYPE datetime DEFAULT time::now(); +DEFINE FIELD updated_at ON TABLE workflow_instances TYPE datetime DEFAULT time::now() VALUE time::now(); + +DEFINE INDEX idx_workflow_instances_template + ON TABLE workflow_instances COLUMNS template_name; + +DEFINE INDEX idx_workflow_instances_created_at + ON TABLE workflow_instances COLUMNS created_at;