# Statements

A body is a list of statements, one on each line, with no semicolons:

| Statement | Form |
|---|---|
| Variable | `var name: T = value`, `var mut name: T = value` |
| Assignment | `name = value` |
| Return | `return value` |
| Rejection | `reject Failure { ... }` ([Raising a failure: `reject`](raising-a-failure-reject.md)) |
| Condition | `if (condition) { } else if (condition) { } else { }` |
| Match | `match value { ... }` |
| Loop | `for item in items { }` ([Loops](loops.md)) |
| Test only | `assert`, `advance clock by` ([Testing](testing.md)) |

There is no `throw`.

A variable nothing reads is an error, so a result nobody needs never has
to be given a name. Instead, three more statements may stand alone:

```jadpo
action archive_todo(todo_id: Todo.id) fails TodoNotFound -> Unit {
    attempt Todo.get(todo_id)  // fails or carries on; the value is not needed
    if (already_archived(todo_id)) {
        return  // leaves a Unit action early
    }
    notify_owner(todo_id)  // a Unit action called for its effect
}
```

- `attempt Todo.get(todo_id)` on its own means "this must succeed". If it
  fails, the failure is passed on; if not, the action carries on, and the
  value isn't needed.
- A bare `return` leaves an action or function that returns `Unit` early.
- A call to an action that returns `Unit`, such as `notify_owner`, is made
  for what it does.

A function call standing alone is an error
([`semantic.unused_result`](../errors/semantic.unused_result.md)): its
value is thrown away, so it does nothing.

## Conditions

```jadpo
action check_due(due_at: DueAt, latest_due_at: DueAt) fails DueDateInPast, DueDateTooFar -> Unit {
    if (due_at <= clock.now) {
        reject DueDateInPast
    } else if (due_at > latest_due_at) {
        reject DueDateTooFar
    }
}
```

The condition must be a `Bool`, or a type built on `Bool`. Nothing else
counts as true or false. A condition is always in brackets, and `else if`
chains are allowed.

`if` is a statement, not a value. To choose between two values, use a
[`match`](match.md).
