Coming From Another Language
● Beginner3 min
Coming from Python, JavaScript, C++, Rust or Go: the same small program in each language and in Kavach, and what changes.
Pick the language you know best. Each page shows one program in that language and in Kavach, then a table of what changes, with a link to the page that teaches each part.
- Python: classes, exceptions and None.
- JavaScript: classes, null, === and async.
- C++: pointers, exceptions and undefined behaviour.
- Rust: borrowing, Result and Option.
- Go: if err != nil, nil and goroutines.
What changes whichever language you know
| In most languages | In Kavach | Learn it |
|---|---|---|
a class that inherits | no inheritance: a field, or an interface | Classes and Inheritance |
null, nil or None | none, only in a type that ends in ? | Optionals |
| errors that pass up unseen | the error type in the signature, ! OrderError, and try at each call that passes it on | try |
| two names for one list | values: b = a copies, so changing b leaves a as it was | Values, Not References |
| any function may touch files or the network | a function says what it may touch: uses Fs | Capabilities |
The program each page uses, in Kavach:
type Order {
item: String
qty: Int
cents: Int
fn cost(self) -> Int {
self.qty * self.cents
}
}
type OrderError = BadQty(item: String)
fn total(orders: [Order]) -> Int ! OrderError {
for o in orders {
if o.qty <= 0 {
fail OrderError.BadQty(item: o.item)
}
}
orders.sum(o => o.cost())
}
fn main() {
const codes = ["SPRING": 10, "VIP": 25]
const orders = [Order(item: "pen", qty: 3, cents: 150), Order(item: "cup", qty: 1, cents: 900)]
const sum = total(orders) catch _ => 0
const off = codes["SPRING"] ?? 0
print("total {sum}, with {off}% off {sum * (100 - off) / 100}")
print("WINTER gives {codes["WINTER"] ?? 0}%")
const broken = [Order(item: "kite", qty: 0, cents: 500)]
match total(broken) {
ok(t) => print("total {t}"),
err(OrderError.BadQty(item)) => print("refused: no quantity for {item}"),
}
}The program ran and printed:
kavach run orders.kav
total 1350, with 10% off 1215WINTER gives 0%refused: no quantity for kite
totalsays in its signature that it can fail withOrderError, and the caller decides what happens then:catchgives a value,matchlooks at each case.codes["WINTER"]may be missing, so its type isInt?, and?? 0says what to use then.
What you give up
- Kavach is young. It has far fewer packages than pip, npm, Cargo or Go modules, so you lean on its standard library and on code you write.
- It runs on Linux and Windows on x86-64 today. macOS and ARM64 are planned for a later phase of the roadmap.
- Some habits are refused on purpose: there is no inheritance, no exception that passes up unseen, and no
null.
No decorators
Kavach has no @decorator: nothing written above a function can change what it does, so its signature stays the whole story. What decorators do elsewhere is said in the signature or in plain code:
| Decorator use elsewhere | In Kavach |
|---|---|
Checking arguments and results (@validate) | require, ensure, invariant (chapter 7) |
| Permissions, rate limits | uses (8.1); an agent's can, limit and approve (8.3) |
Tests and examples (@test) | example clauses and test blocks (chapter 11) |
| Tracing and timing | log.span("name") { … } (4.8, 14.12) |
Generated equality, printing, JSON (@dataclass, derive) | Every record has them already (1.8, 2.12) |
Registering a route (@app.route) | A call that adds it to a router |