Terminal
An interactive prompt for commands your app answers: history, Tab completion, streaming output, Ctrl+C, ANSI colours.
c2-terminal is a command line for apps that take commands: a dev console, a CLI tutorial, chat-ops or an admin shell. Your app answers each command; the terminal keeps the history, completes with Tab, streams long output, cancels with Ctrl+C and shows the colours CLI output carries. It is not a terminal emulator — there is no PTY or cursor addressing; use xterm.js for that — and c2-log-viewer stays the read-only log.
Import
import '@c2n/components/terminal'Usage
Type help in the first example: the built-in lists commands. Every other command goes to your handler, which here plays a small CLI: try deploy web, logs web (Ctrl+C stops it) or test, and Tab to complete.
Answering commands
Set handler to a function that receives the command line and { name, args, print, signal }. args are the words after the name, with quotes removed. Return what to print: a string, a DOM node, a promise of either, or an async iterable of lines, which streams in while a spinner replaces the prompt.
const terminal = document.querySelector('c2-terminal')!
terminal.commands = [{ name: 'deploy', description: 'Deploy a service' }, { name: 'logs', description: 'Stream logs' }]
terminal.complete = (input) => ['deploy web', 'deploy api', 'logs api --follow'].filter((line) => line.startsWith(input))
terminal.handler = async function* (command, { name, args, print, signal }) {
if (name === 'deploy') {
if (!args[0]) return print('usage: deploy <service>', { kind: 'error' })
const result = await api.deploy(args[0], { signal })
return print(`\\u001b[32m✓\\u001b[0m deployed ${args[0]} (${result.revision})`, { kind: 'success' })
}
if (name === 'logs') {
for await (const line of api.logs(args[0], { signal })) yield line
return
}
print(`${name}: command not found`, { kind: 'error' })
}print(text, { kind })prints from anywhere;kindisoutput,error,successorinfo.- Without a
handler, listen tocommand: itsdetailhas the same{ command, name, args, print, signal }. - Text is always drawn as text, never parsed as HTML. ANSI colour and bold codes (SGR 30–37, 90–97, 1 and 0) are shown, extended colours (
38;5;n,38;2;r;g;b) fall back to the default colour, and any other escape is dropped. A carriage return starts its line over, and a print that starts with one rewrites the last line printed, so\rDownloading 20%updates a progress line in place. - A thrown error prints as an
errorblock.
Built-ins and keys
clear, or Ctrl+L, clears the screen; the banner stays.helplistscommandsand the built-ins whilecommandsis set; otherwise it goes to your handler.- Ctrl+C aborts the running command’s
signal, prints^Cand gives the prompt back at once, even when the handler ignoressignal; anything it prints afterwards is dropped. With text selected it copies, as usual. - Tab asks
complete(input)for whole command lines: one match fills the line, several are listed under it and their common start is filled. On an empty line Tab moves focus as usual. - Up and Down walk earlier commands. Read
historyto keep a session and set it to restore one. - The screen keeps the last
max-lineslines (5,000 by default).
Accessibility
The terminal is a region named by heading (or “Terminal”), and the command line a text box named by label (or “Command”). The screen is a log that does not announce on its own: each command’s output is read once the command ends, or only its line count when it is long, so the echoed command is never read twice. Clicking the screen focuses the command line unless text was selected, so output can be copied.