A Claude Code + Codex skill that turns a local project into a macOS Dock-launchable app — native window, its own icon, no Electron. [The Windows version is in BETA]
# Add to your Claude Code skills
git clone https://github.com/Christian-Katzmann/app-itLast scanned: 6/7/2026
{
"issues": [],
"status": "PASSED",
"scannedAt": "2026-06-07T07:56:26.493Z",
"npmAuditRan": true,
"pipAuditRan": true
}No comments yet. Be the first to share your thoughts!
Top skills in this category by stars
30 days in the Featured rail
Turn a local web project — or any hosted web app — into a macOS Dock-launchable .app bundle — a native window, its own Dock icon, and clean start/stop — without Electron, Tauri, or a rewrite.
Unofficial community project — not affiliated with, endorsed by, or sponsored by Anthropic or OpenAI. "Claude Code" and "Codex" are their respective owners' marks, named here only to say which assistants app-it plugs into. This is an independent open-source tool built by one developer.

A real app-it build, in motion. Fjord is an ordinary local web project (node server.js); app-it turns it into a native macOS app — double-click launches it, the window opens with its own Dock icon, and ⌘Q quits the app and frees the dev-server port. The actual generated app, not a mockup.
Status — Working, in daily use. The launcher templates are battle-tested across 12+ real projects; v0.1.0 is the first standalone, marketplace-installable release. macOS only, by design.
Windows beta — macOS is in daily use; Windows is an early beta, now with its first real-hardware fixes but still needing more. A complete sibling plugin (plugins/app-it-windows/), gated by a required windows-latest CI job (build · PowerShell lint · manifest parse · icon round-trip), mirrors the macOS contract with Windows primitives. The author runs only macOS, so for a long time it had never touched real Windows hardware; that changed with #8, the first run on an actual Windows machine, and a run of fixes since — a real start, not a finish line. If you're on Windows and want to help harden it, the doorway is docs/WINDOWS.md.
Local-first — app-it reads your project on your machine to choose a launcher strategy. It uploads nothing, runs no telemetry, adds no runtime dependencies, and never touches your business-logic source. The only thing it produces is an .app on your own Dock. For a hosted web app — a published Claude Artifact, a deployed dashboard, an internal tool — the supported networked path is explicit: wrap the hosted URL so the host handles login and keeps usage on each user's own account. See Privacy and Terms for the plain-language policy.
app-it is an assistant-agnostic plugin/skill. It works with Claude Code and Codex, and builds a small, repeatable launcher around an existing local project or hosted web app so that double-clicking starts the right runtime, opens a native window, keeps the Dock icon as your app, and cleans up when you quit.
.lnk, .ico, SmartScreen), so it belongs in a separate plugin rather than a blurred promise. See Compatibility. WHAT YOU HAVE WHAT APP-IT DOES WHAT YOU GET
─────────────────────── ────────────────────── ───────────────────────────
a local web project inspects it from disk, YourApp.app on your Dock
Vite React, SvelteKit, picks a strategy, then · its own icon
Astro, Next, static, or ──▶ builds & signs a .app ──▶ · native window, one click
a hosted web app URL around a WebKit shell · ⌘Q quits & frees the port
Under the hood, app-it:
WKWebView shell by default (so the Dock icon stays yours), Chrome --app mode only when a project needs Chromium-only APIs.external_url to a hosted link (for example, a published Claude Artifact); each user signs in within the app window and uses their own account..app — universal (arm64 + x86_64), Gatekeeper-friendly, with a generated .icns.Finished app? There's a lighter companion.
app-itruns your project's dev server — perfect while you're still building. Once an app is done, it doesn't need one: theapp-it-staticcompanion serves the built output (dist/,build/,out/, …) so a finished app costs ~15 MB instead of a dev server's ~300–700 MB. Same native window, same Dock Stack — reach for it only when an app is done. How it works →
swiftc (Xcode Command Line Tools) for the native WebKit shell — xcode-select --install.python3 (also from the Xcode Command Line Tools) for app-it-static's server mode.Claude Code:
claude plugin marketplace add Christian-Katzmann/app-it
claude plugin install app-it@app-it
Codex:
codex plugin marketplace add Christian-Katzmann/app-it
codex plugin add app-it@app-it
Then, from inside any local web project, ask your assistant:
/app-it
Natural triggers work too: "make this clickable from the Dock", "give this an icon", "dockify this", "package this as a local app".
To wrap a hosted web app, point app-it at its URL rather than copied source. A Claude Artifact is the common case: use the hosted artifact link, since a raw .jsx file works as an ordinary local React app only when it does not depend on Claude's hosted runtime (window.claude, window.storage, MCP prompts, or Claude-provided auth).
Optional: for finished apps, also install the lighter companion — claude plugin install app-it-static@app-it (or codex plugin add app-it-static@app-it), then run /app-it-static.
claude plugin marketplace add /path/to/app-it
claude plugin install app-it@app-it
codex plugin marketplace add /path/to/app-it
codex plugin add app-it@app-it
Marketplace install is preferred. To copy just the skill folder:
./install.sh # auto-detects Claude Code and/or Codex, asks before overwrite
./install.sh --dry-run # show what it would do, write nothing
All additions are additive and reversible:
scripts/app-it.config.json — single source of truth for the app(s)scripts/desktop-build.sh, desktop-install.sh, desktop-quit.sh, desktop-doctor.sh, desktop-verify.sh, wrapper.swift, …assets/<slug>-icon.png or .svgdesktop/<App Name>.app/ (gitignored — regenerated by the build)docs/desktop-launcher.md and an app-it-report.md decision logpackage.json scripts: desktop:build, desktop:install, desktop:quit, desktop:doctor, desktop:verifyInstalled apps land in ~/Applications/App It/ by default. Drag that folder to the right side of the Dock once and every future appified app appears in its Stack automatically. Override with APP_IT_INSTALL_DIR.
By default, generated launchers use port_mode: "fallback" so sibling local
apps can coexist by scanning upward from the preferred port. Use
port_mode: "fixed" only when the app must stay on one exact localhost origin,
such as browser storage or OAuth callbacks.

A real MyApps Stack, not a mockup. Every icon is an ordinary local web project app-it turned into a native app — its own icon, its own window, one click to launch. Do this a dozen times and your Dock fills itself.
app-it only makes additive, reversible changes. It will not rewrite product logic, add runtime dependencies, require a terminal window to stay open, or assume an already-running dev server. It may start and stop local dev-server processes during verification. It never collects telemetry, sends project data anywhere, or handles secrets. See SECURITY.md.
./scripts/validate.sh
This is the one-command check: it validates manifest shape, shell syntax, template presence, plist syntax, Swift typechecking, and Claude plugin validation (when the claude CLI is available). CI runs the same script on macos-latest.
For launcher/runtime changes, also run the behavioral suite:
./scripts/test-fixtures.sh
It builds tiny fixture apps and checks the lifecycle app-it promises: bundle shape, runtime ports, ownership, doctor/verify JSON, warm reattach, and cleanup.
This repo is agent tooling, and agents are expected to work in it. Start with AGENTS.md — it names the non-obvious conventions (templates are canonical, tr