Lua API · Rex Docs
Lua API
This page lists the full Lua API Rex exposes. Rex only adds API to the global rex table. Rex runs Lua 5.1 with the full standard library, including io, os, and require. The one exception is io.popen and os.execute, which raise an error. Use rex.exec to run commands instead.
Where Each Function Works
Rex runs Lua in two places, the configuration file and scripts, and each function below is tagged with where it works:
| Tag | Description |
|---|---|
| Config | Works in the configuration file. |
| Script | Works in scripts run with rex do. |
| Config at load | Only at load, while the file runs from top to bottom. Either tag can be narrowed this way. |
| Config later | Only later, inside an action, a function bound to a key, or an event handler. |
Anything short of working is noted at the top of the function’s docs.
- No effect means the call is accepted and does nothing useful. A script’s key bindings and hosts never reach a keymap or the server.
- Missing means the name is
nil. Calling it is an error, so a file shared between both should check for it first. - Fails means the call returns
niland an error message, and is reported as a warning.
Key Bindings
See Keyboard Shortcuts, Key Sequences, and Key Modes.
rex.bind(key, action[, args])
Config
Config, later: functions only · Script: no effect
Binds a key to an action by name. args is an optional table of arguments passed to the action.
rex.bind("cmd+d", "pane.split", { direction = "right" })
key is a single key, a sequence written with >, or either one prefixed with a mode and a slash.
rex.bind(key, fn)
Config
Config, later: functions only · Script: no effect
Binds a key to a Lua function called as fn(ctx, ev). Return true to mark the key as handled. Not allowed in a mode.
ev.keybinding is the key that was pressed. For a sequence, ev.prefix is a list of the keys before it.
rex.unbind(key[, target])
Config
Config, later: functions only · Script: no effect
Removes the bindings of a key in this file and in the client’s defaults. Returns the number of this file’s bindings it removed.
target is an action name or a function, and limits the removal to bindings with that target. rex.unbind("mode/key") also blocks the key in that mode.
rex.unbind{ mode = name }
Config
Config, later: functions only · Script: no effect
Removes a whole mode: its bindings, its blocked keys, and its options.
rex.unbind(binding)
Config
Config, later: functions only · Script: no effect
Removes one binding, given a table returned by rex.bindings. Returns 1.
rex.mode(name[, options])
Config at load
Config, later: error · Script, at load: no effect; later: error
Declares a mode and sets its options. The only option is exclusive, a boolean that defaults to false.
rex.bindings([filter])
Config at load
Config, later: error · Script, at load: no effect; later: error
Returns the bindings this file and the files it requires have made so far, in order. filter is an optional table with any of key, mode, and action.
Each binding is a table:
| Field | Description |
|---|---|
key |
The key or sequence, without its mode. |
mode |
The mode, or nil. |
action |
The action name, or nil for a function binding. |
fn |
The function, or nil for an action binding. |
args |
The arguments table, or nil. |
source |
Where it was bound, such as keys.lua:3. |
rex.modes()
Config at load
Config, later: error · Script, at load: no effect; later: error
Returns the modes declared or bound so far, each a table with name, exclusive, and source.
Actions
See Custom Actions.
rex.action{ ... }
Config at loadScript at load
Config, later: error · Script, later: error
Defines an action.
| Field | Type | Description |
|---|---|---|
name |
string | Required. Lowercase letters, digits, and underscores. |
title |
string | Required. Shown in the command palette. |
run |
function | Required. Called as run(ctx, args). |
description |
string | A longer explanation. |
category |
string | A group for the palette. Defaults to Actions. |
keywords |
string | Extra words for search. |
args |
table | Argument types, or a JSON Schema. |
repeats |
boolean | Run again while the key is held. |
args types are string, number, integer, boolean, object, array, and any. A trailing ? marks an argument as optional.
ctx has session_id, block_id, client_id, origin, and server. A field Rex doesn’t know is absent. The value run returns is the action’s result.
rex.invoke(name[, args])
Config laterScript
Config, at load: warning
Runs an action and returns its result, or nil and an error message.
In the configuration file, only that file’s own actions can be invoked. In a script, a name the script doesn’t define is run by the server, so a script can invoke actions from the configuration file.
Calls can nest up to 16 deep.
rex.client.queue(name[, args])
Config laterScript
Config, at load: error; later: actions only
Asks the client to perform one of its own actions, such as pane.zoom.
In an action, queued actions run in order after run returns, and are discarded if it fails. In a script, each one is performed immediately.
Raises an error when there is no client to ask.
Calling Rex
See Lua Scripts.
Every call in this section returns a result table, or nil and an error message. A failure never raises an error.
rex.session.<method>(args)
Config laterScript
Config, at load: fails
Calls a session method. args is a table. session_id is filled in when it is left out. Other IDs, such as block_id, are not.
local view, err = rex.session.view{}
| Method | Description |
|---|---|
view |
Return the session’s windows, layouts, and blocks. |
list_blocks |
List every block and whether it is placed or detached. |
list_clients |
List the clients attached to the session. |
describe_block |
Return a block’s placement and the methods it offers. |
new_window |
Create a window from a layout. |
new_split |
Create a split beside an existing block. |
new_block |
Create a block without placing it in a layout. |
new_layer |
Create a floating layer in a window. |
close_window |
Close a window and every block in it. |
close_layer |
Close a floating layer and every block in it. |
move_block |
Move a block into a new split beside another. |
swap_blocks |
Exchange the positions of two blocks. |
detach_block |
Remove a block from its layout without closing it. |
float_block |
Move a tiled block into a new floating layer. |
zoom_block |
Toggle or set whether a block fills its window. |
resize_pane |
Move the border between two blocks. |
resize_layer |
Set a floating layer’s position and size. |
raise_layer, lower_layer |
Change a floating layer’s stacking order. |
move_window |
Move a window in the tab order. |
focus_block |
Focus a block. |
focus_window |
Focus a window. |
focus_direction |
Focus the nearest block in a direction. |
focus_next_pane, focus_previous_pane |
Focus the next or previous pane. |
focus_next_window, focus_previous_window |
Focus the next or previous window. |
set_label |
Set the session’s label. |
set_window_label |
Set a window’s label. |
set_block_label |
Set a block’s label. |
attach, detach |
Change which session a script hears events from. |
help |
Describe the methods available through the session. |
For the arguments and result of a method, run rex api describe with its full name:
rex api describe session.new_split
rex.call(method[, args])
Config laterScript
Config, at load: fails
Calls any server method by its full name, including the ones rex.session doesn’t cover.
local result, err = rex.call("session.list")
rex api list prints every method.
rex.block.call(creator, method[, args])
Config laterScript
Config, at load: fails
Calls a method on a block. creator is the full name of the kind of block. block_id is filled in from the current block when it is left out.
local terminal = "com.superlogical.terminal"
local title = rex.block.call(terminal, "title", {}).title
The terminal’s methods are:
| Method | Description |
|---|---|
format |
Return the screen as text, HTML, or VT sequences. |
process |
Describe the terminal’s child and foreground processes. |
pwd |
Return the working directory the terminal last reported. |
title |
Return the terminal’s title. |
size |
Return the terminal’s size in cells and pixels. |
write |
Write bytes to the terminal as if they were typed. |
reset |
Reset the terminal. |
resize |
Request a size for the terminal. |
set_theme |
Replace the terminal’s default colors. |
program_status |
Return the status records programs have reported. |
list_dir |
List the directories under a path. |
rex.layout
ConfigScript
Functions that build the layout table taken by new_window, new_split, and new_layer. They only build tables and call nothing.
| Function | Description |
|---|---|
rex.layout.block{ flavor, options } |
One block. flavor names what to create, such as com.superlogical.terminal.shell. |
rex.layout.horizontal(ratio, a, b) |
Two layouts split horizontally. ratio is the share given to a, from 0 to 1. |
rex.layout.vertical(ratio, a, b) |
Two layouts split vertically. |
The options for a terminal are:
| Option | Description |
|---|---|
command |
A list with the program to run and its arguments. Without it, an interactive shell starts. |
shell |
The shell to use. none starts command directly. |
cwd |
The working directory. |
initial_input |
Text typed into the terminal once it starts. |
exit |
{ on_completion = false } keeps the terminal open after its program exits. |
Events
See Lua Events. These work in scripts run with rex do only.
rex.on(event, fn)
Script at load
Config, at load: warning; later: error · Script, later: error
Calls fn(ctx, ev) each time event happens. ev holds the event’s fields. ctx has session_id, and block_id for a block event.
The events reference lists the event names.
rex.wait(event[, filter][, timeout])
Script
Config: missing
Blocks until event happens, and returns ev and ctx. Returns nil and "timeout" if timeout seconds pass first.
filter is a table of fields the event must match, or a function called as filter(ev, ctx) that returns true for a match.
rex.sleep(seconds)
Script
Config: missing
Blocks for a number of seconds, which may be fractional.
rex.stop([code])
Script
Config: missing
Ends the script immediately. rex do exits with code, or 0.
Hosts and Other Servers
rex.host{ ... }
Config at load
Config, later: error · Script, at load: no effect; later: error
Declares another Rex server you connect to. Configuration file only.
| Field | Description |
|---|---|
label |
Required. The host’s name. |
endpoints |
Required. A list of addresses, tried in order. |
endpoint |
A single address, in place of endpoints. |
id |
A stable ID, so the host keeps its identity when renamed. |
icon |
An icon name for clients to show. |
rex.servers()
Returns the labels of the other servers available to the running action or script, as a list.
rex.server(label)
Returns a table with the same session, block, and call functions as rex, whose calls go to that server. Raises an error for an unknown label.
Calls made through it don’t fill in a session_id or block_id.
Other Functions
Functions for running commands, timers, JSON, and logging. See Running Commands and Timers.
rex.exec(argv[, opts])
ConfigScript
Runs a command, waits for it to exit, and returns a result table. Returns nil and an error message only when the command never ran, such as when the program doesn’t exist.
local r, err = rex.exec({ "git", "status", "--short" }, { cwd = dir })
argv is a list of strings: the program, then each of its arguments. No shell reads it, so arguments need no quoting. A program without a slash in its name is looked up in the command’s PATH.
opts is an optional table:
| Option | Description |
|---|---|
cwd |
The working directory. Defaults to Rex’s own. |
env |
Environment variables to set, such as { GIT_DIR = "/repo/.git" }. false removes one. |
clear_env |
true starts from an empty environment. env still applies. |
stdin |
A string written to the command’s standard input. |
timeout |
Seconds until the command is sent SIGTERM, then SIGKILL two seconds later. |
stdout, stderr |
false discards the stream. Both are captured by default. |
text |
false keeps \r\n in the output on Windows. |
An option Rex doesn’t know is ignored with a warning.
The result has:
| Field | Description |
|---|---|
code |
The exit status, or -1 if a signal ended the command. |
signal |
The name of that signal, such as SIGTERM, or nil. |
stdout, stderr |
What the command printed. "" when it printed nothing. |
timed_out |
true if timeout stopped the command. |
ok |
true if code is 0 and the command didn’t time out. |
A non-zero exit is still a result, not an error. Check ok.
While an action in the configuration file waits for a command, the server keeps handling keys and other actions. Everywhere else, the wait blocks the script.
rex.exec.start(argv[, opts])
ConfigScript
Starts a command and returns a handle without waiting, or nil and an error message. It takes the same arguments as rex.exec, and a few more options:
| Option | Description |
|---|---|
stdin |
true keeps standard input open for h:write. |
stdout, stderr |
A function called with each piece of output as it arrives. A piece may end mid-line. |
detach |
true lets the command outlive the work that started it. |
The handle has:
| Method | Description |
|---|---|
h:wait([seconds]) |
Waits for the command to exit and returns the same result as rex.exec. Returns nil and "timeout" if seconds pass first. |
h:write(data) |
Writes to standard input. Returns true, or nil and an error message. |
h:close_stdin() |
Closes standard input. |
h:kill([signal]) |
Sends a signal, SIGTERM by default. signal is a name, such as SIGINT, or a number. |
h:running() |
Returns whether the command is still running. |
h.pid |
The command’s process ID. |
A command lasts as long as the work that started it. When an action, handler, or timer returns, or a script’s top level finishes, Rex stops the commands it started. A command started with detach = true is never stopped this way.
rex.after(seconds, fn)
Script
Config: missing
Calls fn(ctx) once, after seconds, and returns a timer with the same methods as rex.every’s. seconds may be zero or fractional.
ctx is the same table an action’s run gets, with ctx.origin set to timer. API calls default to the script’s session and block.
rex.every(seconds, fn)
Script
Config: missing
Calls fn(ctx) every seconds until the timer is cancelled, and returns a timer. seconds must be more than zero.
If the script is still busy when a tick comes, fn runs once when it is free, and the missed ticks are dropped.
A timer has two methods:
| Method | Description |
|---|---|
t:cancel() |
Stops the timer. |
t:active() |
Returns true until the timer is cancelled or has fired for the last time. |
An error in fn is reported and the timer keeps running. A script can have at most 1,024 timers at once. Creating one more stops the script with status 1.
rex.json.encode(value[, opts])
ConfigScript
Turns a Lua value into JSON text, or returns nil and an error message. opts.indent = true indents the text by two spaces.
local text = rex.json.encode({ name = "work", panes = { 1, 2 } })
Tables convert the same way they do in an API call. A table whose keys are 1 to n becomes an array, and any other table, including an empty one, becomes an object. A function, or a table that contains itself, can’t be encoded.
rex.json.decode(text)
ConfigScript
Turns JSON text into a Lua value, or returns nil and an error message. null becomes nil, and a null in an array is dropped.
rex.log([level, ]message)
ConfigScript
Writes a log message. level is debug, info, warn, or error, and defaults to info. In a script the message is printed to the terminal.
Script Values
Set in scripts run with rex do only.
| Value | Description |
|---|---|
rex.args |
The script’s arguments, as a table. Empty when none were passed. |
rex.session_id |
The ID of the session the script runs against. |
rex.block_id |
The ID of the block the script runs against, or nil. |