Rill v0.13 Reference

Chapter 8

The prelude

Every program has these in scope; any definition of your own with the same name replaces the prelude's.

Types: Option(a) = None | Some(a), Result(a, e) = Ok(a) | Err(e), List(a) = Nil | Cons(head, tail).

Lists: map filter fold len sum range reverse append take drop nth any all find index_of has count last each zip zip_with unzip fst snd enumerate take_while drop_while partition flatten flat_map chunks distinct group_by min_by max_by sort sort_by sort_with

sort is a stable merge sort by <; sort_by(l, key) orders by what key gives, and sort_with(l, before) by before(a, b), whether a may come before b — <=, not <, or equal elements would swap. group_by(l, key) gives (key, members) pairs in the order the keys were first seen. Each of these stands on its own, so a program that defines a find of its own loses the prelude's find and nothing else.

Option/Result: unwrap_or opt_map res_map ok_or map_err

Maps: map_get map_or map_has map_keys map_values map_items map_of

Channels: recv_opt(ch) -> Option(a)

Signals: sig_hup() sig_int() sig_term() — the numbers wait_signal answers with

Standard error: eprintln(x) eprint(x) — what println and print do, on standard error, unbuffered

Numbers: max min abs

Strings: join repeat split lines trim contains starts_with

Strands: apart(x) — x, and the claim that strands share it on purpose; see What strands may share

Characters: char_count char_at char_sub char_take char_drop chars from_char from_chars char_decode char_wide — see Characters; chr is a byte

IO: args() (program name included), read_file(path) -> Result(Str, Str), open_file(path, mode) -> Result(Int, Str), dir_names(path) -> List(Str), replace_file(path, text) -> Result(Int, Str)


The libraries

What the prelude does not have is in lib/, on the search path of every program in the project, imported by path and usually under a name:

import "text/str" as s strings past the prelude: searches, transforms, parsers, every encoding, strands over a long text
import "data/json", "yaml" the two formats, read and written
import "web/http" as h, "ws" an HTTP/1.1 server with middleware, and WebSocket over it
import "web/tls" as tls TLS over a socket through OpenSSL: https:// as a client, verified, and served with a certificate
import "web/url" as url a URL taken apart and put together, a query as pairs, a reference resolved against a base
import "web/mime" as mime the media type a file is served as, from its name
import "web/form" as form what a <form> sends: urlencoded pairs, or multipart parts with their files
import "net/udp" as udp datagrams, sent and received whole, a receive parking the strand
import "net/dns" as dns a name to its addresses through the system's resolver, without holding a worker
import "num/grid" as g arrays of numbers with a shape, as NumPy has them
import "db/kv" a key–value store on disk: a B+ tree, a page cache, a log
import "crypto/sha1", "passwd" SHA-1 and base64; storing a password so it cannot be read back
import "crypto/sha2" as sha SHA-256 and SHA-512, HMAC over each, a tag compared in constant time
import "data/checksum" as ck CRC-32 and Adler-32, whole or in pieces
import "data/csv" as csv CSV as RFC 4180 has it, read to rows or records and written back
import "data/deflate" as z DEFLATE both ways, and gzip and zlib around it
import "time/clock" as clock elapsed time, a timed call, a duration in words
import "time/date" as date civil dates and times in UTC: the counts, the calendar, ISO 8601
import "text/regex" as re regular expressions: a backtracking matcher with groups
import "text/path" as path file paths as text: join, take apart, normalize
import "text/fmt" as fmt a template with slots, padding by width, a float to so many places, thousands, bytes, ordinals, a table
import "random/rnd" as rnd PCG32: a generator that is a value, and the draws made from it
import "random/uuid" as uuid UUIDs, random (v4) and time-ordered (v7), from the operating system's entropy
import "cli/args" as cli what a program takes on its command line, said once, parsed and explained
import "cli/env" as env environment variables, the working directory, the machine's name, the process id
import "cli/proc" as proc running a command: its output and exit code, a line built with each argument quoted
import "cli/log" as log a logger that is a value: the time, the level, the name, on standard error
import "num/decimal" as dec decimals with a fixed number of places, for money
import "num/bigint" as big integers of any size
import "coll/set" as set a set of any key-able value, as storage like Map; union, intersection, difference
import "coll/heap" as heap a priority queue that is a value: a leftist heap, by < or by an order given
import "coll/deque" as dq a queue open at both ends that is a value; constant time on average at either
import "db/oxidb" and friends clients for OxiDB's engines

Each module says at its head what it is for and how it is used, keeps its helpers private, and carries its own tests: rill test lib/text/regex.rill runs them.

Documentation

There is no doc-comment syntax. The comment a declaration has above it — the # lines just before a type, trait, fn, machine or system — is its documentation, and the block after a module line is the module's own, which is how every module in lib/ was written before there was anything to read them. rill doc file.rill turns a file into Markdown: the module's head, its types with their constructors, its traits with their methods, its systems and machines with their diagrams, and its functions with the signatures the checker inferred, private ones left out; rill doc lib -o docs/lib does a folder, one page a module. A program's head comment is the program's, not its first type's, and its main and tests are listed rather than documented.