028 optional branch obligation

✓ Passing This code compiles and runs correctly.

Code

// TEST: Optional branch with obligation - auto-discharge handles it!
// STATUS: IMPLEMENTED
//
// This test verifies that:
// 1. Unhandled optional branches get synthesized continuations
// 2. Auto-discharge inserts disposal calls for obligations in optional branches
// 3. The emitter generates proper switch cases (not direct field access)
//
// If user only handles | success |>, but event returns | ?leaked |>,
// the compiler automatically inserts close() call to dispose the handle!

~import "$app/resource"

// User only handles required branch - auto-discharge handles ?leaked
~app.resource:risky()
| success _ |>
    _
// | ?leaked |> AUTO-SYNTHESIZED with disposal of handle!

pub fn main() void {}
input.kz

Imported Files

// Library module: resource
// Demonstrates optional branch with obligation

const std = @import("std");

const Handle = struct {
    id: i32,
};

// Risky operation - might succeed OR might leak a handle
~pub event risky {}
| success { result: u32 }
| ?leaked { handle: *Handle[owned!] }  // Optional with obligation!

~proc risky {
    // Always succeeds in this test, but the event DECLARES
    // that it COULD return ?leaked with an obligation
    std.debug.print("Operation succeeded\n", .{});
    return .{ .success = .{ .result = 42 } };
}

// Disposer for the obligation (would need to be called for ?leaked)
~pub event close { handle: *Handle[!owned] }
| closed {}

~proc close {
    std.debug.print("Closing handle\n", .{});
    return .{ .closed = .{} };
}
resource.kz