Effect inference
How the compiler validates effects
The compiler checks effects transitively. When you call a function with needs { net }, your function must also declare needs { net } (or a superset).
cleat
fn inner() -> string needs { net } { ... } fn outer() -> string needs { net } { // must declare net return inner() }
Calling inner() from a function without needs { net } is a compile error.
Error messages
The compiler produces clear diagnostics:
text
error: missing needs effect: net
--> main.cleat:4:12
|
4 | return http.get("https://example.com")
| ^Levenshtein suggestions
Misspelled effect names get correction suggestions:
text
error: unknown effect "nett" in fn greet
--> main.cleat:1:27
|
1 | fn greet() -> int needs { nett } {
| ^^^^
= help: did you mean "net"?Agent effect coverage
Agent declarations must cover all their tools' effects:
cleat
tool search(q: string) -> Result[string, string] needs { net } timeout: 10s { ... } agent Bot { model: "claude-sonnet-4-20250514" system: "Search bot." tool: [search] needs { llm } // ← compile error: missing effect "net" required by tool "search" // needs { llm, net } // correct }
Server effect coverage
Server declarations must cover all their handlers' effects:
cleat
fn handler(req: server.Request) -> Result[server.Response, string] needs { llm } { ... } server API { addr: ":8080" needs { net } // ← error: handler requires effect "llm" not declared by server // needs { net, llm } // correct get "/api" = handler }