Standard library overview¶
The candela standard library is a set of modules you import by path. It sits on top of a smaller layer of built-in functions and methods that are always in scope without an import.
How std ships¶
The library ships as candela source. The toolchain installs a libs directory
beside the candela executable:
libs/std/holds one.cdlfile per module:assert.cdl,convert.cdl,json.cdl,list.cdl,map.cdl,math.cdl,option.cdl,random.cdl,result.cdl,set.cdl,string.cdl,time.cdl.libs/std_src/holds the C sources and the compiled dynamic libraries for the three modules that call into native code:math,random, andtime.
Set CANDELA_LIB_PATH to point at a different libs directory. The variable
names the directory that contains std/ and std_src/, and it overrides the
default location for both library imports and the automatic list prelude. A
Rust host that embeds candela names it with Engine::with_lib_dir instead; see
embedding.
Because the modules are ordinary source files, the compiler links the ones you
import into your program. A .cdlb artifact built from a program that imports
only pure-candela modules runs under candela-vm with no library directory
present. The math, random, and time modules bind a dynamic library, so a
.cdlb that uses them records the binding recipe and needs the libs directory
when it runs; candela-vm finds it the way the compiler does, through
CANDELA_LIB_PATH or beside its own binary. See
artifacts.
Importing a module¶
A library import is a quoted path with no file extension. The resolver appends
.cdl and looks the file up in the shipped library directory, never next to
the importing file, so it works from any working directory:
A module of free functions binds a namespace under as (import "std/json" as
json; then json::parse(text)), or merges into the file's own scope under a
bare import. A module of methods (string, map, the enum helpers) only needs
importing; the methods then resolve on the receiver's type. Two bare imports
that export the same free-function name are a compile error; use as to keep
them apart. The import form is covered in full in
modules.
A library import's first segment is looked up among the packages the project
depends on before the library directory, so a dependency named std would
shadow the standard library. Nothing else about std is special: it is the
directory a library path falls back to.
Built-ins and modules¶
Built-in functions and methods are part of the language. print, str,
json_parse, throw, arr.push(x), and s.uppercase() need no import and are
available under candela-vm with nothing installed. They are listed in
built-in functions.
Standard library modules are candela code layered on those built-ins. The
collection, conversion, and enum modules define their helpers as methods in
impl blocks (xs.sum(), s.capitalize(), "42".to_int(), o.unwrap_or(0)),
and the rest are namespaced free functions (json::parse, math::sqrt).
One module is special. std/list loads automatically, so its methods work on
any array with no import at all:
The automatic prelude is skipped when the library directory is missing, and
when your file already binds the name list.
The modules¶
| Module | What it gives you |
|---|---|
| assert | Assertions that raise an error when a check fails |
| builtins | The always-available functions and methods (no import) |
| convert | to_int, to_float, to_string, to_bool methods over the built-in conversions |
| json | Parse a json string into candela values, and serialise back |
| list | Reductions, slicing, and higher-order methods on arrays |
| map | Extra map methods: is_empty and get_or |
| math | Trigonometry, logarithms, roots, rounding, and the constants |
| option | The Option enum: Some(x) or None, with methods |
| random | A seedable pseudo-random generator for ints and floats |
| result | The Result enum: Ok(v) or Err(e), with methods |
| set | Set<T>, a set of unique values, with union, intersection, difference, and symmetric difference |
| string | Substrings, characters, padding, capitalisation, line splitting, counting |
| time | The current unix time, and formatting a timestamp |
Errors¶
Standard library functions report failure the same way the rest of the language does: they raise an error that stops the run and prints a message naming the cause. Each page below states what its functions raise.
A raised error carries a short code as well as a message. The code is what a
catch binds and what catch "code" filters on; the message is what an uncaught
error prints. A throw is its own code, so throw("no such user") is caught as
no such user. A try catches what a library function raises just as it
catches a throw written in the block. See
error handling for the mechanism and
the error catalogue for the codes.