diff options
| author | Chris Boesch <chrboesch@noreply.codeberg.org> | 2026-04-07 09:18:37 +0200 |
|---|---|---|
| committer | Chris Boesch <chrboesch@noreply.codeberg.org> | 2026-04-07 09:18:37 +0200 |
| commit | 7cb7a9948a9f5c9965fedd59f0cd816f28962fe4 (patch) | |
| tree | 1953e653faba351ab103ec030eacbfc79b7dae6c /exercises/089_async5.zig | |
| parent | 1166f3cfb65d7edc9086c6ba6b8edd4754964b33 (diff) | |
| parent | 3574fd3ae037f34510c6bb6657332b57447ac5b1 (diff) | |
Merge branch 'main' into fix-060
Diffstat (limited to 'exercises/089_async5.zig')
| -rw-r--r-- | exercises/089_async5.zig | 67 |
1 files changed, 67 insertions, 0 deletions
diff --git a/exercises/089_async5.zig b/exercises/089_async5.zig new file mode 100644 index 0000000..0c00c1f --- /dev/null +++ b/exercises/089_async5.zig @@ -0,0 +1,67 @@ +// +// One of the most important features of the new Io system is +// structured cancellation! +// +// Every Future has a .cancel() method that: +// 1. Requests the task to stop (via error.Canceled at the +// next "cancellation point") +// 2. BLOCKS until the task actually finishes +// 3. Returns whatever result the task produced +// +// A "cancellation point" is any Io function that can return +// error.Canceled - most commonly io.sleep(): +// +// fn myTask(io: std.Io) u32 { +// io.sleep(...) catch |err| switch (err) { +// error.Canceled => return 0, // error handle +// }; +// return 42; +// } +// +// This is fundamentally different from killing a thread - +// the task gets a chance to clean up and return a value! +// +// Remember: both .await() and .cancel() block and return the +// result. The only difference is that .cancel() also sends +// the cancellation request. And both are idempotent — calling +// either one again just returns the same result. +// +// Fix this program: the slow task would take 10 seconds, +// but we cancel it after 1 second. The task should detect +// the cancellation and return early. +// +const std = @import("std"); +const print = std.debug.print; + +pub fn main(init: std.process.Init) !void { + const io = init.io; + + var future = io.async(slowTask, .{io}); + defer _ = future.cancel(io); // safety net + + // Wait 1 second, then cancel instead of waiting the full 10. + io.sleep(std.Io.Duration.fromSeconds(1), .awake) catch {}; + + print("Canceling slow task...\n", .{}); + + // We don't want to wait 10 seconds! + // Which Future method requests cancellation AND returns the result? + const result = future.???(io); + + print("Task returned: {}\n", .{result}); +} + +fn slowTask(io: std.Io) u32 { + print("Starting long computation...\n", .{}); + + // Try to sleep for 10 seconds - but we might get canceled! + io.sleep(std.Io.Duration.fromSeconds(10), .awake) catch |err| switch (err) { + error.Canceled => { + print("Task was canceled, cleaning up.\n", .{}); + return 0; + }, + }; + + print("Task completed normally.\n", .{}); + return 42; +} |
