Universal multi-language runner and smart REPL written in Rust.
run
Polyglot command runner & smart REPL that lets you script, compile, and iterate in 25+ languages without touching another CLI.
Website โข Docs Overview
Built in Rust for developers who live in multiple runtimes. run gives you a consistent CLI, persistent REPLs, and batteries-included examples for your favorite languages.
What's New in 0.10
- Custom language aliases โ
run alias add,run alias remove, persisted in~/.config/run-kit/aliases.toml. See the aliases docs. run fmt/run sharenow detect all 25 languages by file extension (Kotlin, Swift, Dart, etc.), not just a subset.- Run 2.0 CI โ v2 feature builds and tests run in GitHub Actions.
- WASI target alignment โ
wasm32-wasip1used consistently across build, deploy, and registry metadata. - Toolchain lockfile โ
run.lock.tomlplaceholder hashes removed; runrun v2 toolchain syncto populate.
What's New in 0.9
- Toolchain-aware blake3 build cache under the platform cache directory with
run cache --statsandrun cache --clear. - New workflow commands:
run doctor,run fmt <file>,run snippet <lang> <name>,run watch <file>, andrun share <file>. - Scriptable execution via
--jsonand predictable timeout behavior via--timeout <seconds>with exit code 124. - Per-language REPL history, safer reset behavior, and hardened child-process shutdown.
- C++ precompiled-header cache invalidation now tracks the exact compiler identity, so Clang/Xcode upgrades no longer poison inline, stdin, or REPL runs.
run --helpnow lists all workflow subcommands directly.
Run 2.0 (Experimental)
Run 2.0 adds WASI 0.2 component support for cross-language composition, instant startup, and edge deployment.
run v2 --help
Quick Links:
See Run 2.0 Documentation below for details.Table of contents
- Command Variations - Flexible Syntax
- Command-Line Flags Reference
- When to Use --lang
- Main Function Flexibility
- Examples
- REPL
Website and Docs
The official website and full documentation are available here:
- Website: https://run.esubalew.et/
- Docs Overview: https://run.esubalew.et/docs/overview
- Docs source: https://github.com/esubaalew/run-docs
Overview - Universal Multi-Language Runner
A powerful command-line tool for executing code in 25 programming languages
What is run?
run is a universal multi-language runner and smart REPL (Read-Eval-Print Loop) written in Rust. It provides a unified interface for executing code across 25 programming languages without the hassle of managing multiple compilers, interpreters, or build tools.
Whether you're a beginner learning your first programming language or an experienced polyglot developer, run streamlines your workflow by providing consistent commands and behavior across all supported languages.
Who is this for?
- Beginners: Learn programming without worrying about complex setup procedures. Just install run and start coding in any language.
- Students: Quickly test code snippets and experiment with different programming paradigms across multiple languages.
- Developers: Prototype ideas rapidly, test algorithms, and switch between languages seamlessly without context switching.
- DevOps Engineers: Write and test automation scripts in various languages from a single tool.
- Educators: Teach programming concepts across multiple languages with a consistent interface.
Why was run created?
Traditional development workflows require installing and configuring separate tools for each programming language. This creates several problems:
- Time-consuming setup: Installing compilers, interpreters, package managers, and configuring environments for each language.
- Inconsistent interfaces: Each language has different commands and flags for compilation and execution.
- Cognitive overhead: Remembering different commands and workflows for each language.
- Barrier to entry: Beginners struggle with setup before writing their first line of code.
Why Rust?
run is built with Rust for several compelling reasons:
- Performance: Rust's zero-cost abstractions and efficient memory management ensure run starts instantly and executes with minimal overhead.
- Reliability: Rust's strong type system and ownership model prevent common bugs like null pointer dereferences and data races, making run stable and crash-resistant.
- Cross-platform: Rust compiles to native code for Windows, macOS, and Linux, providing consistent behavior across all platforms.
- Memory safety: No garbage collector means predictable performance without unexpected pauses.
- Modern tooling: Cargo (Rust's package manager) makes building and distributing run straightforward.
- Future-proof: Rust's growing ecosystem and industry adoption ensure long-term maintainability.
Quickstart
# Show build metadata for the current binary
run --version
Execute a snippet explicitly
run --lang python --code "print('hello, polyglot world!')"
Let run detect language from the file extension
run examples/go/hello/main.go
Drop into the interactive REPL (type :help inside)
run
Pipe stdin (here: JSON) into Node.js
echo '{"name":"Ada"}' | run js --code "const data = JSON.parse(require('fs').readFileSync(0, 'utf8')); console.log(\hi \${data.name}\)"
Pipe stdin into Python
echo "Hello from stdin" | run python --code "import sys; print(sys.stdin.read().strip().upper())"
Pipe stdin into Go
echo "world" | run go --code 'import "fmt"; import "bufio"; import "os"; scanner := bufio.NewScanner(os.Stdin); scanner.Scan(); fmt.Printf("Hello, %s!\n", scanner.Text())'
Installation
All release assets are published on the GitHub Releases page, including macOS builds for both Apple Silicon (arm64) and Intel (x8664). Pick the method that fits your platform:
Cargo (Rust)
cargo install run-kit
Installs therunbinary from therun-kitcrate. Updating? Runcargo install run-kit --force.
# Or build from source
git clone https://github.com/Esubaalew/run.git
cd run
cargo install --path .
This builds the run binary using your active Rust toolchain. The project targets Rust 1.70 or newer.
Homebrew (macOS)
brew install --formula https://github.com/Esubaalew/run/releases/latest/download/homebrew-run.rb
This formula is published as a standalone file on each release; it isn't part of the default Homebrew taps.
Debian / Ubuntu
ARCH=${ARCH:-amd64}
DEB_FILE=$(curl -s https://api.github.com/repos/Esubaalew/run/releases/latest \
| grep -oE "run[0-9.]+${ARCH}\\.deb" | head -n 1)
curl -LO "https://github.com/Esubaalew/run/releases/latest/download/${DEB_FILE}"
curl -LO "https://github.com/Esubaalew/run/releases/latest/download/${DEB_FILE}.sha256"
sha256sum --check "${DEB_FILE}.sha256"
sudo apt install "./${DEB_FILE}"
Windows (Scoop)
scoop install https://github.com/Esubaalew/run/releases/latest/download/run-scoop.json
Install script (macOS / Linux)
curl -fsSLO https://raw.githubusercontent.com/Esubaalew/run/master/scripts/install.sh
chmod +x install.sh
./install.sh --add-path
Pass --version v0.2.0, --prefix /usr/local/bin, or --repo yourname/run to customize the install.
Verify installation:
run --version
How it works
run shells out to real toolchains under the hood. Each LanguageEngine implements a small trait that knows how to:
- Detect whether the toolchain is available (e.g.
python3,go,rustc). - Prepare a temporary workspace (compilation for compiled languages, transient scripts for interpreters).
- Execute snippets, files, or stdin streams and surface stdout/stderr consistently.
- Manage session state for the interactive REPL (persistent modules, stateful scripts, or regenerated translation units).
Supported languages
run supports 25 programming languages out of the box:
| Category | Languages & aliases | Toolchain expectations | | ------------------------- | ----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | --------------------------------------- | | Scripting & shells | Bash (bash), Python (py, python), Ruby (rb, ruby), PHP (php), Perl (perl), Groovy (groovy, grv), Lua (lua), R (r), Elixir (ex, elixir) | Matching interpreter on PATH | | Web & typed scripting | JavaScript (js, node), TypeScript (ts, deno), Dart (dart), Kotlin (kt, kotlin) | node, deno, dart, kotlinc + JRE | | Systems & compiled | C (c), C++ (cpp, cxx), Rust (rs, rust), Go (go), Swift (swift), Zig (zig), Nim (nim), Haskell (hs, haskell), Crystal (cr, crystal), C# (cs, csharp), Java (java), Julia (jl, julia) | Respective compiler / toolchain |
Complete Language Aliases Reference
| Alias | Description | Badge | |------------|----------------|------------| | python, py, py3, python3 | Python programming language | | |
javascript, js, node, nodejs | JavaScript (Node.js runtime) | | |
typescript, ts, ts-node, deno | TypeScript with type checking | | |
rust, rs | Rust systems programming language | | |
go, golang | Go programming language | | |
c, gcc, clang | C programming language | | |
cpp, c++, g++ | C++ programming language | | |
java | Java programming language | | |
csharp, cs, dotnet | C# (.NET) | | |
ruby, rb, irb | Ruby programming language | | |
bash, sh, shell, zsh | Bash shell scripting | | |
lua, luajit | Lua scripting language | | |
perl, pl | Perl programming language | | |
groovy, grv, groovysh | Groovy on the JVM | | |
php, php-cli | PHP scripting language | | |
haskell, hs, ghci | Haskell functional language | | |
elixir, ex, exs, iex | Elixir functional language | | |
julia, jl | Julia scientific computing | | |
dart, dartlang, flutter | Dart language (Flutter) | | |
swift, swiftlang | Swift programming language | | |
kotlin, kt, kts | Kotlin (JVM/Native) | | |
r, rscript, cran | R statistical computing | | |
crystal, cr, crystal-lang | Crystal language | | |
zig, ziglang | Zig systems language | | |
nim, nimlang | Nim programming language | |
Command Variations - Flexible Syntax
run supports multiple command formats:
# Full syntax
run --lang rust --code "fn main() { println!(\"hello\"); }"
Shorthand flags
run -l rust -c "fn main() { println!(\"hello\"); }"
Language first, then code
run rust "fn main() { println!(\"hello\"); }"
Auto-detect from file
run examples/rust/hello.rs
Command-Line Flags Reference
| Command / Flag | Purpose | | --- | --- | | run <lang> -c <code> | Execute inline code in a language | | run <file> | Execute a source file with extension-based detection | | run watch <file> | Re-run a file when it changes | | run fmt <file> | Format a source file in place using the standard formatter | | run snippet <lang> <name> | Print a built-in snippet template to stdout | | run snippet <lang> --list | List available templates for a language | | run doctor | Check all supported language toolchains and versions | | run cache --stats | Show persistent build cache usage | | run cache --clear | Clear the persistent build cache | | run share <file> [--port N] | Serve a local highlighted HTML view of a file | | run alias list | List built-in and custom language aliases | | run alias add A LANG | Add a custom alias (saved to config) | | run alias remove A | Remove a custom alias | | --lang, -l | Specify the programming language | | --code, -c | Provide code as a string | | --json | Emit stdout/stderr/exit/duration as a JSON envelope | | --timeout <seconds> | Kill execution after N seconds (0 means unlimited) | | --bench <N> | Benchmark a snippet for N iterations |
run -l python -c "print('hello')"
run --json python -c "print('hello')"
run snippet go goroutine-pool > pool.go
run watch examples/python/counter.py
When to Use --lang (Important!)
Always use --lang when syntax is ambiguous:
# Ambiguous - may choose wrong language
run "print('hello')"
Explicit - always correct
run --lang python "print('hello')"
Main Function Flexibility
For compiled languages, run is smart about main functions:
$ run go
go>>> fmt.Println("Hello, world!")
Hello, world!
go>>> package main import "fmt" func main() { fmt.Println("Hello!") } Hello!
Examples
Real programs live under the examples/ tree:
run examples/rust/hello.rs
run examples/typescript/progress.ts
run examples/python/counter.py
REPL
The REPL supports built-in commands:
| Command | Purpose | | -------------------------- | -------------------------------------------- | | :help | List available meta commands | | :languages | Show detected engines and status | | :lang <id> or :<alias> | Switch the active language (:py, :go, โฆ) | | :detect on/off/toggle | Control snippet language auto-detection | | :load path/to/file | Execute a file inside the current session | | :reset | Clear the accumulated session state | | :exit / :quit | Leave the REPL |
Interactive REPL - Line by Line or Paste All
$ run python
python>>> def fibonacci(n):
if n <= 1:
return n
return fibonacci(n-1) + fibonacci(n-2)
for i in range(10): print(f"F({i}) = {fibonacci(i)}")
Variable Persistence & Language Switching
$ run go
go>>> x := 10
go>>> x
10
go>>> :py switched to python
python>>> y = 10 python>>> print(y) 10
Stdin Piping Examples
# Node.js (JSON Processing)
echo '{"name":"Ada"}' | run js --code "const data = JSON.parse(require('fs').readFileSync(0, 'utf8')); console.log(\hi \${data.name}\)"
Python (Uppercase)
echo "Hello" | run python --code "import sys; print(sys.stdin.read().strip().upper())"
Go (Greeting)
echo "world" | run go --code 'import "fmt"; import "bufio"; import "os"; scanner := bufio.NewScanner(os.Stdin); scanner.Scan(); fmt.Printf("Hello, %s!\n", scanner.Text())'
Language-Specific Notes
For detailed usage and best practices for each language, visit the documentation.
Run 2.0 - WASI Component Runtime
Run 2.0 is an experimental extension that adds WASI 0.2 component support. It is opt-in and does not replace Run 1.0.
What Run 2.0 Adds
- Cross-language composition: Rust, Python, Go, JS components calling each other via WIT interfaces
- Instant startup: <10ms cold start (vs Docker's 5-10 seconds)
- Hermetic builds: Reproducible builds with toolchain lockfiles
- Edge deployment: Deploy to Cloudflare Workers, AWS Lambda, Vercel
Quick Start
# Install with v2 support
cargo install run-kit --features v2
See v2 commands
run v2 --help
Initialize a project
run v2 init my-app
cd my-app
Build and run
run v2 build
run v2 dev
Run 2.0 Commands
| Command | Description | |---------|-------------| | run v2 init | Initialize a new project | | run v2 build | Build WASI components | | run v2 dev | Development server with hot reload | | run v2 test | Run component tests | | run v2 deploy | Deploy to edge/registry | | run v2 install | Install dependencies |
Publishing to the Registry
Run 2.0 publishes components via run v2 publish (alias for run v2 deploy --target registry).
Default registry:
https://registry.esubalew.dev
run v2 build
run v2 publish --token YOUR_TOKEN
Override the registry URL:
run v2 publish \
--registry-url https://registry.esubalew.dev \
--token YOUR_TOKEN
You can also set the token in run.toml:
[registry]
authtoken = "${RUNAUTH_TOKEN}"
Keep tokens in environment variables and do not commit them to source control.
Configuration
run.toml defines your project:
[package]
name = "my-app"
version = "1.0.0"
[[component]] name = "api" source = "src/lib.rs" language = "rust" wit = "wit/api.wit"
[dev] watch = ["src/*/.rs"] hot_reload = true
Resources
- Run 2.0 Examples - Working examples and templates
- Migration Guide - Migrate from Docker to Run 2.0
- Registry Server - Self-hosted component registry
License
Apache 2.0. See LICENSE for details.
Built with Rust. If run helps your workflow, star the repo and share it with other polyglot developers.