diff --git a/rust/basics/src/p0_durable_execution.rs b/rust/basics/src/p0_durable_execution.rs index 1b6be236..2c64d0e7 100644 --- a/rust/basics/src/p0_durable_execution.rs +++ b/rust/basics/src/p0_durable_execution.rs @@ -32,14 +32,11 @@ pub struct SubscriptionRequest { // Whenever a handler uses the Restate Context, an event gets persisted in Restate's log. // After a failure, a retry is triggered and this log gets replayed to recover the state of the handler. -#[restate_sdk::service] -pub trait SubscriptionService { - async fn add(req: Json) -> Result<(), HandlerError>; -} +pub struct SubscriptionService; -struct SubscriptionServiceImpl; - -impl SubscriptionService for SubscriptionServiceImpl { +#[restate_sdk::service] +impl SubscriptionService { + #[handler] async fn add( &self, mut ctx: Context<'_>, @@ -71,7 +68,7 @@ async fn main() { HttpServer::new( Endpoint::builder() - .bind(SubscriptionServiceImpl.serve()) + .bind(SubscriptionService) .build(), ) .listen_and_serve("0.0.0.0:9080".parse().unwrap()) diff --git a/rust/basics/src/p1_building_blocks.rs b/rust/basics/src/p1_building_blocks.rs index 3084638a..91fbff28 100644 --- a/rust/basics/src/p1_building_blocks.rs +++ b/rust/basics/src/p1_building_blocks.rs @@ -16,16 +16,13 @@ use std::time::Duration; * The run handler below shows a catalog of these building blocks. * Look at the other examples in this project to see how to use them in examples. */ -#[restate_sdk::service] -trait MyService { - async fn run() -> Result<(), HandlerError>; -} +struct MyService; -struct MyServiceImpl; - -impl MyService for MyServiceImpl { - // This handler can be called over HTTP at http://restate:8080/myService/handlerName +#[restate_sdk::service] +impl MyService { + // This handler can be called over HTTP at http://restate:8080/MyService/run // Use the context to access Restate's durable building blocks + #[handler] async fn run(&self, mut ctx: Context<'_>) -> Result<(), HandlerError> { // --- // 1. IDEMPOTENCY: Add an idempotency key to the header of your requests @@ -85,7 +82,7 @@ impl MyService for MyServiceImpl { async fn main() { tracing_subscriber::fmt::init(); - HttpServer::new(Endpoint::builder().bind(MyServiceImpl.serve()).build()) + HttpServer::new(Endpoint::builder().bind(MyService).build()) .listen_and_serve("0.0.0.0:9080".parse().unwrap()) .await; } diff --git a/rust/basics/src/p2_virtual_objects.rs b/rust/basics/src/p2_virtual_objects.rs index 5d3cc3f5..b9bb01a3 100644 --- a/rust/basics/src/p2_virtual_objects.rs +++ b/rust/basics/src/p2_virtual_objects.rs @@ -1,10 +1,5 @@ use restate_sdk::prelude::*; -#[restate_sdk::object] -pub trait GreeterObject { - async fn greet(req: String) -> Result; - async fn ungreet() -> Result; -} // Virtual Objects are services that hold K/V state. Its handlers interact with the object state. // An object is identified by a unique id - only one object exists per id. // @@ -18,9 +13,11 @@ pub trait GreeterObject { // // Virtual Objects are Stateful (Serverless) constructs. -pub struct GreeterObjectImpl; +pub struct GreeterObject; -impl GreeterObject for GreeterObjectImpl { +#[restate_sdk::object] +impl GreeterObject { + #[handler] async fn greet( &self, ctx: ObjectContext<'_>, @@ -39,6 +36,7 @@ impl GreeterObject for GreeterObjectImpl { )) } + #[handler] async fn ungreet(&self, ctx: ObjectContext<'_>) -> Result { let mut count: u64 = ctx.get::("count").await?.unwrap_or(0); if count > 0 { @@ -57,7 +55,7 @@ impl GreeterObject for GreeterObjectImpl { async fn main() { tracing_subscriber::fmt::init(); - HttpServer::new(Endpoint::builder().bind(GreeterObjectImpl.serve()).build()) + HttpServer::new(Endpoint::builder().bind(GreeterObject).build()) .listen_and_serve("0.0.0.0:9080".parse().unwrap()) .await; } diff --git a/rust/basics/src/p3_workflows.rs b/rust/basics/src/p3_workflows.rs index 1ce4beb9..f6b7fa61 100644 --- a/rust/basics/src/p3_workflows.rs +++ b/rust/basics/src/p3_workflows.rs @@ -13,17 +13,12 @@ use restate_sdk::prelude::*; // - Additional methods interact with the workflow. // Each workflow instance has a unique ID and runs only once (to success or failure). -#[restate_sdk::workflow] -trait SignupWorkflow { - async fn run(user: Json) -> Result; - #[shared] - async fn click(secret: String) -> Result<(), HandlerError>; -} +struct SignupWorkflow; -struct SignupWorkflowImpl; - -impl SignupWorkflow for SignupWorkflowImpl { +#[restate_sdk::workflow] +impl SignupWorkflow { // --- The workflow logic --- + #[handler] async fn run( &self, mut ctx: WorkflowContext<'_>, @@ -46,6 +41,7 @@ impl SignupWorkflow for SignupWorkflowImpl { } // --- Other handlers interact with the workflow via queries and signals --- + #[handler] async fn click( &self, ctx: SharedWorkflowContext<'_>, @@ -60,7 +56,7 @@ impl SignupWorkflow for SignupWorkflowImpl { async fn main() { tracing_subscriber::fmt::init(); - HttpServer::new(Endpoint::builder().bind(SignupWorkflowImpl.serve()).build()) + HttpServer::new(Endpoint::builder().bind(SignupWorkflow).build()) .listen_and_serve("0.0.0.0:9080".parse().unwrap()) .await; } diff --git a/rust/basics/src/stubs.rs b/rust/basics/src/stubs.rs index d4604894..be36dd29 100644 --- a/rust/basics/src/stubs.rs +++ b/rust/basics/src/stubs.rs @@ -89,15 +89,11 @@ pub async fn charge_bank_account( Ok(()) } -#[restate_sdk::object] -pub trait SubscriptionService { - async fn create(user_id: String) -> Result; - async fn cancel() -> Result<(), HandlerError>; -} +pub struct SubscriptionService; -pub struct SubscriptionServiceImpl; - -impl SubscriptionService for SubscriptionServiceImpl { +#[restate_sdk::object] +impl SubscriptionService { + #[restate_sdk::handler] async fn create( &self, _ctx: ObjectContext<'_>, @@ -106,6 +102,7 @@ impl SubscriptionService for SubscriptionServiceImpl { Ok("SUCCESS".to_string()) } + #[restate_sdk::handler] async fn cancel(&self, ctx: ObjectContext<'_>) -> Result<(), HandlerError> { println!("Cancelling all subscriptions for user {}", ctx.key()); Ok(()) diff --git a/rust/templates/rust-shuttle/src/main.rs b/rust/templates/rust-shuttle/src/main.rs index afad6869..1cbbbd8e 100644 --- a/rust/templates/rust-shuttle/src/main.rs +++ b/rust/templates/rust-shuttle/src/main.rs @@ -7,14 +7,11 @@ use restate_shuttle::RestateShuttleEndpoint; use std::time::Duration; use utils::{send_notification, send_reminder}; -#[restate_sdk::service] -trait Greeter { - async fn greet(name: String) -> Result; -} +struct Greeter; -struct GreeterImpl; - -impl Greeter for GreeterImpl { +#[restate_sdk::service] +impl Greeter { + #[handler] async fn greet(&self, mut ctx: Context<'_>, name: String) -> Result { // Durably execute a set of steps; resilient against failures let greeting_id = ctx.rand_uuid().to_string(); @@ -34,6 +31,6 @@ impl Greeter for GreeterImpl { #[shuttle_runtime::main] async fn main() -> Result { Ok(RestateShuttleEndpoint::new( - Endpoint::builder().bind(GreeterImpl.serve()).build(), + Endpoint::builder().bind(Greeter).build(), )) } diff --git a/rust/templates/rust/src/main.rs b/rust/templates/rust/src/main.rs index 60c2e0fb..46c4586b 100644 --- a/rust/templates/rust/src/main.rs +++ b/rust/templates/rust/src/main.rs @@ -4,14 +4,11 @@ use restate_sdk::prelude::*; use std::time::Duration; use utils::{send_notification, send_reminder}; -#[restate_sdk::service] -trait Greeter { - async fn greet(name: String) -> Result; -} +struct Greeter; -struct GreeterImpl; - -impl Greeter for GreeterImpl { +#[restate_sdk::service] +impl Greeter { + #[handler] async fn greet(&self, mut ctx: Context<'_>, name: String) -> Result { // Durably execute a set of steps; resilient against failures let greeting_id = ctx.rand_uuid().to_string(); @@ -33,7 +30,7 @@ async fn main() { // To enable logging tracing_subscriber::fmt::init(); - HttpServer::new(Endpoint::builder().bind(GreeterImpl.serve()).build()) + HttpServer::new(Endpoint::builder().bind(Greeter).build()) .listen_and_serve("0.0.0.0:9080".parse().unwrap()) .await; }