Early preview

Runlet

The PHP scratchpad that feels at home on your Mac.

Run snippets against a bundled Laravel sandbox, your local projects, Docker containers, or servers over SSH. See the result, the SQL queries it ran, the mail it sent, and the logs it wrote.

Free & open source · MIT License

macOS 26 or later · Apple silicon & Intel

The Runlet window. Vertical tabs on the left list six targets: the Laravel sandbox, a local project, a Docker container, and two SSH servers, one marked production. The editor shows a Laravel snippet that creates users with a factory; the output pane shows a dump and the result as a table of names, handles, and emails.

Run anywhere

One editor. Every place your PHP lives.

Every tab has a target. Switch it from the toolbar or with ⌘P, press Run, and the output, dumps, errors, and Stop behave the same everywhere.

Laravel sandbox

A fresh Laravel app with SQLite, bundled with Runlet. Uses your local PHP, or a php:8.4-cli container when you don’t have one.

Local projects

Open any folder. Laravel, Symfony, WordPress, and Composer projects boot automatically, on PHP 7.4 or newer.

Docker containers

Pick a running container or Compose service. Runlet finds it again after it’s recreated, and never picks a different one silently.

SSH servers

Hosts from ~/.ssh/config, jump hosts included. ssh-agent and 1Password work as in Terminal; password and 2FA logins stay connected until you disconnect.

A tab on the staging SSH server, app.example.com. The snippet returns the server's PHP version, operating system, release folder, memory limit, and extension count; the output shows PHP 8.4 on Linux in a releases folder, and the status bar says Connected.
A snippet on a staging server: the server’s own PHP, in the app’s folder. The runner is streamed over stdin, so nothing is written on the server.

Production asks first.

Mark a target as staging or production. Production gets a red badge on its tab, toolbar, and status bar, and every run shows you what will run, and where, before it does.

  • ⌘↩ runs; ↩ and Esc cancel, so a reflexive Return never runs code on production.
  • Project commands on production confirm every time.
  • Runlet stores no passwords or keys. It uses your system ssh.
A confirmation sheet titled “Run this code on production?” over a tab on the production SSH server. It shows the target, shop.example.com, the code that will run, a “Don't ask again for 10 minutes” checkbox, and Cancel and Run on Production buttons.

Run inspector

See what your code actually did.

Results arrive as structured, expandable values. Next to them, Runlet shows the SQL queries the run made, the mail it sent, and the log messages it wrote.

The Queries section after a run on a local Laravel project: 14 queries with their times, connection, and the snippet line that ran each one. Hints at the top flag a statement run 3 times identically and two N+1 patterns run 6 times.
Queries with their time, bindings, and the line that ran them. Repeated statements are flagged, and N+1 patterns get an eager-loading hint.

Mail you can read, without sending it.

Mailables, notifications, views, and HTML responses render in a locked-down preview: no JavaScript, no navigation, and no remote loads unless you allow them. Turn on mail interception and Laravel builds each message without sending it.

The Mail section: one message marked Intercepted, “Your order AC-10250 is on its way”, with its sender, recipient, mailable class, and a rendered HTML preview of the order email.

Queries everywhere

Laravel, Eloquent without Laravel, Symfony’s Doctrine, and WordPress, with no setup. Standalone DBAL or plain PDO take one line in a driver.

Structured, Plain, or Raw

Expandable value trees, a sortable table for rows and collections, a CLI-style transcript, or the exact bytes.

Take it with you

Copy values as JSON, PHP, or Markdown, export tables as CSV, and save the whole output to a file.

Editor & completion

Completion that knows your project.

Runlet indexes your project with PHPantom, so models, relations, and columns complete as you type, with hover, signature help, and diagnostics. It works for Docker and SSH targets too, from their checkout on your Mac.

The completion list under “$order->” in a Laravel project, listing the Order model's columns and relations with their types: created_at Carbon, customer User, customer_id int, items Collection of OrderItem, number string, and more.
Columns from migrations, relations, and their types, straight from the project.

Everything is a keystroke away.

⌘P opens anything: targets, snippets, recent files, and your run history. ⇧⌘P finds any command. Every shortcut can be changed in Settings.

  • Horizontal tabs, or vertical tabs as cards that show each target, its PHP version, and its framework.
  • Several windows, and workspace files that bring a set of tabs back.
  • History per project, personal snippets, and project snippets in .runlet/snippets.
The Open Anything palette over the editor, listing the Laravel sandbox, a local project, a Docker profile, two SSH servers, and four saved snippets.

Drivers & commands

Speaks Laravel. And your app.

Laravel, Lumen, Laravel Zero, Symfony, WordPress, and Composer projects are detected and booted for you. For anything else, a small driver in your project’s .runlet folder teaches Runlet how to boot it.

The Commands pane lists the project's Artisan commands with descriptions and run buttons, below the driver's variables. The terminal panel at the bottom shows php artisan test passing 6 tests.
The Commands pane lists Artisan or console commands, Composer scripts, and your own tools. Run one and it opens in the integrated terminal.

A driver is one PHP class.

Boot your app, hand snippets the variables they need, add commands to the Commands pane, declare tools that run on your Mac, and add sections of your own to the run inspector.

Read the driver guide

// .runlet/ShopDriver.php
use Runlet\Drivers\LaravelDriver;

class ShopDriver extends LaravelDriver
{
    public function variables(): array
    {
        return parent::variables() + [
            'cart' => $this->app->make(Cart::class),
        ];
    }

    public function hostCommands(): array
    {
        return [
            'up' => 'docker compose up -d',
        ];
    }
}

And plenty more.

  • Integrated terminal

    Your login shell, in the project’s folder. Commands wait until the shell is ready.

  • The runlet command

    runlet . opens the current folder; runlet file.php opens a file.

  • Snippets

    Personal snippets, plus project snippets your team commits in .runlet/snippets.

  • History

    Every run, per project or for all of them, searchable with the keyboard.

  • Windows & workspaces

    Each window has its own tabs. Save them as a workspace file and reopen the set later.

  • Your shortcuts

    Menus, the command palette, and shortcuts share one list of commands. Remap any shortcut in Settings.

  • Follows your files

    Tabs opened from files reload when another app changes them, and ask when you have edits.

  • Open in your editor

    File paths in output open at their line in PhpStorm, VS Code, Cursor, Zed, Sublime Text, and more.

  • Private by design

    No account and no telemetry. Runlet sends no analytics or crash reports and doesn’t check for updates.

Open source

Free. Open source. MIT.

Runlet is free, and the whole app is on GitHub under the MIT License: read the code, file an issue, send a pull request, or build your own copy.

Built with Swift, SwiftUI, and AppKit. Runlet bundles SwiftTerm (MIT), PHPantom, nikic/php-parser (BSD-3-Clause), and a Laravel sandbox (MIT); their notices ship inside the app.

Install

Up and running in a minute.

  1. Download

    Get the .dmg or .zip from the latest release and move Runlet to Applications. One universal app runs on Apple silicon and Intel.

  2. Open it the first time

    Builds are ad-hoc signed and not notarized, so macOS asks before opening them. Right-click Runlet.app and choose Open. If macOS still refuses, click Open Anyway in System Settings ▸ Privacy & Security, or run:

    xattr -dr com.apple.quarantine /Applications/Runlet.app
  3. Run something

    The Laravel sandbox is ready in the first tab. Press ⌘R. Open a project with ⇧⌘O, or from Terminal with the runlet command (Runlet ▸ Install Command-Line Tool…).

Requirements

  • macOS 26 or later, on Apple silicon or Intel.
  • For the sandbox: PHP 8.3 or later on your Mac, or Docker (Docker Desktop or OrbStack).
  • For your projects: PHP 7.4 or later, on your Mac, in the container, or on the server.
  • Docker and SSH are optional; use them only for those targets.

Questions

Is Runlet really free?

Yes. There is no paid version, no trial, and no account. Runlet is open source under the MIT License.

Is it ready for daily use?

Runlet is an early preview, built quickly with AI assistance. Expect rough edges. If something breaks or feels off, please open an issue on GitHub; it helps a lot.

Why does macOS say it can’t check Runlet for malicious software?

Releases are ad-hoc signed and not notarized by Apple, so Gatekeeper asks the first time. Right-click Runlet.app ▸ Open (or System Settings ▸ Privacy & Security ▸ Open Anyway), or remove the quarantine flag with xattr -dr com.apple.quarantine /Applications/Runlet.app. If you prefer, build it from source.

Does Runlet upload my code anywhere?

No. Code runs on the target you pick: your Mac, a Docker container, or a server you connect to with your own ssh. On a server, Runlet’s runner is streamed to PHP over stdin, so nothing is written there. Runlet has no telemetry and stores no SSH keys or passwords.

Will it run code without asking?

No. Your snippets run when you press Run; opening a project, switching tabs, or restoring a session doesn’t run them. The Commands pane boots a project to list its commands only while the pane is open, and never on its own for SSH or production targets. Production targets confirm every run and every project command.

Which PHP versions does it support?

Your projects can use PHP 7.4 or newer, locally, in Docker, or over SSH. The bundled Laravel sandbox needs PHP 8.3 or newer on your Mac; without it, Runlet runs the sandbox in a php:8.4-cli container.

Can I use it with frameworks other than Laravel?

Yes. Symfony, WordPress, Lumen, Laravel Zero, and plain Composer projects work out of the box, and a project driver in .runlet/ can boot anything else. See the driver guide.

How do I update?

Download the newest release and replace the app. Runlet doesn’t update itself yet. Your tabs, snippets, history, and targets stay in ~/Library/Application Support/Runlet.