Skip to main content

stasis/
lib.rs

1//! Stasis is a durable AI orchestration framework with runtime jobs, control-plane
2//! primitives, and memory integration adapters.
3//! Use the [prelude] module for a batteries-included public API surface.
4
5pub mod application;
6pub mod dashboard;
7pub mod domain;
8pub mod infrastructure;
9pub mod ports;
10pub mod sdk;
11
12pub use stasis_macros::stasis_tool;
13
14#[doc(hidden)]
15pub mod macro_support {
16    pub use async_trait;
17    pub use schemars;
18    pub use serde;
19    pub use serde_json;
20}
21
22/// Minimal runtime imports for consumers integrating job handlers and runtime wiring.
23///
24/// `JobConsumer::on_lifecycle` receives [`JobLifecycleEvent`] after each persisted
25/// transition so app-level pending/finishing status can roll back on defer, retry,
26/// cancel, or dead-letter.
27pub mod runtime_prelude {
28    pub use crate::application::runtime::in_memory_runtime::{
29        InMemoryRuntime, JobExecutionOutcome, JobHandler,
30    };
31    pub use crate::application::runtime::job_context::{JobConsumeError, JobContext, JobResult};
32    pub use crate::application::runtime::job_lifecycle::{JobLifecycleEvent, StaleRecoverReport};
33    pub use crate::application::runtime::runtime_factory::{
34        RuntimeBackend, RuntimeComposition, RuntimeFactory, SurrealAuth,
35    };
36    pub use crate::application::runtime::stasis_runtime_builder::StasisRuntimeBuilder;
37    pub use crate::application::runtime::typed_job::{
38        JobConsumer, TypedEnqueueBuilder, TypedJobHandler,
39    };
40    pub use crate::domain::errors::{Result, StasisError};
41    pub use crate::domain::runtime::job::{BackoffPolicy, JobState, NewJob};
42    pub use crate::domain::runtime::recurring::RecurringDefinition;
43    pub use crate::domain::runtime::resource_lease::{
44        FencingToken, OwnerId, ResourceKey, ResourceLease,
45    };
46    pub use crate::domain::runtime::typed_contract::{RetryPolicy, StasisEvent, StasisJob};
47}
48
49/// Extended runtime imports including orchestration payloads, endpoint routing, and store adapters.
50pub mod runtime_prelude_ext {
51    pub use crate::application::dto::{
52        HeartbeatClusterNodeRequest, RegisterClusterNodeRequest, RegisterDeliveryEndpointRequest,
53    };
54    pub use crate::application::orchestration::runtime_job_payloads::{
55        AgentSessionJobPayload, AgentTurnJobPayload, ConcurrentPatternJobPayload,
56        HandoffPatternJobPayload, OrchestratorPatternJobPayload, PromptJobPayload,
57        SequentialPatternJobPayload, ToolLoopJobPayload,
58    };
59    pub use crate::application::orchestration::runtime_workflow_job_builder::RuntimeWorkflowJobBuilder;
60    pub use crate::application::runtime::in_memory_runtime::{
61        InMemoryRuntime, JobExecutionOutcome, JobHandler,
62    };
63    pub use crate::application::runtime::stasis_runtime_builder::StasisRuntimeBuilder;
64    pub use crate::domain::runtime::cluster_node::ClusterNodeRole;
65    pub use crate::domain::runtime::delivery_endpoint::{
66        DeliveryEndpoint, DeliveryProtocol, NewDeliveryEndpoint,
67    };
68    pub use crate::domain::runtime::outbox::OutboxEvent;
69    pub use crate::infrastructure::runtime::composite_control_plane_store::CompositeControlPlaneStore;
70    pub use crate::infrastructure::runtime::endpoint_routing_event_publisher::EndpointRoutingEventPublisher;
71    pub use crate::infrastructure::runtime::in_memory_cluster_node_store::InMemoryClusterNodeStore;
72    pub use crate::infrastructure::runtime::in_memory_delivery_endpoint_store::InMemoryDeliveryEndpointStore;
73    pub use crate::infrastructure::runtime::in_memory_endpoint_delivery_status_store::InMemoryEndpointDeliveryStatusStore;
74    pub use crate::infrastructure::runtime::surreal_cluster_node_store::SurrealClusterNodeStore;
75    pub use crate::infrastructure::runtime::surreal_delivery_endpoint_store::SurrealDeliveryEndpointStore;
76    pub use crate::infrastructure::runtime::surreal_endpoint_delivery_status_store::SurrealEndpointDeliveryStatusStore;
77    pub use crate::ports::outbound::runtime::delivery_endpoint_store::DeliveryEndpointStore;
78    pub use crate::ports::outbound::runtime::endpoint_delivery_status_store::EndpointDeliveryStatusStore;
79    pub use crate::ports::outbound::runtime::endpoint_transport_publisher::EndpointTransportPublisher;
80}
81
82/// Minimal memory imports for consumers using context store/recall/transform APIs.
83pub mod memory_prelude {
84    pub use crate::ports::outbound::memory::memory_models::{
85        MemoryAggregateRequest, MemoryRecallRequest, MemoryRollupRequest, MemoryScope,
86        MemoryStoreRequest, MemoryTransformRequest,
87    };
88    pub use crate::ports::outbound::memory::memory_operations::MemoryOperations;
89}
90
91/// Extended memory imports including concrete Locus adapters and context reader/writer traits.
92pub mod memory_prelude_ext {
93    pub use crate::infrastructure::memory::locus_context_reader::LocusContextReader;
94    pub use crate::infrastructure::memory::locus_context_writer::LocusContextWriter;
95    pub use crate::infrastructure::memory::locus_memory_operations::LocusMemoryOperations;
96    pub use crate::infrastructure::memory::locus_node_store_factory::{
97        LocusMemoryStore, LocusNodeStoreFactory,
98    };
99    pub use crate::ports::outbound::memory::memory_context_reader::MemoryContextReader;
100    pub use crate::ports::outbound::memory::memory_context_writer::MemoryContextWriter;
101    pub use crate::ports::outbound::memory::memory_models::{
102        MemoryAggregateRequest, MemoryRecallRequest, MemoryRollupRequest, MemoryScope,
103        MemoryStoreRequest, MemoryTransformRequest,
104    };
105    pub use crate::ports::outbound::memory::memory_operations::MemoryOperations;
106}
107
108/// Minimal SDK imports for common external consumers.
109pub mod sdk_prelude {
110    pub use crate::application::dto::{InvokeAgentRequest, RegisterAgentRequest};
111    pub use crate::application::runtime::runtime_factory::{
112        RuntimeBackend, RuntimeFactory, SurrealAuth,
113    };
114    pub use crate::domain::errors::{Result, StasisError};
115    pub use crate::domain::runtime::job::{BackoffPolicy, NewJob};
116    pub use crate::infrastructure::llm::mock_gateway::MockLlmGateway;
117    pub use crate::infrastructure::persistence::in_memory_agent_repository::InMemoryAgentRepository;
118    pub use crate::sdk::runtime_sdk::{RuntimeSdk, StasisRuntime};
119    pub use crate::sdk::stasis_sdk::StasisSdk;
120}
121
122/// Extended SDK imports including control-plane and provider-specific integration types.
123pub mod sdk_prelude_ext {
124    pub use crate::application::dto::InvokeAgentResponse;
125    pub use crate::application::runtime::runtime_factory::RuntimeComposition;
126    pub use crate::domain::runtime::job::JobState;
127    pub use crate::domain::runtime::recurring::RecurringDefinition;
128    pub use crate::infrastructure::llm::genai_gateway::GenaiLlmGateway;
129    pub use crate::sdk::control_plane_sdk::ControlPlaneSdk;
130    pub use crate::sdk::runtime_sdk::RuntimeStatsSnapshot;
131}
132
133/// Re-exported minimal public API surface for common Stasis consumers.
134pub mod prelude {
135    pub use crate::memory_prelude::*;
136    pub use crate::runtime_prelude::*;
137    pub use crate::sdk_prelude::*;
138}
139
140/// Environment and secrets configuration helpers.
141pub mod config_prelude {
142    pub use crate::application::config::env::{
143        EnvBootstrapOptions, EnvBootstrapReport, EnvError, bootstrap, bootstrap_with,
144        first_non_empty, load_dotenv_from, non_empty, required, truthy, with_default,
145    };
146    pub use crate::application::config::secrets::{
147        ChainedSecretsSource, FileSecretsSource, OsEnvSource, SecretsSource, default_secrets_dir,
148    };
149}
150
151/// OpenTelemetry contract keys, span names, and runtime telemetry ports.
152pub mod telemetry_prelude {
153    pub use crate::application::telemetry::keys;
154    pub use crate::application::telemetry::operation::OperationTelemetry;
155    pub use crate::application::telemetry::propagation::{
156        TracePropagationMode, generate_w3c_trace_id, is_w3c_trace_id, job_execute_span_attributes,
157        parent_trace_context, parse_traceparent, trace_propagation_mode,
158    };
159    pub use crate::application::telemetry::request_context::{
160        inbound_trace_context, inbound_trace_context_for_propagation, scope_inbound_trace,
161        trace_id_for_enqueue,
162    };
163    pub use crate::application::telemetry::spans;
164    pub use crate::infrastructure::telemetry::{NoopRuntimeTelemetry, NoopRuntimeTracing};
165    pub use crate::ports::outbound::runtime::runtime_metrics::RuntimeMetrics;
166    pub use crate::ports::outbound::runtime::runtime_telemetry::RuntimeTelemetry;
167    pub use crate::ports::outbound::runtime::runtime_tracing::{
168        OtelAttribute, OtelAttributeValue, RuntimeTracing, SpanGuard, TraceContext, in_span,
169    };
170
171    #[cfg(feature = "otel")]
172    pub use crate::infrastructure::telemetry::OpenTelemetryTelemetry;
173}
174
175/// Re-exported extended API surface for advanced integrations.
176pub mod prelude_ext {
177    pub use crate::config_prelude::*;
178    pub use crate::memory_prelude_ext::*;
179    pub use crate::runtime_prelude_ext::*;
180    pub use crate::sdk_prelude_ext::*;
181}
182
183#[cfg(test)]
184mod tests {
185    use crate::application::dto::{InvokeAgentRequest, RegisterAgentRequest};
186    use crate::infrastructure::llm::mock_gateway::MockLlmGateway;
187    use crate::infrastructure::persistence::in_memory_agent_repository::InMemoryAgentRepository;
188    use crate::sdk::stasis_sdk::StasisSdk;
189
190    #[tokio::test]
191    async fn end_to_end_agent_registration_and_invocation_works() {
192        let repository = InMemoryAgentRepository::default();
193        let llm = MockLlmGateway::new("mock completion");
194        let sdk = StasisSdk::new(repository, llm);
195
196        let registration = RegisterAgentRequest {
197            id: "planner".to_string(),
198            name: "Task Planner".to_string(),
199            system_prompt: "Break work down into ordered steps".to_string(),
200        };
201
202        sdk.register_agent(registration)
203            .await
204            .expect("agent should register");
205
206        let response = sdk
207            .invoke_agent(InvokeAgentRequest {
208                agent_id: "planner".to_string(),
209                user_prompt: "Plan a release checklist".to_string(),
210            })
211            .await
212            .expect("agent should invoke");
213
214        assert_eq!(response.completion, "mock completion");
215    }
216}