Keyboard shortcuts

Press ← or → to navigate between chapters

Press S or / to search in the book

Press ? to show this help

Press Esc to hide this help

Introduction

Welcome. Open a terminal, keep it next to this page, and let’s begin.

This book teaches Zuri. It starts with installing the language and printing a line of text, and it ends with a task-board web application that stores data on disk, renders HTML from templates, serves a JSON API, and runs behind a stack of middleware. Everything in between is the road from one to the other.

What Zuri Looks Like

Here is a complete program. You do not need to understand all of it yet; read it the way you would read a paragraph in a language you are learning, and see how much comes through.

class Account {

  @new(owner: string, balance: number) {
    self.owner = owner
    self.balance = balance
  }

  deposit(amount: number) {
    if amount <= 0 {
      raise ValueError('deposit must be positive')
    }

    self.balance += amount
    return self.balance
  }

  to_string() {
    return '${self.owner}: ${self.balance}'
  }
}

var accounts = [
  Account('ada', 100),
  Account('grace', 250),
]

for account in accounts {
  account.deposit(50)
  echo account.to_string()
}
ada: 150
grace: 300

Most of that will be familiar if you have written code before. The pieces worth pointing at now, because they come up on the very first page of Chapter 3:

  • var declares a variable, and class declares a class.
  • A constructor is called @new. Methods whose names begin with @ hook into the language’s own syntax, and Chapter 6 covers the full set.
  • self refers to the instance, and reading a field always goes through it: self.balance, never a bare balance.
  • '${...}' interpolates an expression into a string.
  • echo prints a value and a newline.
  • raise signals an error; Chapter 7 shows how to catch one.
  • Every block is written with braces, and every control-flow statement requires one.

What Comes With Zuri

Installing Zuri installs its whole toolchain with it. Every tool is a subcommand of zuri, and every one has its place in this book:

CommandWhat it doesWhere
zurithe interactive REPLChapter 1
zuri runruns a script, a package or a directoryChapter 1
zuri initstarts a projectChapter 1
zuri fmtlays out Zuri source in the house styleChapter 1
zuri testruns a project’s testsChapter 23
zuri lspthe language server behind your editorChapter 29
zuri installadds packages, resolved into a lockfileChapter 27
zuri publishshares a package on a registryChapter 27
zuri serveruns Nyssa, a package registry of your ownChapter 27
zuri bundleships a program to machines without ZuriChapter 27
zuri upgrademoves the installation to a newer releaseChapter 27

A project adds commands of its own the same way, and so can a package; Appendix I shows how.

Who This Book Is For

Chapters 1 through 6 assume you can open a terminal and nothing else. If this is your first programming language, start at the beginning and go slowly. Every idea is introduced before it is used, and every example is short enough to type out.

If you already write Python, JavaScript, Ruby, Go or Java, you can move through Chapters 3 to 5 quickly. Read Appendix H first: it lists the places where Zuri does something different from what the same syntax does in the language you already know, which is where the hours get lost.

How This Book Is Organised

Getting started, Chapters 1 and 2. Install the language, run something, start a project and format it, then build a small command-line application end to end so you have seen the shape of a real program before we take one apart.

The language, Chapters 3 to 8. Variables, types, operators, control flow, strings, numbers, collections, functions, closures, type annotations, classes, inheritance, decorated methods, errors and modules. Read these in order.

The world outside your program, Chapters 9 to 13. Files, binary data and byte streams, isolates and concurrency, sockets and networking, and a tour of the standard library.

The large modules, Chapters 14 to 20. Wire for templating, HTTP for clients and servers, Imagine for images, SQL for databases, Mail for the three protocols that move messages, env for the configuration all of them read, and args for the command line they are started from. Each is big enough to need a chapter of its own, and each is a reference you will come back to.

Depth, Chapters 21 to 24. Reflection and the compiler API, how Zuri executes your code and how to make it faster, how to test it, and how to debug a program that is doing something you did not expect.

The capstone, Chapter 25. One application, built in seven steps, using almost everything the book has covered.

Interoperability, Chapter 26. Calling C and Rust libraries, and being called back by them.

Sharing and shipping, Chapter 27. Installing and publishing packages, the lockfile, packaging a program to run where Zuri is not installed, and running Nyssa, the package repository, for a team or the public.

Talking to other programs, Chapter 28. JSON-RPC, for calling methods on another program and answering its calls over any connection.

Tooling, Chapter 29. The language server, and setting up your editor to use it.

Appendices. Keywords, operators and precedence, decorated methods, built-in functions, every method on every built-in type, the standard library index, the error hierarchy, the notes for readers arriving from another language, and writing commands of your own. These are reference material; the rest of the book is prose.

How to Read It

Read it with the interpreter running. Zuri has a REPL, every short example in this book can be pasted straight into it, and the fastest way to understand a rule is to break it on purpose and read the error.

Chapters build on each other. When a chapter needs something from later in the book, it says so and links to it, and you can carry on without following the link. When a chapter introduces something you will need again, it says that too.

Conventions

Commands you type in a shell appear with a $ prompt, and the output follows underneath:

$ zuri run main.zu
Hello, world!

Code that belongs in a file appears with the filename above it when the filename matters:

Filename: main.zu

echo 'Hello, world!'

Sessions in the interactive prompt use %> for the first line of an input and .. for its continuations, which is exactly what the REPL itself prints:

%> var name = 'zuri'
%> name.upper()
'ZURI'

Where a rule has an exception, the exception is stated in the same paragraph as the rule. Where a limit exists, it is stated as a limit. Nothing in this book is a guess about how the language behaves; every claim was checked by running it.

Let’s get started.